define a "dependently typed" module functor - coq

How can I make a dependently typed functor (for lack of a better term) ? I want to do something like the following:
Module Type Element.
...
End Element.
Module Wrapper (E : Element).
...
End Wrapper.
Module DepentlyTypedFunctor (E : Element) (W : Wrapper E).
...
End DepentlyTypedFunctor.
The last definition doesn't work, and I guess I'm looking for the correct syntax, if possible at all. My motivation for this kind of definition is to define theorems inside DependentlyTypedFunctor that work for all Wrappers that contain any instance of Element, similar to how one could define a theorem for vectors, forall (E : Element) (W : Wrapper E), some_proposition E W.

I think you just meant to make Wrapper a Module Type. If it's not a module type, there's only one such module and you can just write DependentlyTypedFunctor over E. This might not be sufficient if you have opaque implementations of Element, though, in which case different instantiations of Wrapper might not be equal to each other.
If this is a problem, you might just want to use records instead of modules.

Related

What is a concrete example of the type `Set` and what is the meaning of `Set`?

I've been trying to understand what Set is after encountering it in Adam Chlipala's book in addition to this great discussion in SO. His first example definition binary ops using Set:
Inductive binop : Set := Plus | Times.
in that book he says:
Second, there is the : Set fragment, which declares that we are defining a datatype that should be thought of as a constituent of programs.
Which confuses me. What does Adam mean here?
In addition, I thought that some additional concrete examples would help my understanding. I am not an expert of Coq so I am not sure what type of examples would help but something simple and very concrete/grounded might be useful.
Note, I have seen that Set is the first "type set" in a the type hierarchy e.g. Set = Type(0) <= Type = Type(1) <= Type(2) <= ... . I guess this sort of makes sense intuitively like I'd assume nat \in Type and all usual programming types to be in it but not sure what would be in Type that wouldn't be in Set. Perhaps recursive types? Not sure if that is the right example but I am trying to wrap my head around what this concept means and it's conceptual (& practical) usefulness.
Though Set and Type are different in Coq, this is mostly due to historical reasons. Nowadays, most developments do not rely on Set being different from Type. In particular, Adam's comment would also make sense if you replace Set by Type everywhere. The main point is that, when you want to define a datatype that you can compute with during execution (e.g. a number), you want to put it in Set or Type rather than Prop. This is because things that live in Prop are erased when you extract programs from Coq, so something defined in Prop would end up not computing anything.
As for your second question: Set is something that lives in Type, but not in Set, as the following snippet shows.
Check Set : Type. (* This works *)
Fail Check Set : Set.
(* The command has indeed failed with message: *)
(* The term "Set" has type "Type" while it is expected to have type *)
(* "Set" (universe inconsistency: Cannot enforce Set+1 <= Set). *)
This restriction is in place to prevent paradoxes in the theory. This is pretty much the only difference you see between Set and Type by default. You can also make them more different by invoking Coq with the -impredicative-set option:
(* Needs -impredicative-set; otherwise, the first line will also fail.*)
Check (forall A : Set, A -> A) : Set.
Universe u.
Fail Check (forall A : Type#{u}, A -> A) : Type#{u}.
(* The command has indeed failed with message: *)
(* The term "forall A : Type, A -> A" has type "Type#{u+1}" *)
(* while it is expected to have type "Type#{u}" (universe inconsistency: Cannot enforce *)
(* u < u because u = u). *)
Note that I had to add the Universe u. declaration to force the two occurrences of Type to be at the same level. Without this declaration, Coq would silently put the two Types at different universe levels, and the command would be accepted. (This would not mean that Type would have the same behavior as Set in this example, since Type#{u} and Type#{v} are different things when u and v are different!)
If you're wondering why this feature is useful, it is not by chance. The overwhelming majority of Coq developments does not rely on it. It is turned off by default because it is incompatible with a few axioms that are generally considered more useful in Coq developments, such as the strong law of the excluded middle:
forall A : Prop, {A} + {~ A}
With -impredicative-set turned on, this axiom yields a paradox, while it is safe to use by default.

In the Verified Software Toolchain, how can I specify some Clight which is not the body of a function, and which I'm generating from within Coq?

I would like to write a Gallina function of a type like gen_code : Foo -> statement and then prove that it generates code that satisfies a particular specification. I do have an informal Hoare triple in mind; however, I'm not terribly familiar yet with VST, and I'm not sure exactly how to turn it something that the framework can work with. I think I want a theorem of the form forall {Espec : OracleKind} (foo : Foo), semax ?Delta (P foo) (gen_code foo) (normal_ret_assert (Q foo)), where I know what P and Q are, but I'm not sure what to put for ?Delta. It's worth noting that I have some functions defined in C that I've verified already which I want to invoke from the code generated by gen_code, so presumably ?Delta needs to involve the signatures of those somehow. I assume it probably also needs to mention the free variables of gen_code foo, and here I'm similarly lost.

Best Practices for Dummy Values in Coq

I find that I'm frequently writing code like this:
Fixpoint get_fresh w (Γ : Ctx) : Pat w * Ctx:=
match w with
...
| w1 ⊗ w2 => let (p1, Γ1) := get_fresh w1 Γ in
match Γ ⋓ Γ1 with
| None => (dummy_pat _, dummy_ctx)
| Some Γ' => (p1,Γ')
end.
Where the None branch will never be entered. (Here, it's impossible to enter the branch, sometimes we will never enter the branch on an appropriate input.)
What's the best way to implement the dummy values that should never be returned?
An easy approach is to simply declare
Parameter dummy_pat : forall W, Pat W.
Parameter dummy_ctx : Ctx.
But that sounds seems like bad practice - for all the user knows Ctx and Pat W might have no inhabitants. (This is especially true for dependent types like Pat W.)
I could give simple definitions for dummy_pat and dummy_ctx but I don't want users reasoning about this branch. I could declare dummy_pat and dummy_ctx opaque, but opacity is disturbingly easy to reverse.
Finally, I guess I could declare these as the a projection from a sigma type, but it seems like that would be confusing, and I'm not sure it addresses the problem of reasoning about that case.
(Note that I don't want to intrinsically prove that these branches are inaccessible, using Program or otherwise. I find these functions very difficult to write and to use.)
Any suggestions?
The following way of declaring a module may have better opaqueness guarantees (but if I'm wrong I'd be very interested to know!):
Module Type DummySig.
Parameter dummy_pat : forall W, Pat W.
Parameter dummy_ctx : Ctx.
End DummySig.
Module Import Dummy : DummySig.
Definition dummy_pat := (* some simple definition *)
Definition dummy_ctx := (* some simple definition *)
End Dummy.
Explanation
Module Import Dummy : DummySig. is short for Module Dummy : DummySig followed by Import Dummy. after the closing End Dummy. command.
Module Dummy : DummySig. declares a module with module type (or signature) DummySig, and also seals the module so that only the information declared in DummySig is visible about this Dummy module.
This is a strong abstraction boundary that hides all of the implementation details. In particular, a Parameter in DummySig makes a definition opaque in Dummy, and identifiers defined in Dummy that do not appear in DummySig are not visible at all from outside the module.
As far as I can tell, this opaqueness is irreversible, which is the key point here.
For comparison, the two other ways of declaring modules are:
Module M. exposes everything in the module M, so it is mostly a kind of namespacing.
Module M <: MSig., also exposes everything in M, while checking that it implements the signature MSig (defined via Module Type MSig.), without the "sealing" aspect of Module M : Sig..
Other proposed solutions
You can also turn the dummies into actual parameters, either via a module functor...
Module MyProject (Dummy : DummySig).
Import Dummy.
...
or a section; to avoid having to pass dummies around, a type class may be useful.
Class Dummy (A : Type) := { dummy : A }.
Section Dummies.
Context `{forall W, Dummy (Pat W)}.
Context `{Dummy Ctx}.
...
At the end of the day I wonder whether it is really bad that users can reason about inaccessible branches.

refining types with modules and typeclasses

I'm not very familiar with modules or typeclasses in Coq, but based on my basic understanding of them, I believe I have a problem where I should use them.
I want to define a sum function that adds all the elements of a polymorphic list t. It should only work when the type of elements of the list (t) has some definition for plus_function and plus_id_element. The definition of sum I'd like to write would be something like this:
Fixpoint sum {t : Type} (l : list t) :=
match l with
| Nil => plus_id_element t
| Cons x xs => ((plus_function t) x (sum xs))
end.
I don't know what's the usual way to achieve something like this in Coq. I believe in Idris, for example, one would replace t by an interface/typeclass that defines plus_function and plus_id_element. Although typeclasses exist in Coq, I haven't seen them used very often and I believe people usually use modules instead to achieve something similar. I'm not sure if I'm mixing unrelated concepts. Are modules and typeclasses useful for this problem? What would be the recommended approach?
Indeed typeclasses were designed for this exact task, but then you face the hard problem of designing the particular class hierarchy that will fit your problem well.
Coq doesn't provide a standard hierarchy of mathematical operators, and there are many delicate trade-offs in building one with regard to the choice of classes, operators, and axioms.
I thus recommend starting from a mature development such as the MathComp library. MathComp is based on "Canonical Structures" which are a similar notion to type classes, and provides quite a few ready to use classes. The Packaging Mathematical Structures" paper contains more details, but the basic idea is that types pack their operators. For example, if you want to reason about abelian modules you can use the zmodType structure:
From mathcomp Require Import all_ssreflect all_algebra.
Open Scope ring_scope.
Definition sum (A: zmodType) (s : seq A) := foldr +%R 0 s.
to define the sum over a list of elements of the abelian group A. Even better, don't define you own sum operator and just use the one provided by the library: \sum_(x <- s) x:
Lemma eq_sum (A: zmodType) (s : seq A) : sum s = \sum_(x <- s) x.
Proof. by rewrite unlock. Qed.

Coq: adding implicit variables

Suppose that I have a set of functions, each of which can depend on one or two implicit variables A B: Type. How can I specify this? I.e. add these variables to their variable list and set them as implicit.
The most obvious way is to add {A B: Type} to their definitions. However, in real life and moderately complicated developments such shared lists of implicits can easily be 6-10 entries long and include complicated types, thus making function definitions hard to read and even harder to understand their similarity or make change to mentioned types. Thus this solution is not applicable.
I could include all functions in a section or module and write Variables (A B: Type) etc in the beginning, but that would not make variables implicit and I would have to manually set arguments for all functions at the end of section. Even worse, that would make all variables shared. I.e. if I declare
Section sect.
Variable A B: Type.
Definition f (t: A -> Type) := (..).
Definition g (t: A -> Type) (s: B -> Type) := G (f t) (f s).
End sect.
(G is some two-variable function) then g would not be accepted, since s is not in A -> Type, even though essentially f requires only an arbitrary type family.
I could make a section and declare Context {A B: Type}. That would make those variables implicit for all functions, but the sharing problem like in previous case would still remain. Thus I would have to arbitrarily split my functions into several sections so that I could call functions from Sect.1 with different values of their implicit arguments. This works, but is ugly, and I can easily imagine a situation where each section would have to be 2-3 functions long just so that I could call them properly.
Is there a better solution?
There are two things you can do that are less difficult:
Generalizable All Variables.
Definition g `(t: A -> Type) `(s: B -> Type) := G (f t) (f s).
Now you can use backtick, and it will automatically insert the implicit variables you need to make the definition valid. This is the most common way that I introduce implicits.
The other way is to follow your section with:
Arguments g : default implicits.
You'll need to repeat this for every defined term, but at least you don't need to name all of the arguments.