[PATCH v7 3/8] hw/riscv: sifive_u: Align ROM reset vector data

frank.chang@sifive.com posted 8 patches 1 month, 1 week ago
Maintainers: Alistair Francis <Alistair.Francis@wdc.com>, Palmer Dabbelt <palmer@dabbelt.com>, Weiwei Li <liwei1518@gmail.com>, Daniel Henrique Barboza <daniel.barboza@oss.qualcomm.com>, Liu Zhiwei <zhiwei_liu@linux.alibaba.com>, Chao Liu <chao.liu@processmission.com>
There is a newer version of this series
[PATCH v7 3/8] hw/riscv: sifive_u: Align ROM reset vector data
Posted by frank.chang@sifive.com 1 month, 1 week ago
From: Frank Chang <frank.chang@sifive.com>

The SiFive U ROM reset vector data needs proper 8-byte alignment for
RV64 ld instructions. The misaligned load will cause exception when
Zicclsm is supported as SiFive U CPU doesn't support hardware misaligned
loads and stores.

Add padding to ensure start_addr and fdt_load_addr are placed at 8-byte
aligned offsets and adjust the load instruction offsets to match the new
data layout.

Signed-off-by: Frank Chang <frank.chang@sifive.com>
---
 hw/riscv/sifive_u.c | 11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index 99423ef472d..57a57c96e16 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -564,19 +564,20 @@ static void sifive_u_machine_init(MachineState *machine)
         0,
         0,
         0x00028067,                    /*     jr     t0 */
+        0x00000000,                    /* padding for alignment */
         start_addr,                    /* start: .dword */
         start_addr_hi32,
         fdt_load_addr,                 /* fdt_laddr: .dword */
         fdt_load_addr_hi32,
-        0x00000000,
                                        /* fw_dyn: */
     };
+
     if (riscv_is_32bit(&s->soc.u_cpus)) {
-        reset_vec[4] = 0x0202a583;     /*     lw     a1, 32(t0) */
-        reset_vec[5] = 0x0182a283;     /*     lw     t0, 24(t0) */
+        reset_vec[4] = 0x0242a583;     /*     lw     a1, 36(t0) */
+        reset_vec[5] = 0x01c2a283;     /*     lw     t0, 28(t0) */
     } else {
-        reset_vec[4] = 0x0202b583;     /*     ld     a1, 32(t0) */
-        reset_vec[5] = 0x0182b283;     /*     ld     t0, 24(t0) */
+        reset_vec[4] = 0x0242b583;     /*     ld     a1, 36(t0) */
+        reset_vec[5] = 0x01c2b283;     /*     ld     t0, 28(t0) */
     }
 
 
-- 
2.43.0
Re: [PATCH v7 3/8] hw/riscv: sifive_u: Align ROM reset vector data
Posted by Daniel Henrique Barboza 1 month, 1 week ago

On 8/5/2026 1:43 PM, frank.chang@sifive.com wrote:
> From: Frank Chang <frank.chang@sifive.com>
> 
> The SiFive U ROM reset vector data needs proper 8-byte alignment for
> RV64 ld instructions. The misaligned load will cause exception when
> Zicclsm is supported as SiFive U CPU doesn't support hardware misaligned
> loads and stores.
> 
> Add padding to ensure start_addr and fdt_load_addr are placed at 8-byte
> aligned offsets and adjust the load instruction offsets to match the new
> data layout.
> 
> Signed-off-by: Frank Chang <frank.chang@sifive.com>
> ---

Reviewed-by: Daniel Henrique Barboza <daniel.barboza@oss.qualcomm.com>

>   hw/riscv/sifive_u.c | 11 ++++++-----
>   1 file changed, 6 insertions(+), 5 deletions(-)
> 
> diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
> index 99423ef472d..57a57c96e16 100644
> --- a/hw/riscv/sifive_u.c
> +++ b/hw/riscv/sifive_u.c
> @@ -564,19 +564,20 @@ static void sifive_u_machine_init(MachineState *machine)
>           0,
>           0,
>           0x00028067,                    /*     jr     t0 */
> +        0x00000000,                    /* padding for alignment */
>           start_addr,                    /* start: .dword */
>           start_addr_hi32,
>           fdt_load_addr,                 /* fdt_laddr: .dword */
>           fdt_load_addr_hi32,
> -        0x00000000,
>                                          /* fw_dyn: */
>       };
> +
>       if (riscv_is_32bit(&s->soc.u_cpus)) {
> -        reset_vec[4] = 0x0202a583;     /*     lw     a1, 32(t0) */
> -        reset_vec[5] = 0x0182a283;     /*     lw     t0, 24(t0) */
> +        reset_vec[4] = 0x0242a583;     /*     lw     a1, 36(t0) */
> +        reset_vec[5] = 0x01c2a283;     /*     lw     t0, 28(t0) */
>       } else {
> -        reset_vec[4] = 0x0202b583;     /*     ld     a1, 32(t0) */
> -        reset_vec[5] = 0x0182b283;     /*     ld     t0, 24(t0) */
> +        reset_vec[4] = 0x0242b583;     /*     ld     a1, 36(t0) */
> +        reset_vec[5] = 0x01c2b283;     /*     ld     t0, 28(t0) */
>       }
>   
>