Skip to content

Commit 68cc910

Browse files
committed
Compiler: load shapes for cma.js and cmo.js
1 parent 3230809 commit 68cc910

File tree

4 files changed

+89
-16
lines changed

4 files changed

+89
-16
lines changed

compiler/lib/driver.ml

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,6 @@ let debug = Debug.find "main"
2323

2424
let times = Debug.find "times"
2525

26-
let debug_shapes = Debug.find "shapes"
27-
2826
type optimized_result =
2927
{ program : Code.program
3028
; variable_uses : Deadcode.variable_uses
@@ -103,7 +101,7 @@ let ( +> ) f g x = g (f x)
103101
let map_fst5 f (x, y, z, t, u) = f x, y, z, t, u
104102

105103
let collects_shapes ~shapes (p : Code.program) =
106-
if debug_shapes () || shapes
104+
if shapes
107105
then (
108106
let t = Timer.make () in
109107
let shapes = ref StringMap.empty in
@@ -729,17 +727,17 @@ let full ~standalone ~wrap_with_fun ~shapes ~profile ~link ~source_map ~formatte
729727
+> name_variables
730728
+> output formatter ~source_map ()
731729
in
732-
let shapes = optimized_code.shapes in
730+
let shapes_v = optimized_code.shapes in
733731
StringMap.iter
734732
(fun name shape ->
735733
Shape.Store.set ~name shape;
736-
if debug_shapes ()
734+
if shapes
737735
then
738736
Pretty_print.string
739737
formatter
740738
(Printf.sprintf "//# shape: %s:%s\n" name (Shape.to_string shape)))
741-
shapes;
742-
emit formatter optimized_code, shapes
739+
shapes_v;
740+
emit formatter optimized_code, shapes_v
743741

744742
let full_no_source_map ~formatter ~shapes ~standalone ~wrap_with_fun ~profile ~link p =
745743
let (_ : Source_map.info * _) =

compiler/lib/shape.ml

Lines changed: 82 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,73 @@ let rec to_string (shape : t) =
6464
| Top -> ""
6565
| _ -> "->" ^ to_string res)
6666

67+
let of_string (s : string) =
68+
let pos = ref 0 in
69+
let current () = s.[!pos] in
70+
let next () = incr pos in
71+
let parse_char c =
72+
let c' = current () in
73+
if Char.equal c c' then next () else assert false
74+
in
75+
let parse_char_opt c =
76+
let c' = current () in
77+
if Char.equal c c'
78+
then (
79+
next ();
80+
true)
81+
else false
82+
in
83+
let rec parse_int acc =
84+
match current () with
85+
| '0' .. '9' as c ->
86+
let d = Char.code c - Char.code '0' in
87+
let acc = (acc * 10) + d in
88+
next ();
89+
parse_int acc
90+
| _ -> acc
91+
in
92+
let rec parse_shape () =
93+
match current () with
94+
| '[' ->
95+
next ();
96+
parse_block []
97+
| 'N' ->
98+
next ();
99+
Top
100+
| 'F' ->
101+
next ();
102+
parse_fun ()
103+
| _ -> assert false
104+
and parse_block acc =
105+
match current () with
106+
| ']' ->
107+
next ();
108+
Block (List.rev acc)
109+
| _ -> (
110+
let x = parse_shape () in
111+
match current () with
112+
| ',' ->
113+
next ();
114+
parse_block (x :: acc)
115+
| ']' ->
116+
next ();
117+
Block (List.rev (x :: acc))
118+
| _ -> assert false)
119+
and parse_fun () =
120+
let () = parse_char '(' in
121+
let arity = parse_int 0 in
122+
let () = parse_char ')' in
123+
let pure = parse_char_opt '*' in
124+
match current () with
125+
| '-' ->
126+
next ();
127+
parse_char '>';
128+
let res = parse_shape () in
129+
Function { arity; pure; res }
130+
| _ -> Function { arity; pure; res = Top }
131+
in
132+
parse_shape ()
133+
67134
module Store = struct
68135
let ext = ".jsoo-shape"
69136

@@ -82,11 +149,21 @@ module Store = struct
82149
let load' fn =
83150
let ic = open_in_bin fn in
84151
let m = really_input_string ic (String.length magic) in
85-
if not (String.equal m magic)
86-
then failwith (Printf.sprintf "Invalid magic number for shape file %s" fn);
87-
let shapes : (string * shape) list = Marshal.from_channel ic in
88-
close_in ic;
89-
List.iter shapes ~f:(fun (name, shape) -> set ~name shape)
152+
if String.equal m magic
153+
then (
154+
let shapes : (string * shape) list = Marshal.from_channel ic in
155+
close_in ic;
156+
List.iter shapes ~f:(fun (name, shape) -> set ~name shape))
157+
else (
158+
close_in ic;
159+
let l = file_lines_bin fn in
160+
List.iter l ~f:(fun s ->
161+
match String.drop_prefix ~prefix:"//#shape: " s with
162+
| None -> ()
163+
| Some name_n_shape -> (
164+
match String.lsplit2 name_n_shape ~on:':' with
165+
| None -> ()
166+
| Some (name, shape) -> set ~name (of_string shape))))
90167

91168
let load ~name ~paths =
92169
if String.Hashtbl.mem t name

compiler/lib/shape.mli

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ type t =
2828

2929
val to_string : t -> string
3030

31+
val of_string : string -> t
32+
3133
val equal : t -> t -> bool
3234

3335
val merge : t -> t -> t

compiler/tests-full/dune

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,6 @@
1111
--debug
1212
var
1313
--debuginfo
14-
--debug
15-
shapes
1614
%{lib:stdlib:stdlib.cma}
1715
-o
1816
%{targets})))
@@ -50,8 +48,6 @@
5048
%{bin:js_of_ocaml}
5149
--pretty
5250
--debuginfo
53-
--debug
54-
shapes
5551
%{dep:shapes.cma}
5652
-o
5753
%{targets})))

0 commit comments

Comments
 (0)