Love it! Thanks for creating this.
Anything blocking us from adopting both into the stdlib? :)
Anything blocking us from adopting both into the stdlib? :)
Slow release cycle, tying code that's completely unrelated to the language, to releases of the language, one more threadpool in the standard library that at some point will suffer the same fate as the current, ie being obsolete with no way to remove it etc etc.
The better question to ask: anything blocking asyncdispatch from being moved to a package where it can be developed independently of the language, and also introduce experimental features like thread pools more quickly?
Looks awesome.
Does asynthreadpool offers better "exception handling" from threads than using plain threads or does it have the same limitation and its aim is mostly to improve the ergonomics of concurrent async code ?
Ah, right, I completely forgot about exceptions, as usual :D. Currently the exceptions happening in threads will not be caught by the threadpool, though I believe it should be fairly easy to reroute them to corresponding futures. I'll look into that at some point.
...and its aim is mostly to improve the ergonomics of concurrent async code
Well sure you could say it's about ergonomics, but I would add that async threadpools enable what previously was "impossible" :). That is waiting for a blocking task in the background thread in async manner.
I don't think threadpools should go into the standard library as they don't introduce the interoperability basis, like for instance Futures do. I.e. community split might happen with different Futures implementations, but very not with different threadpools.
Also regarding "both", I would humbly claim that Futures are superior to FlowVars in every aspect, and thus FlowVars should be deprecated at some point :)
The better question to ask: anything blocking asyncdispatch from being moved to a package where it can be developed independently of the language, and also introduce experimental features like thread pools more quickly?
Yes, our breaking changes release policy. We can certainly remove it from Nim 2.0, but who knows how long before that's ready.
I don't think threadpools should go into the standard library as they don't introduce the interoperability basis, like for instance Futures do. I.e. community split might happen with different Futures implementations, but very unlikely with different threadpools.
That's a great point. Perhaps it's time to deprecate the Nim stdlib threadpool implementation in that case.
Also regarding "both", I would humbly claim that Futures are superior to FlowVars in every aspect, and thus FlowVars should be deprecated at some point :)
I won't be humble here: I recall making a passionate plea to reuse futures when the original threadpool was being implemented, too bad I wasn't listened to :)
At this point yes, all we can really do is deprecate them or the full threadpool module completely.
I won't be humble here: I recall making a passionate plea to reuse futures when the original threadpool was being implemented, too bad I wasn't listened to :)
I don't know how I could have "listened", that was before Nim got move semantics and shared memory. It also was hard enough to write, with an additional requirement like "must be compatible with Future[T]" it would have been even harder.
Currently the exceptions happening in threads will not be caught by the threadpool
Update: exceptions in tasks are now propagated to their futures.
This is very exciting!
Maybe a dumb question -- can threadpool-backed Futures be passed to other threads to compose arbitrary multi-threaded computation graphs? Are the futures thread-safe in that sense?
@yglukhov:
The threadpool is not that thread safe...
Both your thread pool contribution and the builtin threadpool library could be re-written to be able to be moved/copied to other threads, especially if the new std/isolation library was also used to move/copy data between threads in a standard way.
I see the problem with using Future{T] as the default output of spawn that it then uses the async library which has cyclic references so that use of --gc:orc (or legacy garbage collection) is a requirement to avoid memory leaks, where use of some sort of FlowVar[T] as output will work with other memory management systems. If the main objection to using the current FlowVar[T] is that one doesn't get an exception "exit status", it shouldn't be that hard to write your library so a new version of FlowVar[T]'s can include "exit status".
It seems to me that there will soon be a new std/threadpool library that works with the new std/channels library as @araq now doesn't like the deep "compiler magic" processes that were formerly required to move/copy reference data between threads. These will use the new std/isolation library as a standard way to move data between threads so that all (and much less) "compiler magic" is only in this one place so it doesn't have to be scattered across the code base.
The language design is still considering the purpose of the =deepcopy hook that can shortcut or modify what happens when an object is deep copied instead of moved.
It seems to me that the language still needs a stdlib version of thread pool so that programmers don't need to write their own for smallish projects, and that the library should be general enough so it minimizes special requirements - ie. it would be best if the same library worked across all memory management systems. As the API is likely to have to change as we move toward using --gc:arc/orc by default, at least the same libraries should be able to be used with both of these.
For most other competing languages, the ability to call into a thread pool is a language facility as part of the runtime when threading is enabled, which facility can be then used by a library. I don't suppose we will get thread pool support directly in the runtime anytime soon, so meantime, the best option is likely a new std/threadpool.
Note: the current std/channels library isn't reliable as it has data races. I will soon have a PR that fixes this.