c++ - 标准全局默认运算符 new 的对齐限制是什么?

标签 c++ visual-c++ com memory-alignment

我正在处理一些使用 ATL 的 CComBSTR 类型的旧代码。我正在更改它,以便它可以使用 ATL 不附带的 Visual C++ Express Edition 进行编译。我只使用了 CComBSTR 的一个非常小的子集,所以这样做相当简单。

但是,在分配BSTR内存块时,我需要用4字节长度的前缀填充前四个字节。我担心如果我使用 new char[size] 表达式为字符串分配内存,我会因为分配的 char 数组而不是导致对齐错误正确对齐四字节前缀。

标准中是否有任何内容说明 new 的返回值有哪些对齐要求?我在 C++11 中看到的是:

5.3.4/1 [expr.new]
It is implementation-defined whether over-aligned types are supported (3.11).

3.11/6 [basic.align]
The alignment requirement of a complete type can be queried using an alignof expression (5.3.6). Furthermore, the types char, signed char, and unsigned char shall have the weakest alignment requirement. [ Note: This enables the character types to be used as the underlying type for an aligned memory area (7.6.2).—end note ]

我觉得这有点令人困惑——“最弱的对齐要求”对我来说是“对对齐的最不严格的约束”,但下面的注释似乎表明标准的意思相反。

像这样使用 new char[sizeof(uint32_t) + 2*(length + 1)] 缓冲区作为 BSTR 安全吗?

编辑:我刚刚意识到,在 BSTR 的这种特定情况下,无论如何都需要使用 SysAllocString 来分配字符串;但我仍然对以这种方式使用 new 是否合适很感兴趣。

最佳答案

这是一个实现细节,但 MSVC 使用操作系统分配器。 HeapAlloc() 用于 CRT 分配,CoTaskMemAlloc() 用于 COM 类型包装器,如 _bstr_t。在 32 位和 64 位代码中,它们都按 8 对齐。

您永远不应该使用 new 运算符为 BSTR 分配内存,必须使用 COM 分配器来确保使用正确的堆释放它们。在使用 BSTR 的任何互操作场景中都很重要,它是一种标准的自动化类型。 CoTaskMemAlloc/Free() 是必需的,但始终使用 BSTR 辅助函数来确保它们得到正确初始化。 SysAllocString() 和 SysFreeString()。使用 SysAllocStringLen() 处理包含嵌入零的字符串。

关于c++ - 标准全局默认运算符 new 的对齐限制是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13097268/

相关文章:

c++ - 如何使用 C++ 在 Windows 上制作一个二进制兼容的动态库?

c++ - 在 C++ 中返回对局部变量的引用

com - 使用脚本/api 更改组件服务 > COM 安全性中的访问权限?

c# - VB 脚本代码不调用 c# 函数

c++ - std::shared_ptr 类工厂 C++

C++ 语法 : Constant Reference Parameter

c++ - 如何获取通过网络驱动器访问的文件的 UNC 路径?

C++鼠标左键按下帮助

c++ - vector 迭代器在类里面不兼容

c++ - COM dll注销问题