将指针转换为引用后使用reinterpret_cast是否属于未定义行为?

7
以下代码是否存在未定义行为(UB)?
int   i  = 5;
void *p  = &i;

int* &r  = reinterpret_cast<int* &>(p);
int*  p2 = r;

请注意我不对指针进行解引用。


使用GCC和Clang(trunk builds),启用额外的警告并启用UB sanitizer进行构建和运行,sanitizer表示一切正常(在编译器浏览器上查看)。但这确实看起来很可疑,如果它看起来可疑,那么我不想接触这样的代码。不要这样做! - Some programmer dude
你真的需要这样做吗?还是只是出于好奇心? - Ivan
为什么不考虑指针的解引用呢?我认为在这种情况下这不是一个问题。如果你花费了那么多精力来创建指针,最好尝试使用它。 - Richard Critten
1
@Ivan,是的,我需要。我正在为GLib / GStreamer制作C ++包装器。我的顶层基类具有void *成员。在派生类中,我需要将此成员强制转换为特定指针的引用。我无法通过值转换指针,因为this。我确切地需要引用。 - anton_rh
请询问您正在尝试解决的实际问题,并告诉我们您想要使用的解决方案以及您在使用此解决方案时遇到的问题。直接询问您的问题可以为我们提供更多上下文和更好地帮助您解决实际问题的机会,而不是您在这里提出的相对缺乏上下文的问题。您可能需要刷新帮助页面,参观SO[tour],阅读[ask]以及此问题清单 - Some programmer dude
2个回答

2

是的,它是未定义行为。

reinterpret_cast<int* &>(p);

等同于

*reinterpret_cast<int**>(&p);

reinterpret_cast 允许将 void** 转换为 int**,但是隐式解引用是未定义的行为,因为数据的类型 (void*) 和被访问的类型 (int*) 不相似。


0
在这个绝对特定的情况下,没有解引用,我认为应该没问题。我验证了指针的值。当sizeof(void*)和sizeof(int*)不同时,情况就不同了(尽管我不知道是否可能)。
通过这样做,你完全承担了非常熟悉的场景的责任。
   int   i = 5;
   void *p = &i; //convert int* => void*


   int* &r = reinterpret_cast<int* &>(p); //convert void* which was int* to int*&
   int*  p2 = r; //**copy** address stays same

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接