您的位置:首页 > Web前端

libuv中handle在不同的loop之间transfer

2016-09-28 17:26 302 查看
对于udp,tcp的handle是可以在不同的loop之间transfer,转移时使用函数uv_udp_init_ex和uv_tcp_init_ex初始化,将handle的flags传入进去即可。 eg:主线程负责监听接受连接请求,另一个线程用传递来的handle,监听读写(防止主线程监听事件过多而影响性能,将部分监视器分配到子线程中去)

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

#include <uv.h>

uv_loop_t* loop1;

uv_loop_t* loop2;

uv_async_t async;

void alloc_buffer(uv_handle_t *handle, size_t suggested_size, uv_buf_t *buf) {

buf->base = (char*)malloc(suggested_size);

buf->len = suggested_size;

}

void echo_write(uv_write_t *req, int status) {

if (status) {

fprintf(stderr, "Write error %s\n", uv_strerror(status));

}

free(req);

}

void echo_read(uv_stream_t *client, ssize_t nread, const uv_buf_t *buf) {

if (nread < 0) {

if (nread != UV_EOF)

//fprintf(stderr, "Read error %s\n", uv_err_name(nread));

uv_close((uv_handle_t*)client, NULL);

}

else if (nread > 0) {

uv_write_t *req = (uv_write_t *)malloc(sizeof(uv_write_t));

uv_buf_t wrbuf = uv_buf_init(buf->base, nread);

printf("read buf:%s\n", buf->base);

uv_write(req, client, &wrbuf, 1, echo_write);

}

if (buf->base)

free(buf->base);

}

void on_new_connection(uv_stream_t *server, int status) {

if (status < 0) {

fprintf(stderr, "New connection error %s\n", uv_strerror(status));

return;

}

char cliIp[17] = { 0 };

int cliPort = 0;

uv_tcp_t *client = (uv_tcp_t*)malloc(sizeof(uv_tcp_t));

uv_tcp_init(loop1, client);

if (uv_accept(server, (uv_stream_t*)client) == 0) {

async.data = (void*)client;

uv_async_send(&async);

}

else {

uv_close((uv_handle_t*)client, NULL);

}

}

void async_cb(uv_async_t* handle)

{

printf("async_cb called!\n");

uv_tcp_t* client = (uv_tcp_t*)handle->data;

uv_tcp_init_ex(loop2, client, client->flags);

uv_read_start((uv_stream_t*)client, alloc_buffer, echo_read);

}

void threadFunc(void* arg)

{

loop2 = uv_default_loop();

uv_thread_t id = uv_thread_self();

printf("threadFunc id:%lu.\n", (unsigned long)id);

uv_async_init(loop2, &async, async_cb);

uv_run(loop2, UV_RUN_DEFAULT);

}

int main() {

loop1 = uv_default_loop();

uv_thread_t id = uv_thread_self();

printf("thread id:%lu.\n", id);

//创建子线程

uv_thread_t thread;

uv_thread_create(&thread, threadFunc, NULL);

uv_tcp_t server;

struct sockaddr_in addr;

uv_tcp_init(loop1, &server);

uv_ip4_addr("127.0.0.1", 7000, &addr);

uv_tcp_bind(&server, (const struct sockaddr*)&addr, 0);

int r = uv_listen((uv_stream_t*)&server, 2, on_new_connection);

if (r) {

fprintf(stderr, "Listen error %s\n", uv_strerror(r));

return 1;

}

uv_run(loop1, UV_RUN_DEFAULT);

uv_thread_join(&thread); //等待子线程完成

getchar();

printf("main thread end!\n");

return 0;

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  libuv