Contiki 中 printf() 函数的意外行为

Unexpected behavior in printf() function in Contiki

我试图在 contikiOS 中测试一些计时器,我使用 printf() 来输出变量的值,但打印的值根据我打印消息的方式而改变。

我是什么意思?好吧,我打印了两个变量,RTIMER_SECOND 是一个 long unsigned int,CLOCK_SECOND 是一个整数。下面的变化是我尝试的,输出是下面的代码:

    printf("1->RTIMER_SECOND=%lu CLOCK_SECOND=%d\n", RTIMER_SECOND, CLOCK_SECOND);
    printf("2->RTIMER_SECOND=%d CLOCK_SECOND=%d\n\n", RTIMER_SECOND, CLOCK_SECOND);

    printf("3->CLOCK_SECOND=%d RTIMER_SECOND=%lu\n", CLOCK_SECOND,RTIMER_SECOND);
    printf("4->CLOCK_SECOND=%d RTIMER_SECOND=%d\n\n", CLOCK_SECOND,RTIMER_SECOND);

    printf("Ticks per second: %lu\n", RTIMER_SECOND);
    printf("second per second: %d\n", CLOCK_SECOND);

输出是这样的:

1->RTIMER_SECOND=15625 CLOCK_SECOND=128

2->RTIMER_SECOND=15625 CLOCK_SECOND=0

3->CLOCK_SECOND=128 RTIMER_SECOND=15625

4->CLOCK_SECOND=128 RTIMER_SECOND=15625

Ticks per second: 15625

second per second: 128

我的问题是,为什么 0 出现在第二次打印中?打印 RTIMER_SECOND 的 %d 而不是 %lu 时未定义的行为会影响下一个变量吗? PS:第4个和第2个相反,CLOCK_SECOND的值不是0。

printf() 将由 OS 实施。我不知道实现的细节。

我的猜测是变量作为堆栈上的字节序列传递给 printf()。说明符字符串告诉函数在打印输出时要消耗多少字节。

一个长无符号整数是 4 个字节,可能是小端顺序。因为 15625 小于 2^16,所以 RTIMER_SECOND 的最后两个字节都是 0。当字符串告诉函数只为 RTIMER_SECOND 打印 2 个字节时,接下来的两个 0 字节被解释为CLOCK_SECOND.

的两个字节

为了验证这个假设,尝试为 RTIMER_SECOND 传入一个超过 2 个字节的值,即超过 65536。在这种情况下,第 4 行也会被弄乱。