我有一个用C编写的服务器,每当新客户端连接时都会生成一个新线程。为了测试我的服务器,我编写了一个模拟500个客户端的脚本。服务器处理前几百个客户端,最后我从Valgrind得到以下错误:
Thread 456: status = VgTs_WaitSys
==4182== at 0x4E383EC: recv (recv.c:34)
==4182== by 0x4017F1: process_data (socket2.h:45)
==4182== by 0x40195E: thread (FBServer.c:82)
==4182== by 0x4E30A03: start_thread (pthread_create.c:300)
==4182== by 0x532DD4C: clone (clone.S:112)
Thread 457: status = VgTs_WaitSys
==4182== at 0x4E383EC: recv (recv.c:34)
==4182== by 0x4017F1: process_data (socket2.h:45)
==4182== by 0x40195E: thread (FBServer.c:82)
==4182== by 0x4E30A03: start_thread (pthread_create.c:300)
==4182== by 0x532DD4C: clone (clone.S:112)
...
Thread 499: status = VgTs_WaitSys
==4182== at 0x4E383EC: recv (recv.c:34)
==4182== by 0x4017F1: process_data (socket2.h:45)
==4182== by 0x40195E: thread (FBServer.c:82)
==4182== by 0x4E30A03: start_thread (pthread_create.c:300)
==4182== by 0x532DD4C: clone (clone.S:112)
在FBServer.c的第82行,线程调用一个名为process_data的函数,该函数从客户端接收数据。函数process_data如下所示:
void process_data(int clientSock)
{
size_t n;
char jstring[MAX_LEN + 1];
int bytes_received_so_far = 0;
int bytes_count;
char *buf = NULL;
while(bytes_count = recv(clientSock, jstring, MAX_LEN, 0))
{
if(bytes_count <= 0)
{
close(clientSock);
pthread_exit(NULL);
}
printf("Bytes received = %d\n", bytes_count);
jstring[bytes_count] = '\0';
...
...
}
}
有人可以帮我解释错误信息。
答案 0 :(得分:1)
您使用的是什么版本的Valgrind?
关于我在源文件中找到的唯一评论是:
VgTs_WaitSys, /* waiting for a syscall to complete */
所以它似乎表明该程序只是在系统调用上阻塞(在你的情况下为recv)。我不确定,但这可能不是一个错误,只是Valgrind踢出了一些额外的信息。
答案 1 :(得分:0)
这是一个糟糕的答案,但作为评论时间太长了。
我猜“VgTs_”的意思是“Valgrind Threads”。 Valgrind 序列化线程。这是一个 link to documentation。所以这意味着 Valgrind 需要能够知道每个线程的状态。
它通过说“以下是可能的状态”来实现这一点:“Runnable”、“Waiting on a sys call”、“Yielding”等。为防止命名冲突,请使用“ValGrind Thread status”作为前缀。
VgTs_WaitSys
表示 Valgrind 知道在系统调用停止阻塞之前它无法运行该线程。VgTs_Runnable
表示 Valgrind 知道它可以运行线程。但这并不意味着它正在积极运行它——因为 Valgrind 一次只会运行一个线程(除非你使用 DRD
或 Helgrind
作为工具,否则我不知道它做了什么.)VgTs_Yielding
我想了解这种过渡状态很有用。