mirror of
https://github.com/c-cube/moonpool.git
synced 2025-12-06 03:05:30 -05:00
112 lines
2.8 KiB
OCaml
112 lines
2.8 KiB
OCaml
open Moonpool
|
|
module F = Moonpool_fib.Fiber
|
|
|
|
let ( let@ ) = ( @@ )
|
|
let runner = Ws_pool.create ~num_threads:8 ()
|
|
let lock = Lock.create ()
|
|
|
|
let logf fmt =
|
|
Printf.ksprintf
|
|
(fun s ->
|
|
let out = stdout in
|
|
(let@ () = Lock.with_ lock in
|
|
output_string out s);
|
|
flush out)
|
|
fmt
|
|
|
|
let () =
|
|
logf "============\nstart\n";
|
|
let fib =
|
|
F.spawn_top ~on:runner @@ fun () ->
|
|
let subs =
|
|
List.init 5 (fun i ->
|
|
F.spawn_link ~protect:false @@ fun () ->
|
|
Thread.delay (float i *. 0.01);
|
|
i)
|
|
in
|
|
|
|
ignore
|
|
(F.spawn_link ~protect:false @@ fun () ->
|
|
Thread.delay 0.4;
|
|
logf "other fib done\n%!"
|
|
: _ F.t);
|
|
logf "wait for subs\n%!";
|
|
List.iteri
|
|
(fun i f ->
|
|
logf "await fiber %d\n%!" i;
|
|
logf "cur fiber is some: %b\n%!"
|
|
(Option.is_some @@ F.Private_.get_cur ());
|
|
let res = F.await f in
|
|
logf "cur fiber is some: %b\n%!"
|
|
(Option.is_some @@ F.Private_.get_cur ());
|
|
Thread.delay 0.000_01;
|
|
F.yield ();
|
|
logf "res %d = %d\n%!" i res)
|
|
subs;
|
|
logf "main fiber done\n%!"
|
|
in
|
|
|
|
Fut.wait_block_exn @@ F.res fib;
|
|
logf "main fiber exited\n%!";
|
|
()
|
|
|
|
let () =
|
|
(* same but now, cancel *)
|
|
logf "============\nstart\n";
|
|
let fib =
|
|
F.spawn_top ~on:runner @@ fun () ->
|
|
let@ () =
|
|
F.with_self_cancel_callback (fun ebt ->
|
|
logf "main fiber cancelled with %s\n%!" @@ Exn_bt.show ebt)
|
|
in
|
|
|
|
let subs =
|
|
List.init 10 (fun i ->
|
|
F.spawn_link ~protect:false @@ fun () ->
|
|
let@ () =
|
|
F.with_self_cancel_callback (fun _ ->
|
|
logf "sub-fiber %d was cancelled\n%!" i)
|
|
in
|
|
Thread.delay (float i *. 0.001);
|
|
F.yield ();
|
|
if i = 7 then (
|
|
logf "I'm fiber %d and I'm about to…\n%!" i;
|
|
failwith "oh no!"
|
|
);
|
|
i)
|
|
in
|
|
|
|
List.iteri
|
|
(fun i fib ->
|
|
F.on_result fib (function
|
|
| Ok _ -> logf "fiber %d resolved as ok\n%!" i
|
|
| Error _ -> logf "fiber %d resolved as error\n%!" i))
|
|
subs;
|
|
|
|
ignore
|
|
(F.spawn_link ~protect:false @@ fun () ->
|
|
Thread.delay 0.2;
|
|
logf "other fib done\n%!"
|
|
: _ F.t);
|
|
|
|
logf "wait for subs\n%!";
|
|
List.iteri
|
|
(fun i f ->
|
|
logf "await fiber %d\n%!" i;
|
|
let res = F.await f in
|
|
logf "res %d = %d\n%!" i res)
|
|
subs;
|
|
logf "yield\n%!";
|
|
F.yield ();
|
|
logf "yielded\n%!";
|
|
logf "main fiber done\n%!"
|
|
in
|
|
|
|
F.on_result fib (function
|
|
| Ok () -> logf "main fiber result: ok\n%!"
|
|
| Error ebt -> logf "main fiber result: error %s\n%!" (Exn_bt.show ebt));
|
|
|
|
(try Fut.wait_block_exn @@ F.res fib
|
|
with Failure msg -> logf "main fib failed with %S\n%!" msg);
|
|
logf "main fiber exited\n%!";
|
|
()
|