Hi folks,
Is there a way to use thread_local memory in a C++ thread invoked from Multicore-OCaml ?
thread.ml
external spawnThread_O : unit -> unit = "spawnThread_C"
let main () =
let t1 =
Domain.spawn (fun _ ->
spawnThread_O ();
spawnThread_O ())
in
Domain.join t1;
;;
main ()
Note that you are creating a brand new thread in spawnThread_C, so having the counter starts at 0 in threadTask is the expected behavior, since the counter is a thread-local object. And this has nothing to do with OCaml; you would get the exact same behavior with any other language that invokes spawnThread_C.
To share the same counter across all the threads created by the domain, you need the counter to be local to the domain, not to the created thread. For example, it might be done as follows:
Definitely. But that is not an issue specific to my suggestion. That will be true of any solution, since c is supposed to be shared between several system threads.
That depends how you understand the original question.
@hemendra I think your question has some confusion about the difference between domains and threads. A domain is a collection of threads synchronised through a domain lock (only one thread runs at a time). This lets them access a domain-local storage (DLS) without additional synchronisation. The spawned threads are not part of the domain since they run without holding the domain lock. Is this what you intend?
From this, one could think about storing the counter in the DLS, but as an atomic integer so it can be accessed concurrently. But since the DLS is on the OCaml side, it is hard to access it in a safe way from a C thread that does not hold a domain lock for at least some domain. One solution is to malloc a pointer to an atomic_int and store it in the DLS (as an out of heap pointer, e.g. with tagging).
Another solution (I think the simplest), since the number of domains is meant to be small, is to allocate an array atomic_int[Max_domains] (cf. caml/config.h) and pass the value of Caml_state->id to the threads to serve as an index.
@silene Thinking about it, the solution you propose might work by making Counter.c atomic (with the drawback that you mention).