1

我对我不太了解的行为有疑问:

我有两种 C++ 代码变体:

CreateThread( NULL, 0, ( LPTHREAD_START_ROUTINE ) clientThread, ( LPVOID ) connectionSocket, 0, NULL ); 

线:

Client a;
a.clientsocket = connectionSocket;
a.testText()
a.sendSocket();

工作得很好(sendSocket 将一些测试数据发送到套接字)。

但是,如果我这样做

Client a;
a.clientsocket = connectionSocket;
CreateThread( NULL, 0, ( LPTHREAD_START_ROUTINE ) clientThread, ( LPVOID ) &a, 0, NULL );

并使用线程:

a.testText();
a.sendSocket();

只有 testText() 有效。

我有点困惑为什么会这样。虽然我是 C++ 的爱好者 :-)

编辑:

添加了客户端类:

class Client
{
public:
    SOCKET clientsocket;

    Client()
{
}
~Client(){}
void displayMessage()
{
        std::cout << "test message client class" << std::endl;
}
int sendSocket()
{
    char *sendbuf = "CLIENT TEST";
    send(clientsocket, sendbuf, (int)strlen(sendbuf),0);
    closesocket(clientsocket);
    return 0;

}
};
4

5 回答 5

2

我猜在您的主线程中 CreateThread 成功,然后您的 Client 变量 a 超出范围并因此被破坏。

于 2012-04-16T18:21:03.763 回答
0

从你的客户类

SOCKET clientsocket;

每当你将它传递给一个线程时,SOCKET 就会调用它的复制构造函数。此复制构造函数可能未定义,或者它可能试图在同一端口上打开一个新连接并导致它失败。

将其更改为:

SOCKET* clientsocket;

然后拥有它,以便每当您想做...

a.clientsocket = connectionSocket;

变量“connectionSocket”是一个指针,然后轰炸药。当它未声明为变量时,将调用复制构造函数,您将获得一个全新的套接字,而不是之前使用的套接字。我认为这应该有帮助吗?

于 2013-06-18T20:17:33.287 回答
0

Anon可能在正确的轨道上,有些东西超出了范围,但我认为它是connectionSocket. a.sendSocket()但是,当您说这不起作用时,您必须提供更多详细信息来说明您的意思。应用程序会崩溃吗?你发现异常了吗?应用程序是否继续工作,但sendSocket()调用并没有导致实际发送内容?实际问题是什么?

于 2012-04-16T18:28:07.703 回答
0

在第一种情况下,您传递一个connectionSocket,在第二种情况下,传递一个指向客户端类型的指针。也许你的意思是:

CreateThread( NULL, 0, ( LPTHREAD_START_ROUTINE ) clientThread, ( LPVOID ) a.clientsocket, 0, NULL );
于 2012-04-16T18:31:11.383 回答
0

在我看来,它是一个超出范围的对象。SOCKET 只是一个 int HANDLE 值,并存储在 a 的成员中。'a' 在创建线程运行时超出线程创建函数的范围,(或在下一个 accept() 返回时损坏)。

尝试:

客户端 a= 新客户端();

在多线程代码中分配堆栈上的对象之前考虑 15 次,然后决定动态分配。

PS - @Anon 先到了 - 我没注意到。

于 2012-04-16T19:06:16.580 回答