传递给方法后结构体值发生变化

发布于 2024-11-25 10:22:43 字数 906 浏览 1 评论 0原文

我正在使用 libpcap 编写数据包解析器,并在尝试从 pcap 标头读取数据包长度时遇到奇怪的行为。

下面的第一个 printf 语句打印出正确的数据包长度,而第二个语句则打印出一个数字,例如 362791。

struct pcap_pkthdr header;
pcap_t *handle;
const u_char *packet;

...

    while((packet = pcap_next(handle, &header)) != NULL) {
        printf("[%d]\n", header.len);   
        process_packet(&header, packet);
    }

...
}

void process_packet(struct pcap_pkthdr *header, const u_char *packet) {
    printf("[%d] %d bytes\n", header->ts, header->len);
}

struct pcap_pkthdr 的定义是:

struct pcap_pkthdr {
    struct timeval ts; /* time stamp */
    bpf_u_int32 caplen; /* length of portion present */
    bpf_u_int32 len; /* length this packet (off wire) */
};

的原型>pcap_nextu_char *pcap_next(pcap_t *p, struct pcap_pkthdr *h)

这有什么原因吗发生?

I am writing a packet parser using libpcap and encounter strange behaviour when trying to read the packet length form the pcap header.

The first printf statement below prints out the correct packet length, whereas the second one prints out a number such as 362791.

struct pcap_pkthdr header;
pcap_t *handle;
const u_char *packet;

...

    while((packet = pcap_next(handle, &header)) != NULL) {
        printf("[%d]\n", header.len);   
        process_packet(&header, packet);
    }

...
}

void process_packet(struct pcap_pkthdr *header, const u_char *packet) {
    printf("[%d] %d bytes\n", header->ts, header->len);
}

The definition of struct pcap_pkthdr is:

struct pcap_pkthdr {
    struct timeval ts; /* time stamp */
    bpf_u_int32 caplen; /* length of portion present */
    bpf_u_int32 len; /* length this packet (off wire) */
};

The prototype for pcap_next is u_char *pcap_next(pcap_t *p, struct pcap_pkthdr *h)

Is there any reason that this is happening?

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

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

发布评论

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

评论(3

伴随着你 2024-12-02 10:22:43

我认为根本问题在于代码

printf("[%d] %d bytes\n", header->ts, header->len);

中的ts< /code> 类型为 struct timeval 的数据段不仅仅是一个简单的整数数据,或者至少 sizeof(timeval) 与 sizeof(int) 不一样。这将导致 printf 在尝试获取 var 参数列表中的第二个参数时使用错误的地址偏移量。

所以我认为 printf("[%d] %d bytes\n", header->len, header->ts ); 应该正确工作,但你不能简单地交换它们。

I think the root problem is that in the code

printf("[%d] %d bytes\n", header->ts, header->len);

the ts data section whose type is struct timeval is not just a simple integer data, or at least the sizeof(timeval) is not the same as sizeof(int). This will cause the printf uses the wrong address offset when trying to fetch the second parameter in a var arguments list.

So I think printf("[%d] %d bytes\n", header->len, header->ts ); should work correct, but you cannot simply exchange them.

野生奥特曼 2024-12-02 10:22:43

你的 C 代码看起来有效,我看不出语法有任何问题。所以这可能与C本身无关。

目前唯一想到的是某些东西正在后台同时运行并撞击您的结构。我对 pcap 了解不多,所以我无法帮助您了解具体细节...

但是,当我有这样的奇怪之处时,我通常会创建一个统计函数,它打印出有关结构的所有可想象的事情...并且到处调用统计函数...这就像一个迷你的内联单元测试。

我希望你将你的代码翻新成这个并尝试一下:

void hdr_stats(struct pcap_pkthdr *header){
    unsigned int i;
    printf("address of header:  %p\n", header);

    printf("caplen:             %d\n", header->caplen);
    i = header->caplen;
    printf("caplen:             %d\n", i);

    printf("len:                %d\n", header->len);
    i = header->len;
    printf("len:                %d\n", i);

    //-------
    // add header->ts.xxxx debugging here, might give other clues...
    //-------
}

...

    while((packet = pcap_next(handle, &header)) != NULL) {
        printf("[%d]\n", header.len);   
        hdr_stats(&header);
        process_packet(&header, packet);
        hdr_stats(&header);
    }

...

void process_packet(struct pcap_pkthdr *header, const u_char *packet) {
    hdr_stats(header);
    printf("[%d]\n", header->len);
    hdr_stats(header);
}

这可能会帮助你解决你的错误。

your C code looks valid, I can't see any problem with the syntax. So it might be something not related to C itself.

The only thing that currently comes to mind is that something is running concurrently in the background and slamming your struct. I don't know a lot about pcap, so I can't help you with the specifics...

BUT, When I have such oddities, I usually create a stats function which prints out every conceivable thing about a structure... and call the stats function everywhere... this is like a mini in-line unit test.

I'd like you to refurbish your code into this and try it out:

void hdr_stats(struct pcap_pkthdr *header){
    unsigned int i;
    printf("address of header:  %p\n", header);

    printf("caplen:             %d\n", header->caplen);
    i = header->caplen;
    printf("caplen:             %d\n", i);

    printf("len:                %d\n", header->len);
    i = header->len;
    printf("len:                %d\n", i);

    //-------
    // add header->ts.xxxx debugging here, might give other clues...
    //-------
}

...

    while((packet = pcap_next(handle, &header)) != NULL) {
        printf("[%d]\n", header.len);   
        hdr_stats(&header);
        process_packet(&header, packet);
        hdr_stats(&header);
    }

...

void process_packet(struct pcap_pkthdr *header, const u_char *packet) {
    hdr_stats(header);
    printf("[%d]\n", header->len);
    hdr_stats(header);
}

this might help you corner your bug.

何以笙箫默 2024-12-02 10:22:43

...您在比较苹果和橙子吗?

/* header.len in brackets */
printf("[%d]\n", header.len); 

/* header->ts in brackets */
printf("[%d] %d bytes\n", header->ts, header->len);

... are you comparing apples to oranges?

/* header.len in brackets */
printf("[%d]\n", header.len); 

/* header->ts in brackets */
printf("[%d] %d bytes\n", header->ts, header->len);
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文