Message ID | 20190507223646.18981-1-jonathan@fintelia.io (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | target/riscv: More accurate handling of `sip` CSR | expand |
On Tue, 07 May 2019 15:36:46 PDT (-0700), jonathan@fintelia.io wrote: > According to the spec, "All bits besides SSIP, USIP, and UEIP in the sip > register are read-only." Further, if an interrupt is not delegated to mode x, > then "the corresponding bits in xip [...] should appear to be hardwired to > zero. This patch implements both of those requirements. > > Signed-off-by: Jonathan Behrens <jonathan@fintelia.io> > --- > target/riscv/csr.c | 7 +++++-- > 1 file changed, 5 insertions(+), 2 deletions(-) > > diff --git a/target/riscv/csr.c b/target/riscv/csr.c > index 1ec1222da1..fff7d834e8 100644 > --- a/target/riscv/csr.c > +++ b/target/riscv/csr.c > @@ -246,6 +246,7 @@ static const target_ulong sstatus_v1_9_mask = SSTATUS_SIE | SSTATUS_SPIE | > static const target_ulong sstatus_v1_10_mask = SSTATUS_SIE | SSTATUS_SPIE | > SSTATUS_UIE | SSTATUS_UPIE | SSTATUS_SPP | SSTATUS_FS | SSTATUS_XS | > SSTATUS_SUM | SSTATUS_MXR | SSTATUS_SD; > +static const target_ulong sip_writable_mask = SIP_SSIP | MIP_USIP | MIP_UEIP; > > #if defined(TARGET_RISCV32) > static const char valid_vm_1_09[16] = { > @@ -694,8 +695,10 @@ static int write_sbadaddr(CPURISCVState *env, int csrno, target_ulong val) > static int rmw_sip(CPURISCVState *env, int csrno, target_ulong *ret_value, > target_ulong new_value, target_ulong write_mask) > { > - return rmw_mip(env, CSR_MSTATUS, ret_value, new_value, > - write_mask & env->mideleg); > + int ret = rmw_mip(env, CSR_MSTATUS, ret_value, new_value, > + write_mask & env->mideleg & sip_writable_mask); > + *ret_value &= env->mideleg; > + return ret; > } > > /* Supervisor Protection and Translation */ Reviewed-by: Palmer Dabbelt <palmer@sifive.com> Thanks!
diff --git a/target/riscv/csr.c b/target/riscv/csr.c index 1ec1222da1..fff7d834e8 100644 --- a/target/riscv/csr.c +++ b/target/riscv/csr.c @@ -246,6 +246,7 @@ static const target_ulong sstatus_v1_9_mask = SSTATUS_SIE | SSTATUS_SPIE | static const target_ulong sstatus_v1_10_mask = SSTATUS_SIE | SSTATUS_SPIE | SSTATUS_UIE | SSTATUS_UPIE | SSTATUS_SPP | SSTATUS_FS | SSTATUS_XS | SSTATUS_SUM | SSTATUS_MXR | SSTATUS_SD; +static const target_ulong sip_writable_mask = SIP_SSIP | MIP_USIP | MIP_UEIP; #if defined(TARGET_RISCV32) static const char valid_vm_1_09[16] = { @@ -694,8 +695,10 @@ static int write_sbadaddr(CPURISCVState *env, int csrno, target_ulong val) static int rmw_sip(CPURISCVState *env, int csrno, target_ulong *ret_value, target_ulong new_value, target_ulong write_mask) { - return rmw_mip(env, CSR_MSTATUS, ret_value, new_value, - write_mask & env->mideleg); + int ret = rmw_mip(env, CSR_MSTATUS, ret_value, new_value, + write_mask & env->mideleg & sip_writable_mask); + *ret_value &= env->mideleg; + return ret; } /* Supervisor Protection and Translation */
According to the spec, "All bits besides SSIP, USIP, and UEIP in the sip register are read-only." Further, if an interrupt is not delegated to mode x, then "the corresponding bits in xip [...] should appear to be hardwired to zero. This patch implements both of those requirements. Signed-off-by: Jonathan Behrens <jonathan@fintelia.io> --- target/riscv/csr.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)