CSocket在工作线程中工作的问题
我从CSocket类继承了一个类CSrvSocket,仅重载了OnReceive函数。但我把CSrvSocket类在工作线程中使用时,虽然收到了数据(如果调用Receive函数时可以收到数据),但是确没有触发OnReceive函数,请问应该怎么办呢? 问题点数:50、回复次数:6Top
1 楼MilitaryMiniatures(++)回复于 2005-06-03 20:57:24 得分 30
CAsyncSocket/CSocket是MFC的类,它们的工作依赖于消息,尤其是那些OnConnect, OnSend, OnReceive之类的,都是需要消息支持的(MFC内部创建了一个隐含的窗口来处理消息)。你在工作线程中创建这样的类,那么MFC将在你的工作线程创建隐含窗口。可是,你的工作线程并没有消息循环,也就是没有处理消息,因此,你的OnReceive肯定不会被执行。你可以看看你的工作线程的代码,它肯定在不停地工作(即便是Sleep,那也是工作,不会执行消息循环的),既然它在不停地工作,它就没有时间、没有机会执行OnReceive。
解决的方法我知道的有:
1,工作线程不停地Send,不停地Receive,不要试图去等待OnReceive的执行。
2,工作线程引入消息循环。Top
2 楼gc2002(耿崞)回复于 2005-06-05 10:06:39 得分 0
那再请问一下,如何把CSocket配置成非阻塞的?我试着在线程中执行Receive函数时,它们等待直到收到数据才继续,而我希望它收到数据或收一定时间没收到数据就继续向下执行。
我用下面的代码创建的CSOCKET:
srvSock.Create(6476,SOCK_STREAM,"192.168.0.94");
srvSock.Listen();
srvSock.Accept(SockRecv); Top
3 楼airhand(暴风雨)回复于 2005-06-05 10:30:40 得分 20
既然你希望等到数据再继续,为什么还要把它设置成非阻塞的呢,非阻塞总是立即返回的,靠消息来通知的.
如果你非要这样做,你在ACCEPT后写个WHILE循环,检测自定义的变量是否为真,当这个变量为真的时候继续下面的程序,这个变量的在你的接受消息函数中改变值.
超时可以在socket中设置的.或者你定义一个计数器,到了时间就发一个消息,更具消息改变你的变量值.Top
4 楼gc2002(耿崞)回复于 2005-06-05 16:51:09 得分 0
可能是我没有说清楚,我再说一遍。我在调试中发现,当执行Receive函数时,此函数会等到有数据收到才能返回,才能继续往下执行程序;但我不希望它无限制的等下去,希望它如果没收到数据等一段时间就结束(也就是楼上说的超时限制吧)。所以我想问一下如何设置超时?Top
5 楼MilitaryMiniatures(++)回复于 2005-06-05 19:42:48 得分 0
建议你不要使用CSocket,而改用CAsyncSocket,因为CSocket是阻塞模式的。
你的代码有点看不懂:
srvSock.Create(6476,SOCK_STREAM,"192.168.0.94");
srvSock.Listen();
srvSock.Accept(SockRecv);
怎么Listen()之后马上就Accept???哪里有那么好的事情,你一Listen,马上就有连接过来,而且,你这边马上就能Accept阿?所以,你这里还要考虑一下。
假设CAsyncSocket SockRecv是已经成功连接的对象,可以考虑如下方法来实现你的功能:
DWORD begin_tick = ::GetTickCount();
while (::GetTickCount() - begin_tick < 1000) //等待1秒钟看看是否有数据
{
int n = SockRecv.Receive(...);
switch (n)
{
case 0:
...
break;
case -1:
// socket 错,因为是非阻塞模式,所以需要检查GetLastError()是否处于等待状态
break;
default:
// 此处接收到数据,该如何处理...
}
}
Top
6 楼gc2002(耿崞)回复于 2005-06-09 15:05:38 得分 0
谢谢了。Top




