Skip to content

Commit a793751

Browse files
committed
AST cleanup: explicit representation for optional record fields in types.
1 parent 9105709 commit a793751

29 files changed

+113
-65
lines changed

analysis/src/ProcessCmt.ml

+5-9
Original file line numberDiff line numberDiff line change
@@ -20,14 +20,14 @@ let attrsToDocstring attrs =
2020
| None -> []
2121
| Some docstring -> [docstring]
2222

23-
let mapRecordField {Types.ld_id; ld_type; ld_attributes} =
23+
let mapRecordField {Types.ld_id; ld_type; ld_attributes; ld_optional} =
2424
let astamp = Ident.binding_time ld_id in
2525
let name = Ident.name ld_id in
2626
{
2727
stamp = astamp;
2828
fname = Location.mknoloc name;
2929
typ = ld_type;
30-
optional = Res_parsetree_viewer.has_optional_attribute ld_attributes;
30+
optional = ld_optional;
3131
docstring =
3232
(match ProcessAttributes.findDocAttribute ld_attributes with
3333
| None -> []
@@ -259,10 +259,7 @@ let forTypeDeclaration ~env ~(exported : Exported.t)
259259
stamp = astamp;
260260
fname = Location.mknoloc name;
261261
typ = f.ld_type.ctyp_type;
262-
optional =
263-
Res_parsetree_viewer
264-
.has_optional_attribute
265-
f.ld_attributes;
262+
optional = f.ld_optional;
266263
docstring =
267264
(match
268265
ProcessAttributes
@@ -300,16 +297,15 @@ let forTypeDeclaration ~env ~(exported : Exported.t)
300297
ld_name = fname;
301298
ld_type = {ctyp_type};
302299
ld_attributes;
300+
ld_optional;
303301
}
304302
->
305303
let fstamp = Ident.binding_time ld_id in
306304
{
307305
stamp = fstamp;
308306
fname;
309307
typ = ctyp_type;
310-
optional =
311-
Res_parsetree_viewer.has_optional_attribute
312-
ld_attributes;
308+
optional = ld_optional;
313309
docstring = attrsToDocstring ld_attributes;
314310
deprecated =
315311
ProcessAttributes.findDeprecatedAttribute

compiler/frontend/bs_ast_mapper.ml

+10-2
Original file line numberDiff line numberDiff line change
@@ -500,9 +500,17 @@ let default_mapper =
500500
~loc:(this.location this pcd_loc)
501501
~attrs:(this.attributes this pcd_attributes));
502502
label_declaration =
503-
(fun this {pld_name; pld_type; pld_loc; pld_mutable; pld_attributes} ->
503+
(fun this
504+
{
505+
pld_name;
506+
pld_type;
507+
pld_loc;
508+
pld_mutable;
509+
pld_optional;
510+
pld_attributes;
511+
} ->
504512
Type.field (map_loc this pld_name) (this.typ this pld_type)
505-
~mut:pld_mutable
513+
~mut:pld_mutable ~optional:pld_optional
506514
~loc:(this.location this pld_loc)
507515
~attrs:(this.attributes this pld_attributes));
508516
cases = (fun this l -> List.map (this.case this) l);

compiler/ml/ast_helper.ml

+3-1
Original file line numberDiff line numberDiff line change
@@ -319,10 +319,12 @@ module Type = struct
319319
pcd_attributes = attrs;
320320
}
321321

322-
let field ?(loc = !default_loc) ?(attrs = []) ?(mut = Immutable) name typ =
322+
let field ?(loc = !default_loc) ?(attrs = []) ?(mut = Immutable)
323+
?(optional = false) name typ =
323324
{
324325
pld_name = name;
325326
pld_mutable = mut;
327+
pld_optional = optional;
326328
pld_type = typ;
327329
pld_loc = loc;
328330
pld_attributes = attrs;

compiler/ml/ast_helper.mli

+1
Original file line numberDiff line numberDiff line change
@@ -241,6 +241,7 @@ module Type : sig
241241
?loc:loc ->
242242
?attrs:attrs ->
243243
?mut:mutable_flag ->
244+
?optional:bool ->
244245
str ->
245246
core_type ->
246247
label_declaration

compiler/ml/ast_mapper.ml

+10-2
Original file line numberDiff line numberDiff line change
@@ -448,9 +448,17 @@ let default_mapper =
448448
~loc:(this.location this pcd_loc)
449449
~attrs:(this.attributes this pcd_attributes));
450450
label_declaration =
451-
(fun this {pld_name; pld_type; pld_loc; pld_mutable; pld_attributes} ->
451+
(fun this
452+
{
453+
pld_name;
454+
pld_type;
455+
pld_loc;
456+
pld_mutable;
457+
pld_optional;
458+
pld_attributes;
459+
} ->
452460
Type.field (map_loc this pld_name) (this.typ this pld_type)
453-
~mut:pld_mutable
461+
~mut:pld_mutable ~optional:pld_optional
454462
~loc:(this.location this pld_loc)
455463
~attrs:(this.attributes this pld_attributes));
456464
cases = (fun this l -> List.map (this.case this) l);

compiler/ml/ast_mapper_from0.ml

+5-2
Original file line numberDiff line numberDiff line change
@@ -459,10 +459,13 @@ let default_mapper =
459459
~attrs:(this.attributes this pcd_attributes));
460460
label_declaration =
461461
(fun this {pld_name; pld_type; pld_loc; pld_mutable; pld_attributes} ->
462+
let optional, attrs =
463+
Parsetree0.get_optional_attr (this.attributes this pld_attributes)
464+
in
462465
Type.field (map_loc this pld_name) (this.typ this pld_type)
463-
~mut:pld_mutable
466+
~mut:pld_mutable ~optional
464467
~loc:(this.location this pld_loc)
465-
~attrs:(this.attributes this pld_attributes));
468+
~attrs);
466469
cases = (fun this l -> List.map (this.case this) l);
467470
case =
468471
(fun this {pc_lhs; pc_guard; pc_rhs} ->

compiler/ml/ast_mapper_to0.ml

+11-2
Original file line numberDiff line numberDiff line change
@@ -455,11 +455,20 @@ let default_mapper =
455455
~loc:(this.location this pcd_loc)
456456
~attrs:(this.attributes this pcd_attributes));
457457
label_declaration =
458-
(fun this {pld_name; pld_type; pld_loc; pld_mutable; pld_attributes} ->
458+
(fun this
459+
{
460+
pld_name;
461+
pld_type;
462+
pld_loc;
463+
pld_mutable;
464+
pld_optional;
465+
pld_attributes;
466+
} ->
459467
Type.field (map_loc this pld_name) (this.typ this pld_type)
460468
~mut:pld_mutable
461469
~loc:(this.location this pld_loc)
462-
~attrs:(this.attributes this pld_attributes));
470+
~attrs:
471+
(Parsetree0.add_optional_attr ~optional:pld_optional (this.attributes this pld_attributes)));
463472
cases = (fun this l -> List.map (this.case this) l);
464473
case =
465474
(fun this {pc_lhs; pc_guard; pc_rhs} ->

compiler/ml/datarepr.ml

+2-5
Original file line numberDiff line numberDiff line change
@@ -107,9 +107,6 @@ let constructor_descrs ty_path decl cstrs =
107107
if cd_args = Cstr_tuple [] then incr num_consts else incr num_nonconsts;
108108
if cd_res = None then incr num_normal)
109109
cstrs;
110-
let has_optional attrs =
111-
Ext_list.exists attrs (fun ({txt}, _) -> txt = "res.optional")
112-
in
113110
let rec describe_constructors idx_const idx_nonconst = function
114111
| [] -> []
115112
| {cd_id; cd_args; cd_res; cd_loc; cd_attributes} :: rem ->
@@ -135,8 +132,8 @@ let constructor_descrs ty_path decl cstrs =
135132
match cd_args with
136133
| Cstr_tuple _ -> []
137134
| Cstr_record lbls ->
138-
Ext_list.filter_map lbls (fun {ld_id; ld_attributes; _} ->
139-
if has_optional ld_attributes then Some ld_id.name else None)
135+
Ext_list.filter_map lbls (fun {ld_id; ld_optional} ->
136+
if ld_optional then Some ld_id.name else None)
140137
in
141138
let existentials, cstr_args, cstr_inlined =
142139
let representation =

compiler/ml/parsetree.ml

+1
Original file line numberDiff line numberDiff line change
@@ -368,6 +368,7 @@ and type_kind =
368368
and label_declaration = {
369369
pld_name: string loc;
370370
pld_mutable: mutable_flag;
371+
pld_optional: bool;
371372
pld_type: core_type;
372373
pld_loc: Location.t;
373374
pld_attributes: attributes; (* l : T [@id1] [@id2] *)

compiler/ml/parsetree0.ml

+14
Original file line numberDiff line numberDiff line change
@@ -596,3 +596,17 @@ and module_binding = {
596596
pmb_loc: Location.t;
597597
}
598598
(* X = ME *)
599+
600+
let optional_attr = (Location.mknoloc "res.optional", Parsetree.PStr [])
601+
let optional_attr0 = (Location.mknoloc "res.optional", PStr [])
602+
603+
let add_optional_attr ~optional attrs =
604+
if optional then optional_attr0 :: attrs else attrs
605+
606+
let get_optional_attr attrs_ =
607+
let remove_optional_attr attrs =
608+
List.filter (fun a -> a <> optional_attr) attrs
609+
in
610+
let attrs = remove_optional_attr attrs_ in
611+
let optional = List.length attrs <> List.length attrs_ in
612+
(optional, attrs)

compiler/ml/pprintast.ml

+6-1
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,10 @@ let mutable_flag f = function
209209
| Immutable -> ()
210210
| Mutable -> pp f "mutable@;"
211211

212+
let optional_flag f = function
213+
| false -> ()
214+
| true -> pp f "?"
215+
212216
(* trailing space added *)
213217
let rec_flag f rf =
214218
match rf with
@@ -1137,9 +1141,10 @@ and type_def_list ctxt f (rf, l) =
11371141

11381142
and record_declaration ctxt f lbls =
11391143
let type_record_field f pld =
1140-
pp f "@[<2>%a%s:@;%a@;%a@]"
1144+
pp f "@[<2>%a%s%a:@;%a@;%a@]"
11411145
mutable_flag pld.pld_mutable
11421146
pld.pld_name.txt
1147+
optional_flag pld.pld_optional
11431148
(core_type ctxt) pld.pld_type
11441149
(attributes ctxt) pld.pld_attributes
11451150
in

compiler/ml/predef.ml

+2-5
Original file line numberDiff line numberDiff line change
@@ -309,13 +309,10 @@ let common_initial_env add_type add_extension empty_env =
309309
( [
310310
{
311311
ld_id = ident_dict_magic_field_name;
312-
ld_attributes =
313-
[
314-
(Location.mknoloc "res.optional", Parsetree.PStr []);
315-
Dict_type_helpers.dict_magic_field_attr;
316-
];
312+
ld_attributes = [Dict_type_helpers.dict_magic_field_attr];
317313
ld_loc = Location.none;
318314
ld_mutable = Immutable;
315+
ld_optional = true;
319316
ld_type = newgenty (Tconstr (path_option, [tvar], ref Mnil));
320317
};
321318
],

compiler/ml/printtyp.ml

+1-5
Original file line numberDiff line numberDiff line change
@@ -923,11 +923,7 @@ and tree_of_constructor cd =
923923
(name, args, Some ret, repr)
924924

925925
and tree_of_label l =
926-
let opt =
927-
l.ld_attributes
928-
|> List.exists (fun ({txt}, _) ->
929-
txt = "ns.optional" || txt = "res.optional")
930-
in
926+
let opt = l.ld_optional in
931927
let typ =
932928
match l.ld_type.desc with
933929
| Tconstr (p, [t1], _) when opt && Path.same p Predef.path_option -> t1

compiler/ml/subst.ml

+1
Original file line numberDiff line numberDiff line change
@@ -251,6 +251,7 @@ let label_declaration s l =
251251
{
252252
ld_id = l.ld_id;
253253
ld_mutable = l.ld_mutable;
254+
ld_optional = l.ld_optional;
254255
ld_type = typexp s l.ld_type;
255256
ld_loc = loc s l.ld_loc;
256257
ld_attributes = attrs s l.ld_attributes;

compiler/ml/typedecl.ml

+9-12
Original file line numberDiff line numberDiff line change
@@ -213,6 +213,7 @@ let transl_labels ?record_name env closed lbls =
213213
{
214214
pld_name = name;
215215
pld_mutable = mut;
216+
pld_optional = optional;
216217
pld_type = arg;
217218
pld_loc = loc;
218219
pld_attributes = attrs;
@@ -224,6 +225,7 @@ let transl_labels ?record_name env closed lbls =
224225
ld_id = Ident.create name.txt;
225226
ld_name = name;
226227
ld_mutable = mut;
228+
ld_optional = optional;
227229
ld_type = cty;
228230
ld_loc = loc;
229231
ld_attributes = attrs;
@@ -242,6 +244,7 @@ let transl_labels ?record_name env closed lbls =
242244
{
243245
Types.ld_id = ld.ld_id;
244246
ld_mutable = ld.ld_mutable;
247+
ld_optional = ld.ld_optional;
245248
ld_type = ty;
246249
ld_loc = ld.ld_loc;
247250
ld_attributes = ld.ld_attributes;
@@ -365,9 +368,6 @@ let transl_declaration ~type_record_as_object env sdecl id =
365368
| [] -> ()
366369
| (_, _, loc) :: _ ->
367370
Location.prerr_warning loc Warnings.Constraint_on_gadt);
368-
let has_optional attrs =
369-
Ext_list.exists attrs (fun ({txt}, _) -> txt = "res.optional")
370-
in
371371
let scstrs =
372372
Ext_list.map scstrs (fun ({pcd_args} as cstr) ->
373373
match pcd_args with
@@ -378,7 +378,7 @@ let transl_declaration ~type_record_as_object env sdecl id =
378378
pcd_args =
379379
Pcstr_record
380380
(Ext_list.map lds (fun ld ->
381-
if has_optional ld.pld_attributes then
381+
if ld.pld_optional then
382382
let typ = ld.pld_type in
383383
let typ =
384384
{
@@ -475,6 +475,7 @@ let transl_declaration ~type_record_as_object env sdecl id =
475475
ld_name =
476476
Location.mkloc (Ident.name l.ld_id) l.ld_loc;
477477
ld_mutable = l.ld_mutable;
478+
ld_optional = l.ld_optional;
478479
ld_type =
479480
{
480481
ctyp_desc = Ttyp_any;
@@ -531,21 +532,17 @@ let transl_declaration ~type_record_as_object env sdecl id =
531532
Ast_untagged_variants.check_well_formed ~env ~is_untagged_def cstrs;
532533
(Ttype_variant tcstrs, Type_variant cstrs, sdecl)
533534
| Ptype_record lbls_ -> (
534-
let has_optional attrs =
535-
Ext_list.exists attrs (fun ({txt}, _) -> txt = "res.optional")
536-
in
537535
let optional_labels =
538536
Ext_list.filter_map lbls_ (fun lbl ->
539-
if has_optional lbl.pld_attributes then Some lbl.pld_name.txt
540-
else None)
537+
if lbl.pld_optional then Some lbl.pld_name.txt else None)
541538
in
542539
let lbls =
543540
if optional_labels = [] then lbls_
544541
else
545542
Ext_list.map lbls_ (fun lbl ->
546543
let typ = lbl.pld_type in
547544
let typ =
548-
if has_optional lbl.pld_attributes then
545+
if lbl.pld_optional then
549546
{
550547
typ with
551548
ptyp_desc =
@@ -575,6 +572,7 @@ let transl_declaration ~type_record_as_object env sdecl id =
575572
ld_id = l.ld_id;
576573
ld_name = {txt = Ident.name l.ld_id; loc = l.ld_loc};
577574
ld_mutable = l.ld_mutable;
575+
ld_optional = l.ld_optional;
578576
ld_type =
579577
{
580578
ld_type with
@@ -634,8 +632,7 @@ let transl_declaration ~type_record_as_object env sdecl id =
634632
check_duplicates sdecl.ptype_loc lbls StringSet.empty;
635633
let optional_labels =
636634
Ext_list.filter_map lbls (fun lbl ->
637-
if has_optional lbl.ld_attributes then Some lbl.ld_name.txt
638-
else None)
635+
if lbl.ld_optional then Some lbl.ld_name.txt else None)
639636
in
640637
( Ttype_record lbls,
641638
Type_record

compiler/ml/typedtree.ml

+1
Original file line numberDiff line numberDiff line change
@@ -365,6 +365,7 @@ and label_declaration = {
365365
ld_id: Ident.t;
366366
ld_name: string loc;
367367
ld_mutable: mutable_flag;
368+
ld_optional: bool;
368369
ld_type: core_type;
369370
ld_loc: Location.t;
370371
ld_attributes: attribute list;

compiler/ml/typedtree.mli

+1
Original file line numberDiff line numberDiff line change
@@ -471,6 +471,7 @@ and label_declaration = {
471471
ld_id: Ident.t;
472472
ld_name: string loc;
473473
ld_mutable: mutable_flag;
474+
ld_optional: bool;
474475
ld_type: core_type;
475476
ld_loc: Location.t;
476477
ld_attributes: attributes;

compiler/ml/types.ml

+1
Original file line numberDiff line numberDiff line change
@@ -162,6 +162,7 @@ and record_representation =
162162
and label_declaration = {
163163
ld_id: Ident.t;
164164
ld_mutable: mutable_flag;
165+
ld_optional: bool;
165166
ld_type: type_expr;
166167
ld_loc: Location.t;
167168
ld_attributes: Parsetree.attributes;

compiler/ml/types.mli

+1
Original file line numberDiff line numberDiff line change
@@ -290,6 +290,7 @@ and record_representation =
290290
and label_declaration = {
291291
ld_id: Ident.t;
292292
ld_mutable: mutable_flag;
293+
ld_optional: bool;
293294
ld_type: type_expr;
294295
ld_loc: Location.t;
295296
ld_attributes: Parsetree.attributes;

compiler/ml/untypeast.ml

+2-2
Original file line numberDiff line numberDiff line change
@@ -199,8 +199,8 @@ let constructor_declaration sub cd =
199199
let label_declaration sub ld =
200200
let loc = sub.location sub ld.ld_loc in
201201
let attrs = sub.attributes sub ld.ld_attributes in
202-
Type.field ~loc ~attrs ~mut:ld.ld_mutable (map_loc sub ld.ld_name)
203-
(sub.typ sub ld.ld_type)
202+
Type.field ~loc ~attrs ~mut:ld.ld_mutable ~optional:ld.ld_optional
203+
(map_loc sub ld.ld_name) (sub.typ sub ld.ld_type)
204204

205205
let type_extension sub tyext =
206206
let attrs = sub.attributes sub tyext.tyext_attributes in

compiler/ml/variant_type_spread.ml

+1
Original file line numberDiff line numberDiff line change
@@ -178,6 +178,7 @@ let expand_dummy_constructor_args (sdecl_list : Parsetree.type_declaration list)
178178
pld_mutable = l.ld_mutable;
179179
pld_loc = l.ld_loc;
180180
pld_attributes = [];
181+
pld_optional = l.ld_optional;
181182
pld_type =
182183
{
183184
ptyp_desc = Ptyp_any;

0 commit comments

Comments
 (0)