增加具有固定值的指针

时间:2013-12-11 09:06:36

标签: c pointers memory microcontroller

下面的代码是一个示例,地址是指微控制器的闪存,因此它不会指向任何垃圾数据。

我要做的是将指针“end_adress”指向内存块的末尾。在这种情况下,块的开始是0x00001000,块的结尾是0x00002000。我想通过使用起始地址和内存块大小的知识来设置“end_adress”变量。

这是解决问题的好方法吗? 好的是可读代码,欢迎任何其他建议!

static const uint32_t memory_size = 0x00001000;
static volatile const uint32_t* start_address = (volatile const uint32_t*)0x00001000;
static volatile uint32_t* end_address;

int main(int argc, char *argv[])
{
    end_address = start_address + (memory_size/sizeof(end_address));
    printf("End adress: %x \n", end_address);

    return 0;
}

2 个答案:

答案 0 :(得分:3)

要解决您的问题,请替换此

end_address = start_address + (memory_size/sizeof(end_address));

使用:

end_address = start_address + (memory_size/sizeof(*end_address));

原因:end_address本身是指针,而*end_address实际上是指针指向的数据类型。 sizeof(uint32_t) != sizeof(char*)例如char*会导致问题。在64位或16位系统上。

然而,当您使用内存地址时,我建议您使用类型为char *memory_size = 0x00001000; uint32_t memory_size = 0x1000; char *end_address = memory_size + memory_size; /* then it's assured that end_address == 0x00002000 */ 的指针,以便您可以使用它进行直接算术:

{{1}}

答案 1 :(得分:1)

你的方式几乎没问题(*end_address除外),如另一个答案所述。但是, 仍然是一个问题。

您的memory_size字节,而sizeof则为 char 的倍数。 sizeof(char)总是一个,但char可能不一定是一个字节(一个例子是我正在编码的TI芯片,其中char有两个字节。)

让我们看看在这种情况下会发生什么:

/* char is two bytes */
/* sizeof(char) == 1 */
/* sizeof(uint32_t) == 2 */
end_address = start_address + (memory_size/sizeof *end_address);

转换为:

end_address = (uint32_t *)0x1000 + (0x1000 / 2);

转换为:

end_address = (uint32_t *)0x1000 + 0x800;

表示0x1000后的0x800 * 4字节,即0x3000(不是0x2000)。

你应该做些什么来确保使用CHAR_BIT(来自limits.h)来说明一个字符有多少字节。然后做:

end_address = start_address + memory_size / sizeof *end_address / (CHAR_BIT / 8);

假设CHAR_BIT是8的倍数。如果不是,你必须知道一个字节中的位数是多少,除以它!

请注意,我/ (CHAR_BIT / 8)(而不是* 8 / CHAR_BIT)以防止任何可能的溢出。


或者,你可以写:

end_address = (void *)((char *)start_address + memory_size / (CHAR_BIT / 8));

根据您习惯的方式,它可能看起来更清晰或更混乱,但在其他方面是相同的。