【发布时间】:2012-10-17 07:54:35
【问题描述】:
我正在处理一些使用 ATL 的 CComBSTR 类型的旧代码。我正在更改它,以便它可以使用 ATL 不附带的 Visual C++ Express Edition 进行编译。我只使用了CComBSTR 的一小部分,所以这样做相当简单。
但是,在分配BSTR 内存块时,我需要用4 字节长度的前缀填充前四个字节。我担心如果我使用new char[size] 表达式为字符串分配内存,我会由于分配的char 数组没有正确对齐四字节前缀而导致对齐错误。
标准中是否有任何内容说明new 的返回值具有哪些对齐要求?我在 C++11 中看到的只有:
5.3.4/1 [expr.new]
是否支持过度对齐的类型由实现定义(3.11)。3.11/6 [basic.align]
可以使用 alignof 表达式 (5.3.6) 查询完整类型的对齐要求。此外,char、signed char 和 unsigned char 类型应具有最弱的对齐要求。 [注意:这使得字符类型可以用作对齐内存区域(7.6.2)的基础类型。—结束注释]
我觉得这有点令人困惑——“最弱的对齐要求”对我来说是“对对齐的最严格限制”,但下面的注释似乎表明标准的意思相反。
像这样使用new char[sizeof(uint32_t) + 2*(length + 1)] 缓冲区作为BSTR 安全吗?
编辑:我刚刚意识到,在BSTR 这种特定情况下,无论如何都需要使用 SysAllocString 来分配字符串;但我仍然对以这种方式使用new 是否可以感兴趣。
【问题讨论】:
-
在实践中您不太可能遇到对齐问题,尽管标准不会对此作出任何说明。如果您使用
malloc(),您可能会发现它返回的内存块是 8 字节甚至 16 字节对齐的(因为它返回的数据必须充分对齐才能与任何基本类型一起使用);new等人的行为似乎是合理的,但不能保证。 -
@JonathanLeffler:
malloc的标准明确表示 (C99, 7.20.3/1)The pointer returned if the allocation succeeds is suitably aligned so that it may be assigned to a pointer to any type of object and then used to access such an object or an array of such objects in the space allocated (until the space is explicitly deallocated).) -- 这对我来说似乎是一个很好的保证。 -
是的——对于
malloc(),这很好;并且“可能 8 字节或 16 字节对齐 [ment]”是因为该保证加上对 32 位和 64 位系统类型的正常限制。但是operator new和new运算符与malloc()不同,我不确定当您要求new char[17]时,C++ 标准对返回值做出了什么承诺。这就是为什么这些也是 cmets,而不是答案。我懒得去看实际的 C++ 标准。
标签: c++ visual-c++ com memory-alignment