* Updates for asm/ptrace/insn code
@ 2024-12-01 10:27 Ben Dooks
2024-12-01 10:27 ` [PATCH v2 1/3] riscv: ptrace: add regs_set_register() Ben Dooks
` (2 more replies)
0 siblings, 3 replies; 9+ messages in thread
From: Ben Dooks @ 2024-12-01 10:27 UTC (permalink / raw)
To: linux-riscv; +Cc: ajones, palmer
This is a re-send of the series that was setting up for the RDCYCLE
emulation in kernel space. I think these are still useful so am
re-sending this series with comments and fixups.
Even if we don't emulate RDCYCLE, we may still want to check for it
in the trap handler and possibly allow for it to be emulated later
if people feel that would be good (or at least some sort of warning
printed)
Thanks for the reviews. Hopefully this isn't too late for inclusion.
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 9+ messages in thread* [PATCH v2 1/3] riscv: ptrace: add regs_set_register() 2024-12-01 10:27 Updates for asm/ptrace/insn code Ben Dooks @ 2024-12-01 10:27 ` Ben Dooks 2024-12-02 9:02 ` Andrew Jones 2024-12-02 17:09 ` Björn Töpel 2024-12-01 10:27 ` [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction Ben Dooks 2024-12-01 10:27 ` [PATCH v2 3/3] riscv: insn: add RV_EXTRACT_FUNCT3() Ben Dooks 2 siblings, 2 replies; 9+ messages in thread From: Ben Dooks @ 2024-12-01 10:27 UTC (permalink / raw) To: linux-riscv; +Cc: ajones, palmer, Ben Dooks Since we have regs_get_register() and we could use the set counterpart for things like fixing up traps, add regs_set_register() to set a pt_regs value from offset. Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> --- v2: - fixed Andrew Jones' suggestions for comments --- arch/riscv/include/asm/ptrace.h | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/arch/riscv/include/asm/ptrace.h b/arch/riscv/include/asm/ptrace.h index b5b0adcc85c1..45c503b592c8 100644 --- a/arch/riscv/include/asm/ptrace.h +++ b/arch/riscv/include/asm/ptrace.h @@ -143,6 +143,26 @@ static inline unsigned long regs_get_register(struct pt_regs *regs, return *(unsigned long *)((unsigned long)regs + offset); } +/** + * regs_set_register() - set register value at its offset + * @regs: pt_regs to which register value is set + * @offset: offset of the register. + * @value: value to set register to + * + * regs_set_register sets the value @to to a register whose offset from @regs. + * The @offset is the offset of the register in struct pt_regs. + * If @offset is bigger than MAX_REG_OFFSET, this will ignore the write. + */ +static inline void regs_set_register(struct pt_regs *regs, + unsigned int offset, + unsigned long value) +{ + if (unlikely(offset > MAX_REG_OFFSET)) + return; + + *(unsigned long *)((unsigned long)regs + offset) = value; +} + /** * regs_get_kernel_argument() - get Nth function argument in kernel * @regs: pt_regs of that context -- 2.37.2.352.g3c44437643 _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [PATCH v2 1/3] riscv: ptrace: add regs_set_register() 2024-12-01 10:27 ` [PATCH v2 1/3] riscv: ptrace: add regs_set_register() Ben Dooks @ 2024-12-02 9:02 ` Andrew Jones 2024-12-02 17:09 ` Björn Töpel 1 sibling, 0 replies; 9+ messages in thread From: Andrew Jones @ 2024-12-02 9:02 UTC (permalink / raw) To: Ben Dooks; +Cc: linux-riscv, palmer On Sun, Dec 01, 2024 at 10:27:57AM +0000, Ben Dooks wrote: > Since we have regs_get_register() and we could use the set counterpart > for things like fixing up traps, add regs_set_register() to set a pt_regs > value from offset. > > Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> > --- > v2: > - fixed Andrew Jones' suggestions for comments > --- > arch/riscv/include/asm/ptrace.h | 20 ++++++++++++++++++++ > 1 file changed, 20 insertions(+) > > diff --git a/arch/riscv/include/asm/ptrace.h b/arch/riscv/include/asm/ptrace.h > index b5b0adcc85c1..45c503b592c8 100644 > --- a/arch/riscv/include/asm/ptrace.h > +++ b/arch/riscv/include/asm/ptrace.h > @@ -143,6 +143,26 @@ static inline unsigned long regs_get_register(struct pt_regs *regs, > return *(unsigned long *)((unsigned long)regs + offset); > } > > +/** > + * regs_set_register() - set register value at its offset > + * @regs: pt_regs to which register value is set > + * @offset: offset of the register. drop the '.' > + * @value: value to set register to > + * > + * regs_set_register sets the value @to to a register whose offset from @regs. ^ @value but just write regs_set_register sets @value... also s/whose/which is/ > + * The @offset is the offset of the register in struct pt_regs. > + * If @offset is bigger than MAX_REG_OFFSET, this will ignore the write. > + */ > +static inline void regs_set_register(struct pt_regs *regs, > + unsigned int offset, > + unsigned long value) > +{ > + if (unlikely(offset > MAX_REG_OFFSET)) > + return; > + > + *(unsigned long *)((unsigned long)regs + offset) = value; > +} > + > /** > * regs_get_kernel_argument() - get Nth function argument in kernel > * @regs: pt_regs of that context > -- > 2.37.2.352.g3c44437643 > Otherwise, Reviewed-by: Andrew Jones <ajones@ventanamicro.com> _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v2 1/3] riscv: ptrace: add regs_set_register() 2024-12-01 10:27 ` [PATCH v2 1/3] riscv: ptrace: add regs_set_register() Ben Dooks 2024-12-02 9:02 ` Andrew Jones @ 2024-12-02 17:09 ` Björn Töpel 1 sibling, 0 replies; 9+ messages in thread From: Björn Töpel @ 2024-12-02 17:09 UTC (permalink / raw) To: Ben Dooks, linux-riscv; +Cc: ajones, palmer, Ben Dooks Ben Dooks <ben.dooks@codethink.co.uk> writes: > Since we have regs_get_register() and we could use the set counterpart > for things like fixing up traps, add regs_set_register() to set a pt_regs > value from offset. > > Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> > --- > v2: > - fixed Andrew Jones' suggestions for comments > --- > arch/riscv/include/asm/ptrace.h | 20 ++++++++++++++++++++ > 1 file changed, 20 insertions(+) > > diff --git a/arch/riscv/include/asm/ptrace.h b/arch/riscv/include/asm/ptrace.h > index b5b0adcc85c1..45c503b592c8 100644 > --- a/arch/riscv/include/asm/ptrace.h > +++ b/arch/riscv/include/asm/ptrace.h > @@ -143,6 +143,26 @@ static inline unsigned long regs_get_register(struct pt_regs *regs, > return *(unsigned long *)((unsigned long)regs + offset); > } > > +/** > + * regs_set_register() - set register value at its offset > + * @regs: pt_regs to which register value is set > + * @offset: offset of the register. > + * @value: value to set register to > + * > + * regs_set_register sets the value @to to a register whose offset from @regs. > + * The @offset is the offset of the register in struct pt_regs. > + * If @offset is bigger than MAX_REG_OFFSET, this will ignore the write. > + */ > +static inline void regs_set_register(struct pt_regs *regs, > + unsigned int offset, > + unsigned long value) Hobby horse warning! If you're resending for drew's comments, please use the full 100 chars! Björn _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply [flat|nested] 9+ messages in thread
* [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction 2024-12-01 10:27 Updates for asm/ptrace/insn code Ben Dooks 2024-12-01 10:27 ` [PATCH v2 1/3] riscv: ptrace: add regs_set_register() Ben Dooks @ 2024-12-01 10:27 ` Ben Dooks 2024-12-02 9:16 ` Andrew Jones 2024-12-02 17:30 ` Björn Töpel 2024-12-01 10:27 ` [PATCH v2 3/3] riscv: insn: add RV_EXTRACT_FUNCT3() Ben Dooks 2 siblings, 2 replies; 9+ messages in thread From: Ben Dooks @ 2024-12-01 10:27 UTC (permalink / raw) To: linux-riscv; +Cc: ajones, palmer, Ben Dooks Add the trapped instruction (insn) as the second argument to riscv_v_first_use_handler() from the trap handler so when we add more handlers we can do the fetch of the instruction just once. Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> --- - fixed wording of patch from rfc v2: - fixed todo by going to illegal instruction error if get_user fails - added pointer print for failed read - fixed issues with rebasing onto main branch --- arch/riscv/include/asm/vector.h | 4 ++-- arch/riscv/kernel/traps.c | 14 +++++++++++++- arch/riscv/kernel/vector.c | 11 +---------- 3 files changed, 16 insertions(+), 13 deletions(-) diff --git a/arch/riscv/include/asm/vector.h b/arch/riscv/include/asm/vector.h index c7c023afbacd..9ec2473c1b73 100644 --- a/arch/riscv/include/asm/vector.h +++ b/arch/riscv/include/asm/vector.h @@ -22,7 +22,7 @@ extern unsigned long riscv_v_vsize; int riscv_v_setup_vsize(void); bool insn_is_vector(u32 insn_buf); -bool riscv_v_first_use_handler(struct pt_regs *regs); +bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn); void kernel_vector_begin(void); void kernel_vector_end(void); void get_cpu_vector_context(void); @@ -270,7 +270,7 @@ struct pt_regs; static inline int riscv_v_setup_vsize(void) { return -EOPNOTSUPP; } static __always_inline bool has_vector(void) { return false; } static __always_inline bool insn_is_vector(u32 insn_buf) { return false; } -static inline bool riscv_v_first_use_handler(struct pt_regs *regs) { return false; } +static inline bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn) { return false; } static inline bool riscv_v_vstate_query(struct pt_regs *regs) { return false; } static inline bool riscv_v_vstate_ctrl_user_allowed(void) { return false; } #define riscv_v_vsize (0) diff --git a/arch/riscv/kernel/traps.c b/arch/riscv/kernel/traps.c index 51ebfd23e007..9662138ba45c 100644 --- a/arch/riscv/kernel/traps.c +++ b/arch/riscv/kernel/traps.c @@ -172,11 +172,23 @@ asmlinkage __visible __trap_section void do_trap_insn_illegal(struct pt_regs *re bool handled; if (user_mode(regs)) { + u32 __user *epc = (u32 __user *)regs->epc; + u32 insn = (u32)regs->badaddr; + irqentry_enter_from_user_mode(regs); local_irq_enable(); - handled = riscv_v_first_use_handler(regs); + if (!insn) { + if (__get_user(insn, epc)) { + printk_ratelimited(KERN_ERR "traps: failed to read instruction at user %px\n", epc); + handled = false; + insn = 0; + } + } + + if (insn) + handled = riscv_v_first_use_handler(regs, insn); local_irq_disable(); diff --git a/arch/riscv/kernel/vector.c b/arch/riscv/kernel/vector.c index 821818886fab..08164a9121fe 100644 --- a/arch/riscv/kernel/vector.c +++ b/arch/riscv/kernel/vector.c @@ -168,11 +168,8 @@ bool riscv_v_vstate_ctrl_user_allowed(void) } EXPORT_SYMBOL_GPL(riscv_v_vstate_ctrl_user_allowed); -bool riscv_v_first_use_handler(struct pt_regs *regs) +bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn) { - u32 __user *epc = (u32 __user *)regs->epc; - u32 insn = (u32)regs->badaddr; - if (!has_vector()) return false; @@ -184,12 +181,6 @@ bool riscv_v_first_use_handler(struct pt_regs *regs) if (riscv_v_vstate_query(regs)) return false; - /* Get the instruction */ - if (!insn) { - if (__get_user(insn, epc)) - return false; - } - /* Filter out non-V instructions */ if (!insn_is_vector(insn)) return false; -- 2.37.2.352.g3c44437643 _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction 2024-12-01 10:27 ` [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction Ben Dooks @ 2024-12-02 9:16 ` Andrew Jones 2024-12-02 9:23 ` Ben Dooks 2024-12-02 17:30 ` Björn Töpel 1 sibling, 1 reply; 9+ messages in thread From: Andrew Jones @ 2024-12-02 9:16 UTC (permalink / raw) To: Ben Dooks; +Cc: linux-riscv, palmer On Sun, Dec 01, 2024 at 10:27:58AM +0000, Ben Dooks wrote: > Add the trapped instruction (insn) as the second argument to > riscv_v_first_use_handler() from the trap handler so when we > add more handlers we can do the fetch of the instruction just > once. > > Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> > --- > - fixed wording of patch from rfc > v2: > - fixed todo by going to illegal instruction error if get_user fails > - added pointer print for failed read > - fixed issues with rebasing onto main branch > --- > arch/riscv/include/asm/vector.h | 4 ++-- > arch/riscv/kernel/traps.c | 14 +++++++++++++- > arch/riscv/kernel/vector.c | 11 +---------- > 3 files changed, 16 insertions(+), 13 deletions(-) > > diff --git a/arch/riscv/include/asm/vector.h b/arch/riscv/include/asm/vector.h > index c7c023afbacd..9ec2473c1b73 100644 > --- a/arch/riscv/include/asm/vector.h > +++ b/arch/riscv/include/asm/vector.h > @@ -22,7 +22,7 @@ > extern unsigned long riscv_v_vsize; > int riscv_v_setup_vsize(void); > bool insn_is_vector(u32 insn_buf); > -bool riscv_v_first_use_handler(struct pt_regs *regs); > +bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn); > void kernel_vector_begin(void); > void kernel_vector_end(void); > void get_cpu_vector_context(void); > @@ -270,7 +270,7 @@ struct pt_regs; > static inline int riscv_v_setup_vsize(void) { return -EOPNOTSUPP; } > static __always_inline bool has_vector(void) { return false; } > static __always_inline bool insn_is_vector(u32 insn_buf) { return false; } > -static inline bool riscv_v_first_use_handler(struct pt_regs *regs) { return false; } > +static inline bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn) { return false; } > static inline bool riscv_v_vstate_query(struct pt_regs *regs) { return false; } > static inline bool riscv_v_vstate_ctrl_user_allowed(void) { return false; } > #define riscv_v_vsize (0) > diff --git a/arch/riscv/kernel/traps.c b/arch/riscv/kernel/traps.c > index 51ebfd23e007..9662138ba45c 100644 > --- a/arch/riscv/kernel/traps.c > +++ b/arch/riscv/kernel/traps.c > @@ -172,11 +172,23 @@ asmlinkage __visible __trap_section void do_trap_insn_illegal(struct pt_regs *re > bool handled; > > if (user_mode(regs)) { > + u32 __user *epc = (u32 __user *)regs->epc; > + u32 insn = (u32)regs->badaddr; > + > irqentry_enter_from_user_mode(regs); > > local_irq_enable(); > > - handled = riscv_v_first_use_handler(regs); > + if (!insn) { > + if (__get_user(insn, epc)) { > + printk_ratelimited(KERN_ERR "traps: failed to read instruction at user %px\n", epc); I don't think we want this, even ratelimited. > + handled = false; > + insn = 0; > + } > + } > + > + if (insn) > + handled = riscv_v_first_use_handler(regs, insn); > > local_irq_disable(); > > diff --git a/arch/riscv/kernel/vector.c b/arch/riscv/kernel/vector.c > index 821818886fab..08164a9121fe 100644 > --- a/arch/riscv/kernel/vector.c > +++ b/arch/riscv/kernel/vector.c > @@ -168,11 +168,8 @@ bool riscv_v_vstate_ctrl_user_allowed(void) > } > EXPORT_SYMBOL_GPL(riscv_v_vstate_ctrl_user_allowed); > > -bool riscv_v_first_use_handler(struct pt_regs *regs) > +bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn) > { > - u32 __user *epc = (u32 __user *)regs->epc; > - u32 insn = (u32)regs->badaddr; > - > if (!has_vector()) > return false; > > @@ -184,12 +181,6 @@ bool riscv_v_first_use_handler(struct pt_regs *regs) > if (riscv_v_vstate_query(regs)) > return false; > > - /* Get the instruction */ > - if (!insn) { > - if (__get_user(insn, epc)) > - return false; > - } > - > /* Filter out non-V instructions */ > if (!insn_is_vector(insn)) > return false; > -- > 2.37.2.352.g3c44437643 > Thanks, drew _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction 2024-12-02 9:16 ` Andrew Jones @ 2024-12-02 9:23 ` Ben Dooks 0 siblings, 0 replies; 9+ messages in thread From: Ben Dooks @ 2024-12-02 9:23 UTC (permalink / raw) To: Andrew Jones; +Cc: linux-riscv, palmer On 02/12/2024 09:16, Andrew Jones wrote: > On Sun, Dec 01, 2024 at 10:27:58AM +0000, Ben Dooks wrote: >> Add the trapped instruction (insn) as the second argument to >> riscv_v_first_use_handler() from the trap handler so when we >> add more handlers we can do the fetch of the instruction just >> once. >> >> Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> >> --- >> - fixed wording of patch from rfc >> v2: >> - fixed todo by going to illegal instruction error if get_user fails >> - added pointer print for failed read >> - fixed issues with rebasing onto main branch >> --- >> arch/riscv/include/asm/vector.h | 4 ++-- >> arch/riscv/kernel/traps.c | 14 +++++++++++++- >> arch/riscv/kernel/vector.c | 11 +---------- >> 3 files changed, 16 insertions(+), 13 deletions(-) >> >> diff --git a/arch/riscv/include/asm/vector.h b/arch/riscv/include/asm/vector.h >> index c7c023afbacd..9ec2473c1b73 100644 >> --- a/arch/riscv/include/asm/vector.h >> +++ b/arch/riscv/include/asm/vector.h >> @@ -22,7 +22,7 @@ >> extern unsigned long riscv_v_vsize; >> int riscv_v_setup_vsize(void); >> bool insn_is_vector(u32 insn_buf); >> -bool riscv_v_first_use_handler(struct pt_regs *regs); >> +bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn); >> void kernel_vector_begin(void); >> void kernel_vector_end(void); >> void get_cpu_vector_context(void); >> @@ -270,7 +270,7 @@ struct pt_regs; >> static inline int riscv_v_setup_vsize(void) { return -EOPNOTSUPP; } >> static __always_inline bool has_vector(void) { return false; } >> static __always_inline bool insn_is_vector(u32 insn_buf) { return false; } >> -static inline bool riscv_v_first_use_handler(struct pt_regs *regs) { return false; } >> +static inline bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn) { return false; } >> static inline bool riscv_v_vstate_query(struct pt_regs *regs) { return false; } >> static inline bool riscv_v_vstate_ctrl_user_allowed(void) { return false; } >> #define riscv_v_vsize (0) >> diff --git a/arch/riscv/kernel/traps.c b/arch/riscv/kernel/traps.c >> index 51ebfd23e007..9662138ba45c 100644 >> --- a/arch/riscv/kernel/traps.c >> +++ b/arch/riscv/kernel/traps.c >> @@ -172,11 +172,23 @@ asmlinkage __visible __trap_section void do_trap_insn_illegal(struct pt_regs *re >> bool handled; >> >> if (user_mode(regs)) { >> + u32 __user *epc = (u32 __user *)regs->epc; >> + u32 insn = (u32)regs->badaddr; >> + >> irqentry_enter_from_user_mode(regs); >> >> local_irq_enable(); >> >> - handled = riscv_v_first_use_handler(regs); >> + if (!insn) { >> + if (__get_user(insn, epc)) { >> + printk_ratelimited(KERN_ERR "traps: failed to read instruction at user %px\n", epc); > > I don't think we want this, even ratelimited. > Ok, it is a bit weird but I suppose it will end up generating a fault. -- Ben Dooks http://www.codethink.co.uk/ Senior Engineer Codethink - Providing Genius https://www.codethink.co.uk/privacy.html _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction 2024-12-01 10:27 ` [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction Ben Dooks 2024-12-02 9:16 ` Andrew Jones @ 2024-12-02 17:30 ` Björn Töpel 1 sibling, 0 replies; 9+ messages in thread From: Björn Töpel @ 2024-12-02 17:30 UTC (permalink / raw) To: Ben Dooks, linux-riscv; +Cc: ajones, palmer, Ben Dooks Ben Dooks <ben.dooks@codethink.co.uk> writes: > Add the trapped instruction (insn) as the second argument to > riscv_v_first_use_handler() from the trap handler so when we > add more handlers we can do the fetch of the instruction just > once. > > Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> > --- > - fixed wording of patch from rfc > v2: > - fixed todo by going to illegal instruction error if get_user fails > - added pointer print for failed read > - fixed issues with rebasing onto main branch > --- > arch/riscv/include/asm/vector.h | 4 ++-- > arch/riscv/kernel/traps.c | 14 +++++++++++++- > arch/riscv/kernel/vector.c | 11 +---------- > 3 files changed, 16 insertions(+), 13 deletions(-) > > diff --git a/arch/riscv/include/asm/vector.h b/arch/riscv/include/asm/vector.h > index c7c023afbacd..9ec2473c1b73 100644 > --- a/arch/riscv/include/asm/vector.h > +++ b/arch/riscv/include/asm/vector.h > @@ -22,7 +22,7 @@ > extern unsigned long riscv_v_vsize; > int riscv_v_setup_vsize(void); > bool insn_is_vector(u32 insn_buf); > -bool riscv_v_first_use_handler(struct pt_regs *regs); > +bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn); > void kernel_vector_begin(void); > void kernel_vector_end(void); > void get_cpu_vector_context(void); > @@ -270,7 +270,7 @@ struct pt_regs; > static inline int riscv_v_setup_vsize(void) { return -EOPNOTSUPP; } > static __always_inline bool has_vector(void) { return false; } > static __always_inline bool insn_is_vector(u32 insn_buf) { return false; } > -static inline bool riscv_v_first_use_handler(struct pt_regs *regs) { return false; } > +static inline bool riscv_v_first_use_handler(struct pt_regs *regs, u32 insn) { return false; } > static inline bool riscv_v_vstate_query(struct pt_regs *regs) { return false; } > static inline bool riscv_v_vstate_ctrl_user_allowed(void) { return false; } > #define riscv_v_vsize (0) > diff --git a/arch/riscv/kernel/traps.c b/arch/riscv/kernel/traps.c > index 51ebfd23e007..9662138ba45c 100644 > --- a/arch/riscv/kernel/traps.c > +++ b/arch/riscv/kernel/traps.c > @@ -172,11 +172,23 @@ asmlinkage __visible __trap_section void do_trap_insn_illegal(struct pt_regs *re > bool handled; > > if (user_mode(regs)) { > + u32 __user *epc = (u32 __user *)regs->epc; > + u32 insn = (u32)regs->badaddr; > + > irqentry_enter_from_user_mode(regs); > > local_irq_enable(); > > - handled = riscv_v_first_use_handler(regs); > + if (!insn) { > + if (__get_user(insn, epc)) { > + printk_ratelimited(KERN_ERR "traps: failed to read instruction at user %px\n", epc); > + handled = false; > + insn = 0; > + } > + } > + > + if (insn) > + handled = riscv_v_first_use_handler(regs, insn); Maybe it's just me, but this addition makes it a bit hard (harder!) to read. Maybe replace the chunk something in the lines of: if (!insn && __get_user(insn, epc)) goto out; handled = riscv_v_first_use_handler(regs, insn); out: Björn _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply [flat|nested] 9+ messages in thread
* [PATCH v2 3/3] riscv: insn: add RV_EXTRACT_FUNCT3() 2024-12-01 10:27 Updates for asm/ptrace/insn code Ben Dooks 2024-12-01 10:27 ` [PATCH v2 1/3] riscv: ptrace: add regs_set_register() Ben Dooks 2024-12-01 10:27 ` [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction Ben Dooks @ 2024-12-01 10:27 ` Ben Dooks 2 siblings, 0 replies; 9+ messages in thread From: Ben Dooks @ 2024-12-01 10:27 UTC (permalink / raw) To: linux-riscv; +Cc: ajones, palmer, Ben Dooks Add extraction for the func3 field of most instructions for use with anyone who needs it. Note, added this for decoding of CSR accesses for work we did looking at the RDCYCLE v RDTIME calls. Signed-off-by: Ben Dooks <ben.dooks@codethink.co.uk> Reviewed-by: Andrew Jones <ajones@ventanamicro.com> --- arch/riscv/include/asm/insn.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/arch/riscv/include/asm/insn.h b/arch/riscv/include/asm/insn.h index 09fde95a5e8f..c67f44ff2066 100644 --- a/arch/riscv/include/asm/insn.h +++ b/arch/riscv/include/asm/insn.h @@ -299,6 +299,10 @@ static __always_inline bool riscv_insn_is_c_jalr(u32 code) ({typeof(x) x_ = (x); \ (RV_X(x_, RVG_RD_OPOFF, RVG_RD_MASK)); }) +#define RV_EXTRACT_FUNCT3(x) \ + ({typeof(x) x_ = (x); \ + (RV_X(x_, RV_INSN_FUNCT3_OPOFF, RV_INSN_FUNCT3_MASK)); }) + #define RV_EXTRACT_UTYPE_IMM(x) \ ({typeof(x) x_ = (x); \ (RV_X(x_, RV_U_IMM_31_12_OPOFF, RV_U_IMM_31_12_MASK)); }) -- 2.37.2.352.g3c44437643 _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv ^ permalink raw reply related [flat|nested] 9+ messages in thread
end of thread, other threads:[~2024-12-02 17:36 UTC | newest] Thread overview: 9+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2024-12-01 10:27 Updates for asm/ptrace/insn code Ben Dooks 2024-12-01 10:27 ` [PATCH v2 1/3] riscv: ptrace: add regs_set_register() Ben Dooks 2024-12-02 9:02 ` Andrew Jones 2024-12-02 17:09 ` Björn Töpel 2024-12-01 10:27 ` [PATCH v2 2/3] riscv: traps: make insn fetch common in unknown instruction Ben Dooks 2024-12-02 9:16 ` Andrew Jones 2024-12-02 9:23 ` Ben Dooks 2024-12-02 17:30 ` Björn Töpel 2024-12-01 10:27 ` [PATCH v2 3/3] riscv: insn: add RV_EXTRACT_FUNCT3() Ben Dooks
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox