You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

指针转换中的未定义行为及自定义偏移指针类的问题咨询

关于NullableOffsetPtr未定义行为及相关标准问题的修复与疑问

编辑:感谢各位精准解答,已解决“为什么”的问题与燃眉之急,但仍纠结“如何解决”的具体方案,以下是附加问题。


核心问题:NullableOffsetPtr优化级别依赖的未定义行为修复

我正在设计极简的NullableOffsetPtr偏移指针类,用于实现共享内存中的链表数据结构,以应对不同进程的虚拟地址偏移差异,设计灵感来自boost::interprocess::offset_ptr。首次测试显示输出结果依赖优化级别,疑似存在未定义行为(UB),请问如何修复?

示例代码如下:

#include <cstddef>
#include <iostream>

template<typename T>
class NullableOffsetPtr
{
public:
    NullableOffsetPtr(T const* ptr) :
        offset_{
            ptr == nullptr ? std::ptrdiff_t{1} : reinterpret_cast<std::byte const*>(ptr) - reinterpret_cast<std::byte const*>(this)}
    {
    }

    T* get()
    {
        return offset_ == 1 ? nullptr : reinterpret_cast<T*>(reinterpret_cast<std::byte*>(this) + offset_);
    }

private:
    std::ptrdiff_t offset_; // Using units of bytes, as alignments of *this and *ptr may not match.
};

class Sample
{
};

int main(int argc, char* argv[])
{
    Sample sample;
    NullableOffsetPtr<Sample> ptr{&sample};

    std::cout << "(ptr.get() == &sample): " << (ptr.get() == &sample) << std::endl;
    std::cout << "ptr.get(): " << ptr.get() << std::endl;
    std::cout << "&sample  : " << &sample << std::endl;

    return 0;
}

在gcc编译器-O1及以上优化级别下,输出为:

(ptr.get() == &sample): 0
ptr.get(): 0x7ffe503cd42f
&sample  : 0x7ffe503cd42f

尽管指针值显示相同,但比较结果为false!我知道reinterpret_cast可能引发UB,但认为其使用符合reinterpret_cast的类型别名规则。


附加问题1:复合对象内指针加减的标准合法性

我理解expr.add#4.2限制指针+/-操作仅适用于同一数组元素的指针,但offsetof宏的存在说明同一复合对象内的指针也可操作,示例代码如下:

#include <iostream>

struct Inner
{
    int i1;
    int i2;
};

struct Outer
{
    int i1;
    int i2;
    Inner inner;
};

int main(int argc, char* argv[])
{
    Outer outer;
    std::cout << "&outer.i2 - &outer.i1: " << &outer.i2 - &outer.i1 << std::endl;
    std::cout << "&outer.inner.i2 - &outer.i1: " << &outer.inner.i2 - &outer.i1 << std::endl;

    return 0;
}

输出为:

&outer.i2 - &outer.i1: 1
&outer.inner.i2 - &outer.i1: 3

所有指针目标都在outer对象内,但无数组参与。expr.add#4.2中提到的“(possibly-hypothetical) array element”是否适用于此场景?该表述具体指什么?


附加问题2:boost::interprocess::offset_ptr的未定义行为规避

boost::interprocess::offset_ptr能在多大程度上避免UB?我看到与内联相关的“illegal but correct”说法,但不理解内联的关联,也不清楚是否存在可验证的广泛认可的“非法但正确”情况,能否给出建议?


内容的提问来源于stack exchange,提问作者Michael Steffens

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.24 19:41:13