使用原始数据包数据和 inet_ntoa() 进行转换

发布于 2025-01-07 04:19:28 字数 1170 浏览 5 评论 0原文

尝试为数据包嗅探器编写处理程序。我在转换和 inet_ntoa() 方面遇到问题。代码如下:

uint32_t *iphdr_srcaddr = malloc(sizeof(uint32_t));
if (*packet_ethertype == ETHERTYPE_IP) { /* IPv4 */
    // copy packet data to vars
    memcpy(iphdr_srcaddr, packet+26, 4);

    // change to host-byte-order
    *iphdr_srcaddr = ntohl(*iphdr_srcaddr);

    struct in_addr *test;
    test = (struct in_addr*) iphdr_srcaddr;

    printf("uint32_t: %u\n", *iphdr_srcaddr); // Gives the correct long integer for the address
    printf("struct in_addr: %u\n", test->s_addr); // Gives the correct long integer through the cast

    char *test2;
    test2 = inet_ntoa(*test);
}

现在,如果我尝试 printf("%s\n", test) 我会得到 SEGV。我确信我混淆了指针、值并进行了某种愚蠢的转换。在下面的运行过程中收到错误:

Program received signal SIGSEGV, Segmentation fault.
0x00007ffff787ec61 in __strlen_sse2 () from /lib/libc.so.6

还有编译警告,我确信这为我指明了正确的方向,但我不确定它的含义以及如何修复它:

mypcap.c: In function ‘handle_sniffed’:
mypcap.c:61:15: warning: assignment makes pointer from integer without a cast [enabled by default]

这指的是行 test2 = inet_ntoa(*测试);

Trying to write a handler for a packet sniffer. I'm having issues with casting and inet_ntoa(). Code is as follows:

uint32_t *iphdr_srcaddr = malloc(sizeof(uint32_t));
if (*packet_ethertype == ETHERTYPE_IP) { /* IPv4 */
    // copy packet data to vars
    memcpy(iphdr_srcaddr, packet+26, 4);

    // change to host-byte-order
    *iphdr_srcaddr = ntohl(*iphdr_srcaddr);

    struct in_addr *test;
    test = (struct in_addr*) iphdr_srcaddr;

    printf("uint32_t: %u\n", *iphdr_srcaddr); // Gives the correct long integer for the address
    printf("struct in_addr: %u\n", test->s_addr); // Gives the correct long integer through the cast

    char *test2;
    test2 = inet_ntoa(*test);
}

Now if I try to printf("%s\n", test) I get SEGV. I'm sure I'm mixing up pointers, values and doing some sort of stupid casting. Error received during run below:

Program received signal SIGSEGV, Segmentation fault.
0x00007ffff787ec61 in __strlen_sse2 () from /lib/libc.so.6

Compilation warning as well, I'm sure this is pointing me in the correct direction, but I'm not sure what to it means and how I can fix it:

mypcap.c: In function ‘handle_sniffed’:
mypcap.c:61:15: warning: assignment makes pointer from integer without a cast [enabled by default]

This refers to the line test2 = inet_ntoa(*test);

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

眼眸印温柔 2025-01-14 04:19:28

该警告可能表明您在 inet_ntoa() 范围内没有正确的原型(因为您没有包含正确的标头)。这意味着编译器假定它的返回类型为 int。

当您应该传递 test2 时,您还将 test 传递给 printf()

另外:

  • 不需要使用malloc()来分配单个uint32_t
  • 您不需要调用 ntohl(),因为 inet_ntoa() 期望其输入为网络字节顺序;并且
  • inet_ntoa() 已过时 - 应在新代码中使用 inet_ntop()

尝试:

#include <arpa/inet.h>

if (*packet_ethertype == ETHERTYPE_IP) { /* IPv4 */
    struct in_addr sin_addr;
    char straddr[INET_ADDRSTRLEN];

    memcpy(&sin_addr.s_addr, packet+26, 4);

    if (inet_ntop(AF_INET, &sin_addr, straddr, sizeof straddr))
        printf("%s\n", straddr);
    else
        perror("inet_ntop");
}

The warning probably indicates that you don't have a correct prototype in scope for inet_ntoa() (because you haven't included the right header). This means that the compiler assumes it has a return type of int.

You're also passing test to printf() when you should be passing test2.

In addition:

  • There's no need to use malloc() to allocate a single uint32_t;
  • You don't need to call ntohl() because inet_ntoa() expects its input in network byte order; and
  • inet_ntoa() is out of date - inet_ntop() should be used in new code.

Try:

#include <arpa/inet.h>

if (*packet_ethertype == ETHERTYPE_IP) { /* IPv4 */
    struct in_addr sin_addr;
    char straddr[INET_ADDRSTRLEN];

    memcpy(&sin_addr.s_addr, packet+26, 4);

    if (inet_ntop(AF_INET, &sin_addr, straddr, sizeof straddr))
        printf("%s\n", straddr);
    else
        perror("inet_ntop");
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文