<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On 10 September 2017 at 04:03, Michael Baikov <span dir="ltr"><<a href="mailto:manpacket@gmail.com" target="_blank">manpacket@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr"><div><div><div><div><div><div><div>Greetings<br><br><br></div>Currently GHC supports two kinds of threads - pinned to a specific capability (bound threads) and those it can migrate between any capabilities (unbound threads). For purposes of achieving lower latency in Haskell applications it would be nice to have something in between - threads GHC can migrate but within a certain subset of capabilities only.<br></div></div></div></div></div></div></div></blockquote><div><br></div><div>That's not correct actually: a bound thread is associated with a particular OS thread, but it can migrate between capabilities just like unbound threads.</div><div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr"><div><div><div><div><div>I'm developing a program that contains several kinds of threads - those that do little work and sensitive to latency and those that can spend more CPU time and less latency sensitive. I looked into several cases of increased latency in those sensitive threads (using GHC eventlog) and in all cases sensitive threads were waiting for non-sensitive threads to finish working. I was able to reduce worst case latency by factor of 10 by pinning all the threads in the program to specific capability but manually distributing threads (60+ of them) between capabilities (several different machines with different numbers of cores available) seems very fragile. World stopping GC is still a problem but at least in my case is much less frequently so.<br></div></div></div></div></div></div></blockquote><div> </div><div><div>If you have a fixed set of threads you might just want to use -N<threads> -qn<cores>, and then pin every thread to a different capability.  This gives you 1:1 scheduling at the GHC level, delegating the scheduling job to the OS.  You will also want to use nursery chunks with something like -n2m, so you don't waste too much nursery space on the idle capabilities.</div></div><div><br></div><div>Even if your set of threads isn't fixed you might be able to use a hybrid scheme with -N<large> -qn<cores> and pin the high-priority threads on their own capability, while putting all the low-priority threads on a single capability, or a few separate ones.</div><div><br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr"><div><div><div><div><div></div>It would be nice to be able to allow GHC runtime to migrate a thread between a subset of capabilities using interface similar to this one:<br><br></div><div>-- creates a thread that is allowed to migrate between capabilities according to following rule: ghc is allowed to run this thread on Nth capability if Nth `mod` size_of_word bit in mask is set.<br></div>forkOn' :: Int -> IO () -> IO ThreadId<br></div>forkOn' mask act = undefined<br><br></div>This should allow to define up to 64 (32) distinct groups and allow user to break down their threads into bigger number of potentially intersecting groups by specifying things like capability 0 does latency sensitive things, caps 1..5 - less  sensitive things, caps 6-7 bulk things.<br></div></div></blockquote><div><br></div><div>We could do this, but it would add some complexity to the scheduler and load balancer (which has already been quite hard to get right, I fixed a handful of bugs there recently). I'd be happy review a patch if you want to try it though.</div><div><br></div><div>Cheers</div><div>Simon</div><div> </div><div><br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr"><div></div><div>Anything obvious I'm missing? Any recommendations to how to implement this?<br></div></div></blockquote><div><br></div><div> <br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr"><div></div></div>
<br>______________________________<wbr>_________________<br>
ghc-devs mailing list<br>
<a href="mailto:ghc-devs@haskell.org">ghc-devs@haskell.org</a><br>
<a href="http://mail.haskell.org/cgi-bin/mailman/listinfo/ghc-devs" rel="noreferrer" target="_blank">http://mail.haskell.org/cgi-<wbr>bin/mailman/listinfo/ghc-devs</a><br>
<br></blockquote></div><br></div></div>