【问题标题】:How do I receive a volatile through a pointer-to-non-volatile?如何通过指向非易失性的指针接收易失性?
【发布时间】:2018-05-27 08:03:01
【问题描述】:

我正在使用一个 API,它为我提供了内存映射 I/O 的指针。它通过填写一个指向指针的参数来做到这一点:

int map(void** p);

因为这是内存映射 I/O,我很确定我应该在这里使用 volatile。 (我不知道他们为什么不将参数设为volatile void**。)

但是,我的volatile void** 不能隐式转换为函数的void**,所以我不能直接将它传入:

volatile void* p;
map(&p); // Error: no known conversion from 'volatile void **' to 'void **'.

我目前正在使用一个额外的变量和一个单独的分配步骤来解决这个问题:

volatile void* p;
void* pNonVolatile;
map(&pNonVolatile);
p = pNonVolatile;

这似乎很冗长。在这种情况下,在传递指针时将volatile 扔掉是否安全?即

volatile void* p;
map(const_cast<void**>(&p));

【问题讨论】:

  • 你确定它一定是易失性的吗?请检查this question
  • 从 API 获取 void *,然后根据需要将其转换为 volatile void **
  • 请注意,volatile 对于进程间同步来说既非必要也不充分
  • 您大概需要将返回值转换为其他类型才能对其进行任何处理,而不是将其传递回相同的 API,无论如何?

标签: c++ type-conversion volatile


【解决方案1】:

从 C++ 语言的角度来看,这可能会导致库中出现未定义的行为,但不会出现在您使用 const_cast 的代码中。

但是,根据您的描述,该库可能不使用 C 或 C++ 写入此内存空间(您提到它使用内存映射 I/O)。因此,如果库在没有volatile 的情况下取消引用您的指针,可能存在的未定义行为是不相关的,因为硬件正在这样做,而不是软件。

在任何情况下,您是否使用const_cast 或“额外指针然后分配”解决方案似乎都无关紧要。如果内存是由硬件设备写入的,它们应该都可以,但如果它是由没有volatile 的库写入的,则它们都可以。

【讨论】:

  • 您能否详细说明为什么额外变量方法可能与 cast 方法一样“不好”?似乎可以保证给图书馆它想要的东西,给我我想要的东西。
  • 如果库从软件写入非易失性指针,读取时只有一个易失性合格指针是不够的。但是在硬件写入的情况下,这取决于实现,并且可能针对您所在的任何平台进行了很好的定义。我不认为演员阵容比额外变量更好或更差,所以你最好使用你觉得更有吸引力的任何方法。
猜你喜欢
  • 2015-04-23
  • 1970-01-01
  • 1970-01-01
  • 2012-04-13
  • 1970-01-01
  • 1970-01-01
  • 2018-01-26
  • 2015-11-07
  • 2018-01-18
相关资源
最近更新 更多