From a4c0deb5ed86f7d66eee191f29e502cac78b2d3d Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 23 Feb 2025 01:12:19 +0000 Subject: [PATCH 01/23] start vset --- arch/inst/V/vsetivli.yaml | 18 +++++++- arch/inst/V/vsetvl.yaml | 88 ++++++++++++++++++++++++++++++++++++++- arch/inst/V/vsetvli.yaml | 18 +++++++- arch/isa/vec.idl | 50 ++++++++++++++++++++++ 4 files changed, 168 insertions(+), 6 deletions(-) create mode 100644 arch/isa/vec.idl diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index e45be1043c..6cb274516c 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -3,9 +3,11 @@ $schema: "inst_schema.json#" kind: instruction name: vsetivli -long_name: No synopsis available. +long_name: Set vector configuration (immediate immediate). description: | - No description available. + Vset (i,i) allows rapid configuration of the values in vl and vtype CSRs to match application + needs. The vsetvl instruction sets the vtype and vl CSRs based on the arguments, and writes + the new value of vl into rd. definedBy: V assembly: xd, imm encoding: @@ -24,7 +26,19 @@ access: vu: always data_independent_timing: false operation(): | + XReg state = vector_state(); + XReg VLMAX = state.log2_multiplier * VLEN * state.sew; + # todo: state.lmul_type + if (xs1 < VLMAX){ + CSR[vl] = uimm; + } else { + CSR[vl] = VLMAX; + } + + CSR[vtype] = zimm11; + X[rd] = CSR[vl]; + CSR[vstart] = 0; sail(): | { let VLEN_pow = get_vlen_pow(); diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index ca13695d80..457e3c815a 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -3,9 +3,11 @@ $schema: "inst_schema.json#" kind: instruction name: vsetvl -long_name: No synopsis available. +long_name: Set vector configuration (register register). description: | - No description available. + Vset (r,r) allows rapid configuration of the values in vl and vtype CSRs to match application + needs. The vsetvl instruction sets the vtype and vl CSRs based on the contents of the argument + registers rs1 and rs2, and writes the new value of vl into rd. definedBy: V assembly: xs2, xs1, xd encoding: @@ -24,3 +26,85 @@ access: vu: always data_independent_timing: false operation(): | + XReg state = vector_state(); + XReg VLMAX = state.log2_multiplier * VLEN * state.sew; + # todo: state.lmul_type + + if (xs1 < VLMAX){ + CSR[vl] = X[rs1]; + } else { + CSR[vl] = VLMAX; + } + + CSR[vtype] = X[rs2]; + X[rd] = CSR[vl]; + CSR[vstart] = 0; +sail(): | + { + let VLEN_pow = get_vlen_pow(); + let ELEN_pow = get_elen_pow(); + let LMUL_pow_ori = get_lmul_pow(); + let SEW_pow_ori = get_sew_pow(); + let ratio_pow_ori = SEW_pow_ori - LMUL_pow_ori; + + /* set vtype */ + match op { + VSETVLI => { + vtype->bits() = 0b0 @ zeros(sizeof(xlen) - 9) @ ma @ ta @ sew @ lmul + }, + VSETVL => { + let rs2 : regidx = sew[1 .. 0] @ lmul; + vtype->bits() = X(rs2) + } + }; + + /* check legal SEW and LMUL and calculate VLMAX */ + let LMUL_pow_new = get_lmul_pow(); + let SEW_pow_new = get_sew_pow(); + if SEW_pow_new > LMUL_pow_new + ELEN_pow then { + /* Note: Implementations can set vill or trap if the vtype setting is not supported. + * TODO: configuration support for both solutions + */ + vtype->bits() = 0b1 @ zeros(sizeof(xlen) - 1); /* set vtype.vill */ + vl = zeros(); + print_reg("CSR vtype <- " ^ BitStr(vtype.bits())); + print_reg("CSR vl <- " ^ BitStr(vl)); + return RETIRE_SUCCESS + }; + let VLMAX = int_power(2, VLEN_pow + LMUL_pow_new - SEW_pow_new); + + /* set vl according to VLMAX and AVL */ + if (rs1 != 0b00000) then { /* normal stripmining */ + let rs1_val = X(rs1); + let AVL = unsigned(rs1_val); + vl = if AVL <= VLMAX then to_bits(sizeof(xlen), AVL) + else if AVL < 2 * VLMAX then to_bits(sizeof(xlen), (AVL + 1) / 2) + else to_bits(sizeof(xlen), VLMAX); + /* Note: ceil(AVL / 2) <= vl <= VLMAX when VLMAX < AVL < (2 * VLMAX) + * TODO: configuration support for either using ceil(AVL / 2) or VLMAX + */ + X(rd) = vl; + } else if (rd != 0b00000) then { /* set vl to VLMAX */ + let AVL = unsigned(ones(sizeof(xlen))); + vl = to_bits(sizeof(xlen), VLMAX); + X(rd) = vl; + } else { /* keep existing vl */ + let AVL = unsigned(vl); + let ratio_pow_new = SEW_pow_new - LMUL_pow_new; + if (ratio_pow_new != ratio_pow_ori) then { + /* Note: Implementations can set vill or trap if the vtype setting is not supported. + * TODO: configuration support for both solutions + */ + vtype->bits() = 0b1 @ zeros(sizeof(xlen) - 1); /* set vtype.vill */ + vl = zeros(); + } + }; + print_reg("CSR vtype <- " ^ BitStr(vtype.bits())); + print_reg("CSR vl <- " ^ BitStr(vl)); + + /* reset vstart to 0 */ + vstart = zeros(); + print_reg("CSR vstart <- " ^ BitStr(vstart)); + + RETIRE_SUCCESS + } diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index aeb3569bb7..e970f01cb5 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -3,9 +3,11 @@ $schema: "inst_schema.json#" kind: instruction name: vsetvli -long_name: No synopsis available. +long_name: Set vector configuration (register immediate). description: | - No description available. + Vset (r,i) allows rapid configuration of the values in vl and vtype CSRs to match application + needs. The vsetvl instruction sets the vtype and vl CSRs based on the contents of the argument + register rs1 and immediate, and writes the new value of vl into rd. definedBy: V assembly: xs1, xd, imm encoding: @@ -24,7 +26,19 @@ access: vu: always data_independent_timing: false operation(): | + XReg state = vector_state(); + XReg VLMAX = state.log2_multiplier * VLEN * state.sew; + # todo: state.lmul_type + if (xs1 < VLMAX){ + CSR[vl] = X[rs1]; + } else { + CSR[vl] = VLMAX; + } + + CSR[vtype] = zimm11; + X[rd] = CSR[vl]; + CSR[vstart] = 0; sail(): | { let VLEN_pow = get_vlen_pow(); diff --git a/arch/isa/vec.idl b/arch/isa/vec.idl new file mode 100644 index 0000000000..c819eb9384 --- /dev/null +++ b/arch/isa/vec.idl @@ -0,0 +1,50 @@ +%version: 1.0 + +# - test suite? +# - Vector params (there will be many) +# - Vector state +# - Order (might be dictated somewhat by test suite) +# - vset* +# - integer arith (vadd/vsub/vrsub(.vv,.vx,.vi), compare, min, max) +# - integer widening arith () + +# the vector register file +Bits v[32] = [0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0]; + +enum VectorLmulType { + Divide + Multiply +} + +struct VectorState { + Bits<7> sew; + VectorMultiplierDirection lmul_type; + Bits<2> log2_multiplier; +} + +function vector_state { + returns VectorState + description { + Get the current vector state from CSRs + } + body { + VectorState state; + + state.sew = 7'b1 << (3 + CSR[VTYPE].VSEW); + Bits<3> vlmul = CSR[VTYPE].VLMUL; + state.lmul_type = CSR[vtype].VLMUL[2] == 1'b1 ? VectorLmulType::Divide : VectorLmulType::Multiply; + state.log2_multiplier = CSR[vtype].VLMUL[1:0]; + if (vlmul == 3'b101) { + state.log2_multiplier = 8; + } else if (vlmul == 3'b110) { + state.log2_multiplier = 4; + } else if (vlmul == 3'b111) { + state.log2_multiplier = 2; + } + + return state; + } +} From 536ad3148d9d60bfc3504ce67929818a7ee82545 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 9 Mar 2025 00:13:46 +0000 Subject: [PATCH 02/23] update vset --- arch/inst/V/vsetivli.yaml | 9 +++++---- arch/inst/V/vsetvl.yaml | 7 ++++--- arch/inst/V/vsetvli.yaml | 7 ++++--- 3 files changed, 13 insertions(+), 10 deletions(-) diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index 6cb274516c..a92c77ae6c 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -26,12 +26,13 @@ access: vu: always data_independent_timing: false operation(): | - XReg state = vector_state(); - XReg VLMAX = state.log2_multiplier * VLEN * state.sew; - # todo: state.lmul_type + VectorState state = vector_state(); + XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); - if (xs1 < VLMAX){ + if (uimm < VLMAX){ CSR[vl] = uimm; + } else if (uimm < 2*VLMAX) { + CSR[vl] = uimm / 2; } else { CSR[vl] = VLMAX; } diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 457e3c815a..5bcb446b45 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -26,12 +26,13 @@ access: vu: always data_independent_timing: false operation(): | - XReg state = vector_state(); - XReg VLMAX = state.log2_multiplier * VLEN * state.sew; - # todo: state.lmul_type + VectorState state = vector_state(); + XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); if (xs1 < VLMAX){ CSR[vl] = X[rs1]; + } else if (xs1 < 2*VLMAX) { + CSR[vl] = X[rs1] / 2; } else { CSR[vl] = VLMAX; } diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index e970f01cb5..c970daf982 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -26,12 +26,13 @@ access: vu: always data_independent_timing: false operation(): | - XReg state = vector_state(); - XReg VLMAX = state.log2_multiplier * VLEN * state.sew; - # todo: state.lmul_type + VectorState state = vector_state(); + XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); if (xs1 < VLMAX){ CSR[vl] = X[rs1]; + } else if (xs1 < 2*VLMAX) { + CSR[vl] = X[rs1] / 2; } else { CSR[vl] = VLMAX; } From c833986bbbccafc99e9efa4da636ac0c10f16ded Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 30 Mar 2025 18:46:59 +0000 Subject: [PATCH 03/23] start adding CSRs --- arch/inst/V/vsetivli.yaml | 6 +++--- arch/inst/V/vsetvl.yaml | 6 +++--- arch/inst/V/vsetvli.yaml | 6 +++--- arch/isa/vec.idl | 4 ++-- 4 files changed, 11 insertions(+), 11 deletions(-) diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index a92c77ae6c..e0e1f204b3 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -30,11 +30,11 @@ operation(): | XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); if (uimm < VLMAX){ - CSR[vl] = uimm; + CSR[vl].VALUE = uimm; } else if (uimm < 2*VLMAX) { - CSR[vl] = uimm / 2; + CSR[vl].VALUE = uimm / 2; } else { - CSR[vl] = VLMAX; + CSR[vl].VALUE = VLMAX; } CSR[vtype] = zimm11; diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 5bcb446b45..22daffa609 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -30,11 +30,11 @@ operation(): | XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); if (xs1 < VLMAX){ - CSR[vl] = X[rs1]; + CSR[vl].VALUE = X[rs1]; } else if (xs1 < 2*VLMAX) { - CSR[vl] = X[rs1] / 2; + CSR[vl].VALUE = X[rs1] / 2; } else { - CSR[vl] = VLMAX; + CSR[vl].VALUE = VLMAX; } CSR[vtype] = X[rs2]; diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index c970daf982..bcdd96cb10 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -30,11 +30,11 @@ operation(): | XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); if (xs1 < VLMAX){ - CSR[vl] = X[rs1]; + CSR[vl].VALUE = X[rs1]; } else if (xs1 < 2*VLMAX) { - CSR[vl] = X[rs1] / 2; + CSR[vl].VALUE = X[rs1] / 2; } else { - CSR[vl] = VLMAX; + CSR[vl].VALUE = VLMAX; } CSR[vtype] = zimm11; diff --git a/arch/isa/vec.idl b/arch/isa/vec.idl index c819eb9384..b1982c4e6e 100644 --- a/arch/isa/vec.idl +++ b/arch/isa/vec.idl @@ -33,8 +33,8 @@ function vector_state { body { VectorState state; - state.sew = 7'b1 << (3 + CSR[VTYPE].VSEW); - Bits<3> vlmul = CSR[VTYPE].VLMUL; + state.sew = 7'b1 << (3 + CSR[vtype].VSEW); + Bits<3> vlmul = CSR[vtype].VLMUL; state.lmul_type = CSR[vtype].VLMUL[2] == 1'b1 ? VectorLmulType::Divide : VectorLmulType::Multiply; state.log2_multiplier = CSR[vtype].VLMUL[1:0]; if (vlmul == 3'b101) { From 35b70f7c70a2caa7825bbf1a873e79704eafe09f Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 30 Mar 2025 18:50:21 +0000 Subject: [PATCH 04/23] start adding CSRs --- arch/csr/V/vl.yaml | 25 ++++++++++++++++++++++ arch/csr/V/vlenb.yaml | 21 +++++++++++++++++++ arch/csr/V/vtype.yaml | 48 +++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 94 insertions(+) create mode 100644 arch/csr/V/vl.yaml create mode 100644 arch/csr/V/vlenb.yaml create mode 100644 arch/csr/V/vtype.yaml diff --git a/arch/csr/V/vl.yaml b/arch/csr/V/vl.yaml new file mode 100644 index 0000000000..bd5cc9cb59 --- /dev/null +++ b/arch/csr/V/vl.yaml @@ -0,0 +1,25 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vl +long_name: Vector Length +address: 0x0 #?? +priv_mode: M #?? +length: MXLEN +description: Holds an unsigned integer specifying number of elements to be updated with results from a vector instruction. +definedBy: V +fields: + VALUE: + location_rv32: 31-0 + location_rv64: 63-0 + description: | + The vl register holds an unsigned integer specifying the number of elements to be updated with + results from a vector instruction, as further detailed in Section Section 31.5.4. + + The number of bits implemented in vl depends on the implementation's maximum vector + length of the smallest supported type. The smallest vector implementation with VLEN=32 + and supporting SEW=8 would need at least six bits in vl to hold the values 0-32 + (VLEN=32, with LMUL=8 and SEW=8, yields VLMAX=32). + type: RO #?? + reset_value: 0 diff --git a/arch/csr/V/vlenb.yaml b/arch/csr/V/vlenb.yaml new file mode 100644 index 0000000000..e6c8c9ad49 --- /dev/null +++ b/arch/csr/V/vlenb.yaml @@ -0,0 +1,21 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vlenb +long_name: Vector Length (Bytes) +address: 0x0 #?? +priv_mode: M #?? +length: MXLEN +description: Holds the value VLEN/8, the vector register length in bytes. +definedBy: V +fields: + VALUE: + location_rv32: 31-0 + location_rv64: 63-0 + description: | + The value in vlenb is a design-time constant in any implementation. + Without this CSR, several instructions are needed to calculate VLEN in bytes, and the code + has to disturb current vl and vtype settings which require them to be saved and restored. + type: RO #?? + reset_value: 0 #VLEN/8 diff --git a/arch/csr/V/vtype.yaml b/arch/csr/V/vtype.yaml new file mode 100644 index 0000000000..c26ef7098f --- /dev/null +++ b/arch/csr/V/vtype.yaml @@ -0,0 +1,48 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vtype +long_name: Vector Type +address: 0x0 #?? +priv_mode: M #?? +length: MXLEN +description: Provides the default type used to interpret the contents of the vector registrer file. +definedBy: V +fields: + VILL: + location_rv32: 31 + location_rv64: 63 + description: Illegal value if set. + type: RO #?? + reset_value: 0 + reserved: + location_rv32: 30-8 + location_rv64: 62-8 + description: Reserved if non-zero + type: RO #?? + reset_value: UNDEFINED_LEGAL + VMA: + location_rv32: 7 + location_rv64: 7 + description: Vector mask agnostic + type: RO #?? + reset_value: 0 + VTA: + location_rv32: 6 + location_rv64: 6 + description: Vector tail agnostic + type: RO #?? + reset_value: 0 + VSEW: + location_rv32: 5-3 + location_rv64: 5-3 + description: Selected element width + type: RO #?? + reset_value: 0 + VLMUL: + location_rv32: 2-0 + location_rv64: 2-0 + description: Vector register group multiplier + type: RO #?? + reset_value: 0 From 9e7ea5bd07bcdd8e0cbb8d5e419bbcb82c4a8ed3 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 30 Mar 2025 19:07:40 +0000 Subject: [PATCH 05/23] add skeleton for remaining CSRs --- arch/csr/V/vl.yaml | 4 ++-- arch/csr/V/vlenb.yaml | 4 ++-- arch/csr/V/vtype.yaml | 4 ++-- arch/inst/V/vsetivli.yaml | 2 +- arch/inst/V/vsetvl.yaml | 2 +- arch/inst/V/vsetvli.yaml | 2 +- 6 files changed, 9 insertions(+), 9 deletions(-) diff --git a/arch/csr/V/vl.yaml b/arch/csr/V/vl.yaml index bd5cc9cb59..db67151c56 100644 --- a/arch/csr/V/vl.yaml +++ b/arch/csr/V/vl.yaml @@ -4,8 +4,8 @@ $schema: "csr_schema.json#" kind: csr name: vl long_name: Vector Length -address: 0x0 #?? -priv_mode: M #?? +address: 0xC20 +priv_mode: U #should be URO length: MXLEN description: Holds an unsigned integer specifying number of elements to be updated with results from a vector instruction. definedBy: V diff --git a/arch/csr/V/vlenb.yaml b/arch/csr/V/vlenb.yaml index e6c8c9ad49..d1481b2843 100644 --- a/arch/csr/V/vlenb.yaml +++ b/arch/csr/V/vlenb.yaml @@ -4,8 +4,8 @@ $schema: "csr_schema.json#" kind: csr name: vlenb long_name: Vector Length (Bytes) -address: 0x0 #?? -priv_mode: M #?? +address: 0xC22 +priv_mode: U #should be URO length: MXLEN description: Holds the value VLEN/8, the vector register length in bytes. definedBy: V diff --git a/arch/csr/V/vtype.yaml b/arch/csr/V/vtype.yaml index c26ef7098f..2711125888 100644 --- a/arch/csr/V/vtype.yaml +++ b/arch/csr/V/vtype.yaml @@ -4,8 +4,8 @@ $schema: "csr_schema.json#" kind: csr name: vtype long_name: Vector Type -address: 0x0 #?? -priv_mode: M #?? +address: 0xC21 +priv_mode: U #should be URO length: MXLEN description: Provides the default type used to interpret the contents of the vector registrer file. definedBy: V diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index e0e1f204b3..5503fec643 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -39,7 +39,7 @@ operation(): | CSR[vtype] = zimm11; X[rd] = CSR[vl]; - CSR[vstart] = 0; + CSR[vstart].VALUE = 0; sail(): | { let VLEN_pow = get_vlen_pow(); diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 22daffa609..8f9feb7cad 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -39,7 +39,7 @@ operation(): | CSR[vtype] = X[rs2]; X[rd] = CSR[vl]; - CSR[vstart] = 0; + CSR[vstart].VALUE = 0; sail(): | { let VLEN_pow = get_vlen_pow(); diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index bcdd96cb10..a79419cbff 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -39,7 +39,7 @@ operation(): | CSR[vtype] = zimm11; X[rd] = CSR[vl]; - CSR[vstart] = 0; + CSR[vstart].VALUE = 0; sail(): | { let VLEN_pow = get_vlen_pow(); From a7134890ea616080036317a32ac974a9704c18df Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 30 Mar 2025 19:08:55 +0000 Subject: [PATCH 06/23] add skeleton for remaining CSRs --- arch/csr/V/vcsr.yaml | 19 ++++++++++++++ arch/csr/V/vstart.yaml | 59 ++++++++++++++++++++++++++++++++++++++++++ arch/csr/V/vxrm.yaml | 19 ++++++++++++++ arch/csr/V/vxsat.yaml | 19 ++++++++++++++ 4 files changed, 116 insertions(+) create mode 100644 arch/csr/V/vcsr.yaml create mode 100644 arch/csr/V/vstart.yaml create mode 100644 arch/csr/V/vxrm.yaml create mode 100644 arch/csr/V/vxsat.yaml diff --git a/arch/csr/V/vcsr.yaml b/arch/csr/V/vcsr.yaml new file mode 100644 index 0000000000..1b7d8622f7 --- /dev/null +++ b/arch/csr/V/vcsr.yaml @@ -0,0 +1,19 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vcsr +long_name: Vector control and status register +address: 0x00F +priv_mode: U #should be URW? +length: MXLEN +description: TBA. +definedBy: V +fields: + VALUE: + location_rv32: 31-0 + location_rv64: 63-0 + description: | + TBA + type: RO #?? + reset_value: 0 diff --git a/arch/csr/V/vstart.yaml b/arch/csr/V/vstart.yaml new file mode 100644 index 0000000000..2310eacfdc --- /dev/null +++ b/arch/csr/V/vstart.yaml @@ -0,0 +1,59 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vstart +long_name: Vector Start Index +address: 0x008 +priv_mode: U #should be URW +length: MXLEN +description: Specifies the index of the first element to be executed by a vector instruction. +definedBy: V +fields: + VALUE: + location_rv32: 31-0 + location_rv64: 63-0 + description: | + Normally, vstart is only written by hardware on a trap on a vector instruction, with the vstart value + representing the element on which the trap was taken (either a synchronous exception or an + asynchronous interrupt), and at which execution should resume after a resumable trap is handled. + All vector instructions are defined to begin execution with the element number given in the vstart + CSR, leaving earlier elements in the destination vector undisturbed, and to reset the vstart CSR to + zero at the end of execution. + All vector instructions, including vset{i}vl{i}, reset the vstart CSR to zero. + vstart is not modified by vector instructions that raise illegal-instruction exceptions. + The vstart CSR is defined to have only enough writable bits to hold the largest element index (one + less than the maximum VLMAX). + + The maximum vector length is obtained with the largest LMUL setting (8) and the smallest + SEW setting (8), so VLMAX_max = 8*VLEN/8 = VLEN. For example, for VLEN=256, + vstart would have 8 bits to represent indices from 0 through 255. + + The use of vstart values greater than the largest element index for the current vtype setting is + reserved. + + It is recommended that implementations trap if vstart is out of bounds. It is not required + to trap, as a possible future use of upper vstart bits is to store imprecise trap + information. + + The vstart CSR is writable by unprivileged code, but non-zero vstart values may cause vector + instructions to run substantially slower on some implementations, so vstart should not be used by + application programmers. A few vector instructions cannot be executed with a non-zero vstart value + and will raise an illegal instruction exception as defined below. + Making vstart visible to unprivileged code supports user-level threading libraries. + Implementations are permitted to raise illegal instruction exceptions when attempting to execute a + vector instruction with a value of vstart that the implementation can never produce when executing + that same instruction with the same vtype setting. + + For example, some implementations will never take interrupts during execution of a vector + arithmetic instruction, instead waiting until the instruction completes to take the + interrupt. Such implementations are permitted to raise an illegal instruction exception + when attempting to execute a vector arithmetic instruction when vstart is nonzero. + + When migrating a software thread between two harts with different microarchitectures, + the vstart value might not be supported by the new hart microarchitecture. The runtime + on the receiving hart might then have to emulate instruction execution up to the next + supported vstart element position. Alternatively, migration events can be constrained to + only occur at mutually supported vstart locations. + type: RO #?? + reset_value: 0 diff --git a/arch/csr/V/vxrm.yaml b/arch/csr/V/vxrm.yaml new file mode 100644 index 0000000000..c1867cd2c1 --- /dev/null +++ b/arch/csr/V/vxrm.yaml @@ -0,0 +1,19 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vxrm +long_name: Fixed-Point Rounding Mode +address: 0x00A +priv_mode: U #should be URW +length: MXLEN +description: TBA. +definedBy: V +fields: + VALUE: + location_rv32: 31-0 + location_rv64: 63-0 + description: | + TBA + type: RO #?? + reset_value: 0 diff --git a/arch/csr/V/vxsat.yaml b/arch/csr/V/vxsat.yaml new file mode 100644 index 0000000000..bfe21cb4e3 --- /dev/null +++ b/arch/csr/V/vxsat.yaml @@ -0,0 +1,19 @@ +# yaml-language-server: $schema=../../schemas/csr_schema.json + +$schema: "csr_schema.json#" +kind: csr +name: vxsat +long_name: Fixed-Point Saturate Flag +address: 0x009 +priv_mode: U #should be URW +length: MXLEN +description: TBA. +definedBy: V +fields: + VALUE: + location_rv32: 31-0 + location_rv64: 63-0 + description: | + TBA + type: RO #?? + reset_value: 0 From e7b2d0463912a08922829a95d4927468de111428 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Tue, 1 Apr 2025 03:06:51 +0000 Subject: [PATCH 07/23] update CSRs based on comments --- arch/csr/V/vcsr.yaml | 23 ++++++--- arch/csr/V/vl.yaml | 7 +-- arch/csr/V/vlenb.yaml | 6 +-- arch/csr/V/vstart.yaml | 17 +++++-- arch/csr/V/vtype.yaml | 111 +++++++++++++++++++++++++++++++++-------- arch/csr/V/vxrm.yaml | 9 ++-- arch/csr/V/vxsat.yaml | 8 +-- 7 files changed, 138 insertions(+), 43 deletions(-) diff --git a/arch/csr/V/vcsr.yaml b/arch/csr/V/vcsr.yaml index 1b7d8622f7..2d42a0785e 100644 --- a/arch/csr/V/vcsr.yaml +++ b/arch/csr/V/vcsr.yaml @@ -5,15 +5,26 @@ kind: csr name: vcsr long_name: Vector control and status register address: 0x00F -priv_mode: U #should be URW? +priv_mode: U length: MXLEN description: TBA. definedBy: V fields: - VALUE: - location_rv32: 31-0 - location_rv64: 63-0 + VXRM: + location_rv32: 2-1 + location_rv64: 2-1 description: | TBA - type: RO #?? - reset_value: 0 + type: RW-RH #?? + sw_write(csr_value): | #to be updated + return csr_value.VALUE; + reset_value: UNDEFINED_LEGAL + VXSAT: + location_rv32: 0 + location_rv64: 0 + description: | + TBA + type: RW-RH #?? + sw_write(csr_value): | #to be updated + return csr_value.VALUE; + reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vl.yaml b/arch/csr/V/vl.yaml index db67151c56..9d4a80d44c 100644 --- a/arch/csr/V/vl.yaml +++ b/arch/csr/V/vl.yaml @@ -5,7 +5,7 @@ kind: csr name: vl long_name: Vector Length address: 0xC20 -priv_mode: U #should be URO +priv_mode: U length: MXLEN description: Holds an unsigned integer specifying number of elements to be updated with results from a vector instruction. definedBy: V @@ -17,9 +17,10 @@ fields: The vl register holds an unsigned integer specifying the number of elements to be updated with results from a vector instruction, as further detailed in Section Section 31.5.4. + [NOTE] The number of bits implemented in vl depends on the implementation's maximum vector length of the smallest supported type. The smallest vector implementation with VLEN=32 and supporting SEW=8 would need at least six bits in vl to hold the values 0-32 (VLEN=32, with LMUL=8 and SEW=8, yields VLMAX=32). - type: RO #?? - reset_value: 0 + type: RO-H + reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vlenb.yaml b/arch/csr/V/vlenb.yaml index d1481b2843..0daf10d987 100644 --- a/arch/csr/V/vlenb.yaml +++ b/arch/csr/V/vlenb.yaml @@ -5,7 +5,7 @@ kind: csr name: vlenb long_name: Vector Length (Bytes) address: 0xC22 -priv_mode: U #should be URO +priv_mode: U length: MXLEN description: Holds the value VLEN/8, the vector register length in bytes. definedBy: V @@ -17,5 +17,5 @@ fields: The value in vlenb is a design-time constant in any implementation. Without this CSR, several instructions are needed to calculate VLEN in bytes, and the code has to disturb current vl and vtype settings which require them to be saved and restored. - type: RO #?? - reset_value: 0 #VLEN/8 + type: RO + reset_value(): return VLEN / 8; diff --git a/arch/csr/V/vstart.yaml b/arch/csr/V/vstart.yaml index 2310eacfdc..f629922284 100644 --- a/arch/csr/V/vstart.yaml +++ b/arch/csr/V/vstart.yaml @@ -5,7 +5,7 @@ kind: csr name: vstart long_name: Vector Start Index address: 0x008 -priv_mode: U #should be URW +priv_mode: U length: MXLEN description: Specifies the index of the first element to be executed by a vector instruction. definedBy: V @@ -20,11 +20,14 @@ fields: All vector instructions are defined to begin execution with the element number given in the vstart CSR, leaving earlier elements in the destination vector undisturbed, and to reset the vstart CSR to zero at the end of execution. + + [NOTE] All vector instructions, including vset{i}vl{i}, reset the vstart CSR to zero. vstart is not modified by vector instructions that raise illegal-instruction exceptions. The vstart CSR is defined to have only enough writable bits to hold the largest element index (one less than the maximum VLMAX). + [NOTE] The maximum vector length is obtained with the largest LMUL setting (8) and the smallest SEW setting (8), so VLMAX_max = 8*VLEN/8 = VLEN. For example, for VLEN=256, vstart would have 8 bits to represent indices from 0 through 255. @@ -32,6 +35,7 @@ fields: The use of vstart values greater than the largest element index for the current vtype setting is reserved. + [NOTE] It is recommended that implementations trap if vstart is out of bounds. It is not required to trap, as a possible future use of upper vstart bits is to store imprecise trap information. @@ -40,20 +44,27 @@ fields: instructions to run substantially slower on some implementations, so vstart should not be used by application programmers. A few vector instructions cannot be executed with a non-zero vstart value and will raise an illegal instruction exception as defined below. + + [NOTE] Making vstart visible to unprivileged code supports user-level threading libraries. + Implementations are permitted to raise illegal instruction exceptions when attempting to execute a vector instruction with a value of vstart that the implementation can never produce when executing that same instruction with the same vtype setting. + [NOTE] For example, some implementations will never take interrupts during execution of a vector arithmetic instruction, instead waiting until the instruction completes to take the interrupt. Such implementations are permitted to raise an illegal instruction exception when attempting to execute a vector arithmetic instruction when vstart is nonzero. + [NOTE] When migrating a software thread between two harts with different microarchitectures, the vstart value might not be supported by the new hart microarchitecture. The runtime on the receiving hart might then have to emulate instruction execution up to the next supported vstart element position. Alternatively, migration events can be constrained to only occur at mutually supported vstart locations. - type: RO #?? - reset_value: 0 + sw_write(csr_value): | + return csr_value.VALUE & (VLEN - 1); + type: RW-RH + reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vtype.yaml b/arch/csr/V/vtype.yaml index 2711125888..e6581bb03d 100644 --- a/arch/csr/V/vtype.yaml +++ b/arch/csr/V/vtype.yaml @@ -5,44 +5,111 @@ kind: csr name: vtype long_name: Vector Type address: 0xC21 -priv_mode: U #should be URO +priv_mode: U length: MXLEN -description: Provides the default type used to interpret the contents of the vector registrer file. +description: Provides the default type used to interpret the contents of the vector register file. definedBy: V fields: VILL: location_rv32: 31 location_rv64: 63 - description: Illegal value if set. - type: RO #?? - reset_value: 0 - reserved: - location_rv32: 30-8 - location_rv64: 62-8 - description: Reserved if non-zero - type: RO #?? + description: | + The vill bit is used to encode that a previous vset{i}vl{i} instruction attempted to write an + unsupported value to vtype. + + [NOTE] + The vill bit is held in bit XLEN-1 of the CSR to support checking for illegal values with a + branch on the sign bit. + + If the vill bit is set, then any attempt to execute a vector instruction that depends upon vtype will + raise an illegal-instruction exception. + + When the vill bit is set, the other XLEN-1 bits in vtype shall be zero. + type: RO-H reset_value: UNDEFINED_LEGAL VMA: location_rv32: 7 location_rv64: 7 - description: Vector mask agnostic - type: RO #?? - reset_value: 0 + description: | + Vector mask agnostic bit. Modifies the behavior of destination inactive masked-off elements during the + execution of vector instructions. + + A value of 0 means inactive elements are undisturbed, meaning the corresponding set of destination elements + in a vector register group retain the value they previously held. + + A value of 1 means inactive elements are agnostic, meaning the corresponding set of destination elements + in any vector destination operand can either retain the value they previously held, or are overwritten with 1s. + Within a single vector instruction, each destination element can be either left undisturbed or overwritten + with 1s, in any combination, and the pattern of undisturbed or overwritten with 1s is not required to be + deterministic when the instruction is executed with the same inputs. + type: RO-H + reset_value: UNDEFINED_LEGAL VTA: location_rv32: 6 location_rv64: 6 - description: Vector tail agnostic - type: RO #?? - reset_value: 0 + description: | + Vector tail agnostic bit. Modifies the bahavior of destination tail elements during the execution of vector + instructions. + + A value of 0 means tail elements are undisturbed, meaning the corresponding set of destination elements + in a vector register group retain the value they previously held. + + A value of 1 means tail elements are agnostic, meaning the corresponding set of destination elements + in any vector destination operand can either retain the value they previously held, or are overwritten with 1s. + Within a single vector instruction, each destination element can be either left undisturbed or overwritten + with 1s, in any combination, and the pattern of undisturbed or overwritten with 1s is not required to be + deterministic when the instruction is executed with the same inputs. + type: RO-H + reset_value: UNDEFINED_LEGAL VSEW: location_rv32: 5-3 location_rv64: 5-3 - description: Selected element width - type: RO #?? - reset_value: 0 + description: | + The value in vsew sets the dynamic selected element width (SEW). + + [NOTE] + vsew encoding: + 000 = 8 + 001 = 16 + 010 = 32 + 011 = 64 + 1XX = Reserved + + [NOTE] + elements per vector register: + SEW 64 = 2 + SEW 32 = 4 + SEW 16 = 8 + SEW 8 = 16 + # I feel like the encoding tables are important here. Is there a better way than the "note" tag? + type: RO-H + reset_value: UNDEFINED_LEGAL VLMUL: location_rv32: 2-0 location_rv64: 2-0 - description: Vector register group multiplier - type: RO #?? - reset_value: 0 + description: | + Vector register group multiplier. + + Multiple vector registers can be grouped together, so that a single vector instruction can operate on + multiple vector registers. The term vector register group is used herein to refer to one or more vector + registers used as a single operand to a vector instruction. Vector register groups can be used to provide + greater execution efficiency for longer application vectors, but the main reason for their inclusion is to + allow double-width or larger elements to be operated on with the same vector length as single-width + elements. The vector length multiplier, LMUL, when greater than 1, represents the default number of + vector registers that are combined to form a vector register group. Implementations must support + LMUL integer values of 1, 2, 4, and 8. + + [NOTE] + The vector architecture includes instructions that take multiple source and destination + vector operands with different element widths, but the same number of elements. The + effective LMUL (EMUL) of each vector operand is determined by the number of registers + required to hold the elements. For example, for a widening add operation, such as add 32- + bit values to produce 64-bit results, a double-width result requires twice the LMUL of the + single-width inputs. + + LMUL can also be a fractional value, reducing the number of bits used in a single vector register. + Fractional LMUL is used to increase the number of effective usable vector register groups when + operating on mixed-width values. + # the spec provides more details on vlmul. Should I include all of it or leave it here? How much detail needs to go into the CSR field descriptions? + type: RO-H + reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vxrm.yaml b/arch/csr/V/vxrm.yaml index c1867cd2c1..d2fc2c0df1 100644 --- a/arch/csr/V/vxrm.yaml +++ b/arch/csr/V/vxrm.yaml @@ -5,15 +5,18 @@ kind: csr name: vxrm long_name: Fixed-Point Rounding Mode address: 0x00A -priv_mode: U #should be URW +priv_mode: U length: MXLEN description: TBA. definedBy: V +sw_read(): | + return CSR[vcsr].VXRM; fields: VALUE: + alias: vcsr.VXRM location_rv32: 31-0 location_rv64: 63-0 description: | TBA - type: RO #?? - reset_value: 0 + type: RO-H + reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vxsat.yaml b/arch/csr/V/vxsat.yaml index bfe21cb4e3..e431141331 100644 --- a/arch/csr/V/vxsat.yaml +++ b/arch/csr/V/vxsat.yaml @@ -5,15 +5,17 @@ kind: csr name: vxsat long_name: Fixed-Point Saturate Flag address: 0x009 -priv_mode: U #should be URW +priv_mode: U length: MXLEN description: TBA. definedBy: V +sw_read(): | + return CSR[vcsr].VXSAT; fields: VALUE: location_rv32: 31-0 location_rv64: 63-0 description: | TBA - type: RO #?? - reset_value: 0 + type: RO-H + reset_value: UNDEFINED_LEGAL From fe42aadb27315383e7befa2c5733658080b103cf Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Mon, 7 Apr 2025 01:26:26 +0000 Subject: [PATCH 08/23] add remaining csr details --- arch/csr/V/vcsr.yaml | 14 +++++++------- arch/csr/V/vl.yaml | 4 +++- arch/csr/V/vtype.yaml | 20 +++++++++++++++----- arch/csr/V/vxrm.yaml | 20 ++++++++++++++++++-- arch/csr/V/vxsat.yaml | 8 ++++++-- 5 files changed, 49 insertions(+), 17 deletions(-) diff --git a/arch/csr/V/vcsr.yaml b/arch/csr/V/vcsr.yaml index 2d42a0785e..d9aa72b09a 100644 --- a/arch/csr/V/vcsr.yaml +++ b/arch/csr/V/vcsr.yaml @@ -7,24 +7,24 @@ long_name: Vector control and status register address: 0x00F priv_mode: U length: MXLEN -description: TBA. +description: Allows access to vxrm and vxsat CSRs definedBy: V fields: VXRM: location_rv32: 2-1 location_rv64: 2-1 description: | - TBA - type: RW-RH #?? - sw_write(csr_value): | #to be updated + See vxrm. + type: RW-RH + sw_write(csr_value): | return csr_value.VALUE; reset_value: UNDEFINED_LEGAL VXSAT: location_rv32: 0 location_rv64: 0 description: | - TBA - type: RW-RH #?? - sw_write(csr_value): | #to be updated + See vxsat. + type: RW-RH + sw_write(csr_value): | return csr_value.VALUE; reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vl.yaml b/arch/csr/V/vl.yaml index 9d4a80d44c..fd15426e7f 100644 --- a/arch/csr/V/vl.yaml +++ b/arch/csr/V/vl.yaml @@ -22,5 +22,7 @@ fields: length of the smallest supported type. The smallest vector implementation with VLEN=32 and supporting SEW=8 would need at least six bits in vl to hold the values 0-32 (VLEN=32, with LMUL=8 and SEW=8, yields VLMAX=32). + + It is recommended that at reset, vl is set to zero. type: RO-H - reset_value: UNDEFINED_LEGAL + reset_value: 0 diff --git a/arch/csr/V/vtype.yaml b/arch/csr/V/vtype.yaml index e6581bb03d..262a57be07 100644 --- a/arch/csr/V/vtype.yaml +++ b/arch/csr/V/vtype.yaml @@ -25,8 +25,10 @@ fields: raise an illegal-instruction exception. When the vill bit is set, the other XLEN-1 bits in vtype shall be zero. + + It is recommended that at reset, vill is set. type: RO-H - reset_value: UNDEFINED_LEGAL + reset_value: 1 VMA: location_rv32: 7 location_rv64: 7 @@ -42,8 +44,10 @@ fields: Within a single vector instruction, each destination element can be either left undisturbed or overwritten with 1s, in any combination, and the pattern of undisturbed or overwritten with 1s is not required to be deterministic when the instruction is executed with the same inputs. + + It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. type: RO-H - reset_value: UNDEFINED_LEGAL + reset_value: 0 VTA: location_rv32: 6 location_rv64: 6 @@ -59,8 +63,10 @@ fields: Within a single vector instruction, each destination element can be either left undisturbed or overwritten with 1s, in any combination, and the pattern of undisturbed or overwritten with 1s is not required to be deterministic when the instruction is executed with the same inputs. + + It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. type: RO-H - reset_value: UNDEFINED_LEGAL + reset_value: 0 VSEW: location_rv32: 5-3 location_rv64: 5-3 @@ -81,9 +87,11 @@ fields: SEW 32 = 4 SEW 16 = 8 SEW 8 = 16 + + It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. # I feel like the encoding tables are important here. Is there a better way than the "note" tag? type: RO-H - reset_value: UNDEFINED_LEGAL + reset_value: 0 VLMUL: location_rv32: 2-0 location_rv64: 2-0 @@ -110,6 +118,8 @@ fields: LMUL can also be a fractional value, reducing the number of bits used in a single vector register. Fractional LMUL is used to increase the number of effective usable vector register groups when operating on mixed-width values. + + It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. # the spec provides more details on vlmul. Should I include all of it or leave it here? How much detail needs to go into the CSR field descriptions? type: RO-H - reset_value: UNDEFINED_LEGAL + reset_value: 0 diff --git a/arch/csr/V/vxrm.yaml b/arch/csr/V/vxrm.yaml index d2fc2c0df1..a04dd25e7e 100644 --- a/arch/csr/V/vxrm.yaml +++ b/arch/csr/V/vxrm.yaml @@ -7,7 +7,7 @@ long_name: Fixed-Point Rounding Mode address: 0x00A priv_mode: U length: MXLEN -description: TBA. +description: Holds a 2-bit read-write rounding-mode field in the least-significant bits definedBy: V sw_read(): | return CSR[vcsr].VXRM; @@ -17,6 +17,22 @@ fields: location_rv32: 31-0 location_rv64: 63-0 description: | - TBA + The vector fixed-point rounding-mode register holds a two-bit read-write rounding-mode field in the + least-significant bits (vxrm[1:0]). The upper bits, vxrm[XLEN-1:2], should be written as zeros. + The vector fixed-point rounding-mode is given a separate CSR address to allow independent access, + but is also reflected as a field in vcsr. + + [NOTE] + A new rounding mode can be set while saving the original rounding mode using a single csrwi instruction. + + The fixed-point rounding algorithm is specified as follows. Suppose the pre-rounding result is v, and d + bits of that result are to be rounded off. Then the rounded result is (v >> d) + r, where r depends on + the rounding mode as specified in the following table of vxrm[1:0] values. + + - 00: rnu (round to nearest up), r = v[d-1] + - 01: rne (round to nearest even), r = v[d-1] & ( v[d-2:0]!=0 | v[d]) + - 10: rdn (round down, truncate), r = 0 + - 11: rod (round to odd), r = !v[d] & v[d-1:0]!=0 + # I feel like the encoding table is important here. Is there a better way than this list? type: RO-H reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vxsat.yaml b/arch/csr/V/vxsat.yaml index e431141331..9e3f01cc02 100644 --- a/arch/csr/V/vxsat.yaml +++ b/arch/csr/V/vxsat.yaml @@ -7,7 +7,7 @@ long_name: Fixed-Point Saturate Flag address: 0x009 priv_mode: U length: MXLEN -description: TBA. +description: Indicates if a fixed-point instruction has had to saturate an output value to fit into a destination format definedBy: V sw_read(): | return CSR[vcsr].VXSAT; @@ -16,6 +16,10 @@ fields: location_rv32: 31-0 location_rv64: 63-0 description: | - TBA + The vxsat CSR has a single read-write least-significant bit (vxsat[0]) that indicates if a fixed-point + instruction has had to saturate an output value to fit into a destination format. Bits vxsat[XLEN-1:1] + should be written as zeros. + + The vxsat bit is mirrored in vcsr. type: RO-H reset_value: UNDEFINED_LEGAL From f1f3cfce791a54e6944166a95133796103267589 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Mon, 7 Apr 2025 01:28:42 +0000 Subject: [PATCH 09/23] update csr read in vset --- arch/inst/V/vsetivli.yaml | 2 +- arch/inst/V/vsetvl.yaml | 2 +- arch/inst/V/vsetvli.yaml | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index 5503fec643..a6e3f6e9e7 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -38,7 +38,7 @@ operation(): | } CSR[vtype] = zimm11; - X[rd] = CSR[vl]; + X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | { diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 8f9feb7cad..29b44b8734 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -38,7 +38,7 @@ operation(): | } CSR[vtype] = X[rs2]; - X[rd] = CSR[vl]; + X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | { diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index a79419cbff..57afd5c321 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -38,7 +38,7 @@ operation(): | } CSR[vtype] = zimm11; - X[rd] = CSR[vl]; + X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | { From 31b051f1e5ba27b0116dde945f146aab7d161c35 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Mon, 21 Apr 2025 21:42:09 +0000 Subject: [PATCH 10/23] address comments --- arch/csr/V/vcsr.yaml | 14 +++++--------- arch/csr/V/vl.yaml | 2 -- arch/csr/V/vlenb.yaml | 2 +- arch/csr/V/vtype.yaml | 12 ++++-------- arch/csr/V/vxrm.yaml | 4 ++-- arch/csr/V/vxsat.yaml | 4 ++-- arch/inst/V/vsetivli.yaml | 9 +++------ arch/inst/V/vsetvl.yaml | 9 +++------ arch/inst/V/vsetvli.yaml | 9 +++------ 9 files changed, 23 insertions(+), 42 deletions(-) diff --git a/arch/csr/V/vcsr.yaml b/arch/csr/V/vcsr.yaml index d9aa72b09a..fcc3c32367 100644 --- a/arch/csr/V/vcsr.yaml +++ b/arch/csr/V/vcsr.yaml @@ -3,7 +3,7 @@ $schema: "csr_schema.json#" kind: csr name: vcsr -long_name: Vector control and status register +long_name: Vector Control and Status Register address: 0x00F priv_mode: U length: MXLEN @@ -11,19 +11,15 @@ description: Allows access to vxrm and vxsat CSRs definedBy: V fields: VXRM: - location_rv32: 2-1 - location_rv64: 2-1 - description: | - See vxrm. + location: 2-1 + description: See vxrm. type: RW-RH sw_write(csr_value): | return csr_value.VALUE; reset_value: UNDEFINED_LEGAL VXSAT: - location_rv32: 0 - location_rv64: 0 - description: | - See vxsat. + location: 0 + description: See vxsat. type: RW-RH sw_write(csr_value): | return csr_value.VALUE; diff --git a/arch/csr/V/vl.yaml b/arch/csr/V/vl.yaml index fd15426e7f..a76267abbf 100644 --- a/arch/csr/V/vl.yaml +++ b/arch/csr/V/vl.yaml @@ -22,7 +22,5 @@ fields: length of the smallest supported type. The smallest vector implementation with VLEN=32 and supporting SEW=8 would need at least six bits in vl to hold the values 0-32 (VLEN=32, with LMUL=8 and SEW=8, yields VLMAX=32). - - It is recommended that at reset, vl is set to zero. type: RO-H reset_value: 0 diff --git a/arch/csr/V/vlenb.yaml b/arch/csr/V/vlenb.yaml index 0daf10d987..739441db61 100644 --- a/arch/csr/V/vlenb.yaml +++ b/arch/csr/V/vlenb.yaml @@ -3,7 +3,7 @@ $schema: "csr_schema.json#" kind: csr name: vlenb -long_name: Vector Length (Bytes) +long_name: Vector Byte Length address: 0xC22 priv_mode: U length: MXLEN diff --git a/arch/csr/V/vtype.yaml b/arch/csr/V/vtype.yaml index 262a57be07..9bcc1b207c 100644 --- a/arch/csr/V/vtype.yaml +++ b/arch/csr/V/vtype.yaml @@ -30,8 +30,7 @@ fields: type: RO-H reset_value: 1 VMA: - location_rv32: 7 - location_rv64: 7 + location: 7 description: | Vector mask agnostic bit. Modifies the behavior of destination inactive masked-off elements during the execution of vector instructions. @@ -49,8 +48,7 @@ fields: type: RO-H reset_value: 0 VTA: - location_rv32: 6 - location_rv64: 6 + location: 6 description: | Vector tail agnostic bit. Modifies the bahavior of destination tail elements during the execution of vector instructions. @@ -68,8 +66,7 @@ fields: type: RO-H reset_value: 0 VSEW: - location_rv32: 5-3 - location_rv64: 5-3 + location: 5-3 description: | The value in vsew sets the dynamic selected element width (SEW). @@ -93,8 +90,7 @@ fields: type: RO-H reset_value: 0 VLMUL: - location_rv32: 2-0 - location_rv64: 2-0 + location: 2-0 description: | Vector register group multiplier. diff --git a/arch/csr/V/vxrm.yaml b/arch/csr/V/vxrm.yaml index a04dd25e7e..7a58aec9c9 100644 --- a/arch/csr/V/vxrm.yaml +++ b/arch/csr/V/vxrm.yaml @@ -3,7 +3,7 @@ $schema: "csr_schema.json#" kind: csr name: vxrm -long_name: Fixed-Point Rounding Mode +long_name: Vector Fixed-Point Rounding Mode address: 0x00A priv_mode: U length: MXLEN @@ -34,5 +34,5 @@ fields: - 10: rdn (round down, truncate), r = 0 - 11: rod (round to odd), r = !v[d] & v[d-1:0]!=0 # I feel like the encoding table is important here. Is there a better way than this list? - type: RO-H + type: RW-H reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vxsat.yaml b/arch/csr/V/vxsat.yaml index 9e3f01cc02..9f013bb197 100644 --- a/arch/csr/V/vxsat.yaml +++ b/arch/csr/V/vxsat.yaml @@ -3,7 +3,7 @@ $schema: "csr_schema.json#" kind: csr name: vxsat -long_name: Fixed-Point Saturate Flag +long_name: Vector Fixed-Point Saturate Flag address: 0x009 priv_mode: U length: MXLEN @@ -21,5 +21,5 @@ fields: should be written as zeros. The vxsat bit is mirrored in vcsr. - type: RO-H + type: RW-H reset_value: UNDEFINED_LEGAL diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index a6e3f6e9e7..685b3175ef 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -3,11 +3,8 @@ $schema: "inst_schema.json#" kind: instruction name: vsetivli -long_name: Set vector configuration (immediate immediate). -description: | - Vset (i,i) allows rapid configuration of the values in vl and vtype CSRs to match application - needs. The vsetvl instruction sets the vtype and vl CSRs based on the arguments, and writes - the new value of vl into rd. +long_name: Vector Set Vector Type Immediate and Vector Length Immediate +description: Set the vtype and vl CSRs, and write the new value of vl into rd. definedBy: V assembly: xd, imm encoding: @@ -29,7 +26,7 @@ operation(): | VectorState state = vector_state(); XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); - if (uimm < VLMAX){ + if (uimm < VLMAX) { CSR[vl].VALUE = uimm; } else if (uimm < 2*VLMAX) { CSR[vl].VALUE = uimm / 2; diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 29b44b8734..59d50c92e1 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -3,11 +3,8 @@ $schema: "inst_schema.json#" kind: instruction name: vsetvl -long_name: Set vector configuration (register register). -description: | - Vset (r,r) allows rapid configuration of the values in vl and vtype CSRs to match application - needs. The vsetvl instruction sets the vtype and vl CSRs based on the contents of the argument - registers rs1 and rs2, and writes the new value of vl into rd. +long_name: Vector Set Vector Type and Vector Length +description: Set the vtype and vl CSRs, and write the new value of vl into rd. definedBy: V assembly: xs2, xs1, xd encoding: @@ -29,7 +26,7 @@ operation(): | VectorState state = vector_state(); XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); - if (xs1 < VLMAX){ + if (xs1 < VLMAX) { CSR[vl].VALUE = X[rs1]; } else if (xs1 < 2*VLMAX) { CSR[vl].VALUE = X[rs1] / 2; diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index 57afd5c321..39d05043c6 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -3,11 +3,8 @@ $schema: "inst_schema.json#" kind: instruction name: vsetvli -long_name: Set vector configuration (register immediate). -description: | - Vset (r,i) allows rapid configuration of the values in vl and vtype CSRs to match application - needs. The vsetvl instruction sets the vtype and vl CSRs based on the contents of the argument - register rs1 and immediate, and writes the new value of vl into rd. +long_name: Vector Set Vector Type and Vector Length Immediate +description: Set the vtype and vl CSRs, and write the new value of vl into rd. definedBy: V assembly: xs1, xd, imm encoding: @@ -29,7 +26,7 @@ operation(): | VectorState state = vector_state(); XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); - if (xs1 < VLMAX){ + if (xs1 < VLMAX) { CSR[vl].VALUE = X[rs1]; } else if (xs1 < 2*VLMAX) { CSR[vl].VALUE = X[rs1] / 2; From b4fd2b8dafa02479a94b8cde452df72a8a99628d Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Mon, 21 Apr 2025 22:17:16 +0000 Subject: [PATCH 11/23] add pretty tables in csr descriptions --- arch/csr/V/vtype.yaml | 25 +++++++++---------------- arch/csr/V/vxrm.yaml | 13 ++++++++----- 2 files changed, 17 insertions(+), 21 deletions(-) diff --git a/arch/csr/V/vtype.yaml b/arch/csr/V/vtype.yaml index 9bcc1b207c..c966c5a0a0 100644 --- a/arch/csr/V/vtype.yaml +++ b/arch/csr/V/vtype.yaml @@ -70,23 +70,17 @@ fields: description: | The value in vsew sets the dynamic selected element width (SEW). - [NOTE] - vsew encoding: - 000 = 8 - 001 = 16 - 010 = 32 - 011 = 64 - 1XX = Reserved - - [NOTE] - elements per vector register: - SEW 64 = 2 - SEW 32 = 4 - SEW 16 = 8 - SEW 8 = 16 + [separator="!"] + !=== + ! vsew[2:0] ! SEW ! Elements per vector register + ! 000 ! 8 ! 16 + ! 001 ! 16 ! 8 + ! 010 ! 32 ! 4 + ! 011 ! 64 ! 2 + ! 1XX ! Reserved ! Reserved + !=== It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. - # I feel like the encoding tables are important here. Is there a better way than the "note" tag? type: RO-H reset_value: 0 VLMUL: @@ -116,6 +110,5 @@ fields: operating on mixed-width values. It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. - # the spec provides more details on vlmul. Should I include all of it or leave it here? How much detail needs to go into the CSR field descriptions? type: RO-H reset_value: 0 diff --git a/arch/csr/V/vxrm.yaml b/arch/csr/V/vxrm.yaml index 7a58aec9c9..ec4f3651e4 100644 --- a/arch/csr/V/vxrm.yaml +++ b/arch/csr/V/vxrm.yaml @@ -29,10 +29,13 @@ fields: bits of that result are to be rounded off. Then the rounded result is (v >> d) + r, where r depends on the rounding mode as specified in the following table of vxrm[1:0] values. - - 00: rnu (round to nearest up), r = v[d-1] - - 01: rne (round to nearest even), r = v[d-1] & ( v[d-2:0]!=0 | v[d]) - - 10: rdn (round down, truncate), r = 0 - - 11: rod (round to odd), r = !v[d] & v[d-1:0]!=0 - # I feel like the encoding table is important here. Is there a better way than this list? + [separator="!"] + !=== + ! vxrm[1:0] ! Abbreviation ! Rounding Mode ! Rounding increment, r + ! 00 ! rnu ! round-to-nearest-up (add +0.5 LSB) ! v[d-1] + ! 01 ! rne ! round-to-nearest-even ! v[d-1] & (v[d-2:0]\!=0 | v[d]) + ! 10 ! rdn ! round-down (truncate) ! 0 + ! 11 ! rod ! round-to-odd (OR bits into LSB, aka "jam") ! \!v[d] & v[d-1:0]\!=0 + type: RW-H reset_value: UNDEFINED_LEGAL From cb984f972d235eb2af55fa4e6360143a7eeb3280 Mon Sep 17 00:00:00 2001 From: root Date: Tue, 22 Apr 2025 17:48:50 -0700 Subject: [PATCH 12/23] break up csr write fields in vset --- arch/inst/V/vsetivli.yaml | 5 ++++- arch/inst/V/vsetvl.yaml | 6 +++++- arch/inst/V/vsetvli.yaml | 5 ++++- 3 files changed, 13 insertions(+), 3 deletions(-) diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index 685b3175ef..dbf29ec904 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -34,7 +34,10 @@ operation(): | CSR[vl].VALUE = VLMAX; } - CSR[vtype] = zimm11; + CSR[vtype].VMA = zimm11[7]; + CSR[vtype].VTA = zimm11[6]; + CSR[vtype].VSEW = zimm11[5:3]; + CSR[vtype].VLMUL = zimm11[2:0]; X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 59d50c92e1..372646ed32 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -34,7 +34,11 @@ operation(): | CSR[vl].VALUE = VLMAX; } - CSR[vtype] = X[rs2]; + XReg input2 = X[rs2]; + CSR[vtype].VMA = input2[7]; + CSR[vtype].VTA = input2[6]; + CSR[vtype].VSEW = input2[5:3]; + CSR[vtype].VLMUL = input2[2:0]; X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index 39d05043c6..ae7d0d6655 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -34,7 +34,10 @@ operation(): | CSR[vl].VALUE = VLMAX; } - CSR[vtype] = zimm11; + CSR[vtype].VMA = zimm11[7]; + CSR[vtype].VTA = zimm11[6]; + CSR[vtype].VSEW = zimm11[5:3]; + CSR[vtype].VLMUL = zimm11[2:0]; X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | From 46c52cd4cc6f22bc609b41da2e534df02882b76b Mon Sep 17 00:00:00 2001 From: root Date: Thu, 14 Aug 2025 19:50:22 -0700 Subject: [PATCH 13/23] update vl assignment in ranged case --- arch/ext/V.yaml | 6 ++++++ arch/inst/V/vsetivli.yaml | 16 ++++++++++++---- arch/inst/V/vsetvl.yaml | 16 ++++++++++++---- arch/inst/V/vsetvli.yaml | 16 ++++++++++++---- 4 files changed, 42 insertions(+), 12 deletions(-) diff --git a/arch/ext/V.yaml b/arch/ext/V.yaml index de7b3fe6de..3ad49b591d 100644 --- a/arch/ext/V.yaml +++ b/arch/ext/V.yaml @@ -47,3 +47,9 @@ params: # if HW is writing VS, then Dirty (3) better be a supported value assert MSTATUS_VS_LEGAL_VALUES.include?(3) if ext?(:V) && (HW_MSTATUS_VS_DIRTY_UPDATE != "never") + RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX: + description: | + The value assigned to VL when AVL < 2*VLMAX. + schema: + type: string + enum: ["ceil(AVL/2)", "VLMAX", "custom"] diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index dbf29ec904..944582f62b 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -25,11 +25,19 @@ data_independent_timing: false operation(): | VectorState state = vector_state(); XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); + XReg AVL = uimm; + XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (uimm < VLMAX) { - CSR[vl].VALUE = uimm; - } else if (uimm < 2*VLMAX) { - CSR[vl].VALUE = uimm / 2; + if (AVL < VLMAX) { + CSR[vl].VALUE = AVL; + } else if (AVL < 2*VLMAX) { + if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { + CSR[vl].VALUE = CEIL_AVL_OVER_TWO; + } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { + CSR[vl].VALUE = VLMAX; + } else { + unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); + } } else { CSR[vl].VALUE = VLMAX; } diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 372646ed32..67aae2e5d1 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -25,11 +25,19 @@ data_independent_timing: false operation(): | VectorState state = vector_state(); XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); + XReg AVL = X[rs1]; + XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (xs1 < VLMAX) { - CSR[vl].VALUE = X[rs1]; - } else if (xs1 < 2*VLMAX) { - CSR[vl].VALUE = X[rs1] / 2; + if (AVL < VLMAX) { + CSR[vl].VALUE = AVL; + } else if (AVL < 2*VLMAX) { + if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { + CSR[vl].VALUE = CEIL_AVL_OVER_TWO; + } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { + CSR[vl].VALUE = VLMAX; + } else { + unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); + } } else { CSR[vl].VALUE = VLMAX; } diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index ae7d0d6655..26cb0dc752 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -25,11 +25,19 @@ data_independent_timing: false operation(): | VectorState state = vector_state(); XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); + XReg AVL = X[rs1]; + XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (xs1 < VLMAX) { - CSR[vl].VALUE = X[rs1]; - } else if (xs1 < 2*VLMAX) { - CSR[vl].VALUE = X[rs1] / 2; + if (AVL < VLMAX) { + CSR[vl].VALUE = AVL; + } else if (AVL < 2*VLMAX) { + if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { + CSR[vl].VALUE = CEIL_AVL_OVER_TWO; + } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { + CSR[vl].VALUE = VLMAX; + } else { + unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); + } } else { CSR[vl].VALUE = VLMAX; } From b474edf710191cfdad9101d1c24857fdaa88634b Mon Sep 17 00:00:00 2001 From: root Date: Thu, 14 Aug 2025 20:07:16 -0700 Subject: [PATCH 14/23] add vxsat and vxrm sw_write --- arch/csr/V/vxrm.yaml | 2 ++ arch/csr/V/vxsat.yaml | 2 ++ 2 files changed, 4 insertions(+) diff --git a/arch/csr/V/vxrm.yaml b/arch/csr/V/vxrm.yaml index ec4f3651e4..f86666259a 100644 --- a/arch/csr/V/vxrm.yaml +++ b/arch/csr/V/vxrm.yaml @@ -37,5 +37,7 @@ fields: ! 10 ! rdn ! round-down (truncate) ! 0 ! 11 ! rod ! round-to-odd (OR bits into LSB, aka "jam") ! \!v[d] & v[d-1:0]\!=0 + sw_write(csr_value): | + return csr_value.VALUE & (VLEN - 1); type: RW-H reset_value: UNDEFINED_LEGAL diff --git a/arch/csr/V/vxsat.yaml b/arch/csr/V/vxsat.yaml index 9f013bb197..71efd82174 100644 --- a/arch/csr/V/vxsat.yaml +++ b/arch/csr/V/vxsat.yaml @@ -21,5 +21,7 @@ fields: should be written as zeros. The vxsat bit is mirrored in vcsr. + sw_write(csr_value): | + return csr_value.VALUE & (VLEN - 1); type: RW-H reset_value: UNDEFINED_LEGAL From d143311e81ec370d0e0f161c20b5849e6fec5875 Mon Sep 17 00:00:00 2001 From: root Date: Fri, 22 Aug 2025 18:29:21 -0700 Subject: [PATCH 15/23] set vill in unsupported cases --- arch/ext/V.yaml | 8 ++++++ arch/inst/V/vsetivli.yaml | 50 ++++++++++++++++++++++++++++++++++---- arch/inst/V/vsetvl.yaml | 51 ++++++++++++++++++++++++++++++++++----- arch/inst/V/vsetvli.yaml | 50 ++++++++++++++++++++++++++++++++++---- 4 files changed, 143 insertions(+), 16 deletions(-) diff --git a/arch/ext/V.yaml b/arch/ext/V.yaml index 3ad49b591d..9aed91c483 100644 --- a/arch/ext/V.yaml +++ b/arch/ext/V.yaml @@ -53,3 +53,11 @@ params: schema: type: string enum: ["ceil(AVL/2)", "VLMAX", "custom"] + UNSUPPORTED_VTYPES: + description: | + The set of values for vtype that are unsupported. + schema: + type: array + items: + type: integer + uniqueItems: true diff --git a/arch/inst/V/vsetivli.yaml b/arch/inst/V/vsetivli.yaml index 944582f62b..1b6cb4c79c 100644 --- a/arch/inst/V/vsetivli.yaml +++ b/arch/inst/V/vsetivli.yaml @@ -24,7 +24,7 @@ access: data_independent_timing: false operation(): | VectorState state = vector_state(); - XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); + XReg VLMAX = (VLEN `<< state.log2_multiplier) >> (3 + state.vsew); XReg AVL = uimm; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; @@ -42,10 +42,50 @@ operation(): | CSR[vl].VALUE = VLMAX; } - CSR[vtype].VMA = zimm11[7]; - CSR[vtype].VTA = zimm11[6]; - CSR[vtype].VSEW = zimm11[5:3]; - CSR[vtype].VLMUL = zimm11[2:0]; + XReg new_vtype = zimm11; + if (new_vtype[xlen() - 1] == 1'b1) { + # software is setting the illegal bit + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if ((new_vtype & 8'd0) != 0) { + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (new_vtype[5] == 1) { + # reserved vsew encoding + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (new_type[2:0] == 3'b100) { + # reserved LMUL + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (xlen() == 32 && new_type[2:0] == 3'b101) { + # reserved LMUL in RV32 + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else { + # valid, do the write + CSR[vtype].VILL = 0; + CSR[vtype].VMA = new_vtype[7]; + CSR[vtype].VTA = new_vtype[6]; + CSR[vtype].VSEW = new_vtype[5:3]; + CSR[vtype].VLMUL = new_vtype[2:0]; + } + X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | diff --git a/arch/inst/V/vsetvl.yaml b/arch/inst/V/vsetvl.yaml index 67aae2e5d1..d031525e4d 100644 --- a/arch/inst/V/vsetvl.yaml +++ b/arch/inst/V/vsetvl.yaml @@ -24,7 +24,7 @@ access: data_independent_timing: false operation(): | VectorState state = vector_state(); - XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); + XReg VLMAX = (VLEN `<< state.log2_multiplier) >> (3 + state.vsew); XReg AVL = X[rs1]; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; @@ -42,11 +42,50 @@ operation(): | CSR[vl].VALUE = VLMAX; } - XReg input2 = X[rs2]; - CSR[vtype].VMA = input2[7]; - CSR[vtype].VTA = input2[6]; - CSR[vtype].VSEW = input2[5:3]; - CSR[vtype].VLMUL = input2[2:0]; + XReg new_vtype = X[rs2]; + if (new_vtype[xlen() - 1] == 1'b1) { + # software is setting the illegal bit + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if ((new_vtype & 8'd0) != 0) { + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (new_vtype[5] == 1) { + # reserved vsew encoding + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (new_type[2:0] == 3'b100) { + # reserved LMUL + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (xlen() == 32 && new_type[2:0] == 3'b101) { + # reserved LMUL in RV32 + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else { + # valid, do the write + CSR[vtype].VILL = 0; + CSR[vtype].VMA = new_vtype[7]; + CSR[vtype].VTA = new_vtype[6]; + CSR[vtype].VSEW = new_vtype[5:3]; + CSR[vtype].VLMUL = new_vtype[2:0]; + } + X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | diff --git a/arch/inst/V/vsetvli.yaml b/arch/inst/V/vsetvli.yaml index 26cb0dc752..01fd8da723 100644 --- a/arch/inst/V/vsetvli.yaml +++ b/arch/inst/V/vsetvli.yaml @@ -24,7 +24,7 @@ access: data_independent_timing: false operation(): | VectorState state = vector_state(); - XReg VLMAX = (VLEN <<< state.log2_multiplier) >> (3 + state.vsew); + XReg VLMAX = (VLEN `<< state.log2_multiplier) >> (3 + state.vsew); XReg AVL = X[rs1]; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; @@ -42,10 +42,50 @@ operation(): | CSR[vl].VALUE = VLMAX; } - CSR[vtype].VMA = zimm11[7]; - CSR[vtype].VTA = zimm11[6]; - CSR[vtype].VSEW = zimm11[5:3]; - CSR[vtype].VLMUL = zimm11[2:0]; + XReg new_vtype = zimm11; + if (new_vtype[xlen() - 1] == 1'b1) { + # software is setting the illegal bit + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if ((new_vtype & 8'd0) != 0) { + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (new_vtype[5] == 1) { + # reserved vsew encoding + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (new_type[2:0] == 3'b100) { + # reserved LMUL + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else if (xlen() == 32 && new_type[2:0] == 3'b101) { + # reserved LMUL in RV32 + CSR[vtype].VILL = 1; + CSR[vtype].VMA = 0; + CSR[vtype].VTA = 0; + CSR[vtype].VSEW = 0; + CSR[vtype].VLMUL = 0; + } else { + # valid, do the write + CSR[vtype].VILL = 0; + CSR[vtype].VMA = new_vtype[7]; + CSR[vtype].VTA = new_vtype[6]; + CSR[vtype].VSEW = new_vtype[5:3]; + CSR[vtype].VLMUL = new_vtype[2:0]; + } + X[rd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; sail(): | From 7fe516baf091cc595712f111a5328e05e908ab45 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier Date: Sun, 7 Sep 2025 12:25:04 -0700 Subject: [PATCH 16/23] fix idl compile errors --- spec/std/isa/csr/V/vcsr.yaml | 5 +++-- spec/std/isa/csr/V/vl.yaml | 1 + spec/std/isa/csr/V/vlenb.yaml | 1 + spec/std/isa/csr/V/vstart.yaml | 1 + spec/std/isa/csr/V/vtype.yaml | 1 + spec/std/isa/csr/V/vxrm.yaml | 1 + spec/std/isa/csr/V/vxsat.yaml | 1 + spec/std/isa/ext/V.yaml | 14 ++++++++------ spec/std/isa/inst/V/vsetivli.yaml | 19 ++++++++++--------- spec/std/isa/inst/V/vsetvl.yaml | 21 +++++++++++---------- spec/std/isa/inst/V/vsetvli.yaml | 23 ++++++++++++----------- spec/std/isa/isa/globals.isa | 1 + spec/std/isa/isa/vec.idl | 6 +++--- 13 files changed, 54 insertions(+), 41 deletions(-) diff --git a/spec/std/isa/csr/V/vcsr.yaml b/spec/std/isa/csr/V/vcsr.yaml index dacf0a3453..d5b7c6f40d 100644 --- a/spec/std/isa/csr/V/vcsr.yaml +++ b/spec/std/isa/csr/V/vcsr.yaml @@ -8,6 +8,7 @@ kind: csr name: vcsr long_name: Vector Control and Status Register address: 0x00F +writable: true priv_mode: U length: MXLEN description: Allows access to vxrm and vxsat CSRs @@ -18,12 +19,12 @@ fields: description: See vxrm. type: RW-RH sw_write(csr_value): | - return csr_value.VALUE; + return csr_value.VXRM; reset_value: UNDEFINED_LEGAL VXSAT: location: 0 description: See vxsat. type: RW-RH sw_write(csr_value): | - return csr_value.VALUE; + return csr_value.VXSAT; reset_value: UNDEFINED_LEGAL diff --git a/spec/std/isa/csr/V/vl.yaml b/spec/std/isa/csr/V/vl.yaml index 9d78eb2902..1644b1bd6a 100644 --- a/spec/std/isa/csr/V/vl.yaml +++ b/spec/std/isa/csr/V/vl.yaml @@ -8,6 +8,7 @@ kind: csr name: vl long_name: Vector Length address: 0xC20 +writable: false priv_mode: U length: MXLEN description: Holds an unsigned integer specifying number of elements to be updated with results from a vector instruction. diff --git a/spec/std/isa/csr/V/vlenb.yaml b/spec/std/isa/csr/V/vlenb.yaml index 8dca64b792..222c0d39d0 100644 --- a/spec/std/isa/csr/V/vlenb.yaml +++ b/spec/std/isa/csr/V/vlenb.yaml @@ -8,6 +8,7 @@ kind: csr name: vlenb long_name: Vector Byte Length address: 0xC22 +writable: false priv_mode: U length: MXLEN description: Holds the value VLEN/8, the vector register length in bytes. diff --git a/spec/std/isa/csr/V/vstart.yaml b/spec/std/isa/csr/V/vstart.yaml index 2dc96ecc24..d75f02934f 100644 --- a/spec/std/isa/csr/V/vstart.yaml +++ b/spec/std/isa/csr/V/vstart.yaml @@ -8,6 +8,7 @@ kind: csr name: vstart long_name: Vector Start Index address: 0x008 +writable: true priv_mode: U length: MXLEN description: Specifies the index of the first element to be executed by a vector instruction. diff --git a/spec/std/isa/csr/V/vtype.yaml b/spec/std/isa/csr/V/vtype.yaml index 4465abfc45..0e44deffc0 100644 --- a/spec/std/isa/csr/V/vtype.yaml +++ b/spec/std/isa/csr/V/vtype.yaml @@ -8,6 +8,7 @@ kind: csr name: vtype long_name: Vector Type address: 0xC21 +writable: false priv_mode: U length: MXLEN description: Provides the default type used to interpret the contents of the vector register file. diff --git a/spec/std/isa/csr/V/vxrm.yaml b/spec/std/isa/csr/V/vxrm.yaml index bf03f4dedd..f50130236c 100644 --- a/spec/std/isa/csr/V/vxrm.yaml +++ b/spec/std/isa/csr/V/vxrm.yaml @@ -8,6 +8,7 @@ kind: csr name: vxrm long_name: Vector Fixed-Point Rounding Mode address: 0x00A +writable: true priv_mode: U length: MXLEN description: Holds a 2-bit read-write rounding-mode field in the least-significant bits diff --git a/spec/std/isa/csr/V/vxsat.yaml b/spec/std/isa/csr/V/vxsat.yaml index f300832098..2e8fed6caa 100644 --- a/spec/std/isa/csr/V/vxsat.yaml +++ b/spec/std/isa/csr/V/vxsat.yaml @@ -8,6 +8,7 @@ kind: csr name: vxsat long_name: Vector Fixed-Point Saturate Flag address: 0x009 +writable: true priv_mode: U length: MXLEN description: Indicates if a fixed-point instruction has had to saturate an output value to fit into a destination format diff --git a/spec/std/isa/ext/V.yaml b/spec/std/isa/ext/V.yaml index 2d688d93ad..6e9f551904 100644 --- a/spec/std/isa/ext/V.yaml +++ b/spec/std/isa/ext/V.yaml @@ -56,11 +56,13 @@ params: schema: type: string enum: ["ceil(AVL/2)", "VLMAX", "custom"] - UNSUPPORTED_VTYPES: + VLEN: description: | - The set of values for vtype that are unsupported. + The number of bits in a single vector register. VLEN >= ELEN, which must be a power of 2, and must be no greater than 2^16. schema: - type: array - items: - type: integer - uniqueItems: true + type: integer + ELEN: + description: | + The maximum size in bits of a vector element that any operation can produce or consume, ELEN >= 8, which must be a power of 2. + schema: + type: integer diff --git a/spec/std/isa/inst/V/vsetivli.yaml b/spec/std/isa/inst/V/vsetivli.yaml index a661166bbc..0e3e9e4bc1 100644 --- a/spec/std/isa/inst/V/vsetivli.yaml +++ b/spec/std/isa/inst/V/vsetivli.yaml @@ -27,25 +27,26 @@ access: data_independent_timing: false operation(): | VectorState state = vector_state(); - XReg VLMAX = (VLEN `<< state.log2_multiplier) >> (3 + state.vsew); + XReg vlen = VLEN; + XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.vsew); XReg AVL = uimm; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (AVL < VLMAX) { + if (AVL < vlmax) { CSR[vl].VALUE = AVL; - } else if (AVL < 2*VLMAX) { + } else if (AVL < 2*vlmax) { if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { CSR[vl].VALUE = CEIL_AVL_OVER_TWO; } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { - CSR[vl].VALUE = VLMAX; + CSR[vl].VALUE = vlmax; } else { unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); } } else { - CSR[vl].VALUE = VLMAX; + CSR[vl].VALUE = vlmax; } - XReg new_vtype = zimm11; + XReg new_vtype = vtypei; if (new_vtype[xlen() - 1] == 1'b1) { # software is setting the illegal bit CSR[vtype].VILL = 1; @@ -66,14 +67,14 @@ operation(): | CSR[vtype].VTA = 0; CSR[vtype].VSEW = 0; CSR[vtype].VLMUL = 0; - } else if (new_type[2:0] == 3'b100) { + } else if (new_vtype[2:0] == 3'b100) { # reserved LMUL CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; CSR[vtype].VTA = 0; CSR[vtype].VSEW = 0; CSR[vtype].VLMUL = 0; - } else if (xlen() == 32 && new_type[2:0] == 3'b101) { + } else if (xlen() == 32 && new_vtype[2:0] == 3'b101) { # reserved LMUL in RV32 CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; @@ -89,7 +90,7 @@ operation(): | CSR[vtype].VLMUL = new_vtype[2:0]; } - X[rd] = CSR[vl].VALUE; + X[xd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; # SPDX-SnippetBegin diff --git a/spec/std/isa/inst/V/vsetvl.yaml b/spec/std/isa/inst/V/vsetvl.yaml index 4c13e420fd..6d5d772308 100644 --- a/spec/std/isa/inst/V/vsetvl.yaml +++ b/spec/std/isa/inst/V/vsetvl.yaml @@ -27,25 +27,26 @@ access: data_independent_timing: false operation(): | VectorState state = vector_state(); - XReg VLMAX = (VLEN `<< state.log2_multiplier) >> (3 + state.vsew); - XReg AVL = X[rs1]; + XReg vlen = VLEN; + XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.vsew); + XReg AVL = xs1; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (AVL < VLMAX) { + if (AVL < vlmax) { CSR[vl].VALUE = AVL; - } else if (AVL < 2*VLMAX) { + } else if (AVL < 2*vlmax) { if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { CSR[vl].VALUE = CEIL_AVL_OVER_TWO; } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { - CSR[vl].VALUE = VLMAX; + CSR[vl].VALUE = vlmax; } else { unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); } } else { - CSR[vl].VALUE = VLMAX; + CSR[vl].VALUE = vlmax; } - XReg new_vtype = X[rs2]; + XReg new_vtype = xs2; if (new_vtype[xlen() - 1] == 1'b1) { # software is setting the illegal bit CSR[vtype].VILL = 1; @@ -66,14 +67,14 @@ operation(): | CSR[vtype].VTA = 0; CSR[vtype].VSEW = 0; CSR[vtype].VLMUL = 0; - } else if (new_type[2:0] == 3'b100) { + } else if (new_vtype[2:0] == 3'b100) { # reserved LMUL CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; CSR[vtype].VTA = 0; CSR[vtype].VSEW = 0; CSR[vtype].VLMUL = 0; - } else if (xlen() == 32 && new_type[2:0] == 3'b101) { + } else if (xlen() == 32 && new_vtype[2:0] == 3'b101) { # reserved LMUL in RV32 CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; @@ -89,7 +90,7 @@ operation(): | CSR[vtype].VLMUL = new_vtype[2:0]; } - X[rd] = CSR[vl].VALUE; + X[xd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; # SPDX-SnippetBegin diff --git a/spec/std/isa/inst/V/vsetvli.yaml b/spec/std/isa/inst/V/vsetvli.yaml index 4bf21acdc6..7eb86a2993 100644 --- a/spec/std/isa/inst/V/vsetvli.yaml +++ b/spec/std/isa/inst/V/vsetvli.yaml @@ -13,7 +13,7 @@ assembly: xd, xs1, vtypei encoding: match: 0----------------111-----1010111 variables: - - name: zimm + - name: vtypei location: 30-20 - name: xs1 location: 19-15 @@ -27,25 +27,26 @@ access: data_independent_timing: false operation(): | VectorState state = vector_state(); - XReg VLMAX = (VLEN `<< state.log2_multiplier) >> (3 + state.vsew); - XReg AVL = X[rs1]; + XReg vlen = VLEN; + XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.vsew); + XReg AVL = xs1; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (AVL < VLMAX) { + if (AVL < vlmax) { CSR[vl].VALUE = AVL; - } else if (AVL < 2*VLMAX) { + } else if (AVL < 2*vlmax) { if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { CSR[vl].VALUE = CEIL_AVL_OVER_TWO; } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { - CSR[vl].VALUE = VLMAX; + CSR[vl].VALUE = vlmax; } else { unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); } } else { - CSR[vl].VALUE = VLMAX; + CSR[vl].VALUE = vlmax; } - XReg new_vtype = zimm11; + XReg new_vtype = vtypei; if (new_vtype[xlen() - 1] == 1'b1) { # software is setting the illegal bit CSR[vtype].VILL = 1; @@ -66,14 +67,14 @@ operation(): | CSR[vtype].VTA = 0; CSR[vtype].VSEW = 0; CSR[vtype].VLMUL = 0; - } else if (new_type[2:0] == 3'b100) { + } else if (new_vtype[2:0] == 3'b100) { # reserved LMUL CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; CSR[vtype].VTA = 0; CSR[vtype].VSEW = 0; CSR[vtype].VLMUL = 0; - } else if (xlen() == 32 && new_type[2:0] == 3'b101) { + } else if (xlen() == 32 && new_vtype[2:0] == 3'b101) { # reserved LMUL in RV32 CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; @@ -89,7 +90,7 @@ operation(): | CSR[vtype].VLMUL = new_vtype[2:0]; } - X[rd] = CSR[vl].VALUE; + X[xd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; # SPDX-SnippetBegin diff --git a/spec/std/isa/isa/globals.isa b/spec/std/isa/isa/globals.isa index 47a4e271a7..8336035685 100644 --- a/spec/std/isa/isa/globals.isa +++ b/spec/std/isa/isa/globals.isa @@ -8,6 +8,7 @@ include "interrupts.idl" include "fetch.idl" include "util.idl" include "fp.idl" +include "vec.idl" # global state diff --git a/spec/std/isa/isa/vec.idl b/spec/std/isa/isa/vec.idl index 4802f617e1..c3b967a8ab 100644 --- a/spec/std/isa/isa/vec.idl +++ b/spec/std/isa/isa/vec.idl @@ -23,8 +23,8 @@ enum VectorLmulType { } struct VectorState { - Bits<7> sew; - VectorMultiplierDirection lmul_type; + Bits<7> vsew; + VectorLmulType lmul_type; Bits<2> log2_multiplier; } @@ -36,7 +36,7 @@ function vector_state { body { VectorState state; - state.sew = 7'b1 << (3 + CSR[vtype].VSEW); + state.vsew = 7'b1 << (3 + CSR[vtype].VSEW); Bits<3> vlmul = CSR[vtype].VLMUL; state.lmul_type = CSR[vtype].VLMUL[2] == 1'b1 ? VectorLmulType::Divide : VectorLmulType::Multiply; state.log2_multiplier = CSR[vtype].VLMUL[1:0]; From 879a5484edd83c00b27464e24e6101db7392af16 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier Date: Sun, 14 Sep 2025 17:53:20 -0700 Subject: [PATCH 17/23] adress dhower's feedback --- spec/std/isa/csr/V/vcsr.yaml | 4 ++++ spec/std/isa/csr/V/vl.yaml | 3 ++- spec/std/isa/csr/V/vstart.yaml | 7 ++++++- spec/std/isa/csr/V/vtype.yaml | 15 ++++++++++----- spec/std/isa/csr/V/vxrm.yaml | 1 - spec/std/isa/ext/V.yaml | 18 ++++++++++++++++-- spec/std/isa/inst/V/vsetivli.yaml | 2 +- spec/std/isa/inst/V/vsetvl.yaml | 2 +- spec/std/isa/inst/V/vsetvli.yaml | 2 +- spec/std/isa/isa/vec.idl | 9 +++------ 10 files changed, 44 insertions(+), 19 deletions(-) diff --git a/spec/std/isa/csr/V/vcsr.yaml b/spec/std/isa/csr/V/vcsr.yaml index d5b7c6f40d..513e189ba9 100644 --- a/spec/std/isa/csr/V/vcsr.yaml +++ b/spec/std/isa/csr/V/vcsr.yaml @@ -18,13 +18,17 @@ fields: location: 2-1 description: See vxrm. type: RW-RH + alias: vxrm.VALUE[1:0] sw_write(csr_value): | + CSR[vxrm].VALUE = csr_value.VXRM; return csr_value.VXRM; reset_value: UNDEFINED_LEGAL VXSAT: location: 0 description: See vxsat. type: RW-RH + alias: vxsat.VALUE[0] sw_write(csr_value): | + CSR[vxsat].VALUE = csr_value.VXSAT; return csr_value.VXSAT; reset_value: UNDEFINED_LEGAL diff --git a/spec/std/isa/csr/V/vl.yaml b/spec/std/isa/csr/V/vl.yaml index 1644b1bd6a..c01aab5fd4 100644 --- a/spec/std/isa/csr/V/vl.yaml +++ b/spec/std/isa/csr/V/vl.yaml @@ -27,4 +27,5 @@ fields: and supporting SEW=8 would need at least six bits in vl to hold the values 0-32 (VLEN=32, with LMUL=8 and SEW=8, yields VLMAX=32). type: RO-H - reset_value: 0 + reset_value(): | + return (FOLLOW_VTYPE_RESET_RECOMMENDATION)? 0 : UNDEFINED_LEGAL; diff --git a/spec/std/isa/csr/V/vstart.yaml b/spec/std/isa/csr/V/vstart.yaml index d75f02934f..b0f3e18c01 100644 --- a/spec/std/isa/csr/V/vstart.yaml +++ b/spec/std/isa/csr/V/vstart.yaml @@ -69,6 +69,11 @@ fields: supported vstart element position. Alternatively, migration events can be constrained to only occur at mutually supported vstart locations. sw_write(csr_value): | - return csr_value.VALUE & (VLEN - 1); + XReg newval = csr_value.VALUE & (VLEN - 1); + if (newval != csr_value.VALUE) { + return UNDEFINED_LEGAL; + } else { + return newval; + } type: RW-RH reset_value: UNDEFINED_LEGAL diff --git a/spec/std/isa/csr/V/vtype.yaml b/spec/std/isa/csr/V/vtype.yaml index 0e44deffc0..b92fb1e3a2 100644 --- a/spec/std/isa/csr/V/vtype.yaml +++ b/spec/std/isa/csr/V/vtype.yaml @@ -32,7 +32,8 @@ fields: It is recommended that at reset, vill is set. type: RO-H - reset_value: 1 + reset_value(): | + return (FOLLOW_VTYPE_RESET_RECOMMENDATION)? 1 : UNDEFINED_LEGAL; VMA: location: 7 description: | @@ -50,7 +51,8 @@ fields: It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. type: RO-H - reset_value: 0 + reset_value(): | + return (FOLLOW_VTYPE_RESET_RECOMMENDATION)? 0 : UNDEFINED_LEGAL; VTA: location: 6 description: | @@ -68,7 +70,8 @@ fields: It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. type: RO-H - reset_value: 0 + reset_value(): | + return (FOLLOW_VTYPE_RESET_RECOMMENDATION)? 0 : UNDEFINED_LEGAL; VSEW: location: 5-3 description: | @@ -86,7 +89,8 @@ fields: It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. type: RO-H - reset_value: 0 + reset_value(): | + return (FOLLOW_VTYPE_RESET_RECOMMENDATION)? 0 : UNDEFINED_LEGAL; VLMUL: location: 2-0 description: | @@ -115,4 +119,5 @@ fields: It is recommended that at reset, vill is set, and the remaining bits in vtype are zero. type: RO-H - reset_value: 0 + reset_value(): | + return (FOLLOW_VTYPE_RESET_RECOMMENDATION)? 0 : UNDEFINED_LEGAL; diff --git a/spec/std/isa/csr/V/vxrm.yaml b/spec/std/isa/csr/V/vxrm.yaml index f50130236c..d0f32d44dc 100644 --- a/spec/std/isa/csr/V/vxrm.yaml +++ b/spec/std/isa/csr/V/vxrm.yaml @@ -17,7 +17,6 @@ sw_read(): | return CSR[vcsr].VXRM; fields: VALUE: - alias: vcsr.VXRM location_rv32: 31-0 location_rv64: 63-0 description: | diff --git a/spec/std/isa/ext/V.yaml b/spec/std/isa/ext/V.yaml index 6e9f551904..3bd2d28f6c 100644 --- a/spec/std/isa/ext/V.yaml +++ b/spec/std/isa/ext/V.yaml @@ -56,13 +56,27 @@ params: schema: type: string enum: ["ceil(AVL/2)", "VLMAX", "custom"] + FOLLOW_VTYPE_RESET_RECOMMENDATION: + description: | + The spec recommends - but does not require - that on reset, vill is set, and remaining bits in vtype and vl are set to 0. + If this parameter is set to true, the CSR resets will follow this recommandation. If it is false, the resets will be "UNDEFINED_LEGAL". + schema: + type: boolean VLEN: description: | - The number of bits in a single vector register. VLEN >= ELEN, which must be a power of 2, and must be no greater than 2^16. + The number of bits in a single vector register. schema: type: integer +# requirements: +# idl(): | +# -> (VLEN >= ELEN) && (VLEN <='h10000) && (popcount(VLEN) == 1); +# reason: VLEN >= ELEN, which must be a power of 2, and must be no greater than 2^16. ELEN: description: | - The maximum size in bits of a vector element that any operation can produce or consume, ELEN >= 8, which must be a power of 2. + The maximum size in bits of a vector element that any operation can produce or consume. schema: type: integer +# requirements: +# idl(): | +# -> (ELEN >='h8) && (popcount(ELEN) == 1); +# reason: ELEN >= 8, which must be a power of 2. diff --git a/spec/std/isa/inst/V/vsetivli.yaml b/spec/std/isa/inst/V/vsetivli.yaml index 0e3e9e4bc1..d0eb3b9e28 100644 --- a/spec/std/isa/inst/V/vsetivli.yaml +++ b/spec/std/isa/inst/V/vsetivli.yaml @@ -28,7 +28,7 @@ data_independent_timing: false operation(): | VectorState state = vector_state(); XReg vlen = VLEN; - XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.vsew); + XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.sew); XReg AVL = uimm; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; diff --git a/spec/std/isa/inst/V/vsetvl.yaml b/spec/std/isa/inst/V/vsetvl.yaml index 6d5d772308..dab232cdf8 100644 --- a/spec/std/isa/inst/V/vsetvl.yaml +++ b/spec/std/isa/inst/V/vsetvl.yaml @@ -28,7 +28,7 @@ data_independent_timing: false operation(): | VectorState state = vector_state(); XReg vlen = VLEN; - XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.vsew); + XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.sew); XReg AVL = xs1; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; diff --git a/spec/std/isa/inst/V/vsetvli.yaml b/spec/std/isa/inst/V/vsetvli.yaml index 7eb86a2993..b2a58380b7 100644 --- a/spec/std/isa/inst/V/vsetvli.yaml +++ b/spec/std/isa/inst/V/vsetvli.yaml @@ -28,7 +28,7 @@ data_independent_timing: false operation(): | VectorState state = vector_state(); XReg vlen = VLEN; - XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.vsew); + XReg vlmax = (vlen << state.log2_multiplier) >> (3 + state.sew); XReg AVL = xs1; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; diff --git a/spec/std/isa/isa/vec.idl b/spec/std/isa/isa/vec.idl index c3b967a8ab..a3473cdc81 100644 --- a/spec/std/isa/isa/vec.idl +++ b/spec/std/isa/isa/vec.idl @@ -12,10 +12,7 @@ # - integer widening arith () # the vector register file -Bits v[32] = [0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0]; +Bits v[32]; enum VectorLmulType { Divide @@ -23,7 +20,7 @@ enum VectorLmulType { } struct VectorState { - Bits<7> vsew; + Bits<7> sew; VectorLmulType lmul_type; Bits<2> log2_multiplier; } @@ -36,7 +33,7 @@ function vector_state { body { VectorState state; - state.vsew = 7'b1 << (3 + CSR[vtype].VSEW); + state.sew = 7'b1 << (3 + CSR[vtype].VSEW); Bits<3> vlmul = CSR[vtype].VLMUL; state.lmul_type = CSR[vtype].VLMUL[2] == 1'b1 ? VectorLmulType::Divide : VectorLmulType::Multiply; state.log2_multiplier = CSR[vtype].VLMUL[1:0]; From a88e07933158ac160598b2616574c07b9e071455 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 21 Sep 2025 11:49:13 -0700 Subject: [PATCH 18/23] Update spec/std/isa/ext/V.yaml Co-authored-by: Paul Clarke Signed-off-by: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> --- spec/std/isa/ext/V.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/spec/std/isa/ext/V.yaml b/spec/std/isa/ext/V.yaml index 3bd2d28f6c..ece774b922 100644 --- a/spec/std/isa/ext/V.yaml +++ b/spec/std/isa/ext/V.yaml @@ -58,8 +58,8 @@ params: enum: ["ceil(AVL/2)", "VLMAX", "custom"] FOLLOW_VTYPE_RESET_RECOMMENDATION: description: | - The spec recommends - but does not require - that on reset, vill is set, and remaining bits in vtype and vl are set to 0. - If this parameter is set to true, the CSR resets will follow this recommandation. If it is false, the resets will be "UNDEFINED_LEGAL". + It is recommended that at reset, vtype.vill is set, the remaining bits in vtype are zero, and vl is set to zero. + If this parameter is set to true, this recommendation is followed. If it is false, at reset the respective fields will be "UNDEFINED_LEGAL". schema: type: boolean VLEN: From fe0a0da1be435b5780d4844912f79be155f51c68 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 21 Sep 2025 11:49:50 -0700 Subject: [PATCH 19/23] Update spec/std/isa/csr/V/vxsat.yaml Co-authored-by: Paul Clarke Signed-off-by: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> --- spec/std/isa/csr/V/vxsat.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/std/isa/csr/V/vxsat.yaml b/spec/std/isa/csr/V/vxsat.yaml index 2e8fed6caa..aa247af097 100644 --- a/spec/std/isa/csr/V/vxsat.yaml +++ b/spec/std/isa/csr/V/vxsat.yaml @@ -26,6 +26,6 @@ fields: The vxsat bit is mirrored in vcsr. sw_write(csr_value): | - return csr_value.VALUE & (VLEN - 1); + return csr_value.VALUE & 1; type: RW-H reset_value: UNDEFINED_LEGAL From c0b3b3ce18cf0e9e3261dc9e2da4ba2e9600b1d6 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 21 Sep 2025 11:50:13 -0700 Subject: [PATCH 20/23] Update spec/std/isa/csr/V/vxrm.yaml Co-authored-by: Paul Clarke Signed-off-by: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> --- spec/std/isa/csr/V/vxrm.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/std/isa/csr/V/vxrm.yaml b/spec/std/isa/csr/V/vxrm.yaml index d0f32d44dc..9efcd7fe3b 100644 --- a/spec/std/isa/csr/V/vxrm.yaml +++ b/spec/std/isa/csr/V/vxrm.yaml @@ -41,6 +41,6 @@ fields: ! 11 ! rod ! round-to-odd (OR bits into LSB, aka "jam") ! \!v[d] & v[d-1:0]\!=0 sw_write(csr_value): | - return csr_value.VALUE & (VLEN - 1); + return csr_value.VALUE & 2b'11; type: RW-H reset_value: UNDEFINED_LEGAL From 34e2bb009e03f6ba2557944a4b096eac11978a47 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 21 Sep 2025 11:50:26 -0700 Subject: [PATCH 21/23] Update spec/std/isa/csr/V/vcsr.yaml Co-authored-by: Paul Clarke Signed-off-by: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> --- spec/std/isa/csr/V/vcsr.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/std/isa/csr/V/vcsr.yaml b/spec/std/isa/csr/V/vcsr.yaml index 513e189ba9..7c362829f2 100644 --- a/spec/std/isa/csr/V/vcsr.yaml +++ b/spec/std/isa/csr/V/vcsr.yaml @@ -11,7 +11,7 @@ address: 0x00F writable: true priv_mode: U length: MXLEN -description: Allows access to vxrm and vxsat CSRs +description: Contains aliases to vxrm and vxsat CSRs definedBy: V fields: VXRM: From 94daf9ddd99191a82897ac914b4c63c08fa46ec5 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> Date: Sun, 21 Sep 2025 11:51:00 -0700 Subject: [PATCH 22/23] Update spec/std/isa/inst/V/vsetivli.yaml Co-authored-by: Paul Clarke Signed-off-by: Jennifer Dupaquier <11723765+jmawet@users.noreply.github.com> --- spec/std/isa/inst/V/vsetivli.yaml | 35 ++++++------------------------- 1 file changed, 6 insertions(+), 29 deletions(-) diff --git a/spec/std/isa/inst/V/vsetivli.yaml b/spec/std/isa/inst/V/vsetivli.yaml index d0eb3b9e28..b4e57ac05b 100644 --- a/spec/std/isa/inst/V/vsetivli.yaml +++ b/spec/std/isa/inst/V/vsetivli.yaml @@ -47,35 +47,12 @@ operation(): | } XReg new_vtype = vtypei; - if (new_vtype[xlen() - 1] == 1'b1) { - # software is setting the illegal bit - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if ((new_vtype & 8'd0) != 0) { - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (new_vtype[5] == 1) { - # reserved vsew encoding - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (new_vtype[2:0] == 3'b100) { - # reserved LMUL - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (xlen() == 32 && new_vtype[2:0] == 3'b101) { - # reserved LMUL in RV32 + if ((new_vtype[xlen() - 1] == 1'b1) # software is setting the illegal bit + || ((new_vtype & 8'd0) != 0) # reserved bits + || (new_vtype[5] == 1) # reserved vsew encoding + || (new_vtype[2:0] == 3'b100) # reserved vlmul encoding + || (xlen() == 32 && new_vtype[2:0] == 3'b101)) # reserved LMUL in RV32 + { CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; CSR[vtype].VTA = 0; From 2921e24f97369ba164cd7d72061533d86f340294 Mon Sep 17 00:00:00 2001 From: Jennifer Dupaquier Date: Sun, 21 Sep 2025 12:04:53 -0700 Subject: [PATCH 23/23] adress thinkopenly's comments --- spec/std/isa/csr/V/vxrm.yaml | 2 +- spec/std/isa/inst/V/vsetivli.yaml | 28 +++++++------- spec/std/isa/inst/V/vsetvl.yaml | 63 ++++++++++--------------------- spec/std/isa/inst/V/vsetvli.yaml | 63 ++++++++++--------------------- 4 files changed, 55 insertions(+), 101 deletions(-) diff --git a/spec/std/isa/csr/V/vxrm.yaml b/spec/std/isa/csr/V/vxrm.yaml index 9efcd7fe3b..c071971a15 100644 --- a/spec/std/isa/csr/V/vxrm.yaml +++ b/spec/std/isa/csr/V/vxrm.yaml @@ -41,6 +41,6 @@ fields: ! 11 ! rod ! round-to-odd (OR bits into LSB, aka "jam") ! \!v[d] & v[d-1:0]\!=0 sw_write(csr_value): | - return csr_value.VALUE & 2b'11; + return csr_value.VALUE & 3; type: RW-H reset_value: UNDEFINED_LEGAL diff --git a/spec/std/isa/inst/V/vsetivli.yaml b/spec/std/isa/inst/V/vsetivli.yaml index b4e57ac05b..b77a4e8753 100644 --- a/spec/std/isa/inst/V/vsetivli.yaml +++ b/spec/std/isa/inst/V/vsetivli.yaml @@ -32,20 +32,6 @@ operation(): | XReg AVL = uimm; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (AVL < vlmax) { - CSR[vl].VALUE = AVL; - } else if (AVL < 2*vlmax) { - if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { - CSR[vl].VALUE = CEIL_AVL_OVER_TWO; - } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { - CSR[vl].VALUE = vlmax; - } else { - unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); - } - } else { - CSR[vl].VALUE = vlmax; - } - XReg new_vtype = vtypei; if ((new_vtype[xlen() - 1] == 1'b1) # software is setting the illegal bit || ((new_vtype & 8'd0) != 0) # reserved bits @@ -67,6 +53,20 @@ operation(): | CSR[vtype].VLMUL = new_vtype[2:0]; } + if (AVL < vlmax) { + CSR[vl].VALUE = AVL; + } else if (AVL < 2*vlmax) { + if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { + CSR[vl].VALUE = CEIL_AVL_OVER_TWO; + } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { + CSR[vl].VALUE = vlmax; + } else { + unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); + } + } else { + CSR[vl].VALUE = vlmax; + } + X[xd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; diff --git a/spec/std/isa/inst/V/vsetvl.yaml b/spec/std/isa/inst/V/vsetvl.yaml index dab232cdf8..b51ecd54cb 100644 --- a/spec/std/isa/inst/V/vsetvl.yaml +++ b/spec/std/isa/inst/V/vsetvl.yaml @@ -32,50 +32,13 @@ operation(): | XReg AVL = xs1; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (AVL < vlmax) { - CSR[vl].VALUE = AVL; - } else if (AVL < 2*vlmax) { - if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { - CSR[vl].VALUE = CEIL_AVL_OVER_TWO; - } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { - CSR[vl].VALUE = vlmax; - } else { - unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); - } - } else { - CSR[vl].VALUE = vlmax; - } - XReg new_vtype = xs2; - if (new_vtype[xlen() - 1] == 1'b1) { - # software is setting the illegal bit - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if ((new_vtype & 8'd0) != 0) { - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (new_vtype[5] == 1) { - # reserved vsew encoding - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (new_vtype[2:0] == 3'b100) { - # reserved LMUL - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (xlen() == 32 && new_vtype[2:0] == 3'b101) { - # reserved LMUL in RV32 + if ((new_vtype[xlen() - 1] == 1'b1) # software is setting the illegal bit + || ((new_vtype & 8'd0) != 0) # reserved bits + || (new_vtype[5] == 1) # reserved vsew encoding + || (new_vtype[2:0] == 3'b100) # reserved vlmul encoding + || (xlen() == 32 && new_vtype[2:0] == 3'b101)) # reserved LMUL in RV32 + { CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; CSR[vtype].VTA = 0; @@ -90,6 +53,20 @@ operation(): | CSR[vtype].VLMUL = new_vtype[2:0]; } + if (AVL < vlmax) { + CSR[vl].VALUE = AVL; + } else if (AVL < 2*vlmax) { + if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { + CSR[vl].VALUE = CEIL_AVL_OVER_TWO; + } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { + CSR[vl].VALUE = vlmax; + } else { + unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); + } + } else { + CSR[vl].VALUE = vlmax; + } + X[xd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0; diff --git a/spec/std/isa/inst/V/vsetvli.yaml b/spec/std/isa/inst/V/vsetvli.yaml index b2a58380b7..af434b805b 100644 --- a/spec/std/isa/inst/V/vsetvli.yaml +++ b/spec/std/isa/inst/V/vsetvli.yaml @@ -32,50 +32,13 @@ operation(): | XReg AVL = xs1; XReg CEIL_AVL_OVER_TWO = (AVL + 1) / 2; - if (AVL < vlmax) { - CSR[vl].VALUE = AVL; - } else if (AVL < 2*vlmax) { - if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { - CSR[vl].VALUE = CEIL_AVL_OVER_TWO; - } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { - CSR[vl].VALUE = vlmax; - } else { - unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); - } - } else { - CSR[vl].VALUE = vlmax; - } - XReg new_vtype = vtypei; - if (new_vtype[xlen() - 1] == 1'b1) { - # software is setting the illegal bit - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if ((new_vtype & 8'd0) != 0) { - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (new_vtype[5] == 1) { - # reserved vsew encoding - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (new_vtype[2:0] == 3'b100) { - # reserved LMUL - CSR[vtype].VILL = 1; - CSR[vtype].VMA = 0; - CSR[vtype].VTA = 0; - CSR[vtype].VSEW = 0; - CSR[vtype].VLMUL = 0; - } else if (xlen() == 32 && new_vtype[2:0] == 3'b101) { - # reserved LMUL in RV32 + if ((new_vtype[xlen() - 1] == 1'b1) # software is setting the illegal bit + || ((new_vtype & 8'd0) != 0) # reserved bits + || (new_vtype[5] == 1) # reserved vsew encoding + || (new_vtype[2:0] == 3'b100) # reserved vlmul encoding + || (xlen() == 32 && new_vtype[2:0] == 3'b101)) # reserved LMUL in RV32 + { CSR[vtype].VILL = 1; CSR[vtype].VMA = 0; CSR[vtype].VTA = 0; @@ -90,6 +53,20 @@ operation(): | CSR[vtype].VLMUL = new_vtype[2:0]; } + if (AVL < vlmax) { + CSR[vl].VALUE = AVL; + } else if (AVL < 2*vlmax) { + if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "ceil(AVL/2)") { + CSR[vl].VALUE = CEIL_AVL_OVER_TWO; + } else if (RVV_VL_WHEN_AVL_LT_DOUBLE_VLMAX == "VLMAX") { + CSR[vl].VALUE = vlmax; + } else { + unpredictable("Implementations may choose a custom value for vl in the case AVL < (2*VLMAX), so long as ceil(AVL/2) <= vl <= VLMAX"); + } + } else { + CSR[vl].VALUE = vlmax; + } + X[xd] = CSR[vl].VALUE; CSR[vstart].VALUE = 0;