php网站开发第三章,WordPress留言板插件使用,网站建设网上消费算在年费,宁波新闻1. 引言
以下是《riscv-v-spec-1.0.pdf》文档的关键内容#xff1a; 这是一份关于向量扩展的详细技术文档#xff0c;内容覆盖了向量指令集的多个关键方面#xff0c;如向量寄存器状态映射、向量指令格式、向量加载和存储操作、向量内存对齐约束、向量内存一致性模型、向量… 1. 引言
以下是《riscv-v-spec-1.0.pdf》文档的关键内容 这是一份关于向量扩展的详细技术文档内容覆盖了向量指令集的多个关键方面如向量寄存器状态映射、向量指令格式、向量加载和存储操作、向量内存对齐约束、向量内存一致性模型、向量算术指令格式、向量整数和浮点算术指令、向量归约操作、向量掩码指令、向量置换指令、异常处理以及标准向量扩展等。 首先文档定义了向量元素和向量寄存器状态之间的映射关系并阐述了向量指令的格式。在此基础上提出了配置设置指令如vsetvl、ivsetiv和vlsetvl用于设定向量长度VL和向量对齐长度AVL。 接着文档详细说明了向量加载和存储操作以及向量内存对齐和一致性模型。这些模型确保了向量操作的高效性和准确性。 然后文档介绍了向量算术指令格式包括向量整数、固定点和浮点算术指令。这些指令支持广泛的数学运算为高性能计算提供了强大的支持。 此外文档还涉及向量归约操作、掩码指令和置换指令这些指令增强了向量操作的灵活性和功能性。 最后文档讨论了异常处理机制并列举了标准向量扩展指令列表。这些扩展指令为向量处理器提供了丰富的功能集使其能够适应不同的应用场景和性能需求。 综上所述这份文档为向量指令集的设计和实现提供了全面的指导和参考有助于开发者更好地理解和利用向量处理器的能力。
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(一)-向量扩展编程模型-CSDN博客
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(二)-向量元素到向量寄存器状态的映射-CSDN博客【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(三)-向量指令格式-CSDN博客
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(四)- 配置和设置指令(vsetvli/vsetivli/vsetvl)-CSDN博客
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(五)- 向量加载和存储-CSDN博客
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(六)- 向量内存一致性模型-CSDN博客
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(七)- 向量算术指令格式-CSDN博客
【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(八)- 向量整数算术指令-CSDN博客
11. 向量整数算术指令
提供了一组向量整数算术指令。除非另有说明否则整数操作会在溢出时环绕。
11.1 向量整数加法和减法
提供了向量整数加法和减法。对于向量-标量形式还提供了反向减法指令。 # Integer adds.
vadd.vv vd, vs2, vs1, vm # Vector-vector
vadd.vx vd, vs2, rs1, vm # vector-scalar
vadd.vi vd, vs2, imm, vm # vector-immediate# Integer subtract
vsub.vv vd, vs2, vs1, vm # Vector-vector
vsub.vx vd, vs2, rs1, vm # vector-scalar # Integer reverse subtract
vrsub.vx vd, vs2, rs1, vm # vd[i] x[rs1] - vs2[i]
vrsub.vi vd, vs2, imm, vm # vd[i] imm - vs2[i]注意可以使用反向减法指令和x0的标量操作数对整数值向量求反。提供了一个汇编伪指令vneg.v vd, vs2 vrsub.vx vd, vs2, x0。
11.2 扩展向量加法和减法
根据较窄的源操作数在形成双倍宽度和之前是否首先进行符号扩展或零扩展提供了有符号和无符号两种扩展的加/减指令。 # Widening unsigned integer add/subtract, 2*SEW
vwaddu.vv vd, vs2, vs1, vm # vector-vector
vwaddu.vx vd, vs2, rs1, vm # vector-scalar
vwsubu.vv vd, vs2, vs1, vm # vector-vector
vwsubu.vx vd, vs2, rs1, vm # vector-scalar SEW /- SEW
# Widening signed integer add/subtract, 2*SEW
vwadd.vv vd, vs2, vs1, vm # vector-vector
vwadd.vx vd, vs2, rs1, vm # vector-scalar
vwsub.vv vd, vs2, vs1, vm # vector-vector
vwsub.vx vd, vs2, rs1, vm # vector-scalar SEW /- SEW
# Widening unsigned integer add/subtract, 2*SEW
vwaddu.wv vd, vs2, vs1, vm # vector-vector
vwaddu.wx vd, vs2, rs1, vm # vector-scalar
vwsubu.wv vd, vs2, vs1, vm # vector-vector
vwsubu.wx vd, vs2, rs1, vm # vector-scalar 2*SEW /- SEW
# Widening signed integer add/subtract, 2*SEW
vwadd.wv vd, vs2, vs1, vm # vector-vector
vwadd.wx vd, vs2, rs1, vm # vector-scalar
vwsub.wv vd, vs2, vs1, vm # vector-vector
vwsub.wx vd, vs2, rs1, vm # vector-scalar 2*SEW /- SEW可以使用带有x0标量操作数的扩展加法指令将整数值的宽度加倍。提供了汇编伪指令vwcvt.x.x.v vd, vs, vm vwadd.vx vd, vs, x0, vm和vwcvtu.x.x.v vd, vs, vm vwaddu.vx vd, vs, x0, vm。
11.3 向量整数扩展指令
向量整数扩展指令将源向量整数操作数其EEW小于SEW进行零扩展或符号扩展以填充目标中的SEW大小元素。源的EEW是SEW的1/2、1/4或1/8而源的EMUL为(EEW/SEW)*LMUL。目标的EEW等于SEWEMUL等于LMUL。 vzext.vf2 vd, vs2, vm # Zero-extend SEW/2 source to SEW destination
vsext.vf2 vd, vs2, vm # Sign-extend SEW/2 source to SEW destination
vzext.vf4 vd, vs2, vm # Zero-extend SEW/4 source to SEW destination
vsext.vf4 vd, vs2, vm # Sign-extend SEW/4 source to SEW destination
vzext.vf8 vd, vs2, vm # Zero-extend SEW/8 source to SEW destination
vsext.vf8 vd, vs2, vm # Sign-extend SEW/8 source to SEW destination如果源EEW不是受支持的宽度或者源EMUL低于合法的最小LMUL则该指令编码将被保留。
标准向量加载指令访问与目标寄存器元素大小相同的内存值。一些应用程序代码需要在更宽的元素中对一系列操作数宽度进行操作例如从内存中加载一个字节并将其添加到八个字节的元素中。为了避免通过数据类型字节、字、半字以及有符号/无符号变体的数量来提供向量加载指令的交叉乘积我们改为添加明确的扩展指令如果缺少适当的扩展算术指令则可以使用这些扩展指令。
11.4 向量整数进位加/借位减指令
为了支持多字整数算术提供了对进位位进行操作的指令。对于每个操作加法或减法都提供了两条指令一条用于提供结果SEW宽度另一条用于生成进位输出编码为掩码布尔值的单一位。
进位输入和输出使用掩码寄存器布局表示如“掩码寄存器布局”部分所述。由于编码限制进位输入必须来自隐式v0寄存器但进位输出可以写入任何遵循源/目标重叠限制的向量寄存器。
vadc和vsbc将源操作数与进位或借位相加或相减并将结果写入向量寄存器vd。这些指令被编码为掩码指令vm0但它们在所有主体元素上运行并写回结果。
对应于未屏蔽版本vm1的编码被保留。
vmadc和vmsbc将源操作数相加或相减如果屏蔽vm0则选择性地加上进位或减去借位并将结果写回掩码寄存器vd。如果未屏蔽vm1则没有进位或借位。这些指令即使在屏蔽的情况下也在所有主体元素上运行并写回结果。因为这些指令产生掩码值所以它们总是以与尾部无关的策略运行。 # Produce sum with carry .
# vd[i] vs2[i] vs1[i] v0.mask[i]
vadc.vvm vd, vs2, vs1, v0 # Vector-vector
# vd[i] vs2[i] x[rs1] v0.mask[i]
vadc.vxm vd, vs2, rs1, v0 # Vector-scalar
# vd[i] vs2[i] imm v0.mask[i]
vadc.vim vd, vs2, imm, v0 # Vector-immediate
# Produce carry out in mask register format
# vd.mask[i] carry_out(vs2[i] vs1[i] v0.mask[i])
vmadc.vvm vd, vs2, vs1, v0 # Vector-vector
# vd.mask[i] carry_out(vs2[i] x[rs1] v0.mask[i])
vmadc.vxm vd, vs2, rs1, v0 # Vector-scalar
# vd.mask[i] carry_out(vs2[i] imm v0.mask[i])
vmadc.vim vd, vs2, imm, v0 # Vector-immediate
# vd.mask[i] carry_out(vs2[i] vs1[i])
vmadc.vv vd, vs2, vs1 # Vector-vector, no carry-in
# vd.mask[i] carry_out(vs2[i] x[rs1])
vmadc.vx vd, vs2, rs1 # Vector-scalar, no carry-in
# vd.mask[i] carry_out(vs2[i] imm)
vmadc.vi vd, vs2, imm # Vector-immediate, no carry-in由于实现进位传播需要执行两个输入不变的指令因此具有破坏性的累加将需要额外的移动才能获得正确的结果。 # Example multi-word arithmetic sequence, accumulating into v4
vmadc.vvm v1, v4, v8, v0 # Get carry into temp register v1
vadc.vvm v4, v4, v8, v0 # Calc new sum
vmmv.m v0, v1 # Move temp carry into v0 for next word带借位的减法指令vsbc执行与长字算术减法相当的功能。没有带立即数的减法指令。 # Produce difference with borrow.
# vd[i] vs2[i] - vs1[i] - v0.mask[i]
vsbc.vvm vd, vs2, vs1, v0 # Vector-vector
# vd[i] vs2[i] - x[rs1] - v0.mask[i]
vsbc.vxm vd, vs2, rs1, v0 # Vector-scalar
# Produce borrow out in mask register format
# vd.mask[i] borrow_out(vs2[i] - vs1[i] - v0.mask[i])
vmsbc.vvm vd, vs2, vs1, v0 # Vector-vector
# vd.mask[i] borrow_out(vs2[i] - x[rs1] - v0.mask[i])
vmsbc.vxm vd, vs2, rs1, v0 # Vector-scalar
# vd.mask[i] borrow_out(vs2[i] - vs1[i])
vmsbc.vv vd, vs2, vs1 # Vector-vector, no borrow-in
# vd.mask[i] borrow_out(vs2[i] - x[rs1])
vmsbc.vx vd, vs2, rs1 # Vector-scalar, no borrow-in对于vmsbc如果差异在截断之前为负则借位被定义为1。
对于vadc和vsbc如果目标向量寄存器是v0则指令编码将被保留。
注意此约束对应于覆盖掩码寄存器的掩码向量操作的约束。
11.5 位逻辑运算 # Bitwise logical operations.
vand.vv vd, vs2, vs1, vm # vector-vector
vand.vx vd, vs2, rs1, vm # vector-scalar
vand.vi vd, vs2, imm, vm # Vector-immediatevor.vv vd, vs2, vs1, vm # Vector-vector
vor.vx vd, vs2, rs1, vm # vector-scalar
vor.vi vd, vs2, imm, vm # vector-immediatevxor.vv vd, vs2, vs1, vm # Vector-vector
vxor.vx vd, vs2, rs1, vm # vector-scalar
vxor.vi vd, vs2, imm, vm # vector-immediate注当立即数为-1时vxor指令的标量立即数形式提供了按位非操作。这作为汇编伪指令vnot.v vd,vs,vm vxor.vi vd,vs,-1,vm提供。
11.6 向量移位指令
提供了一套完整的向量移位指令包括逻辑左移(sll)以及逻辑右移零扩展srl和算术右移符号扩展sra。要移位的数据位于由vs2指定的向量寄存器组中并且移位量值可以来自向量寄存器组vs1、标量整数寄存器rs1或零扩展的5位立即数。仅使用移位量值的低lg2(SEW)位来控制移位量。 # Bit shift operations
vsll.vv vd, vs2, vs1, vm # Vector-vector
vsll.vx vd, vs2, rs1, vm # vector-scalar
vsll.vi vd, vs2, uimm, vm # vector-immediatevs rl.vv vd, vs2, vs1, vm # Vector-vector
vs rl.vx vd, vs2, rs1, vm # vector-scalar
vs rl.vi vd, vs2, uimm, vm # vector-immediate
vs ra.vv vd, vs2, vs1, vm # Vector-vector
vs ra.vx vd, vs2, rs1, vm # vector-scalar
vs ra.vi vd, vs2, uimm, vm # vector-immediate 11.7 向量右移指令
缩小右移从较宽的操作数中提取一个较小的字段并具有零扩展srl和符号扩展sra两种形式。移位量可以来自向量寄存器组、标量x寄存器或零扩展的5位立即数。移位量值的低lg2(2*SEW)位被使用例如对于SEW64位到SEW32位的缩小操作使用低6位。 # Narrowing shift right logical, SEW (2*SEW) SEW
vns rl.wv vd, vs2, vs1, vm # vector-vector
vns rl.wx vd, vs2, rs1, vm # vector-scalar
vns rl.wi vd, vs2, uimm, vm # vector-immediate
# Narrowing shift right arithmetic, SEW (2*SEW) SEW
vnsra.wv vd, vs2, vs1, vm # vector-vector
vnsra.wx vd, vs2, rs1, vm # vector-scalar
vnsra.wi vd, vs2, uimm, vm # vector-immediate 注未来的扩展可能会增加对目标宽度为源宽度1/4的缩小版本的支持。
通过使用带有x0标量操作数的缩小整数移位指令可以将整数值的宽度减半。提供了一个汇编伪指令vncvt.x.x.w vd,vs,vm vnsrl.wx vd,vs,x0,vm。
11.8 整数比较指令
以下整数比较指令在比较结果为真时将1写入目标掩码寄存器元素否则写入0。目标掩码向量始终保存在单个向量寄存器中元素的布局如“掩码寄存器布局”部分所述。目标掩码向量寄存器可能与源向量掩码寄存器v0相同。 # Set if equal
vmseq.vv vd, vs2, vs1, vm # Vector-vector
vmseq.vx vd, vs2, rs1, vm # vector-scalar
vmseq.vi vd, vs2, imm, vm # vector-immediate
# Set if not equal
vmsne.vv vd, vs2, vs1, vm # Vector-vector
vmsne.vx vd, vs2, rs1, vm # vector-scalar
vmsne.vi vd, vs2, imm, vm # vector-immediate
# Set if less than, unsigned
vmsltu.vv vd, vs2, vs1, vm # Vector-vector
vmsltu.vx vd, vs2, rs1, vm # Vector-scalar
# Set if less than, signed
vmslt.vv vd, vs2, vs1, vm # Vector-vector
vmslt.vx vd, vs2, rs1, vm # vector-scalar
# Set if less than or equal, unsigned
vmsleu.vv vd, vs2, vs1, vm # Vector-vector
vmsleu.vx vd, vs2, rs1, vm # vector-scalar
vmsleu.vi vd, vs2, imm, vm # Vector-immediate
# Set if less than or equal, signed
vmsle.vv vd, vs2, vs1, vm # Vector-vector
vmsle.vx vd, vs2, rs1, vm # vector-scalar
vmsle.vi vd, vs2, imm, vm # vector-immediate
# Set if greater than, unsigned
vmsgtu.vx vd, vs2, rs1, vm # Vector-scalar
vmsgtu.vi vd, vs2, imm, vm # Vector-immediate
# Set if greater than, signed
vmsgt.vx vd, vs2, rs1, vm # Vector-scalar
vmsgt.vi vd, vs2, imm, vm # Vector-immediate
# Following two instructions are not provided directly
# Set if greater than or equal, unsigned
# vmsgeu.vx vd, vs2, rs1, vm # Vector-scalar
# Set if greater than or equal, signed
# vmsge.vx vd, vs2, rs1, vm # Vector-scalar下表显示了所有比较如何在原生机器代码中实现。 Comparison Assembler Mapping Assembler Pseudoinstruction
va vb vmslt{u}.vv vd, va, vb, vm
va vb vmsle{u}.vv vd, va, vb, vm
va vb vmslt{u}.vv vd, vb, va, vm vmsgt{u}.vv vd, va, vb, vm
va vb vmsle{u}.vv vd, vb, va, vm vmsge{u}.vv vd, va, vb, vm
va x vmslt{u}.vx vd, va, x, vm
va x vmsle{u}.vx vd, va, x, vm
va x vmsgt{u}.vx vd, va, x, vm
va x see below
va i vmsle{u}.vi vd, va, i-1, vm vmslt{u}.vi vd, va, i, vm
va i vmsle{u}.vi vd, va, i, vm
va i vmsgt{u}.vi vd, va, i, vm
va i vmsgt{u}.vi vd, va, i-1, vm vmsge{u}.vi vd, va, i, vm
va, vb vector register groups
x scalar integer register
i immediate 注意没有提供vmslt{u}.vi的立即数形式因为可以通过将立即数值减1并使用vmsle{u}.vi变体来替代。vmsle.vi的范围是-16到15这使得vmslt.vi的有效范围为-15到16。vmsleu.vi的范围是0到15从而使得vmsltu.vi的有效范围为1到16注意vmsltu.vi的立即数为0时是没有用的因为它总是返回假。
由于5位向量立即数总是进行符号扩展因此当设置simm5立即数的高位时vmsleu.vi还支持2^(SEW-16)到2^(SEW-1)范围内的无符号立即数值允许相应的vmsltu.vi与2^(SEW-15)到2^SEW范围内的无符号立即数进行比较。请注意vmsltu.vi的立即数为2^SEW时是无用的因为它总是返回真。
类似地没有提供vmsge{u}.vi而是使用立即数减1的vmsgt{u}.vi来实现比较。这产生的有效vmsge.vi范围是-15到16而有效的vmsgeu.vi范围是1到16注意vmsgeu.vi的立即数为0时是无用的因为它总是返回真。
注意提供寄存器标量和立即数的vmsgt形式是为了允许单个比较指令提供正确的掩码值极性而无需使用额外的掩码逻辑指令。
为了减少编码空间没有直接提供vmsge{u}.vx形式因此对于va x的情况需要特殊处理。
注意vmsge{u}.vx可能以非正交方式在未使用的vmslt{u}的OPIVI变体下进行编码。然而这些将是OPIVI中唯一使用标量x寄存器的指令。或者可以使用另外两个funct6编码但这些编码的操作数格式写入掩码寄存器将与同一组8个funct6编码中的其他编码不同。当前的建议是省略这些指令并在需要时按如下所述进行合成。
当知道不会使x中的表示形式下溢时可以通过将x的值减小1并使用vmsgt{u}.vx指令来合成vmsge{u}.vx操作。 Sequences to synthesize vmsge{u}.vx instruction
va x, x minimum
addi t0, x, -1; vmsgt{u}.vx vd, va, t0, vm 上述序列通常将是最有效的实现方式但是在x的范围未知的情况下可以提供汇编伪指令。 unmasked va x
pseudoinstruction: vmsge{u}.vx vd, va, x
expansion: vmslt{u}.vx vd, va, x; vmnand.mm vd, vd, vd
masked va x, vd ! v0
pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t
expansion: vmslt{u}.vx vd, va, x, v0.t; vmxor.mm vd, vd, v0
masked va x, vd v0
pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t, vt
expansion: vmslt{u}.vx vt, va, x; vmandn.mm vd, vd, vt
masked va x, any vd
pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t, vt
expansion: vmslt{u}.vx vt, va, x; vmandn.mm vt, v0, vt; vmandn.mm vd, vd, v0; vmor.mm vd, vt, vd
The vt argument to the pseudoinstruction must name a temporary vector register that is
not same as vd and which will be clobbered by the pseudoinstruction例如在不受掩码干扰的策略下有效地在掩码中进行与比较。 # (a b) (b c) in two instructions when mask-undisturbed
vmslt.vv v0, va, vb # All body elements written
vmslt.vv v0, vb, vc, v0.t # Only update at set mask 比较写掩码寄存器因此总是在尾部不可知策略下操作。
11.9 向量整数的最小值和最大值指令
支持有符号和无符号整数的最小值和最大值指令。 # Unsigned minimum
vminu.vv vd, vs2, vs1, vm # Vector-vector
vminu.vx vd, vs2, rs1, vm # vector-scalar
# Signed minimum
vmin.vv vd, vs2, vs1, vm # Vector-vector
vmin.vx vd, vs2, rs1, vm # vector-scalar
# Unsigned maximum
vmaxu.vv vd, vs2, vs1, vm # Vector-vector
vmaxu.vx vd, vs2, rs1, vm # vector-scalar
# Signed maximum
vmax.vv vd, vs2, vs1, vm # Vector-vector
vmax.vx vd, vs2, rs1, vm # vector-scalar 11.10 向量单宽度乘法指令
单宽度乘法指令执行SEW位SEW位乘法以生成2SEW位乘积然后在SEW位宽的目标位置返回乘积的一半。mul版本将乘积的低字写入目标寄存器而mulh版本将乘积的高字写入目标寄存器。 # Signed multiply, returning low bits of product
vmul.vv vd, vs2, vs1, vm # Vector-vector
vmul.vx vd, vs2, rs1, vm # vector-scalar
# Signed multiply, returning high bits of product
vmulh.vv vd, vs2, vs1, vm # Vector-vector
vmulh.vx vd, vs2, rs1, vm # vector-scalar
# Unsigned multiply, returning high bits of product
vmulhu.vv vd, vs2, vs1, vm # Vector-vector
vmulhu.vx vd, vs2, rs1, vm # vector-scalar
# Signed(vs2)-Unsigned multiply, returning high bits of product
vmulhsu.vv vd, vs2, vs1, vm # Vector-vector
vmulhsu.vx vd, vs2, rs1, vm # vector-scalar注意没有vmulhus.vx操作码来返回无符号向量*有符号标量乘积的高半部分。可以将标量扩展为向量然后使用vmulhsu.vv。
当前的vmulh*操作码执行简单的分数乘法但没有选项来对结果进行缩放、四舍五入和/或饱和处理。未来可能的扩展可以考虑vmulh、vmulhu、vmulhsu的变体这些变体在丢弃乘积的低半部分时使用vx rm舍入模式。在这些情况下不可能发生溢出。
11.11 向量除法和取余指令
除法和取余指令等同于RISC-V标准标量整数乘/除指令对于极端输入结果相同。 # Unsigned divide.
vdivu.vv vd, vs2, vs1, vm # Vector-vector
vdivu.vx vd, vs2, rs1, vm # vector-scalar
# Signed divide
vdiv.vv vd, vs2, vs1, vm # Vector-vector
vdiv.vx vd, vs2, rs1, vm # vector-scalar
# Unsigned remainder
vremu.vv vd, vs2, vs1, vm # Vector-vector
vremu.vx vd, vs2, rs1, vm # vector-scalar
# Signed remainder
vrem.vv vd, vs2, vs1, vm # Vector-vector
vrem.vx vd, vs2, rs1, vm # vector-scalar 注意关于是否包含整数除法和取余功能的决定是有争议的。支持这一决定的论点是如果没有标准指令软件将不得不选择某种算法来执行该操作而这可能在某些微体系结构上表现不佳与其他体系相比会处于劣势。
没有执行“标量除以向量”操作的指令。
11.12 向量扩展整数乘法指令
扩展整数乘法指令从SEW位SEW位乘法中返回完整的2SEW位乘积。 # Widening signed-integer multiply
vwmul.vv vd, vs2, vs1, vm # vector-vector
vwmul.vx vd, vs2, rs1, vm # vector-scalar
# Widening unsigned-integer multiply
vwmulu.vv vd, vs2, vs1, vm # vector-vector
vwmulu.vx vd, vs2, rs1, vm # vector-scalar
# Widening signed(vs2)-unsigned integer multiply
vwmulsu.vv vd, vs2, vs1, vm # vector-vector
vwmulsu.vx vd, vs2, rs1, vm # vector-scalar11.13 向量整数乘加指令
整数乘法-加法指令具有破坏性并提供两种形式一种是覆盖加数或被减数的vmacc, vnmsac另一种是覆盖第一个乘数的vmadd, vnmsub。
乘积的低半部分与第三个操作数相加或相减。
注意sac应读作“从累加器中减去”。操作码vnmsac是为了与不幸的是这有点违反直觉浮点fnmsub指令定义相匹配。vnmsub操作码也类似。
# Integer multiply-add, overwrite addend
vmacc.vv vd, vs1, vs2, vm # vd[i] (vs1[i] * vs2[i]) vd[i]
vmacc.vx vd, rs1, vs2, vm # vd[i] (x[rs1] * vs2[i]) vd[i]
# Integer multiply-sub, overwrite minuend
vnmsac.vv vd, vs1, vs2, vm # vd[i] -(vs1[i] * vs2[i]) vd[i]
vnmsac.vx vd, rs1, vs2, vm # vd[i] -(x[rs1] * vs2[i]) vd[i]
# Integer multiply-add, overwrite multiplicand
vmadd.vv vd, vs1, vs2, vm # vd[i] (vs1[i] * vd[i]) vs2[i]
vmadd.vx vd, rs1, vs2, vm # vd[i] (x[rs1] * vd[i]) vs2[i]
# Integer multiply-sub, overwrite multiplicand
vnmsub.vv vd, vs1, vs2, vm # vd[i] -(vs1[i] * vd[i]) vs2[i]
vnmsub.vx vd, rs1, vs2, vm # vd[i] -(x[rs1] * vd[i]) vs2[i]11.14 向量扩展整数乘法-加法指令
扩展整数乘法-加法指令将一个SEW位SEW位乘法的完整2SEW位乘积加到一个2SEW位的值上并生成一个2SEW位的结果。支持有符号和无符号乘法操作数的所有组合。
# Widening unsigned-integer multiply-add, overwrite addend
vwmaccu.vv vd, vs1, vs2, vm # vd[i] (vs1[i] * vs2[i]) vd[i]
vwmaccu.vx vd, rs1, vs2, vm # vd[i] (x[rs1] * vs2[i]) vd[i]
# Widening signed-integer multiply-add, overwrite addend
vwmacc.vv vd, vs1, vs2, vm # vd[i] (vs1[i] * vs2[i]) vd[i]
vwmacc.vx vd, rs1, vs2, vm # vd[i] (x[rs1] * vs2[i]) vd[i]
# Widening signed-unsigned-integer multiply-add, overwrite addend
vwmaccsu.vv vd, vs1, vs2, vm # vd[i] (signed(vs1[i]) * unsigned(vs2[i])) vd[i]
vwmaccsu.vx vd, rs1, vs2, vm # vd[i] (signed(x[rs1]) * unsigned(vs2[i])) vd[i]
# Widening unsigned-signed-integer multiply-add, overwrite addend
vwmaccus.vx vd, rs1, vs2, vm # vd[i] (unsigned(x[rs1]) * signed(vs2[i])) vd[i]11.15 向量整数合并指令
向量整数合并指令基于掩码组合两个源操作数。与常规算术指令不同合并操作对所有主体元素即从vstart到当前向量长度vl的元素集进行操作。
vmerge指令被编码为带掩码的指令vm0。这些指令按以下方式组合两个源。在掩码值为零的元素处将第一个操作数复制到目标元素否则将第二个操作数复制到目标元素。第一个操作数始终是由vs2指定的向量寄存器组。第二个操作数是由vs1指定的向量寄存器组或由rs1指定的标量x寄存器或是一个5位符号扩展的立即数。
vmerge.vvm vd, vs2, vs1, v0 # vd[i] v0.mask[i] ? vs1[i] : vs2[i]
vmerge.vxm vd, vs2, rs1, v0 # vd[i] v0.mask[i] ? x[rs1] : vs2[i]
vmerge.vim vd, vs2, imm, v0 # vd[i] v0.mask[i] ? imm : vs2[i]11.6 向量整数移动指令
向量整数移动指令将一个源操作数复制到向量寄存器组。vmv.v.v变体复制一个向量寄存器组而vmv.v.x和vmv.v.i变体将标量寄存器或立即数分散到目标向量寄存器组的所有活动元素中。这些指令被编码为未屏蔽的指令vm1。第一个操作数指定器vs2必须包含v0vs2中的任何其他向量寄存器号都是保留的。
vmv.v.v vd, vs1 # vd[i] vs1[i]
vmv.v.x vd, rs1 # vd[i] x[rs1]
vmv.v.i vd, imm # vd[i] imm注意
可以使用序列vmv.v.i vd, 0; vmerge.vim vd, vd, 1, v0将掩码值加宽为SEW宽度元素。
向量整数移动指令与向量合并指令共享编码但vm1且vs2v0。
形式为vmv.v.v vd, vd的指令它使主体元素保持不变可以用来表示该寄存器接下来将与等于SEW的EEW一起使用。
注意
根据EEW在内部重新组织数据的实现可以根据SEW对内部表示进行混洗。不在内部重新组织数据的实现可以动态地省略此指令并将其视为NOP。
vmv.v.v vd.vd指令不是RISC-V HINT因为在某些实现上尾部不可知的设置可能会导致体系结构状态发生变化。