Skip to content

Commit edf63a8

Browse files
committed
chore: formatting + cleanup types
1 parent f31abbc commit edf63a8

File tree

9 files changed

+100
-89
lines changed

9 files changed

+100
-89
lines changed

Makefile

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,3 +37,7 @@ shell:
3737
nix develop .
3838

3939
release: vendor build-release
40+
41+
# helpful for testing pyroscope integration
42+
pyroscope:
43+
docker run --rm -it -p 4040:4040 grafana/pyroscope:latest

bindings/Pyro_caml_rust_bindings.ml

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,9 @@
1515
(* Bindings for the pyro-caml binary to the pyro caml instrumentation library *)
1616

1717
let read_poll cursor interval = Pyro_caml_instruments.read_poll cursor interval
18-
1918
let create_cursor = Pyro_caml_instruments.create_cursor
2019

2120
let () =
2221
(* Register them for binding into rust *)
23-
Callback.register "read_poll_ml" read_poll ;
22+
Callback.register "read_poll_ml" read_poll;
2423
Callback.register "create_cursor_ml" create_cursor

example/Example.ml

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
(* Prelude *)
1818
(*****************************************************************************)
1919
let example_func2 () =
20-
My_module.do_short_thing () ;
20+
My_module.do_short_thing ();
2121
My_module.alloc_thing ()
2222

2323
let example_func () =
@@ -27,14 +27,18 @@ let example_func () =
2727
let example_func3 () = My_module.do_long_thing ()
2828

2929
let () =
30-
Pyro_caml_instruments.with_memprof_sampler
31-
@@ fun () ->
32-
Printf.printf "Starting loop\n" ;
33-
flush_all () ;
30+
Pyro_caml_instruments.with_memprof_sampler @@ fun () ->
31+
Printf.printf "Starting loop\n";
32+
flush_all ();
3433
let do_main_thing () =
3534
while true do
36-
example_func () ; example_func3 () ; example_func () ; example_func3 ()
35+
example_func ();
36+
example_func3 ();
37+
example_func ();
38+
example_func3 ()
3739
done
3840
in
39-
let domains = List.init 8 (fun _ -> Domain.spawn (fun () -> do_main_thing ())) in
41+
let domains =
42+
List.init 8 (fun _ -> Domain.spawn (fun () -> do_main_thing ()))
43+
in
4044
List.iter Domain.join domains

example/My_module.ml

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
(* Prelude *)
1818
(*****************************************************************************)
1919

20-
type t = {x: int; y: string}
20+
type t = { x : int; y : string }
2121

2222
external comp_and_callback : (unit -> unit) -> unit = "ml_comp_and_callback"
2323

@@ -27,17 +27,22 @@ let f x y z =
2727
let c = b - y in
2828
c
2929

30+
let rec non_tail_recursive_fold_right f lst acc =
31+
match lst with
32+
| [] -> acc
33+
| x :: xs -> f x (non_tail_recursive_fold_right f xs acc)
3034

3135
let alloc_thing () =
3236
let random_list =
33-
List.init 1000 (fun _ ->
34-
{x= Random.int 100000; y= string_of_int (Random.int 100000)} )
37+
List.init 2048 (fun _ ->
38+
{ x = Random.int 100000; y = string_of_int (Random.int 100000) })
3539
in
3640
let _sorted = List.sort compare random_list in
37-
List.iter
38-
(fun x ->
39-
if f x.x (String.length x.y) 100 mod 10 = 10000000000 then assert false )
40-
random_list
41+
non_tail_recursive_fold_right
42+
(fun x acc ->
43+
if f x.x (String.length x.y) 100 mod 10 = 42 then assert false;
44+
acc)
45+
random_list ()
4146

4247
class stack_of_ints =
4348
object (_self)
@@ -50,7 +55,7 @@ class stack_of_ints =
5055
method pop =
5156
(* pop method *)
5257
let result = List.hd the_list in
53-
the_list <- List.tl the_list ;
58+
the_list <- List.tl the_list;
5459
result
5560

5661
method peek =
@@ -66,19 +71,19 @@ let do_thing () =
6671
let stack = new stack_of_ints in
6772
for _i = 1 to 1000 do
6873
stack#push (Random.int 100000)
69-
done ;
74+
done;
7075
while stack#size > 0 do
7176
let _ = stack#pop in
7277
()
73-
done ;
78+
done;
7479
alloc_thing ()
7580

7681
let do_short_thing () = alloc_thing ()
7782

7883
let do_long_thing () =
79-
alloc_thing () ;
80-
alloc_thing () ;
81-
alloc_thing () ;
84+
alloc_thing ();
85+
alloc_thing ();
86+
alloc_thing ();
8287
comp_and_callback alloc_thing
8388

8489
(* Example object *)

lib/Event.ml

Lines changed: 16 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,12 @@ module Hash = Digest.MD5
2626
profiler *)
2727
type t =
2828
| Point of (float * Stack_trace.raw_stack_trace)
29-
| Partial of {id: Hash.t; bytes: Bytes.t; part: int; part_count: int}
29+
| Partial of { id : Hash.t; bytes : Bytes.t; part : int; part_count : int }
3030

