3

C ++とrawソケットを使用してICMP要求をルーターに送信していますが、その後、ICMP応答を読み取ります。私の問題は、select()が常にリプレイとタイムアウトを受信して​​いないことです。エラーが発生していません(errnoが成功を返しています)。Wiresharkを使用して応答を確認できるため、ルーターはICMP応答を送信しています。

http://i.imgur.com/0Wra1.pngwireshark のスクリーンショット

プログラムをテストするために、VirtualBox4.2.6で実行されているUbuntu12.10と仮想ネットワーク用のGN3を使用しています。

私のソースコード:

char buffer[IP_MAXPACKET]; // for the received ICMP reply
struct iphdr *ipRec; // ICMP header
timeval tv; // timeout
fd_set mySet; // descriptor set
...
tv.tv_sec = 3; // default time-out 3s
tv.tv_usec = 0;

int retval; // select
...
do {
        FD_ZERO(&mySet);
        FD_SET(mysocket, &mySet);

        retval = select(mysocket+1, &mySet, NULL, NULL, &tv);

        cout << "Errno after select:" << strerror(errno) << endl;

        if(retval == -1) {
            cerr << "select error" << endl;
            break;
        }
        else if (retval) {
            if((length = recvfrom(mysocket, buffer, MAX, 0, result->ai_addr, &(result->ai_addrlen))) == -1) {
                cerr << "Error: while receiving data." << endl;
            }
            else {
                cout << "good" << endl;

                ipRec = (struct iphdr*) buffer;
                icmpRec = (struct icmphdr*) (buffer + ipRec->ihl * 4);

                cout << "the packet." << " PID: " << ntohs(icmpRec->un.echo.id) << " Seq: " << ntohs(icmpRec->un.echo.sequence) << endl;

                if ((icmpRec->type == ICMP_ECHOREPLY) && (ntohs(icmpRec->un.echo.id) == pid) && (ntohs(icmpRec->un.echo.sequence) == (seq - 1))) {
                    minBuff = lengthBuff;
                }
            }
        } else {
            // getting here all the time = select times-out and reads no data

            cout << "mysocket:" << mysocket << endl;
            cout << "retval:" << retval << endl;
            maxBuff = lengthBuff;
            break;
        }
    } while (!((icmpRec->type == ICMP_ECHOREPLY) && (ntohs(icmpRec->un.echo.id) == pid) && (ntohs(icmpRec->un.echo.sequence) == (seq - 1))));

    if (packet)
        delete(packet);
    ...

助けてくれてありがとう。

4

1 に答える 1

1

問題を修正しました。別のスレッドで解決策を見つけました: ICMP パケットが送信されていません C。IPPROTO_RAW を IPPROTO_ICMP に変更すると修正されました。ここで、ICMP 応答パケットの読み取りを選択します。

于 2012-12-29T18:40:09.573 に答える