如何判断是否有客户端套接字接入(针对tcp的accept函数)

wuleixxh 2004-08-26 03:38:52
我初学socket通信编程
可是有一点总是不明白,我写的程序如何判断accept已经成功调用,并AcceptSocket已被正确填充,每次我在调用完accept后,调用Recv时不管客户端有没有连接,服务器端都是在报错,10038就是
WSAENOTSOCK,说明没有得到accept没有返回正确的socket
请大家指教
...全文
300 9 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
Josephhu83 2004-08-27
  • 打赏
  • 举报
回复
不好意思,SOCKADDR就是struct sockaddr,这个参数类型是没问题的。那就把clientLen的内容改正确就没问题了。
Josephhu83 2004-08-27
  • 打赏
  • 举报
回复
给你看过了,clientaddr没什么问题,问题在于ClientLen是个输入输出参数,也就是说你得初始化为clientaddr的大小,而不是0。可以这样做
size_t clientLen;
clientLen = sizeof(clientaddr);

再把(int*)clientLen作为参数传进,这样就没问题了。
SOCKADDR应该就相当于struct sockaddr_in吧?如果没记错的话。还有问题的话就把这改改。
Josephhu83 2004-08-27
  • 打赏
  • 举报
回复
我最早也遇过这样的问题,想得到client的地址,可是出错,改了以后就没事。后来我没试过,我猜测,有可能是因为传进去的参数类型或内容不对,比如说clientAddr应该初始化一个值之类,可以去试试。
wuleixxh 2004-08-27
  • 打赏
  • 举报
回复
谢谢楼上的朋友的回答,我改了一下,
把"AcceptSocket=accept(ListenSocket,(SOCKADDR *)&clientAddr, &ClientLen)
改成AcceptSocket=accept(ListenSocket,NULL,NULL)就可以正常运行,这是怎么回事啊
Josephhu83 2004-08-27
  • 打赏
  • 举报
回复
看过你的代码,确实监听的套接字是阻塞的,在这种情况下应该返回的就是正确的套接字。你可以在调试的时候看看。后面代码中所用的是Unix下的select模型,在windows下我没用过,不过建议还是采用windows下的方法。至于出现的问题,我也感到很纳闷。所以,建议你在accept之后,立即使用recv,看看所得到的结果。
wuleixxh 2004-08-27
  • 打赏
  • 举报
回复
真的太感谢了,问题解决了,谢谢您
wuleixxh 2004-08-26
  • 打赏
  • 举报
回复
第一我没有设为非阻塞,第二,我用了select了
以下是我的源码:
#define FD_SETSIZE 1024
#include <winsock2.h>
#include <ws2tcpip.h>
#include <stdio.h>
#include <stdlib.h>

#define DATA_SIZE 1024

int main()
{
SOCKET ListenSocket,AcceptSocket=NULL;
SOCKADDR_IN serverAddr,clientAddr;
char dataBuf[DATA_SIZE];
int ret=0,ClientLen=0;
WSADATA wsaData;
int port=5050;
fd_set fdRead;
timeval timeout;

if((ret=WSAStartup(MAKEWORD(2,2),&wsaData))!=0)
{
printf("WSAStartup failed with error %d\n",ret);
return 0;
}

if((ListenSocket=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP))==SOCKET_ERROR)
{
printf("Socket failed with error %d\n",WSAGetLastError());
WSACleanup();
return 0;
}

serverAddr.sin_family=AF_INET;
serverAddr.sin_port=htons(port);
serverAddr.sin_addr.s_addr=htonl(INADDR_ANY);

if(bind(ListenSocket,(SOCKADDR *)&serverAddr,sizeof(serverAddr))==SOCKET_ERROR)
{
printf("Bind failed with error %d\n",WSAGetLastError());
WSACleanup();
return 0;
}

if(listen(ListenSocket,6)==SOCKET_ERROR)
{
printf("Listen failed with error %d\n",WSAGetLastError());
WSACleanup();
return 0;
}
AcceptSocket=accept(ListenSocket,(SOCKADDR *)&clientAddr, &ClientLen);
while(true)
{
if(AcceptSocket!=NULL)
{
printf("%\n",WSAGetLastError());
FD_ZERO(&fdRead);
FD_SET(AcceptSocket,&fdRead);
timeout.tv_sec=5;
timeout.tv_usec=0;
if((ret=select(0,&fdRead,NULL,NULL,&timeout))==SOCKET_ERROR)
{
printf("Select failed with error %d\n",WSAGetLastError());
// WSACleanup();
// return 0;
continue;
}
if(ret==0)
printf("select zero");
if(ret>0)
{
if(FD_ISSET(AcceptSocket,&fdRead))
{

if(recv(AcceptSocket,dataBuf,sizeof(dataBuf),0)==SOCKET_ERROR)
{
printf("Recvie failed with error %d\n",WSAGetLastError());
WSACleanup();
return 0;
}
printf("%s\n",dataBuf);
}
}
}
Sleep(100);
}
}
tgame 2004-08-26
  • 打赏
  • 举报
回复
监听套接字是阻塞的还是非阻塞的?
非阻塞的套接字调用accept要客户端已经连接的情况下连接才能够成功返回
阻塞的就会等待直到客户端连接
Josephhu83 2004-08-26
  • 打赏
  • 举报
回复
在阻塞模式下,调用accept会阻塞,直到有连接进来或者有错误发生。
你的情况应该是使用了非阻塞模式,在这种情况下,accept会立刻返回,而不管是否有连接,因此在非阻塞模式时,最好采用select,然后等待连接事件,当有连接时,再使用accept。

4,387

社区成员

发帖
与我相关
我的任务
社区描述
通信技术相关讨论
社区管理员
  • 网络通信
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