主机接收不到数据包

rongyihit 2010-03-15 05:31:49
大家好:
我编了一个服务器程序,向224.0.0.1这个组播地址发送数据包,客户主机与服务器主机在同一个局域网中,通过集线器连接,但是客户主机没有收到服务器的数据包,请问这是什么原因啊?
...全文
187 6 打赏 收藏 转发到动态 举报
写回复
用AI写文章
6 条回复
切换为时间正序
请发表友善的回复…
发表回复
rongyihit 2010-03-19
  • 打赏
  • 举报
回复
谢谢你的帮助啊!但是我想知道的是224.0.0.1这个组地址也需要显示加入吗?[Quote=引用 5 楼 zhangliuxue 的回复:]
把你接受组播的代码贴出来,然后才知道为什么。
下面是组播初始化的代码,希望对你有所帮助。
void InitMcast(void)
{
WSAData wsaData;
struct sockaddr_in local;
struct sockaddr_in remote;
if( WSAStartup(MAKEWORD(2,2), &wsaData) != 0 )
{
……
[/Quote]
WizardK 2010-03-18
  • 打赏
  • 举报
回复
WSAJoinLeaf
newasoft 2010-03-18
  • 打赏
  • 举报
回复
把你接受组播的代码贴出来,然后才知道为什么。
下面是组播初始化的代码,希望对你有所帮助。
void InitMcast(void)
{
WSAData wsaData;
struct sockaddr_in local;
struct sockaddr_in remote;
if( WSAStartup(MAKEWORD(2,2), &wsaData) != 0 )
{
cout<<"网络初始化错误!"<<endl;
return;
}
InitializeCriticalSection(&csSkype);
InitializeCriticalSection(&m_skype2skype);
#ifdef NET1_1
server = socket(AF_INET, SOCK_DGRAM, 0); //创建一个UDP套接口

int ret ;
const int on = 1; //允许程序的多个实例运行在同一台机器上
ret = setsockopt(server, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof(on));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"SO_REUSEADDR错误: "<<WSAGetLastError()<<endl;
return;
}

const int routenum = 10;
ret = setsockopt(server,IPPROTO_IP,IP_MULTICAST_TTL,\
(char*)&routenum,sizeof(routenum));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"IP_MULTICAST_TTL: "<<WSAGetLastError()<<endl;
return ;
}

const int loopback = 1; //允许回馈
ret = setsockopt(server,IPPROTO_IP,IP_MULTICAST_LOOP,\
(char*)&loopback,sizeof(loopback));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"IP_MULTICAST_LOOP: "<<WSAGetLastError()<<endl;
return;
}

memset(&local, 0, sizeof(local));
local.sin_family = AF_INET;
local.sin_port = htons(MULTICAST_PORT);
local.sin_addr.S_un.S_addr = INADDR_ANY;
//local.sin_addr.s_addr = inet_addr ( "192.168.0.206" );

ret = bind(server, (sockaddr*)(&local), sizeof(local));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"Error in bind: "<<WSAGetLastError()<<endl;
return ;
}


ip_mreq mreq;
memset(&mreq, 0, sizeof(mreq));
mreq.imr_interface.S_un.S_addr = INADDR_ANY;
//mreq.imr_interface.S_un.S_addr = inet_addr ( "192.168.0.206" );
mreq.imr_multiaddr.S_un.S_addr = inet_addr(MULTICAST_IP);

//加入一个多播组
ret = setsockopt(server,IPPROTO_IP,IP_ADD_MEMBERSHIP,\
(char*)&mreq,sizeof(mreq));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"Error in setsockopt(IP_ADD_MEMBERSHIP): "<<WSAGetLastError()<<endl;
return ;
}

int sinlen = sizeof(local);
if (getsockname(server, (struct sockaddr *) &local, &sinlen) < 0)
{
closesocket(server);
server = -1;
return ;
}

int flags = 1;
if (ioctlsocket(server,FIONBIO,(unsigned long *) &flags))
{
closesocket(server);
server = -1;
return ;
}
#else
/*创建一个SOCK_DGRAM类型的SOCKET
其中,WSA_FLAG_MULTIPOINT_C_LEAF表示IP多播在控制面层上属于 "无根 "类型;
WSA_FLAG_MULTIPOINT_D_LEAF表示IP多播在数据面层上属于 "无根 ",有关控制面层和
数据面层有关概念请参阅MSDN说明。*/
if((server=WSASocket(AF_INET,SOCK_DGRAM,0,NULL,0,
WSA_FLAG_MULTIPOINT_C_LEAF|WSA_FLAG_MULTIPOINT_D_LEAF|WSA_FLAG_OVERLAPPED))
== INVALID_SOCKET)
{
printf( "socket failed with:%d\n ",WSAGetLastError());
WSACleanup();
return ;
}

int ret ;
const int on = 1; //允许程序的多个实例运行在同一台机器上
ret = setsockopt(server, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof(on));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"SO_REUSEADDR错误: "<<WSAGetLastError()<<endl;
return;
}

const int routenum = 10;
ret = setsockopt(server,IPPROTO_IP,IP_MULTICAST_TTL,\
(char*)&routenum,sizeof(routenum));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"IP_MULTICAST_TTL: "<<WSAGetLastError()<<endl;
return ;
}

