Hi Aaron,

On Sun, May 31, 2026 at 09:54:53PM -0400, Aaron Merey wrote:
> The riscv_disasm function reads instruction mnemonics from static
> arrays based on the Control and Status Register (CSR) number encoded
> in an instruction.  Two separate bounds checks performed before reading
> from these arrays had incorrect upper bounds and allowed out-of-bounds
> reads.

So this is all for 0x1c SYSTEM. Nice catch. Looking at the code it is
fairly obvious only those described in those (small) static arrays can
be decoded.

> Fix two CSR bounds checks to prevent this. The affected CSR numbers that
> are no longer included in the modified checks are now properly handled
> in a generic CSR handler in the riscv_disasm function.

Where they are just printed as hex numbers.

> Signed-off-by: Aaron Merey <[email protected]>
> ---
>  libcpu/riscv_disasm.c | 4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)
> 
> diff --git a/libcpu/riscv_disasm.c b/libcpu/riscv_disasm.c
> index 749d4567..38a9ab9f 100644
> --- a/libcpu/riscv_disasm.c
> +++ b/libcpu/riscv_disasm.c
> @@ -1097,7 +1097,7 @@ riscv_disasm (Ebl *ebl,
>             else if ((word & 0x3000) == 0x2000 && rs1 == 0)
>               {
>                 uint32_t csr = word >> 20;
> -               if (/* csr >= 0x000 && */ csr <= 0x007)
> +               if (/* csr >= 0x000 && */ csr <= 0x003)
>                   {
>                     static const char *const unprivrw[4] =

Right, they have to fit in that array.

>                       {
> @@ -1105,7 +1105,7 @@ riscv_disasm (Ebl *ebl,
>                       };
>                     mne = unprivrw[csr - 0x000];
>                   }
> -               else if (csr >= 0xc00 && csr <= 0xc03)
> +               else if (csr >= 0xc00 && csr <= 0xc02)
>                   {
>                     static const char *const unprivrolow[3] =

Likewise in this 3 element array.

Looks good,

Mark

Reply via email to