3131
type marshaled = bytes * int
3232

33-
let make_partial id part_count part bytes = Partial {id; bytes; part; part_count}
33+
let make_partial id part_count part bytes =
34+
Partial { id; bytes; part; part_count }
3435

3536
let split_bytes bytes size =
3637
let rec aux offset parts =
@@ -55,7 +56,7 @@ let marshal_event ?(max_size = 800) e =
5556
let marshaled_event, len = marshal e in
5657
(* Max size of runtime event type payload *)
5758
(* https://ocaml.org/manual/5.3/api/Runtime_events.Type.html *)
58-
if len <= 1024 then [(marshaled_event, len)]
59+
if len <= 1024 then [ (marshaled_event, len) ]
5960
else
6061
(* if it's bigger split it up! *)
6162
let id = Hash.bytes marshaled_event in
@@ -73,7 +74,7 @@ type Runtime_events.User.tag += Perf_event_tag
7374

7475
let perf_event_type =
7576
let encode (bytes : bytes) ((marshaled, len) : marshaled) : int =
76-
Bytes.blit marshaled 0 bytes 0 len ;
77+
Bytes.blit marshaled 0 bytes 0 len;
7778
len
7879
in
7980
let decode (bytes : bytes) (len : int) : marshaled = (bytes, len) in
@@ -99,13 +100,11 @@ type event_buffer = (Hash.t, (int * Bytes.t) list) Hashtbl.t
99100
let event_of_perf_event buffer (marshaled, _) : t =
100101
let event = Marshal.from_bytes marshaled 0 in
101102
match event with
102-
| Partial {id; bytes; part_count; part} ->
103+
| Partial { id; bytes; part_count; part } ->
103104
let parts =
104105
match Hashtbl.find_opt buffer id with
105-
| Some parts ->
106-
(part, bytes) :: parts
107-
| None ->
108-
[(part, bytes)]
106+
| Some parts -> (part, bytes) :: parts
107+
| None -> [ (part, bytes) ]
109108
in
110109
let parts =
111110
List.sort_uniq (fun (id1, _) (id2, _) -> Int.compare id1 id2) parts
@@ -118,16 +117,15 @@ let event_of_perf_event buffer (marshaled, _) : t =
118117
let new_acc =
119118
Bytes.create (Bytes.length acc + Bytes.length bytes)
120119
in
121-
Bytes.blit acc 0 new_acc 0 (Bytes.length acc) ;
120+
Bytes.blit acc 0 new_acc 0 (Bytes.length acc);
122121
Bytes.blit bytes 0 new_acc (Bytes.length acc)
123-
(Bytes.length bytes) ;
124-
new_acc )
122+
(Bytes.length bytes);
123+
new_acc)
125124
(Bytes.create 0)
126125
in
127-
Hashtbl.remove buffer id ;
128-
Marshal.from_bytes full_bytes 0 )
126+
Hashtbl.remove buffer id;
127+
Marshal.from_bytes full_bytes 0)
129128
else (
130-
Hashtbl.replace buffer id parts ;
131-
event )
132-
| _ ->
133-
event
129+
Hashtbl.replace buffer id parts;
130+
event)
131+
| _ -> event

