有識者の方、ご教示ください。Win10 64bit/cygwin64(gcc 7.4.0)環境で、C言語によるUDPポートチェックを試みています。UDPソケットでsendto()を要求した後、タイムアウト付きのselect()でICMPソケットのreadfdsを監視しています。目的のUDPポートは閉じているため、Wiresharkでは期待どおり"port unreachable"の受信を確認しています。しかし、readfdsがreadyにならずにselect()ではタイムアウトが生じ、UDPポートは空いていると判断してしまいます。どうもICMP受信をアプリケーションに返却してない(?)ようです。何か情報をお持ちではないでしょうか?以下コードの抜粋。
send = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
recv = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);
dst_addr.sin_addr.s_addr = inet_addr("192.168.1.100");
dst_addr.sin_port = htons(12345);
sendto(send, NULL, 0, 0, (struct sockaddr *)(&dst_addr), sizeof(dst_addr));
tv.tv_sec = 1;
tv.tv_usec = 0;
FD_ZERO(&readfds);
FD_SET(recv, &readfds);
if(0 > select(recv+1, &readfds, (fd_set *)NULL, (fd_set *)NULL, &tv))
{
fprintf(stderr, "select() error.??/n");
} else {
if(FD_ISSET(recv, &readfds))
{
recvfrom(recv, buf, MAXBUF, 0, NULL, NULL);
ip = (struct ip *)buf;
ihlen = ip->ip_hl << 2;
icmp = (struct icmp *) ((char *)ip + ihlen);
if ((ip->ip_src.s_addr == dst_addr.sin_addr.s_addr)
&& (icmp->icmp_type == ICMP_UNREACH)
&& (icmp->icmp_code == ICMP_UNREACH_PORT)
{
fprintf(stdout, "NOT open.??/n");
} else {
fprintf(stdout, "Unexpected ICMP response.??/n");
}
} else {
fprintf(stdout, "May be open (due to a timeout).??/n");
}
}