wil*_*ill 5 c unix sockets multithreading
我正在尝试制作一个简单的客户端 - 服务器聊天程序.在客户端,我分拆另一个线程来读取服务器上的任何输入数据.问题是,当一个人从主线程注销时,我想优雅地终止第二个线程.我试图使用共享变量'running'来终止,问题是,socket read()命令是一个阻塞命令,所以如果我这样做(运行== 1),服务器必须在读取之前发送一些东西并且可以再次检查while条件.我正在寻找一种方法(仅使用常见的unix套接字)来执行非阻塞读取,基本上某种形式的peek()可以工作,因为我可以不断检查循环以查看我是否已完成.
读取线程循环在下面,现在它没有任何共享变量的互斥锁,但我打算稍后添加,不要担心!;)
void *serverlisten(void *vargp)
{
while(running == 1)
{
read(socket, readbuffer, sizeof(readbuffer));
printf("CLIENT RECIEVED: %s\n", readbuffer);
}
pthread_exit(NULL);
}
Run Code Online (Sandbox Code Playgroud)
您可以使socket不可阻塞,如另一篇文章中所建议的那样使用select来等待输入超时,如下所示:
fd_set input;
FD_ZERO(&input);
FD_SET(sd, &input);
struct timeval timeout;
timeout.tv_sec = sec;
timeout.tv_usec = msec * 1000;
int n = select(sd + 1, &input, NULL, NULL, &timeout);
if (n == -1) {
//something wrong
} else if (n == 0)
continue;//timeout
if (!FD_ISSET(sd, &input))
;//again something wrong
//here we can call not blockable read
Run Code Online (Sandbox Code Playgroud)
fcntl(socket, F_SETFL, O_NONBLOCK);
Run Code Online (Sandbox Code Playgroud)
或者,如果你有其他标志:
int x;
x=fcntl(socket ,F_GETFL, 0);
fcntl(socket, F_SETFL, x | O_NONBLOCK);
Run Code Online (Sandbox Code Playgroud)
然后检查读取的返回值以查看是否有可用数据.
注意:一些谷歌搜索会产生很多完整的例子.
您还可以使用阻塞套接字,并select在超时时"查看" .这似乎更合适,所以你不要忙等待.