C++ 何时将未对齐的说明符与指针一起使用? 背景

C++ 何时将未对齐的说明符与指针一起使用? 背景,c++,c++11,templates,visual-c++,memory-alignment,C++,C++11,Templates,Visual C++,Memory Alignment,我目前正在使用可变长度数组,它们的长度存储在元素的前两个字节中。由于阵列没有填充,单个元素可能未对齐。只有第一个元素保证是对齐的,整个元素以双空终止。这些数组由我需要访问且无法更改的API使用 我正在编写一个const_迭代器,它接受一个对齐的指针,并可以迭代未对齐的元素。这些数组的API为指向元素的指针指定了“\uuu unaligned”,因此我主要是想确认或否认我对应用\uu unaligned说明符的理解 问题 简单地说:在处理指向潜在未对齐数据的指针时,什么时候应该使用\uu unal

我目前正在使用可变长度数组,它们的长度存储在元素的前两个字节中。由于阵列没有填充,单个元素可能未对齐。只有第一个元素保证是对齐的,整个元素以双空终止。这些数组由我需要访问且无法更改的API使用

我正在编写一个
const_迭代器
,它接受一个对齐的指针,并可以迭代未对齐的元素。这些数组的API为指向元素的指针指定了“\uuu unaligned”,因此我主要是想确认或否认我对应用
\uu unaligned
说明符的理解

问题 简单地说:在处理指向潜在未对齐数据的指针时,什么时候应该使用
\uu unaligned
说明符

让我们说我有

Foo *foo = pointerToFirstElement(); //aligned
auto next_ptr = reinterpret_cast<unsigned char *>(foo);
next_ptr += bytesToNextElement(foo);
//reinterpret_cast here to retrieve the next element

使用Visual C++,<>代码>未对齐关键字仅被引入支持ItANIAL,它需要对未对齐的读取进行特殊处理。这不适用于x86、x64或任何其他平台

简而言之,不要使用它。

简单地说:在处理指向潜在未对齐数据的指针时,什么时候应该使用_unaligned说明符

  • 简而言之,当您使用的平台需要它时,例如x86-64上的Windows API。这是对安腾的传统回溯,而不是x86-32上的问题。其他一些处理器也存在未对齐数据的问题(例如MIPS)

  • 具体来说,
    \uu unaligned
    说明符仅仅意味着数据可能不在对齐的边界上

  • 在32位x86平台上,Windows本身只是声明
    #define u未对齐

然后我是否需要检查新地址是否对齐,如果没有对齐,则重新解释\u cast(next\u ptr)以访问下一个元素

  • 如上所述,没有。添加
    \uuu unaligned
    说明符对于访问获取指向未对齐数据的参数的函数非常有用,例如

  • 后续:当不需要时,如何删除未对齐的说明符?使用或执行类似Windows的操作:
    #在包含标题之前定义u未对齐
    使用预处理器检查您是否在x86-64或其他安全平台上。

最后,

此外,我是否可以使用uu unaligned作为模板参数推断的一部分,方式类似于const,如下所示

template <class T, class = std::enable_if<std::is_pointer<T>::value>>
struct is_pointer_to_aligned_data : std::true_type {};

template <class T>
struct is_pointer_to_aligned_data<T __unaligned *> : std::false_type {};
是的,但是像这样:

template< class T > struct is_aligned_helper : std::true_type {};
template< class T > struct is_aligned_helper<__unaligned T> : std::false_type {};
template< class T > struct is_aligned : is_aligned_helper<typename std::remove_cv_t<std::remove_pointer_t<T>>> {};
templatestruct是对齐的\u助手:std::true\u type{};
模板struct是对齐的\u助手:std::false\u type{};
模板结构是对齐的:是对齐的\u助手{};

您需要首先删除指针以检查指向的数据的类型。然后删除任何常量或volatile以获得裸类型+
\uu unaligned
(如果存在)。

我别无选择:我很确定这是“unaligned”的不同含义。在任何情况下,您都不需要使用
\u unaligned
关键字:您只需读/写未对齐的数据,硬件就会处理它。在x86和x64体系结构上的C/C++中,您可以在任何地址读取单个字节,它就可以正常工作正如我所说,这只是安腾的问题。它在所有其他平台上都被忽略。微软不久前就停止了对安腾的支持,但在平台标题中仍有一些内容挥之不去。除非您是为安腾编写的,否则请忽略
\uuuu unsigned
,永远不要使用它。如果忽略了
\uuu unaligned
,为什么编译器错误中会出现
\uuuu unaligned
?具体来说,这是在清除我的代码中对
\uu unaligned
的所有引用之后进行的。它在
typedefs
中。