-
Notifications
You must be signed in to change notification settings - Fork 203
Description
https://github.com/Xavorim/cpp_tasks_bench?tab=readme-ov-file#results-on-my-system benchmarks libunifex against a few other concurrency libraries. The benchmark attempts to launch 1 million concurrent tasks. Unfortunately, the benchmark states libunifex hangs at just 100K tasks. I am able to replicate this myself, with the benchmark program at 100% for a minute until I killed the program.
I reimplemented the benchmark with async_manual_reset_event instead of timed_single_thread_context, and I am able to launch 1 million tasks in about 4 seconds: Xavorim/cpp_tasks_bench#1
I'm entering this issue to see if the timer scheduler can be improved. I'll also compare against stdexec (as the benchmark repo doesn't include it currently).
stdexec benchmark
stdexec appears to be able to run 1 million tasks with exec::timed_thread_context
#include <stdexec/execution.hpp>
#include <exec/timed_thread_scheduler.hpp>
#include <exec/task.hpp>
#include <exec/async_scope.hpp>
#include <chrono>
#include <cstdio>
#include <iostream>
#include <cstdlib>
#include <ranges>
exec::timed_thread_context TIMER;
auto async_sleep(auto s) { return exec::schedule_after(TIMER.get_scheduler(), s); }
int main(int argc, char **argv) {
if (argc < 2) {
fprintf(stderr,
"Please specify the number of tasks\n"
"example: %s 10000\n",
argv[0]);
return EXIT_FAILURE;
}
exec::async_scope scope;
for (auto i : std::views::iota(0, std::stoi(argv[1]))) {
scope.spawn([]() -> exec::task<void> { co_await async_sleep(std::chrono::seconds(10)); }());
}
stdexec::sync_wait(scope.on_empty());
return 0;
}
$ time ./a.out 1000000
real 0m17.098s
user 0m11.241s
sys 0m4.150s