我的问题与以下代码有关:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <iostream>
#include <pthread.h>
#include <sys/types.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <netinet/in.h>
int connections[100];
int connectionCounter = 0;
pthread_t clientHandlerThread;
void *ClientHandlerThread(void *index) {
int id = *reinterpret_cast<int*>(index);
char buffer[256];
while(true) {
recv(connections[id-1], buffer, sizeof(buffer), 0);
for(int i = 0; i < connectionCounter; i++) {
if(i == (id-1))
continue;
send(connections[i], buffer, sizeof(buffer), 0);
}
}
}
int main() {
sockaddr_in addr;
int addrlen = sizeof(addr);
addr.sin_addr.s_addr = inet_addr("127.0.0.1");
addr.sin_port = htons(1111);
addr.sin_family = AF_INET;
int sListen = socket(AF_INET, SOCK_STREAM, 0);
bind(sListen, (sockaddr*)&addr, addrlen);
listen(sListen, SOMAXCONN);
int newConnection;
for (int i = 0; i < 100; i++) {
newConnection = accept(sListen, (sockaddr*)&addr, (socklen_t*)&addrlen);
if (newConnection == 0) {
std::cout << "Failed to accept the client's connection." << std::endl;
}
else {
char MOTD[256] = "Welcome! This is the Message of the Day.";
send(newConnection, MOTD, sizeof(MOTD), 0);
connections[i] = newConnection;
connectionCounter++;
pthread_create(&clientHandlerThread, NULL, ClientHandlerThread, (void*)&i);
}
}
return 0;
}
这只是一个简单的TCP服务器(这只是一个了解Linux下套接字的测试项目,因为它们在Windows下是不同的),这导致了一个很大的问题,虽然这也是一个简单的理解问题。
我的问题:我启动服务器(使用G ++编译,Debian Stretch 64位,g ++ main。cpp -o server -lpthread)并连接到2个客户端。到目前为止工作,但我只能从一个客户发送消息,而不是另一个客户。我在&#34; ClientHandlerThread&#34;中找到了问题。功能。论证&#34;索引&#34;被强制转换为int,但它会增加+1。这意味着我的ID不是1(因为它应该是,因为只有2个客户端,它从0开始)但是2。
我是否有某种理解问题?我刚刚开始在Linux下编写C ++,也许我的线程有问题。
感谢您的帮助!
答案 0 :(得分:2)
您正在从多个线程中读取来自example.getMaxResults();
函数的i
局部变量的内容,而没有任何同步导致未定义的行为。您可以按值传递索引:
main
您还应该重写程序以执行正确的清理:为线程退出并为所有生成的线程调用pthread_create(&clientHandlerThread, NULL, ClientHandlerThread, reinterpret_cast<void*>(static_cast<::std::intptr_t>(i)));
// in handler
int id = static_cast<int>(reinterpret_cast<::std::intptr_t>(index));
。
答案 1 :(得分:2)
将指向同一个变量的指针传递给所有线程。如果你足够快地连接两个(或多个客户端),那么两个或多个线程可以从该指针的取消引用获得相同的值。
这是极少数情况下通常认为将整数值强制转换为指针并返回的情况之一。
在致电pthread_create
时首先使用(void *) (intptr_t) i
。然后在线程函数中执行int id = (int) (intptr_t) index
。
或者,由于您使用C ++编程,您可以使用std::thread
代替,这允许您通过值传递参数。