gpt4 book ai didi

c - 从内存加载 vector 的更好方法。 (铛)

转载 作者:太空狗 更新时间:2023-10-29 17:11:55 26 4
gpt4 key购买 nike

我正在编写一个测试程序以适应 Clang 对 OpenCL 样式 vector 的语言扩展。我可以让代码工作,但我在降低它的一个方面时遇到了问题。我似乎无法弄清楚如何让 clang 很好地从标量数组加载 vector 。

目前我必须做类似的事情:

byte16 va = (byte16){ argv[1][start], argv[1][start + 1], argv[1][start + 2], 
argv[1][start + 3], argv[1][start + 4], argv[1][start + 5],
argv[1][start + 6], argv[1][start + 7], argv[1][start + 8],
argv[1][start + 9], argv[1][start + 10], argv[1][start + 11],
argv[1][start + 12], argv[1][start + 13], argv[1][start + 14],
argv[1][start + 15]};

理想情况下,我会喜欢这样的东西:

byte16 va = *(byte16 *)(&(argv[1][start]));

我可以使用适用于 ARM 或 x86 的适当内在函数轻松地做到这一点。但是该代码导致程序在编译时崩溃。

最佳答案

在 x86 上发生崩溃的原因之一是对齐问题。我的系统上没有 clang 来重现该问题,但我可以在 GCC 示例中进行演示。

如果你这样做:

/* Define a vector type of 16 characters.  */
typedef char __attribute__ ((vector_size (16))) byte16;

/* Global pointer. */
char * foo;

byte16 test ()
{
return *(byte16 *)&foo[1];
}

现在,如果您在支持 vector 的 x86 上编译它:

$  gcc -O3 -march=native -mtune=native   a.c

您将获得以下程序集进行测试:

test:
movq foo(%rip), %rax
vmovdqa 1(%rax), %xmm0
ret

请注意,移动是对齐的,这当然是错误的。现在,如果你将这个函数内联到 main 中,你将得到如下内容:

int main ()
{
foo = __builtin_malloc (22);
byte16 x = *(byte16 *)&foo[1];
return x[0];
}

你会没事的,你会得到未对齐的指令。这是一种错误,在编译器中没有很好的修复,因为它需要通过添加新数据结构等进行过程间优化。

问题的根源在于编译器假定 vector 类型是对齐的,因此当您取消引用对齐 vector 类型的数组时,您可以使用对齐移动。作为 GCC 中问题的解决方法,可以定义一个未对齐的 vector 类型,例如:

typedef char __attribute__ ((vector_size (16),aligned (1))) unaligned_byte16;

并用它来取消引用未对齐的内存。

我不确定您在设置中是否确实遇到了这个问题,但我建议您通过检查编译器的程序集输出来检查这一点。

关于c - 从内存加载 vector 的更好方法。 (铛),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18199605/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com