const int loopback = 1; //允许回馈
ret = setsockopt(server,IPPROTO_IP,IP_MULTICAST_LOOP,\
(char*)&loopback,sizeof(loopback));
if( ret == SOCKET_ERROR )
{
WSACleanup();

cout<<"IP_MULTICAST_LOOP: "<<WSAGetLastError()<<endl;
return;
}
//将sock绑定到本机某端口上。
local.sin_family = AF_INET;
local.sin_port = htons((u_short)MULTICAST_PORT);
local.sin_addr.s_addr = htonl(INADDR_ANY);
if(bind(server,(struct sockaddr*)&local,sizeof(local)) == SOCKET_ERROR)
{
printf( "bind failed with:%d \n ",WSAGetLastError());
closesocket(server);
WSACleanup();
return;
}

//加入多播组
remote.sin_family = AF_INET;
remote.sin_port = htons((u_short)MULTICAST_PORT);
remote.sin_addr.s_addr = inet_addr(MULTICAST_IP);


if((socketSend = WSAJoinLeaf(server,(SOCKADDR*)&remote,sizeof(remote),NULL,NULL,NULL,NULL,JL_BOTH)) == INVALID_SOCKET)
{
printf( "WSAJoinLeaf() failed:%d\n ",WSAGetLastError());
closesocket(server);
WSACleanup();
return;
}
int flags = 1;
if (ioctlsocket(server,FIONBIO,(unsigned long *) &flags))
{
closesocket(server);
server = -1;
return ;
}
#endif
//启动你的接受线程
StartMcastThread();

}

//发送命令
void SendCommand(const char* cBuffer ,int iLen)
{
sockaddr_in remote;
memset(&remote, 0, sizeof(remote));
remote.sin_addr.s_addr = inet_addr ( MULTICAST_IP );
remote.sin_family = AF_INET ;
remote.sin_port = htons(MULTICAST_PORT);

#ifdef NET1_1
socketSend = server;
#endif
int ret;
ret = sendto(socketSend, cBuffer, iLen, 0, (sockaddr*)(&remote), sizeof(remote));
}
//读取组播的代码
int Mcast_net_read(SOCKET netfd,char *buf,int iLen)
{
int res = 0;
struct sockaddr_in sin;
socklen_t sinlen;
int i=0;

struct timeval tv;
fd_set fdSet;
int e=0;
#ifdef WIN32
unsigned int maxFd=0;
#else
int maxFd=0;
#endif
FD_ZERO(&fdSet);
FD_SET(netfd,&fdSet);

sinlen = sizeof(sin);
if ( netfd >= maxFd )
{
maxFd = (unsigned int) netfd + 1;
}

tv.tv_sec = 0;
tv.tv_usec = 40;

e = select( maxFd, &fdSet, NULL,NULL, &tv );
if (e < 0)
{
int err = WSAGetLastError();
return NULL;
}
else if (e >= 0)
{

if (FD_ISSET(netfd,&fdSet))
{
res = recvfrom(netfd, buf, iLen, 0, (struct sockaddr *) &sin, &sinlen);
//printf("recv mcast %d \n",res);
{//对不是本机发送的消息不予理会
char cHostName[200];
int namelen = 200;
hostent * m_hostent;
if(0 == gethostname(cHostName,namelen))
{
m_hostent = gethostbyaddr((const char*)&sin.sin_addr,4,AF_INET);
if(m_hostent!=NULL)
{
char *pp = strstr(m_hostent->h_name,".");
if(pp>0)
m_hostent->h_name[(int)(pp-m_hostent->h_name)]='\0';

if(stricmp(m_hostent->h_name,cHostName)!=0)
{
return 0;
}
}else
{
return 0;
}
}
}
}
}

if (res < 0) {
int i = WSAGetLastError();
#if defined(_WIN32_WCE)
if (WSAGetLastError() != WSAEWOULDBLOCK) {
DEBU(G "Error on read: %d\n", WSAGetLastError());
IAXERROR "Read error on network socket: ???");
}
#elif defined(WIN32) || defined(_WIN32_WCE)
if (WSAGetLastError() != WSAEWOULDBLOCK) {
cout<< "Error on read:"<<WSAGetLastError()<<endl;
}
#else
if (errno != EAGAIN) {
cout<<"Error on read: "<<strerror(errno)<<endl;
}
#endif
return NULL;
}

return res;
}
rongyihit 2010-03-18
  • 打赏
  • 举报
回复
我用的是2240.0.0.1这个地址,但是不行。关键问题是我不知道怎样配置Windows才能让我的主机加入一个多播组。[Quote=引用 1 楼 wizardk 的回复:]
组播组是谁建的?加入组播组了吗?
[/Quote]
bragi523 2010-03-15
  • 打赏
  • 举报
回复
224.0.0.0~224.0.0.255为预留的组播地址,最好不要使用
另外就是是否加入等
WizardK 2010-03-15
  • 打赏
  • 举报
回复
组播组是谁建的?加入组播组了吗?

18,356

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 网络编程
c++c语言开发语言 技术论坛(原bbs)
社区管理员
  • 网络编程
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

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