Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/linux/26.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/powershell/12.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ Linux UDP服务器-目标IP错误_C++_Linux_Sockets_Networking_Udp - Fatal编程技术网

C++ Linux UDP服务器-目标IP错误

C++ Linux UDP服务器-目标IP错误,c++,linux,sockets,networking,udp,C++,Linux,Sockets,Networking,Udp,我有一个嵌入式linux设备,可以监听UDP数据包。 该设备有两个以太网接口,因此可以在两个接口上检索数据包。 在某些UDP消息/数据包上,我必须针对接收到它的接口执行一些特定的操作。所以我需要检测哪个接口接收了数据包 我在Stackoverflow上找到了一些帖子和示例,展示了如何从IP\u PKTINFO提取目标IP。如果我一个接一个地测试接口,这就可以了。连接两个接口并接收目标IP的情况相同 我注意到,iIndex是不一样的,但我不明白为什么当我在两个不同IP的不同接口上收到一个数据包时,

我有一个嵌入式linux设备,可以监听UDP数据包。 该设备有两个以太网接口,因此可以在两个接口上检索数据包。 在某些UDP消息/数据包上,我必须针对接收到它的接口执行一些特定的操作。所以我需要检测哪个接口接收了数据包

我在Stackoverflow上找到了一些帖子和示例,展示了如何从
IP\u PKTINFO
提取目标IP。如果我一个接一个地测试接口,这就可以了。连接两个接口并接收目标IP的情况相同

我注意到,
iIndex
是不一样的,但我不明白为什么当我在两个不同IP的不同接口上收到一个数据包时,
ipi_spec_dst
是一样的

负责提取目标IP的C/C++代码:

    ssize_t byteCount=recvmsg(f_socket, &message, 0);
    if (byteCount==-1) {
        printf("%s",strerror(errno));
    }

    for (struct cmsghdr *cmsg = CMSG_FIRSTHDR(&message); 
         cmsg != NULL; 
         cmsg = CMSG_NXTHDR(&message, cmsg)) 
    {
        if (cmsg->cmsg_level != IPPROTO_IP || cmsg->cmsg_type != IP_PKTINFO) continue;
        struct in_pktinfo *pi = (struct in_pktinfo*) CMSG_DATA(cmsg);
        char* destAddr = (char*) calloc(4, sizeof(char));
        destAddr = inet_ntoa(pi->ipi_spec_dst);
        std::cout << destAddr << " " << std::to_string(pi->ipi_ifindex) << std::endl;
    }
输出eth0已连接:

172.20.55.9 4
172.20.55.9 4
172.20.55.9 4
...
200.0.0.101 6
200.0.0.101 6
200.0.0.101 6
...
172.20.55.9 6
172.20.55.9 4
172.20.55.9 6
172.20.55.9 4
...
已连接输出eth0和eth1:

172.20.55.9 4
172.20.55.9 4
172.20.55.9 4
...
200.0.0.101 6
200.0.0.101 6
200.0.0.101 6
...
172.20.55.9 6
172.20.55.9 4
172.20.55.9 6
172.20.55.9 4
...
预期产出:

200.0.0.101 6
172.20.55.9 4
200.0.0.101 6
172.20.55.9 4
...
首先,我不确定这是否是预期的,我认为不是,但我可能没有正确理解文档

如果需要,我可以提供更多的代码

代码取自:


  • 非常感谢您的任何帮助。多谢各位


    -aln

    我认为线路有问题:

    char* destAddr = (char*) calloc(4, sizeof(char));
    destAddr = inet_ntoa(pi->ipi_spec_dst);
    std::cout << destAddr << " " << std::to_string(pi->ipi_ifindex) << std::endl;
    
    因此,要继续,您的循环可能如下所示:

    for (   struct cmsghdr *cmsg = CMSG_FIRSTHDR(&message); 
            cmsg != NULL; 
            cmsg = CMSG_NXTHDR(&message, cmsg)) 
    {
        if (cmsg->cmsg_level != IPPROTO_IP || cmsg->cmsg_type != IP_PKTINFO) 
            continue;
    
        struct in_pktinfo *pi = (struct in_pktinfo*) CMSG_DATA(cmsg);
        printf("%s %d\n", inet_ntoa(pi->ipi_addr), pi->ipi_ifindex);
    }
    

    我通过使用
    ifindex
    获取接口名称来解决这个问题,然后使用该名称执行接口特定的代码。

    ipi_addr返回“255.255.255.255”,这是正确的,因为它是广播消息,而不是直接消息。不管怎样,谢谢你清理了calloc的东西,它只是一个复制粘贴,我是c/c++新手。@AndréNicolaysen好的,所以在这种情况下,你可以使用
    recvfrom
    并使用最后两个参数?
    recvfrom
    给我
    src_addr
    ,这是数据包的地址
    pi->ipi\u spec\u dest
    应该给我接收数据包的本地地址。确实如此,但如果我同时连接两个接口,那就错了。看来你想做的事情很难:似乎是这样。谢谢你找到它。我得试试那些东西。这是一个奇怪的问题,因为 iFixe/Cuth>每次都是正确的。这显然不是C,而是C++。没有C/C++,只有C和C++两个不同的问题。这怎么不是C?因为它包含一行C++代码?真正感兴趣。因为你不能/不可以用C编译器编译它。阅读标准,相同的语法并不意味着相同的语义!好的,谢谢。我会记住的。