ALM*_*865 5 c c++ sockets networking
我有一个通过在端口4930上向255.255.255.255发送广播数据包而发现的设备,并且设备通过在端口4930上将数据包发送回255.255.255.255来响应.
我有一段C++代码,它可以在端口4930(源端口和目标端口)上发送数据包到255.255.255.255,但它无法从广播地址255.255.255.255接收回数据包.
我可以看到设备工作正常,wireshark可以看到来回来回的数据包,设备提供的专有软件可以很好地发现设备,问题在于C++程序,所以请继续回答主题.
现在,正如我所说,我可以发送一个数据包,但首先我无法绑定到IP地址255.255.255.255来接收数据包.我可以将组播地址更改为239.255.255.250,套接字将绑定,但我需要地址255.255.255.255.
我的代码片段如下,我使用的是VC++ 2010
bool CPTUProgramDlg::FindPTU(u_short port, const char * Destaddress){
{
//Data to send
char packet_data[10] = {0x44,0x43,0x55,0x44,0x5f,0x50,0x49,0x4e,0x47,0x00};
int packet_size=10;
SOCKET sock;
struct sockaddr_in addr;
sock = socket(AF_INET, SOCK_DGRAM, 0);
// set SO_BROADCAST on a socket to true (1): (so we can transmit to 255 addr)
//In order to use broadcast the options of socket must change
char broadcastON = 1;
setsockopt(sock, SOL_SOCKET, SO_BROADCAST, &broadcastON, sizeof broadcastON);
if (sock < 0)
return false;
addr.sin_family = AF_INET;
addr.sin_port = htons(port);
addr.sin_addr.s_addr = inet_addr(Destaddress); // Specify dest IP
sendto(sock, packet_data, packet_size, 0, (struct sockaddr*)&addr, sizeof(addr));
if (bind(sock,(struct sockaddr*) &addr,sizeof(addr)) != -1){
char Buff[512];
recv(sock,Buff,512,0);
}
closesocket(sock);
}
return 1;
}
Run Code Online (Sandbox Code Playgroud)
Wireshark截图以证明正在发送数据包:
从wireshark的输出中可以看出,特殊设备正在使用广播进行通信,并将使用与源和目标相同的端口号。
正常的套接字通信需要使用匹配的端口号,但广播消息不能通过同一套接字交换,特别是当端口号与使用wireshark 看到的不匹配时。
绑定到 255.255.255.255 ( INADDR_BROADCAST) 通常应该有效,但可能会受到操作系统特权和权限的限制。
您可以尝试使用两个套接字来解决问题 - 一个用于接收,一个用于发送。当然,必须首先设置侦听套接字并将其绑定到 0.0.0.0 ( INADDR_ANY) 和端口 4930。在这种情况下,没有简单的方法可以按目标地址进行过滤(正如我在评论中错误地写的那样),因为大多数标准套接字 API 都这样做不提供从套接字获取目标地址的方法。在 Linux 上有一个例外 -IP_PKTINFO在SOL_IP...
通过使用recvfrom,您将获得响应设备的源单播地址。您必须注意,如果您的网络上有不止一台此类设备,您将收到多个响应。
| 归档时间: |
|
| 查看次数: |
4478 次 |
| 最近记录: |