前言
libuv没有asio的post函数,但我们可以uv_async_init+uv_async_send模拟,uv_async_send传参可以借助 async.data。由于某些任务很耗时(如文件读写,或者连接mysql),如果直接通过上面这种方式添加到eventloop中,会影响eventloop的吞吐量,所以libuv提供了uv_queue_work来解决这种情况。
libuv的异步任务逻辑
这部分其实就是uv_loop_run的延伸,就不逐代码分析了直接上流程图。
uv_queue_work(loop,callback, done)
libuv提供了线程池。为了解决某些异步任务耗时过长会影响eventloop的吞吐率问题,我们可以将这种任务分成两部分:callback为耗时逻辑 ,done 为执行完callback的后续逻辑。callback交给线程池完成,完成后立刻添加done到eventloop中,然后唤醒eventloop,调用uv_work_done函数,调用done函数。
uv_queue_work 的work req添加和回调触发的详细流程图
在这我更能体会到req和handle的区别,handle初始化后就一直存在在loop中,我们需要调用close将其从loop中移除,但req则不需要,在添加到线程池工作队列中后,在执行一次后,就会将其从工作队列中移除,done部分也是如此(从loop的wq中移除)。