You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Next you can install the background libraries again
53
53
```
54
-
opam install coq-lsp.0.2.2+8.20
54
+
opam install coq-lsp.0.2.3+9.0
55
55
opam install ocaml-lsp-server
56
56
```
57
-
again replacing 8.20 with the desired version of Coq
57
+
again replacing 9.0 with the desired version of Coq
58
58
59
59
### Caveat: locally compiling the coq-master branch
60
60
@@ -139,110 +139,18 @@ If you use VSCode, we recommend installing the [OCaml Platform](https://marketpl
139
139
140
140
One can make Ocaml functions available for use in Ltac2 by using the
141
141
foreign function interface (ffi). For now, we gather all such
142
-
definitions in `Wp_ffi.ml`.
143
-
144
-
Suppose one has an Ocaml function `f : a -> b -> c -> d` where `a, b, c, d` are types, and one would like to make this function available as an Ltac2 tactic.
145
-
146
-
### Make a tactic
147
-
148
-
First of all, only tactics can pass the ffi, so one needs to convert `f` into
149
-
something that outputs a tactic. An element of type `'a` can be converted into an `'a`-valued tactic, ie.e. an element of type `'a tactic` by using `tclUNIT`:
150
-
151
-
Consider this example:
152
-
```
153
-
let my_unit_tactic : unit tactic = tclUNIT ()
154
-
```
155
-
156
-
```
157
-
let my_bool_tactic : bool tactic = tclUNIT true
158
-
```
159
-
160
-
Hence, we can convert `f` into something that outputs a tactic by
161
-
162
-
```
163
-
let my_f_tactic : a -> b -> c -> d tactic =
164
-
fun input_a input_b input_c -> tclUNIT (f input_a input_b input_c)
165
-
```
166
-
167
-
### Make a `valexpr` tactic
168
-
169
-
Datatypes in Ocaml and in Ltac2 need to be translated to each other
170
-
by using an intermediate datatype: namely `valexpr`. This also means that
171
-
only `valexpr`-valued tactics can pass the ffi.
172
-
Luckily, for many types there are already conversion functions available from
173
-
and to `valexpr`, such as `of_bool`, `to_bool` and `of_unit`, `to_unit`.
174
-
In general, these conversions are captured in elements of the type `'a repr`:
175
-
an element `c` of `'a repr` has a conversion `repr_to c : valexpr -> 'a` and
176
-
a conversion `repr_of c : 'a -> valexpr`. For more information, one can look
177
-
at Coq's `tac2ffi.ml` file.
178
-
179
-
We can then use the strategy from the previous section to make a valexpr tactic.
180
-
```
181
-
let my_valexpr_tactic_from_unit : valexpr tactic = tclUNIT (of_unit ())
182
-
```
183
-
It is common to use the `@@` operator to put everything that comes after it
184
-
in parentheses, so one could also write
185
-
```
186
-
let my_valexpr_tactic_from_unit : valexpr tactic = tclUNIT @@ of_unit ()
187
-
```
188
-
Similarly, here is a `valexpr` tactic created from a `bool`
189
-
```
190
-
let my_valexpr_tactic_from_bool : valexpr tactic = tclUNIT @@ of_bool ()
191
-
```
192
-
193
-
### Make the function available for the ffi
194
-
195
-
Considering an example of a function `f : a -> b -> c -> d`, and given
196
-
`a_repr : a repr`, `b_repr : b repr`, `c_repr : c repr`, `d_repr : d repr`, we can
197
-
make this function available for the ffi by
198
-
199
-
```
200
-
let () = define3 "my_f_external" a_repr b_repr c_repr @@
201
-
fun input_a, input_b, input_c ->
202
-
tclUNIT (repr_of d (f input_a input_b input_c))
203
-
```
204
-
205
-
The `3` is chosen because `f` has `3` inputs.
206
-
207
-
Note that with some monad magic, the same definition can also be
208
-
achieved by
209
-
```
210
-
let () = define3 "my_f_external" a_repr b_repr c_repr @@
211
-
fun input_a input_b input_c ->
212
-
tclUNIT @@ f input_a input_b input_c >>= fun z -> tclUNIT @@ repr_of d z
213
-
```
214
-
Here "my_f_external" is the name by which you can refer to this function
215
-
from Ltac2. Any name can be chosen, and it won't be the name that you use
216
-
to call the function from Ltac2. Representations for many different datatypes
217
-
can be found in Coq's `tac2ffi.ml`. For many datatypes, the respresentation
218
-
of that datatype is called the same: `bool` is for instance the name for `bool repr`, so that the following would be valid code
219
-
220
-
```
221
-
let () = define1 "my_bool_tactic" bool @@
222
-
fun input -> tclUNIT input >>= fun z -> tclUNIT @@ of_bool z
223
-
```
224
-
or yet another option
225
-
```
226
-
let () = define1 "my_bool_tactic" bool @@
227
-
fun input -> tclUNIT input >>= fun z -> tclUNIT @@ repr_of bool z
228
-
```
229
-
230
-
Note that in Coq v8.19, a new file `tac2externals.ml` was created, which
231
-
can be used to handle a lot of the above issues.
232
-
233
-
### Make the function available from Ltac2
234
-
235
-
From a `.v` file, one can simply load
236
-
```
237
-
Require Import Waterproof.Waterproof.
238
-
```
239
-
and then define (in Coq v8.17) (given the caveat below)
where `a_ltac2`, ... `d_ltac2` are the corresponding types on the
244
-
Ltac2 side of the types `a`, ..., `d`. The caveat is that there aren't always
245
-
corresponding types on the Ltac2 side of Ocaml types.
246
-
247
-
Note that the syntax is a bit different in different versions of Coq.
248
-
Please see the code for examples.
142
+
definitions in `wp_ffi.ml`.
143
+
144
+
Note that with Coq v8.19, using the ffi got a lot easier.
145
+
It may be possible to just look at the examples in `wp_ffi.ml`.
146
+
This process is also explained in [tuto2](https://github.com/rocq-prover/rocq/tree/master/doc/plugin_tutorial/tuto4) of the [Rocq plugin tutorial](https://github.com/rocq-prover/rocq/tree/master/doc/plugin_tutorial).
147
+
The documentation in the file `Tac2externals.mli` may also help.
148
+
149
+
A few remarks:
150
+
- For passing variables through the ffi, one needs to convert them to an intermediate datatype: namely `valexpr`.
151
+
For existing datatypes these conversion functions exist and can be used conveniently.
152
+
With some syntactic sugar from `Tac2externals`, there's really nothing to do.
153
+
For inductive datatypes, it is relatively easy to create new conversion functions.
154
+
This process is explained in the tutorial mentioned above.
155
+
- Although this is not really necessary for the ffi anymore, an element of type `'a` can be converted into an `'a`-valued tactic by using `tclUNIT`.
156
+
- To make a tactic available from Ltac2, one needs to use the `Ltac2 @ external` syntax. It may be best to look for examples in the code.
0 commit comments