lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Date:   Tue, 6 Sep 2022 11:20:40 +0200
From:   Peter Zijlstra <peterz@...radead.org>
To:     guoren@...nel.org
Cc:     arnd@...db.de, palmer@...osinc.com, tglx@...utronix.de,
        luto@...nel.org, conor.dooley@...rochip.com, heiko@...ech.de,
        jszhang@...nel.org, lazyparser@...il.com, falcon@...ylab.org,
        chenhuacai@...nel.org, apatel@...tanamicro.com,
        atishp@...shpatra.org, palmer@...belt.com,
        paul.walmsley@...ive.com, bigeasy@...utronix.de,
        linux-arch@...r.kernel.org, linux-kernel@...r.kernel.org,
        linux-riscv@...ts.infradead.org, Guo Ren <guoren@...ux.alibaba.com>
Subject: Re: [PATCH V3 4/7] riscv: convert to generic entry

On Mon, Sep 05, 2022 at 11:54:20PM -0400, guoren@...nel.org wrote:

> +asmlinkage void noinstr do_riscv_irq(struct pt_regs *regs)
> +{
> +	struct pt_regs *old_regs;
> +	irqentry_state_t state = irqentry_enter(regs);
> +
> +	irq_enter_rcu();
> +	old_regs = set_irq_regs(regs);
> +	handle_arch_irq(regs);
> +	set_irq_regs(old_regs);
> +	irq_exit_rcu();
> +
> +	irqentry_exit(regs, state);
> +}

The above is right in that everything that calls irqentry_enter() should
be noinstr; however all the below instances get it wrong:

>  #define DO_ERROR_INFO(name, signo, code, str)				\
>  asmlinkage __visible __trap_section void name(struct pt_regs *regs)	\
>  {									\
> +	irqentry_state_t state = irqentry_enter(regs);			\
>  	do_trap_error(regs, signo, code, regs->epc, "Oops - " str);	\
> +	irqentry_exit(regs, state);					\
>  }
>  
>  DO_ERROR_INFO(do_trap_unknown,
> @@ -123,18 +126,22 @@ int handle_misaligned_store(struct pt_regs *regs);
>  
>  asmlinkage void __trap_section do_trap_load_misaligned(struct pt_regs *regs)
>  {
> +	irqentry_state_t state = irqentry_enter(regs);
>  	if (!handle_misaligned_load(regs))
>  		return;
>  	do_trap_error(regs, SIGBUS, BUS_ADRALN, regs->epc,
>  		      "Oops - load address misaligned");
> +	irqentry_exit(regs, state);
>  }
>  
>  asmlinkage void __trap_section do_trap_store_misaligned(struct pt_regs *regs)
>  {
> +	irqentry_state_t state = irqentry_enter(regs);
>  	if (!handle_misaligned_store(regs))
>  		return;
>  	do_trap_error(regs, SIGBUS, BUS_ADRALN, regs->epc,
>  		      "Oops - store (or AMO) address misaligned");
> +	irqentry_exit(regs, state);
>  }
>  #endif
>  DO_ERROR_INFO(do_trap_store_fault,
> @@ -158,6 +165,8 @@ static inline unsigned long get_break_insn_length(unsigned long pc)
>  
>  asmlinkage __visible __trap_section void do_trap_break(struct pt_regs *regs)
>  {
> +	irqentry_state_t state = irqentry_enter(regs);
> +
>  #ifdef CONFIG_KPROBES
>  	if (kprobe_single_step_handler(regs))
>  		return;
> @@ -185,6 +194,8 @@ asmlinkage __visible __trap_section void do_trap_break(struct pt_regs *regs)
>  		regs->epc += get_break_insn_length(regs->epc);
>  	else
>  		die(regs, "Kernel BUG");
> +
> +	irqentry_exit(regs, state);
>  }
>  NOKPROBE_SYMBOL(do_trap_break);

> +asmlinkage void do_page_fault(struct pt_regs *regs)
> +{
> +	irqentry_state_t state = irqentry_enter(regs);
> +
> +	__do_page_fault(regs);
> +
> +	irqentry_exit(regs, state);
> +}
>  NOKPROBE_SYMBOL(do_page_fault);

Without noinstr the compiler is free to insert instrumentation (think
all the k*SAN, KCov, GCov, ftrace etc..) which can call code we're not
yet ready to run this early in the entry path, for instance it could
rely on RCU which isn't on yet, or expect lockdep state.


Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