CSocket断言错误 ASSERT(pState->m_hSocketWindow != NULL);

CSocket断言错误 ASSERT(pState->m_hSocketWindow != NULL);

flyfish

BOOL CAsyncSocket::AsyncSelect(long lEvent)
{
	ASSERT(m_hSocket != INVALID_SOCKET);


	_AFX_SOCK_THREAD_STATE* pState = _afxSockThreadState;
	ASSERT(pState->m_hSocketWindow != NULL);


	return WSAAsyncSelect(m_hSocket, pState->m_hSocketWindow,
		WM_SOCKET_NOTIFY, lEvent) != SOCKET_ERROR;
}


断言在ASSERT(pState->m_hSocketWindow != NULL);

产生断言的原因
http://support.microsoft.com/kb/140527/en-us
 this problem is due to the sharing of CSocket objects between multiple threads.
也就是在多线程中使用了CSocket对象,主线程中创建socket,在其他线程中关闭socket出现的断言


查找什么地方启动了关闭线程
在主窗口中只调用函数 timeSetEvent
查看MSDN

The timeSetEvent function starts a specified timer event. The multimedia timer runs in its own thread. After the event is activated, it calls the specified callback function or sets or pulses the specified event object The multimedia timer runs in its own thread 

多媒体定时器运行在它自己的线程,也就是这个函数会启动一个线程。

原因找到确定是 多线程中使用了CSocket对象


解决方法
a CAsyncSocket object should be used only in the context of a single thread. If you need to switch the thread that is accessing a SOCKET connection with another thread, then you should use a separate CAsyncSocket object in each thread, and use the Detach and Attach functions to attach the CAsyncSocket object to the SOCKET handle in the thread that is about to use the socket. 


CSocket派生自CAsyncSocket
一个 CAsyncSocket 对象应该只在一个单线程的上下文。如果你想切换到其他的线程中访问SOCKET连接,你应该在每个线程中使用单独的 CAsyncSocket 对象,并使用Detach 和Attach函数将 CAsyncSocket 对象attach到SOCKET handle。


当前拥有这个socket的线程调用Detach方法,socket handle就与当前线程无关
在另一个线程调用 Attach,这个socket handle 就在此线程了
有点类似C++对象和Windows对象之间的关系
如果一个线程要使用其他线程的Windows对象,则必须传递Windows对象句柄,不能传递C++对象指针。


另一种解决方法

仍然是单线程使用CSocket,在主窗口中自定义消息,使用PostMessage向主窗口发送消息



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

西笑生

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值