Skip to content

Commit 40d69ce

Browse files
authored
flambda-backend: Stop local function optimisation from moving code into function bodies; opaque_identity fixes for class compilation (oxcaml#537)
* Forbid local function optimisation across functions * Wrap blocks for shared method arrays in Popaque * More opacity in Translclass * Even more opacity around objects * Promote test * Refactoring
1 parent f08ae58 commit 40d69ce

4 files changed

Lines changed: 53 additions & 26 deletions

File tree

lambda/simplif.ml

Lines changed: 17 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -818,6 +818,7 @@ let split_default_wrapper ~id:fun_id ~kind ~params ~return ~body
818818
type slot =
819819
{
820820
func: lfunction;
821+
function_scope: lambda;
821822
mutable scope: lambda option;
822823
}
823824

@@ -836,6 +837,7 @@ let simplify_local_functions lam =
836837
is in tail position. *)
837838
let current_scope = ref lam in
838839
let current_region_scope = ref lam in
840+
let current_function_scope = ref lam in
839841
let check_static lf =
840842
if lf.attr.local = Always_local then
841843
Location.prerr_warning (to_location lf.loc)
@@ -854,7 +856,9 @@ let simplify_local_functions lam =
854856
in
855857
let rec tail = function
856858
| Llet (_str, _kind, id, Lfunction lf, cont) when enabled lf.attr ->
857-
let r = {func = lf; scope = None} in
859+
let r =
860+
{func = lf; function_scope = !current_function_scope; scope = None}
861+
in
858862
Hashtbl.add slots id r;
859863
tail cont;
860864
begin match Hashtbl.find_opt slots id with
@@ -874,7 +878,7 @@ let simplify_local_functions lam =
874878
| _ ->
875879
check_static lf;
876880
(* note: if scope = None, the function is unused *)
877-
non_tail lf.body
881+
function_definition lf
878882
end
879883
| Lapply {ap_func = Lvar id; ap_args; ap_region_close; _} ->
880884
let curr_scope =
@@ -890,6 +894,10 @@ let simplify_local_functions lam =
890894
| Some {scope = Some scope; _} when scope != curr_scope ->
891895
(* Different "tail scope" *)
892896
Hashtbl.remove slots id
897+
| Some {function_scope = fscope; _}
898+
when fscope != !current_function_scope ->
899+
(* Different function *)
900+
Hashtbl.remove slots id
893901
| Some ({scope = None; _} as slot) ->
894902
(* First use of the function: remember the current tail scope *)
895903
slot.scope <- Some curr_scope
@@ -899,9 +907,9 @@ let simplify_local_functions lam =
899907
List.iter non_tail ap_args
900908
| Lvar id ->
901909
Hashtbl.remove slots id
902-
| Lfunction lf as lam ->
910+
| Lfunction lf ->
903911
check_static lf;
904-
Lambda.shallow_iter ~tail ~non_tail lam
912+
function_definition lf
905913
| Lregion lam -> region lam
906914
| lam ->
907915
Lambda.shallow_iter ~tail ~non_tail lam
@@ -914,6 +922,11 @@ let simplify_local_functions lam =
914922
tail lam;
915923
current_scope := !current_region_scope;
916924
current_region_scope := old_tail_scope
925+
and function_definition lf =
926+
let old_function_scope = !current_function_scope in
927+
current_function_scope := lf.body;
928+
non_tail lf.body;
929+
current_function_scope := old_function_scope
917930
and with_scope ~scope lam =
918931
let old_scope = !current_scope in
919932
let old_tail_scope = !current_region_scope in

lambda/translclass.ml

Lines changed: 19 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -52,17 +52,20 @@ let lapply ap =
5252
Lapply ap
5353

5454
let mkappl (func, args) =
55-
Lapply {
56-
ap_loc=Loc_unknown;
57-
ap_func=func;
58-
ap_args=args;
59-
ap_region_close=Rc_normal;
60-
ap_mode=Alloc_heap;
61-
ap_tailcall=Default_tailcall;
62-
ap_inlined=Default_inlined;
63-
ap_specialised=Default_specialise;
64-
ap_probe=None;
65-
};;
55+
Lprim
56+
(Popaque,
57+
[Lapply {
58+
ap_loc=Loc_unknown;
59+
ap_func=func;
60+
ap_args=args;
61+
ap_region_close=Rc_normal;
62+
ap_mode=Alloc_heap;
63+
ap_tailcall=Default_tailcall;
64+
ap_inlined=Default_inlined;
65+
ap_specialised=Default_specialise;
66+
ap_probe=None;
67+
}],
68+
Loc_unknown);;
6669