lib/Pyro_caml_instruments.ml

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -45,26 +45,29 @@ let tracker : (unit, unit) Gc.Memprof.tracker =
4545
Printexc.get_callstack in the other functions. Plus for some reason the
4646
memprof backtraces seem way more comprehensive than those from
4747
Printexc.get_callstack *)
48-
let alloc_minor {Gc.Memprof.callstack; _} =
49-
emit_point_event callstack ;
48+
let alloc_minor { Gc.Memprof.callstack; _ } =
49+
emit_point_event callstack;
5050
(* Don't care about tacking on any data to memory *)
5151
None
5252
in
53-
let alloc_major {Gc.Memprof.callstack; _} =
54-
emit_point_event callstack ; None
53+
let alloc_major { Gc.Memprof.callstack; _ } =
54+
emit_point_event callstack;
55+
None
5556
in
5657
let promote () = None in
5758
let dealloc_minor = Fun.id in
5859
let dealloc_major = Fun.id in
59-
{Gc.Memprof.alloc_minor; alloc_major; promote; dealloc_minor; dealloc_major}
60+
{ Gc.Memprof.alloc_minor; alloc_major; promote; dealloc_minor; dealloc_major }
6061

6162
(* 1e-6 is nice but chosen somewhat randomly. Too high and you end up sending
6263
too many points and overwhelming the profiler, too little and you don't get
6364
enough info *)
6465
let with_memprof_sampler ?(sampling_rate = 1e-6) f =
6566
let memprof = Gc.Memprof.start ~sampling_rate tracker in
6667
Fun.protect
67-
~finally:(fun () -> Gc.Memprof.stop () ; Gc.Memprof.discard memprof)
68+
~finally:(fun () ->
69+
Gc.Memprof.stop ();
70+
Gc.Memprof.discard memprof)
6871
f
6972

7073
let maybe_with_memprof_sampler ?sampling_rate f =
@@ -74,7 +77,6 @@ let maybe_with_memprof_sampler ?sampling_rate f =
7477
(* Profiler code *)
7578
(*****************************************************************************)
7679
let create_cursor path pid = Runtime_events.create_cursor (Some (path, pid))
77-
7880
let empty_callbacks = Runtime_events.Callbacks.create ()
7981

8082
(* Minimize work we do in process event since the instrumented program can write
@@ -83,8 +85,7 @@ let process_event now interval sample_points = function
8385
| Point (time, raw_st) ->
8486
if now -. time < interval then
8587
sample_points := (time, raw_st) :: !sample_points
86-
| Partial _ ->
87-
()
88+
| Partial _ -> ()
8889

8990
let read_poll ?(max_events = None) ?(callbacks = empty_callbacks) cursor
9091
interval =
@@ -97,7 +98,7 @@ let read_poll ?(max_events = None) ?(callbacks = empty_callbacks) cursor
9798
_event_t (e : marshaled) ->
9899
e
99100
|> event_of_perf_event event_buffer
100-
|> process_event now interval sample_points )
101+
|> process_event now interval sample_points)
101102
callbacks
102103
in
103104
(* TODO? Multithread this? *)
@@ -113,9 +114,9 @@ let read_poll ?(max_events = None) ?(callbacks = empty_callbacks) cursor
113114
don't have a sample within 1ms or some other resolution of the sample
114115
time *)
115116
List.sort (fun (a_time, _) (b_time, _) ->
116-
Float.compare (now -. a_time) (now -. b_time) )
117+
Float.compare (now -. a_time) (now -. b_time))
117118
|> List.map (fun (_, raw_st) -> Stack_trace.t_of_raw_stack_trace raw_st)
118119
|> List.sort_uniq (fun a b ->
119-
Int.compare a.Stack_trace.thread_id b.Stack_trace.thread_id )
120+
Int.compare a.Stack_trace.thread_id b.Stack_trace.thread_id)
120121
in
121122
sample_points

lib/Pyro_caml_instruments.mli

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,11 @@ val create_cursor : string -> int -> Runtime_events.cursor
2222
from the given [path] and [pid]. *)
2323

2424
val read_poll :
25-
?max_events:int option
26-
-> ?callbacks:Runtime_events.Callbacks.t
27-
-> Runtime_events.cursor
28-
-> float
29-
-> Stack_trace.t list
25+
?max_events:int option ->
26+
?callbacks:Runtime_events.Callbacks.t ->
27+
Runtime_events.cursor ->
28+
float ->
29+
Stack_trace.t list
3030
(** [read_poll cursor sample_interval] will read the profiling runtime events
3131
from the given cursor, and will give attempt to give a single
3232
{!Stack_trace.t} per every unique thread id, within [sample_interval] of the

lib/Stack_trace.ml

Lines changed: 14 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -44,31 +44,26 @@ let raw_stack_trace_of_backtrace bt : raw_stack_trace =
4444
probably want to give that as an option at some point *)
4545
(* coupling: ocaml_intf *)
4646
type frame = {
47-
name : string;
48-
filename : string;
49-
line : int;
47+
name : string option;
48+
filename : string option;
49+
line : int option;
5050
inlined : bool; [@eq.skip]
5151
(* We really don't care about if a function is inlined for equality*)
5252
}
5353
[@@deriving eq]
5454

55-
let stack_frame_of_slot (slot : Printexc.backtrace_slot) : frame option =
56-
let loc = Printexc.Slot.location slot in
55+
let other_frame =
56+
{ name = Some "other"; filename = None; line = None; inlined = false }
57+
58+
let stack_frame_of_slot (slot : Printexc.backtrace_slot) : frame =
59+
let filename, line =
60+
match Printexc.Slot.location slot with
61+
| Some loc -> (Some loc.filename, Some loc.line_number)
62+
| None -> (None, None)
63+
in
5764
let name = Printexc.Slot.name slot in
5865
let inlined = Printexc.Slot.is_inline slot in
59-
match (loc, name) with
60-
| Some loc, Some name ->
61-
Some { name; filename = loc.filename; line = loc.line_number; inlined }
62-
| None, Some name -> Some { name; filename = "<unknown>"; line = 0; inlined }
63-
| Some loc, None ->
64-
Some
65-
{
66-
name = "<unknown>";
67-
filename = loc.filename;
68-
line = loc.line_number;
69-
inlined;
70-
}
71-
| None, None -> None
66+
{ name; filename; line; inlined }
7267

7368
(* Looking ahead by up to 3 can be useful for recursive functions to make them
7469
much more legible. E.g. List.map can be very recursive, and pyroscope has a
@@ -90,7 +85,7 @@ let compress frames =
9085
aux [] frames
9186

9287
let stack_frames_of_slots slots =
93-
slots |> List.filter_map stack_frame_of_slot |> compress
88+
slots |> List.map stack_frame_of_slot |> compress
9489

9590
(*****************************************************************************)
9691
(* Stack traces *)

0 commit comments

Comments
 (0)