【问题标题】:invalid 'asm': nested assembly dialect alternatives无效的“asm”:嵌套的程序集方言替代方案
【发布时间】:2015-12-17 06:17:13
【问题描述】:

我正在尝试使用k1om-mpss-linux-gcc 编译器为 Xeon Phi 平台编写一些带有 KNC 指令的内联汇编代码。我想在我的代码中使用掩码寄存器来矢量化我的计算。这是我的代码:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/time.h>
#include <assert.h>
#include <stdint.h>

void* aligned_malloc(size_t size, size_t alignment) {

    uintptr_t r = (uintptr_t)malloc(size + --alignment + sizeof(uintptr_t));
    uintptr_t t = r + sizeof(uintptr_t);
    uintptr_t o =(t + alignment) & ~(uintptr_t)alignment;
    if (!r) return NULL;
    ((uintptr_t*)o)[-1] = r;
    return (void*)o;
}

int main(int argc, char* argv[])
{
    const int vectorSize = 16;
    int * n_arr = (int *) aligned_malloc(16 * sizeof(int),64);
    int * lenS_arr = (int *) aligned_malloc(16 * sizeof(int),64);
    int * tt_i = (int *) aligned_malloc(16 * sizeof(int),64);
    int * tt = (int *) aligned_malloc(16 * sizeof(int),64);
    int n = 5;
    int lenS = 16;
    int i;

    for(i=0; i< 16; i++){
        tt_i[i] = 1;
        n_arr[i] = n;
        lenS_arr[i] = lenS;
    }
    __asm__("vmovdqa32 %1,%%zmm0\n\t"
            "vmovdqa32 %2,%%zmm1\n\t"
            "vmovdqa32 %3,%%zmm2\n\t"
            "vpaddd %%zmm0,%%zmm1,%%zmm0\n\t"
            "vpcmpgtd %%zmm0,%%zmm2,%%k1\n\t"
            "vpsubd %%zmm2,%%zmm0,%%zmm0 {{%%k1}}\n\t"
            "vmovdqa32 %%zmm1,%0;"
            : "=m" (tt[0]) : "m" (tt_i[0]), "m" (n_arr[0]), "m" (lenS_arr[0]));
    for (i=0; i <16 ; i++)
    {
        printf("tt_i[%d] = %d --- tt[%d] = %d\n",i, tt_i[i], i, tt[i]);
    }

    return 0;
}

当我编译代码时,我得到了这个错误:

error: invalid 'asm': nested assembly dialect alternatives

与这条流水线有什么关系:

"vpsubd %%zmm2,%%zmm0,%%zmm0 {{%%k1}}\n\t"

对这个错误有什么想法吗?

【问题讨论】:

  • 不要忘记将 %zmm0,1 和 2 声明为已破坏。我猜还有 %k1。

标签: gcc assembly inline-assembly xeon-phi avx512


【解决方案1】:

尝试在内联 asm 中使用 %{%%k1%} 以将 {%k1} 放入实际的 asm 输出中。 {} need to be escaped.


通过谷歌搜索错误消息:nested assembly dialect alternatives 找到了一个关于 asm 方言替代方案的mailing list post,包括一个示例测试用例。

{} 在 GNU C 内联 asm 中已经有了一个特殊的含义:为不同的 ASM 方言提供替代方案。

使用{{%%k1}} 看起来像嵌套的替代方案,这是无效的。

测试用例/示例是:

int main (void) {
  int f = 0;
  asm ("{movl $42, %%eax | mov eax, 42}" : :);
  asm ("{movl $41, %0||mov %0, 43}" : "=r"(f));
  if (f != 42)
    abort ();

  return 0;
}

【讨论】:

  • 您还可以查看 gcc 的文档以了解 (asm)[gcc.gnu.org/onlinedocs/gcc/Extended-Asm.html#AssemblerTemplate)。
  • @DavidWohlferd:呃,好点子,当然它已经记录在案了。谢谢 :)。用解决方案更新了我的答案并确定了问题。
  • 实际上,直到最近才没有文档化。整个内联 asm 部分终于惹恼了准备对此采取行动的人。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-08-23
  • 1970-01-01
  • 2017-03-06
  • 2021-05-25
相关资源
最近更新 更多