【问题标题】:What makes that volatile breaks pointer-arithmetic with structs? [duplicate]是什么让 volatile 破坏了结构的指针算术? [复制]
【发布时间】:2019-09-12 16:19:43
【问题描述】:

在我们的代码中,我们使用指向结构的指针来扣除硬件寄存器的地址以保持代码的可读性。

例如:

#include <cstdint>
#include <iostream>

struct reg {
    uint32_t t;
    uint32_t x;
    uint32_t value;
};

int main(void)
{
    struct reg *r = reinterpret_cast<struct reg *>(0x800000);

    std::cerr << &r->value << "\n";
    std::cerr << &r->t << "\n";
    std::cerr << &r->x << "\n";

    return 0;
}

硬件基地址为 0x800000,使用writeReg(&amp;t-&gt;x, 123); 将使其写入 0x800004。

不小心将volatile-keyword 错误地放置在结构定义中:


struct reg {
    volatile uint32_t t;
    volatile uint32_t x;
    volatile uint32_t value;
};

现在发生的事情是所有字段的偏移量都为 1,使用 &amp;r-&gt;field-syntax。

在这里使用g++ (Debian 9.2.1-4) 9.2.1 20190821

使用 printf 和 C-style-cast 在 C 中重写测试,即使使用 volatile,也会再次给出正确的偏移量。

我无法理解为什么 volatile-keyword 似乎破坏了指针算术?为什么呢?发生了什么?

【问题讨论】:

    标签: c++ pointers structure


    【解决方案1】:

    operator&lt;&lt; 没有重载用于打印指向 volatile 的指针。

    您的编译器找到的最合适的重载是用于打印bool 的重载,因此您的指针将转换为bool

    试试:

    std::cerr << (void *)&r->value << "\n";
    

    【讨论】:

    • 等等,这行得通吗?你也不需要const_cast 吗?
    • @Brian 哎呀,它没有。已编辑。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-07-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-10-15
    • 1970-01-01
    • 2021-11-03
    相关资源
    最近更新 更多