c++ - 将缓冲区对齐到 N 字节边界而不是 2N 字节边界?

标签 c++ c++11 assembly

我想分配一些 char 缓冲区0,以传递给具有特定对齐要求的外部非 C++ 函数。

要求是缓冲区对齐到 N-byte1 边界,但不是 2N边界。例如,如果 N 为 64,则指向此缓冲区的指针 p 应满足 ((uintptr_t)p) % 64 == 0((uintptr_t)p) % 128 != 0 - 至少在指针在转换为 uintptr_t 时通常被解释为普通地址的平台上。

有没有一种合理的方法可以使用 C++11 的标准设施来做到这一点?

如果不是,是否有一种合理的方法可以在标准工具2 之外执行此操作,这在实践中适用于现代编译器和平台?

缓冲区将被传递给外部例程(遵循 C ABI 但用 asm 编写)。所需的对齐方式通常大于 16,但小于 8192。

过度分配或任何其他轻微的资源浪费问题都没有问题。与浪费几个字节或几毫秒相比,我对正确性和可移植性更感兴趣。

同时适用于堆和堆栈的东西是理想的,但任何适用于其中任何一个的东西仍然相当不错(优先考虑堆分配)。


0 这可以使用 operator new[]malloc 或者可能是其他一些对齐感知的方法:任何有意义的方法。

1 通常,N 是 2 的幂。

2 是的,我知道这种类型的回答会导致语言律师变得中风,所以如果那是你忽略这部分。

最佳答案

逻辑上,为了满足“对齐到 N,但不是 2N”,我们对齐到 2N 然后将 N 添加到指针。请注意,这将过度分配 N 字节。

因此,假设我们要分配 B 字节,如果您只需要堆栈空间,alignas也许会奏效。

alignas(N*2) char buffer[B+N];
char *p = buffer + N;

如果你想要堆空间,std::aligned_storage可能会:

typedef std::aligned_storage<B+N,N*2>::type ALIGNED_CHAR;
ALIGNED_CHAR buffer;
char *p = reinterpret_cast<char *>(&buffer) + N;

我还没有测试过,但文档表明它应该没问题。

关于c++ - 将缓冲区对齐到 N 字节边界而不是 2N 字节边界?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44232777/

相关文章:

ios - 因为不理解 'm' 标志

linux - 使用 gcc 编译和运行程序集的最小示例?

c++ - 如何在 C++ 中创建一个矩阵大小由参数决定的函数?

c++ - 没有来自 'const std::__1::basic_string<char> to ' std::__1::basic_string<char> *' 的可行转换

c++ - std::to_string 是跨平台的吗?

c++ - std::function 在移动后是否重置其内部功能

c - 需要帮助在给定 64 位汇编指令的情况下在 C 中构建 Long loop(long x, int n) 函数

c++ - 正确读写串口Windows API

c++ - 迭代 C++ 中的对列表?

c++ - 带有非常量参数的 boost::bind 方法