Skip to content

Commit bd6f227

Browse files
committed
Fix CPS application function and reformat generate.ml
This fixes the trampoline call in caml_call_cps_exact_mono_N functions.
1 parent e099dfc commit bd6f227

File tree

1 file changed

+57
-52
lines changed

1 file changed

+57
-52
lines changed

compiler/lib/generate.ml

Lines changed: 57 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -960,63 +960,68 @@ let parallel_renaming params args continuation queue =
960960

961961
(****)
962962

963-
964963
let apply_fun_raw =
965964
let cps_field = Utf8_string.of_string_exn "cps" in
966965
fun ctx f params exact cps single_version ->
967-
let n = List.length params in
968-
let apply_directly f params =
969-
(* Make sure we are performing a regular call, not a (slower)
970-
method call *)
971-
match f with
972-
| J.EAccess _ | J.EDot _ ->
973-
J.call (J.dot f (Utf8_string.of_string_exn "call")) (s_var "null" :: params) J.N
974-
| _ -> J.call f params J.N
975-
in
976-
let apply cps single =
977-
(* Adapt if [f] is a (direct-style, CPS) closure pair *)
978-
let real_closure =
979-
if (not (Config.Flag.effects ())) || not cps || single
980-
then f
981-
else (* Effects enabled, CPS version, not single-version *)
982-
J.EDot (f, J.ANormal, cps_field)
966+
let n = List.length params in
967+
let apply_directly f params =
968+
(* Make sure we are performing a regular call, not a (slower)
969+
method call *)
970+
match f with
971+
| J.EAccess _ | J.EDot _ ->
972+
J.call (J.dot f (Utf8_string.of_string_exn "call")) (s_var "null" :: params) J.N
973+
| _ -> J.call f params J.N
983974
in
984-
(* We skip the arity check when we know that we have the right
985-
number of parameters, since this test is expensive. *)
986-
if exact
987-
then apply_directly real_closure params
988-
else
989-
let l = Utf8_string.of_string_exn "l" in
975+
let apply cps single =
976+
(* Adapt if [f] is a (direct-style, CPS) closure pair *)
977+
let real_closure =
978+
if (not (Config.Flag.effects ())) || (not cps) || single
979+
then f
980+
else
981+
(* Effects enabled, CPS version, not single-version *)
982+
J.EDot (f, J.ANormal, cps_field)
983+
in
984+
(* We skip the arity check when we know that we have the right
985+
number of parameters, since this test is expensive. *)
986+
if exact
987+
then apply_directly real_closure params
988+
else
989+
let l = Utf8_string.of_string_exn "l" in
990+
J.ECond
991+
( J.EBin
992+
( J.EqEq
993+
, J.ECond
994+
( J.EBin (J.Ge, J.dot real_closure l, int 0)
995+
, J.dot real_closure l
996+
, J.EBin
997+
( J.Eq
998+
, J.dot real_closure l
999+
, J.dot real_closure (Utf8_string.of_string_exn "length") ) )
1000+
, int n )
1001+
, apply_directly real_closure params
1002+
, J.call
1003+
(* Note: [caml_call_gen*] functions takes a two-version function *)
1004+
(runtime_fun ctx (if cps then "caml_call_gen_cps" else "caml_call_gen"))
1005+
[ f; J.array params ]
1006+
J.N )
1007+
in
1008+
if cps
1009+
then (
1010+
assert (Config.Flag.effects ());
1011+
(* When supporting effect, we systematically perform tailcall
1012+
optimization. To implement it, we check the stack depth and
1013+
bounce to a trampoline if needed, to avoid a stack overflow.
1014+
The trampoline then performs the call in an shorter stack. *)
1015+
let f =
1016+
if single_version
1017+
then J.(EObj [ Property (PNS (Utf8_string.of_string_exn "cps"), f) ])
1018+
else f
1019+
in
9901020
J.ECond
991-
( J.EBin
992-
( J.EqEq
993-
, J.ECond
994-
( J.EBin (J.Ge, J.dot real_closure l, int 0)
995-
, J.dot real_closure l
996-
, J.EBin
997-
( J.Eq
998-
, J.dot real_closure l
999-
, J.dot real_closure (Utf8_string.of_string_exn "length") ) )
1000-
, int n )
1001-
, apply_directly real_closure params
1002-
, J.call
1003-
(* Note: [caml_call_gen*] functions takes a two-version function *)
1004-
(runtime_fun ctx (if cps then "caml_call_gen_cps" else "caml_call_gen"))
1005-
[ f; J.array params ]
1006-
J.N )
1007-
in
1008-
if cps
1009-
then (
1010-
assert (Config.Flag.effects ());
1011-
(* When supporting effect, we systematically perform tailcall
1012-
optimization. To implement it, we check the stack depth and
1013-
bounce to a trampoline if needed, to avoid a stack overflow.
1014-
The trampoline then performs the call in an shorter stack. *)
1015-
J.ECond
1016-
( J.call (runtime_fun ctx "caml_stack_check_depth") [] J.N
1017-
, apply cps single_version
1018-
, J.call (runtime_fun ctx "caml_trampoline_return") [ f; J.array params ] J.N ))
1019-
else apply cps single_version
1021+
( J.call (runtime_fun ctx "caml_stack_check_depth") [] J.N
1022+
, apply cps single_version
1023+
, J.call (runtime_fun ctx "caml_trampoline_return") [ f; J.array params ] J.N ))
1024+
else apply cps single_version
10201025

10211026
let generate_apply_fun ctx { arity; exact; cps; single_version } =
10221027
let f' = Var.fresh_n "f" in

0 commit comments

Comments
 (0)