Skip to content

Commit 2a3fb53

Browse files
authored
Merge pull request #629 from NathanReb/support-5-4-bivariant-params
Add support for 5.4 bivariant type parameters in type declaration
2 parents 8961335 + e1257bc commit 2a3fb53

File tree

7 files changed

+572
-153
lines changed

7 files changed

+572
-153
lines changed

CHANGES.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
unreleased
22
----------
33

4+
- Add support for OCaml 5.4 bivariant type parameters, they can now be used
5+
alongside ppx-es. (#629, @NathanReb)
6+
47
- Add `Attribute.Floating.declare_with_attr_loc` and `.declare_with_name_loc`,
58
by analogy to the same functions at top level of `Attribute`. (#631, @ceastlund)
69

astlib/encoding_504.ml

Lines changed: 155 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,13 @@
1+
open Stdlib0
2+
13
module Ext_name = struct
2-
let ptyp_labeled_tuple = "ppxlib.migration.ptyp_labeled_tuple_504"
3-
let pexp_labeled_tuple = "ppxlib.migration.pexp_labeled_tuple_504"
4-
let ppat_labeled_tuple = "ppxlib.migration.ppat_labeled_tuple_504"
4+
let ptyp_labeled_tuple = "ppxlib.migration.ptyp_labeled_tuple_5_4"
5+
let pexp_labeled_tuple = "ppxlib.migration.pexp_labeled_tuple_5_4"
6+
let ppat_labeled_tuple = "ppxlib.migration.ppat_labeled_tuple_5_4"
7+
let bivariant_param = "ppxlib.migration.bivariant_param_5_4"
8+
let bivariant_pstr = "ppxlib.migration.bivariant_str_item_5_4"
9+
let bivariant_psig = "ppxlib.migration.bivariant_sig_item_5_4"
10+
let bivariant_pmty_with = "ppxlib.migration.bivariant_pmty_with_5_4"
511
end
612

713
let invalid_encoding ~loc name =
@@ -197,7 +203,7 @@ module Make (X : AST) = struct
197203
| None -> invalid_encoding ~loc Ext_name.ppat_labeled_tuple
198204
end
199205

200-
module Ast_503 = struct
206+
module Ast_503_arg = struct
201207
include Ast_503.Asttypes
202208
include Ast_503.Parsetree
203209

@@ -277,7 +283,7 @@ module Ast_503 = struct
277283
end
278284
end
279285

280-
module Ast_502 = struct
286+
module Ast_502_arg = struct
281287
include Ast_502.Asttypes
282288
include Ast_502.Parsetree
283289

@@ -358,9 +364,151 @@ module Ast_502 = struct
358364
end
359365

360366
module To_503 = struct
361-
include Make (Ast_503)
367+
include Make (Ast_503_arg)
368+
open Ast_503.Asttypes
369+
open Ast_503.Parsetree
370+
371+
let encode_bivariant_param typ inj =
372+
let loc = { typ.ptyp_loc with Location.loc_ghost = true } in
373+
let attr =
374+
{
375+
attr_name = { txt = Ext_name.bivariant_param; loc };
376+
attr_payload = PStr [];
377+
attr_loc = loc;
378+
}
379+
in
380+
( { typ with ptyp_attributes = attr :: typ.ptyp_attributes },
381+
(NoVariance, inj) )
382+
383+
let decode_bivariant_param (typ, (var, inj)) =
384+
let ptyp_attributes =
385+
List.without_first typ.ptyp_attributes ~pred:(fun attr ->
386+
String.equal attr.attr_name.txt Ext_name.bivariant_param)
387+
in
388+
match (ptyp_attributes, var) with
389+
| Some ptyp_attributes, NoVariance ->
390+
Some ({ typ with ptyp_attributes }, inj)
391+
| None, _ -> None
392+
| Some _, _ -> invalid_encoding ~loc:typ.ptyp_loc "bivariant type parameter"
393+
394+
let encode_bivariant_pstr ~loc pstr_desc =
395+
let loc = { loc with Location.loc_ghost = true } in
396+
let ext =
397+
( { txt = Ext_name.bivariant_pstr; loc },
398+
PStr [ { pstr_loc = loc; pstr_desc } ] )
399+
in
400+
Pstr_extension (ext, [])
401+
402+
let encode_bivariant_pstr_type ~loc rec_flag tds =
403+
encode_bivariant_pstr ~loc (Pstr_type (rec_flag, tds))
404+
405+
let encode_bivariant_pstr_typext ~loc te =
406+
encode_bivariant_pstr ~loc (Pstr_typext te)
407+
408+
let encode_bivariant_pstr_class ~loc cds =
409+
encode_bivariant_pstr ~loc (Pstr_class cds)
410+
411+
let encode_bivariant_pstr_class_type ~loc ctds =
412+
encode_bivariant_pstr ~loc (Pstr_class_type ctds)
413+
414+
let encode_bivariant_psig ~loc psig_desc =
415+
let loc = { loc with Location.loc_ghost = true } in
416+
let ext =
417+
( { txt = Ext_name.bivariant_psig; loc },
418+
PSig [ { psig_loc = loc; psig_desc } ] )
419+
in
420+
Psig_extension (ext, [])
421+
422+
let encode_bivariant_psig_type ~loc rec_flag tds =
423+
encode_bivariant_psig ~loc (Psig_type (rec_flag, tds))
424+
425+
let encode_bivariant_psig_typesubst ~loc tds =
426+
encode_bivariant_psig ~loc (Psig_typesubst tds)
427+
428+
let encode_bivariant_psig_typext ~loc te =
429+
encode_bivariant_psig ~loc (Psig_typext te)
430+
431+
let encode_bivariant_psig_class ~loc cds =
432+
encode_bivariant_psig ~loc (Psig_class cds)
433+
434+
let encode_bivariant_psig_class_type ~loc ctds =
435+
encode_bivariant_psig ~loc (Psig_class_type ctds)
436+
437+
let decode_bivariant_pstr ~loc payload attributes =
438+
match (payload, attributes) with
439+
| ( PStr
440+
[
441+
{
442+
pstr_desc =
443+
(Pstr_type _ | Pstr_typext _ | Pstr_class _ | Pstr_class_type _)
444+
as x;
445+
_;
446+
};
447+
],
448+
[] ) ->
449+
x
450+
| _ -> invalid_encoding ~loc "bivariant structure_item"
451+
452+
let decode_bivariant_psig ~loc payload attributes =
453+
match (payload, attributes) with
454+
| ( PSig
455+
[
456+
{
457+
psig_desc =
458+
( Psig_type _ | Psig_typesubst _ | Psig_typext _ | Psig_class _
459+
| Psig_class_type _ ) as x;
460+
_;
461+
};
462+
],
463+
[] ) ->
464+
x
465+
| _ -> invalid_encoding ~loc "bivariant signature_item"
466+
467+
let encode_bivariant_pmty_with ~loc mty constraints =
468+
let loc = { loc with Location.loc_ghost = true } in
469+
let pmd_type =
470+
{
471+
pmty_loc = loc;
472+
pmty_attributes = [];
473+
pmty_desc = Pmty_with (mty, constraints);
474+
}
475+
in
476+
let psig_desc =
477+
Psig_module
478+
{
479+
pmd_name = { txt = None; loc };
480+
pmd_type;
481+
pmd_attributes = [];
482+
pmd_loc = loc;
483+
}
484+
in
485+
let ext =
486+
( { txt = Ext_name.bivariant_pmty_with; loc },
487+
PSig [ { psig_loc = loc; psig_desc } ] )
488+
in
489+
Pmty_extension ext
490+
491+
let decode_bivariant_pmty_with ~loc payload =
492+
match payload with
493+
| PSig
494+
[
495+
{
496+
psig_desc =
497+
Psig_module
498+
{
499+
pmd_name = { txt = None; _ };
500+
pmd_attributes = [];
501+
pmd_type =
502+
{ pmty_attributes = []; pmty_desc = Pmty_with _ as x; _ };
503+
_;
504+
};
505+
_;
506+
};
507+
] ->
508+
x
509+
| _ -> invalid_encoding ~loc "bivariant pmty_with"
362510
end
363511

364512
module To_502 = struct
365-
include Make (Ast_502)
513+
include Make (Ast_502_arg)
366514
end

astlib/encoding_504.mli

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,9 @@ module Ext_name : sig
22
val ptyp_labeled_tuple : string
33
val pexp_labeled_tuple : string
44
val ppat_labeled_tuple : string
5+
val bivariant_pstr : string
6+
val bivariant_psig : string
7+
val bivariant_pmty_with : string
58
end
69

710
module To_503 : sig
@@ -28,6 +31,50 @@ module To_503 : sig
2831

2932
val decode_ppat_labeled_tuple :
3033
loc:Location.t -> payload -> (string option * pattern) list * closed_flag
34+
35+
val encode_bivariant_param :
36+
core_type -> injectivity -> core_type * (variance * injectivity)
37+
38+
val decode_bivariant_param :
39+
core_type * (variance * injectivity) -> (core_type * injectivity) option
40+
41+
val encode_bivariant_pstr_type :
42+
loc:Location.t -> rec_flag -> type_declaration list -> structure_item_desc
43+
44+
val encode_bivariant_pstr_typext :
45+
loc:Location.t -> type_extension -> structure_item_desc
46+
47+
val encode_bivariant_pstr_class :
48+
loc:Location.t -> class_declaration list -> structure_item_desc
49+
50+
val encode_bivariant_pstr_class_type :
51+
loc:Location.t -> class_type_declaration list -> structure_item_desc
52+
53+
val encode_bivariant_psig_type :
54+
loc:Location.t -> rec_flag -> type_declaration list -> signature_item_desc
55+
56+
val encode_bivariant_psig_typesubst :
57+
loc:Location.t -> type_declaration list -> signature_item_desc
58+
59+
val encode_bivariant_psig_typext :
60+
loc:Location.t -> type_extension -> signature_item_desc
61+
62+
val encode_bivariant_psig_class :
63+
loc:Location.t -> class_description list -> signature_item_desc
64+
65+
val encode_bivariant_psig_class_type :
66+
loc:Location.t -> class_type_declaration list -> signature_item_desc
67+
68+
val encode_bivariant_pmty_with :
69+
loc:Location.t -> module_type -> with_constraint list -> module_type_desc
70+
71+
val decode_bivariant_pstr :
72+
loc:Location.t -> payload -> attributes -> structure_item_desc
73+
74+
val decode_bivariant_psig :
75+
loc:Location.t -> payload -> attributes -> signature_item_desc
76+
77+
val decode_bivariant_pmty_with : loc:Location.t -> payload -> module_type_desc
3178
end
3279

3380
module To_502 : sig

0 commit comments

Comments
 (0)