Вопрос

I am reading a buffer from a socket (AF_PACKET, SOCK_DGRAM, htons(ETH_P_ARP)) with the following code. I am using an arp_frame struct to access the component parts of the contained ARP reply. The inet_ntoa() returns the correct first octet of the IP but the other octets are 0 producing 172.0.0.0.

Question 1 is why might this happen? Question 2 is how can I print r bytes of the msg buffer as hex in host byte order to debug the packet?

    unsigned char msg[65535];
    struct ether_arp *arp_frame = (struct ether_arp *)msg;

    while ((r = recv(sock, msg, sizeof(msg), 0))) {
            // skip it's not an ARP REPLY
            if (ntohs(arp_frame->arp_op) != ARPOP_REPLY)
                    continue;

            for (i = 0; i < SONOS_PREFIX_NUM; i++) {
                    if (!memcmp(sonos_prefixes[i], arp_frame->arp_sha, 3)) {
                            struct in_addr addr;
                            addr.s_addr = *arp_frame->arp_spa;

                            printf("Blah: %lu\n", ntohl(*arp_frame->arp_spa));
                            printf("Sonos found at %s\n", inet_ntoa(addr));
                    }
            }
    }
Это было полезно?

Решение

struct ether_arp looks like this:

struct  ether_arp {
    struct  arphdr ea_hdr;          /* fixed-size header */
    u_int8_t arp_sha[ETH_ALEN];     /* sender hardware address */
    u_int8_t arp_spa[4];            /* sender protocol address */
    u_int8_t arp_tha[ETH_ALEN];     /* target hardware address */
    u_int8_t arp_tpa[4];            /* target protocol address */
};

With that in mind, I think that your addr.s_addr = *arp_frame->arp_spa; looks a little fishy. arp_frame->arp_spa yields a u_int8_t[4], which you then dereference as a pointer. I think memcpy() might be more appropriate there.

Другие советы

If you think the API is broken, print out the bytes.

"Methinks, Brutus, the fault is not in the stars."

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top