6770
let lsequence l1 l2 =
6871
if l2 = lambda_unit then l1 else Lsequence(l1, l2)
@@ -264,9 +267,11 @@ let output_methods tbl methods lam =
264267
| [lab; code] ->
265268
lsequence (mkappl(oo_prim "set_method", [Lvar tbl; lab; code])) lam
266269
| _ ->
270+
let methods =
271+
Lprim(Pmakeblock(0,Immutable,None,Alloc_heap), methods, Loc_unknown)
272+
in
267273
lsequence (mkappl(oo_prim "set_methods",
268-
[Lvar tbl; Lprim(Pmakeblock(0,Immutable,None,Alloc_heap),
269-
methods, Loc_unknown)]))
274+
[Lvar tbl; Lprim (Popaque, [methods], Loc_unknown)]))
270275
lam
271276

272277
let rec ignore_cstrs cl =
@@ -910,7 +915,7 @@ let transl_class ~scopes ids cl_id pub_meths cl vflag =
910915
if inh_keys = [] then Llet(Alias, Pgenval, cached, Lvar tables, lam) else
911916
Llet(Strict, Pgenval, cached,
912917
mkappl (oo_prim "lookup_tables",
913-
[Lvar tables; Lprim(Pmakeblock(0, Immutable, None, Alloc_heap),
918+
[Lvar tables; Lprim(Pmakearray(Paddrarray, Immutable, Alloc_heap),
914919
inh_keys, Loc_unknown)]),
915920
lam)
916921
and lset cached i lam =

lambda/translobj.ml

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,11 @@ let transl_label_init_general f =
9191
let expr, size = f () in
9292
let expr =
9393
Hashtbl.fold
94-
(fun c id expr -> Llet(Alias, Pgenval, id, Lconst c, expr))
94+
(fun c id expr ->
95+
let const =
96+
Lprim (Popaque, [Lconst c], Debuginfo.Scoped_location.Loc_unknown)
97+
in
98+
Llet(Alias, Pgenval, id, const, expr))
9599
consts expr
96100
in
97101
(*let expr =
@@ -177,10 +181,13 @@ let oo_wrap env req f x =
177181
let lambda =
178182
List.fold_left
179183
(fun lambda id ->
184+
let cl =
185+
Lprim(Pmakeblock(0, Mutable, None, Alloc_heap),
186+
[lambda_unit; lambda_unit; lambda_unit],
187+
Loc_unknown)
188+
in
180189
Llet(StrictOpt, Pgenval, id,
181-
Lprim(Pmakeblock(0, Mutable, None, Alloc_heap),
182-
[lambda_unit; lambda_unit; lambda_unit],
183-
Loc_unknown),
190+
Lprim (Popaque, [cl], Loc_unknown),
184191
lambda))
185192
lambda !classes
186193
in

testsuite/tests/functors/functors.compilers.reference

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,19 +20,21 @@
2020
(module-defn(F1) Functors functors.ml(31):516-632
2121
(function X Y is_a_functor always_inline
2222
(let
23-
(sheep =
23+
(cow =
2424
(function x[int] : int
25-
(+ 1 (apply (field 0 Y) (apply (field 0 X) x)))))
25+
(apply (field 0 Y) (apply (field 0 X) x)))
26+
sheep = (function x[int] : int (+ 1 (apply cow x))))
2627
(makeblock 0 sheep))))
2728
F2 =
2829
(module-defn(F2) Functors functors.ml(36):634-784
2930
(function X Y is_a_functor always_inline
3031
(let
3132
(X =a (makeblock 0 (field 1 X))
3233
Y =a (makeblock 0 (field 1 Y))
33-
sheep =
34+
cow =
3435
(function x[int] : int
35-
(+ 1 (apply (field 0 Y) (apply (field 0 X) x)))))
36+
(apply (field 0 Y) (apply (field 0 X) x)))
37+
sheep = (function x[int] : int (+ 1 (apply cow x))))
3638
(makeblock 0 sheep))))
3739
M =
3840
(module-defn(M) Functors functors.ml(41):786-970

0 commit comments

Comments
 (0)