VPCMPB 的操作数
Operands for VPCMPB
我在 Intel intrinsics guide 上看到可以不用 immediate 使用 vpcmpb
来达到相等比较的效果:https://software.intel.com/sites/landingpage/IntrinsicsGuide/#techs=AVX_512&expand=6816,804,804,4867,351,804,4222,914&text=vpcmpb
我尝试编写以下汇编指令:vpcmpb %zmm30, %zmm0, %k1
(g++语法),比较等于zmm30
和zmm0
,将结果写入k1
。但是,汇编程序抱怨操作数的数量错误。这是怎么回事?
执行此操作有 3 个有效的机器操作码:
vpcmpeqb k, zmm, zmm
(EVEX form of the MMX/SSE2/AVX2 66 0F 74
opcode 用于 [v]pcmpeq [xy]mm, [xy]mm
。这些从未立即执行,只有 eq
和带符号的 gt
谓词可用作不同的操作码)
vpcmpb
or vpcmpub
立即 0
(只有 EVEX 形式的新指令,EVEX.512.66.0F3A.W0 3F
或 3E
)。
在 asm source 中,assemblers 允许您使用 vpcmpleb k, zmm, zmm
作为更有意义的方式来编写 vpcmpb k, z, z, 2
,如推荐的在 Intel 的第 2 卷手册中的 Table 5-17 中。即谓词作为助记符的一部分,暗示直接。
table 包含一行 VPCMPEQ* reg1, reg2, reg3
-> VPCMP* reg1, reg2, reg3, 0
,但较短的非立即形式在实际 assemble 中优先于 vpcmpeqb k, zmm, zmm
rs.
NASM 源与 objdump -S -drwC -Mintel
反汇编混合。 (用 gas .intel_syntax noprefix
组装的结果相同):
vpcmpeqb k1, zmm0, zmm1
0: 62 f1 7d 48 74 c9 vpcmpeqb k1,zmm0,zmm1 # 74 opcode
vpcmpb k1, zmm0, zmm1, 0
6: 62 f3 7d 48 3f c9 00 vpcmpeqb k1,zmm0,zmm1 # 3f opcode
vpcmpequb k1, zmm0, zmm1
d: 62 f3 7d 48 3e c9 00 vpcmpequb k1,zmm0,zmm1 # 3e opcode
vpcmpub k1, zmm0, zmm1, 0
14: 62 f3 7d 48 3e c9 00 vpcmpequb k1,zmm0,zmm1 # 3e opcode
有趣的是,NASM/GAS将assemble如vpcmpb k1, zmm0, zmm1, 0
所写,以立即数的形式出现。但是 objdump
会将 assemble 返回到 vpcmpeqb k1,zmm0,zmm1
,与非立即操作码相同,因此这是 disassemble/reassemble 往返会改变机器的情况之一代码。 (当然不是指令的架构效果)
NASM / GAS 不会为您将 vpcmpequb
优化为 vpcmpeqb
,因此在比较整数相等时始终避免使用无符号版本。
内在函数指南中存在错误
如果您使用 asm 编写,请查看 asm 参考手册(HTML 摘录 https://www.felixcloutier.com/x86/vpcmpb:vpcmpub 或从中删除的英特尔原始 PDF),而不是 Intrinsics 指南。尤其是当你 运行 对某些东西所说的和 and/or CPU 似乎在做什么的工具之间存在任何神秘或分歧时!
众所周知,内在函数指南存在错误(尽管人们在 Intel 的论坛上报告这些错误后它们确实得到了修复)。特别有可能在对使用 C/C++ 内在函数的正确性不重要的部分看到错误。
Intel 的 asm 手册也不是不可能有错误,但不会像遗漏已经发布的指令集的指令的整个机器操作码形式那样严重。
如果没有明确的立即数,在真正的 asm 源代码中或作为机器代码的描述,vpcmpb k, zmm, zmm
永远不会有效,所以是的,这绝对是内在函数指南中的一个错误。
具有反向操作数列表的 vpcmpeqb %zmm, %zmm, %k
asm 语法和 $immediate
是“AT&T 语法”。它恰好是 .s
/ .S
文件默认使用的一种 GAS,但您可以使用 .intel_syntax noprefix
.
对单个指令使用内联汇编通常没有意义 - 编译器通常可以很好地处理内在函数,尽管对于 AVX-512 掩码内容可能并非总是如此。
我在 Intel intrinsics guide 上看到可以不用 immediate 使用 vpcmpb
来达到相等比较的效果:https://software.intel.com/sites/landingpage/IntrinsicsGuide/#techs=AVX_512&expand=6816,804,804,4867,351,804,4222,914&text=vpcmpb
我尝试编写以下汇编指令:vpcmpb %zmm30, %zmm0, %k1
(g++语法),比较等于zmm30
和zmm0
,将结果写入k1
。但是,汇编程序抱怨操作数的数量错误。这是怎么回事?
执行此操作有 3 个有效的机器操作码:
vpcmpeqb k, zmm, zmm
(EVEX form of the MMX/SSE2/AVX266 0F 74
opcode 用于[v]pcmpeq [xy]mm, [xy]mm
。这些从未立即执行,只有eq
和带符号的gt
谓词可用作不同的操作码)vpcmpb
orvpcmpub
立即0
(只有 EVEX 形式的新指令,EVEX.512.66.0F3A.W0 3F
或3E
)。
在 asm source 中,assemblers 允许您使用 vpcmpleb k, zmm, zmm
作为更有意义的方式来编写 vpcmpb k, z, z, 2
,如推荐的在 Intel 的第 2 卷手册中的 Table 5-17 中。即谓词作为助记符的一部分,暗示直接。
table 包含一行 VPCMPEQ* reg1, reg2, reg3
-> VPCMP* reg1, reg2, reg3, 0
,但较短的非立即形式在实际 assemble 中优先于 vpcmpeqb k, zmm, zmm
rs.
NASM 源与 objdump -S -drwC -Mintel
反汇编混合。 (用 gas .intel_syntax noprefix
组装的结果相同):
vpcmpeqb k1, zmm0, zmm1
0: 62 f1 7d 48 74 c9 vpcmpeqb k1,zmm0,zmm1 # 74 opcode
vpcmpb k1, zmm0, zmm1, 0
6: 62 f3 7d 48 3f c9 00 vpcmpeqb k1,zmm0,zmm1 # 3f opcode
vpcmpequb k1, zmm0, zmm1
d: 62 f3 7d 48 3e c9 00 vpcmpequb k1,zmm0,zmm1 # 3e opcode
vpcmpub k1, zmm0, zmm1, 0
14: 62 f3 7d 48 3e c9 00 vpcmpequb k1,zmm0,zmm1 # 3e opcode
有趣的是,NASM/GAS将assemble如vpcmpb k1, zmm0, zmm1, 0
所写,以立即数的形式出现。但是 objdump
会将 assemble 返回到 vpcmpeqb k1,zmm0,zmm1
,与非立即操作码相同,因此这是 disassemble/reassemble 往返会改变机器的情况之一代码。 (当然不是指令的架构效果)
NASM / GAS 不会为您将 vpcmpequb
优化为 vpcmpeqb
,因此在比较整数相等时始终避免使用无符号版本。
内在函数指南中存在错误
如果您使用 asm 编写,请查看 asm 参考手册(HTML 摘录 https://www.felixcloutier.com/x86/vpcmpb:vpcmpub 或从中删除的英特尔原始 PDF),而不是 Intrinsics 指南。尤其是当你 运行 对某些东西所说的和 and/or CPU 似乎在做什么的工具之间存在任何神秘或分歧时!
众所周知,内在函数指南存在错误(尽管人们在 Intel 的论坛上报告这些错误后它们确实得到了修复)。特别有可能在对使用 C/C++ 内在函数的正确性不重要的部分看到错误。
Intel 的 asm 手册也不是不可能有错误,但不会像遗漏已经发布的指令集的指令的整个机器操作码形式那样严重。
如果没有明确的立即数,在真正的 asm 源代码中或作为机器代码的描述,vpcmpb k, zmm, zmm
永远不会有效,所以是的,这绝对是内在函数指南中的一个错误。
具有反向操作数列表的 vpcmpeqb %zmm, %zmm, %k
asm 语法和 $immediate
是“AT&T 语法”。它恰好是 .s
/ .S
文件默认使用的一种 GAS,但您可以使用 .intel_syntax noprefix
.
对单个指令使用内联汇编通常没有意义 - 编译器通常可以很好地处理内在函数,尽管对于 AVX-512 掩码内容可能并非总是如此。