对齐类型并按值传递参数
按值传递对齐类型或具有对齐类型的结构不适用于某些实现。这会破坏 STL 容器,因为某些方法(例如 resize)按值获取参数。
我使用 Visual Studio 2008 运行了一些测试,但不完全确定按值传递何时以及如何失败。我主要关心的是函数foo。它似乎工作正常,但这可能是内联的结果还是其他巧合的结果?如果我将其签名更改为 void foo(const __m128&) 会怎样?
非常感谢您的意见。谢谢。
struct A
{
__m128 x;
int n;
};
void foo(__m128);
void bar(A);
void f1()
{
// won't compile
// std::vector<A> vec1(3);
// compiles, but fails at runtime when elements are accessed
std::vector<__m128> vec2(3);
// this seems to work. WHY???
std::vector<__m128, some_16_byte_aligned_allocator<__m128> > vec3(3);
__m128 x;
A a;
// passed by value, is it OK?
foo(x);
// won't compile
//bar(a);
}
编辑。即使使用对齐的分配器,STL 也会失败,因为传值问题仍然存在。
找到此链接 按值传递 __m128
Passing aligned types or structures with aligned types by value doesn't work with some implementations. This breaks STL containers, because some of the methods (such as resize) take their arguments by value.
I run some tests with Visual Studio 2008 and not entirely sure when and how pass by value fails. My main concern is function foo. It seems to work fine, but could it be a result of inlining or some other coincidence? What if I change its signature to void foo(const __m128&)?
Your input is greatly appreciated. Thank you.
struct A
{
__m128 x;
int n;
};
void foo(__m128);
void bar(A);
void f1()
{
// won't compile
// std::vector<A> vec1(3);
// compiles, but fails at runtime when elements are accessed
std::vector<__m128> vec2(3);
// this seems to work. WHY???
std::vector<__m128, some_16_byte_aligned_allocator<__m128> > vec3(3);
__m128 x;
A a;
// passed by value, is it OK?
foo(x);
// won't compile
//bar(a);
}
EDIT. STL fails even with aligned allocator, because pass by value problem remains.
Found this link pass __m128 by value
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我认为一般来说唯一安全的方法是通过引用传递。某些平台(例如 Xbox 360)支持在寄存器中传递向量参数,但我认为这在 x86 上是不可能的。
对于
std::vector
情况,您需要确保分配的内存与 16 字节对齐;否则,当您尝试对未对齐的向量执行大多数操作时,您会崩溃。如果您支持多个平台,一个安全的计划是使用
typedef
例如,您可以在支持向量按值传递的平台上更改 typedef。
I think the only safe way to do this in general is to pass by reference. Some platforms (e.g. Xbox 360) support passing vector arguments in registers, but I don't think this is possible on x86.
For the
std::vector
case, you'll need to make sure that the memory allocated is aligned to 16 bytes; otherwise you'll get crashes when you try to perform most operations on unaligned vectors.If you're supporting multiple platforms, a safe plan is to use a
typedef
e.g.You can then change the typedef on platforms that support vector pass-by-value.
经常使用的 resize() 函数导致所有对齐,也许您可以尝试专门针对 __m128 的矢量模板?
the oftenly used resize() function is causing all the alignment and perhaps you can try to specialise vector template for __m128 ?