From: Daniel Thompson <hidden> Date: 2015-09-14 09:18:39
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This can be fixed by detecting that the calling context cannot be
preempted and issuing the backtrace directly in this case. Some small
changes to the generic code are required to support this.
Signed-off-by: Daniel Thompson <redacted>
---
arch/arm/kernel/smp.c | 7 +++++++
lib/nmi_backtrace.c | 5 ++++-
2 files changed, 11 insertions(+), 1 deletion(-)
@@ -149,7 +149,10 @@ bool nmi_cpu_backtrace(struct pt_regs *regs)/* Replace printk to write into the NMI seq */this_cpu_write(printk_func,nmi_vprintk);pr_warn("NMI backtrace for cpu %d\n",cpu);-show_regs(regs);+if(regs)+show_regs(regs);+else+dump_stack();this_cpu_write(printk_func,printk_func_save);cpumask_clear_cpu(cpu,to_cpumask(backtrace_mask));--
From: Daniel Thompson <hidden> Date: 2015-09-15 11:05:36
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This can be fixed by detecting that the calling context cannot be
preempted and issuing the backtrace directly in this case. Issuing
directly leaves us without any pt_regs to pass to nmi_cpu_backtrace()
so we also modify the generic code to call dump_stack() when its
argument is NULL.
Signed-off-by: Daniel Thompson <redacted>
---
Notes:
Changes in v2:
* Improved commit message to better describe the changes to the generic
code (Hillf Danton).
arch/arm/kernel/smp.c | 7 +++++++
lib/nmi_backtrace.c | 5 ++++-
2 files changed, 11 insertions(+), 1 deletion(-)
@@ -149,7 +149,10 @@ bool nmi_cpu_backtrace(struct pt_regs *regs)/* Replace printk to write into the NMI seq */this_cpu_write(printk_func,nmi_vprintk);pr_warn("NMI backtrace for cpu %d\n",cpu);-show_regs(regs);+if(regs)+show_regs(regs);+else+dump_stack();this_cpu_write(printk_func,printk_func_save);cpumask_clear_cpu(cpu,to_cpumask(backtrace_mask));--
From: Russell King - ARM Linux <hidden> Date: 2015-09-15 11:30:25
On Tue, Sep 15, 2015 at 12:05:12PM +0100, Daniel Thompson wrote:
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This patch needs a little more work - what happens to the IPI_CPU_BACKTRACE
we've sent to ourselves? (It fires after the interrupt handler for the
UART/kbd has finished.) It ought to be masked out if we're going to
handle it a different way.
--
FTTC broadband for 0.8mile line: currently at 9.6Mbps down 400kbps up
according to speedtest.net.
From: Daniel Thompson <hidden> Date: 2015-09-15 13:15:16
On 15/09/15 12:30, Russell King - ARM Linux wrote:
On Tue, Sep 15, 2015 at 12:05:12PM +0100, Daniel Thompson wrote:
quoted
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This patch needs a little more work - what happens to the IPI_CPU_BACKTRACE
we've sent to ourselves? (It fires after the interrupt handler for the
UART/kbd has finished.) It ought to be masked out if we're going to
handle it a different way.
Actually it already gets masked out. The argument to raise_nmi() points
to a data structure owned by the backtrace library functions and this
structure if altered during the execution of nmi_cpu_backtrace() to
clear the calling CPU.
I had originally planned to use cpumask_test_and_clear_cpu() for the
conditional branch but that would be broken because nmi_cpu_backtrace()
would become a nop if we clear anything from the mask before calling it!
I guess I should add a comment about this to save us from broken but
"obviously correct" cleanups in the future...
Daniel.
From: Russell King - ARM Linux <hidden> Date: 2015-09-15 13:42:24
On Tue, Sep 15, 2015 at 02:15:10PM +0100, Daniel Thompson wrote:
Actually it already gets masked out. The argument to raise_nmi() points to a
data structure owned by the backtrace library functions and this structure
if altered during the execution of nmi_cpu_backtrace() to clear the calling
CPU.
I had originally planned to use cpumask_test_and_clear_cpu() for the
conditional branch but that would be broken because nmi_cpu_backtrace()
would become a nop if we clear anything from the mask before calling it!
I guess I should add a comment about this to save us from broken but
"obviously correct" cleanups in the future...
Absolutely.
--
FTTC broadband for 0.8mile line: currently at 9.6Mbps down 400kbps up
according to speedtest.net.
From: Daniel Thompson <hidden> Date: 2015-09-15 14:40:29
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This can be fixed by detecting that the calling context cannot be
preempted and issuing the backtrace directly in this case. Issuing
directly leaves us without any pt_regs to pass to nmi_cpu_backtrace()
so we also modify the generic code to call dump_stack() when its
argument is NULL.
Signed-off-by: Daniel Thompson <redacted>
---
Notes:
Changes in v3:
* Added comments to describe how raise_nmi() and nmi_cpu_backtrace()
interact with backtrace_mask (Russell King).
Changes in v2:
* Improved commit message to better describe the changes to the generic
code (Hillf Danton).
arch/arm/kernel/smp.c | 9 +++++++++
lib/nmi_backtrace.c | 11 ++++++++++-
2 files changed, 19 insertions(+), 1 deletion(-)
@@ -43,6 +43,12 @@ static void print_seq_line(struct nmi_seq_buf *s, int start, int end)printk("%.*s",(end-start)+1,buf);}+/*+*Whenraise()iscalleditwillbeispassedapointertothe+*backtrace_mask.Architecturesthatcallnmi_cpu_backtrace()+*directlyfromtheirraise()functionsmayrelyonthemask+*theyarepassedbeingupdatedasasideeffectofthiscall.+*/voidnmi_trigger_all_cpu_backtrace(boolinclude_self,void(*raise)(cpumask_t*mask)){
@@ -149,7 +155,10 @@ bool nmi_cpu_backtrace(struct pt_regs *regs)/* Replace printk to write into the NMI seq */this_cpu_write(printk_func,nmi_vprintk);pr_warn("NMI backtrace for cpu %d\n",cpu);-show_regs(regs);+if(regs)+show_regs(regs);+else+dump_stack();this_cpu_write(printk_func,printk_func_save);cpumask_clear_cpu(cpu,to_cpumask(backtrace_mask));--
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This can be fixed by detecting that the calling context cannot be
preempted and issuing the backtrace directly in this case. Issuing
directly leaves us without any pt_regs to pass to nmi_cpu_backtrace()
so we also modify the generic code to call dump_stack() when its
argument is NULL.
Signed-off-by: Daniel Thompson <redacted>
---
Acked-by: Hillf Danton <redacted>
quoted hunk
Notes:
Changes in v3:
* Added comments to describe how raise_nmi() and nmi_cpu_backtrace()
interact with backtrace_mask (Russell King).
Changes in v2:
* Improved commit message to better describe the changes to the generic
code (Hillf Danton).
arch/arm/kernel/smp.c | 9 +++++++++
lib/nmi_backtrace.c | 11 ++++++++++-
2 files changed, 19 insertions(+), 1 deletion(-)
@@ -43,6 +43,12 @@ static void print_seq_line(struct nmi_seq_buf *s, int start, int end)printk("%.*s",(end-start)+1,buf);}+/*+*Whenraise()iscalleditwillbeispassedapointertothe+*backtrace_mask.Architecturesthatcallnmi_cpu_backtrace()+*directlyfromtheirraise()functionsmayrelyonthemask+*theyarepassedbeingupdatedasasideeffectofthiscall.+*/voidnmi_trigger_all_cpu_backtrace(boolinclude_self,void(*raise)(cpumask_t*mask)){
@@ -149,7 +155,10 @@ bool nmi_cpu_backtrace(struct pt_regs *regs)/* Replace printk to write into the NMI seq */this_cpu_write(printk_func,nmi_vprintk);pr_warn("NMI backtrace for cpu %d\n",cpu);-show_regs(regs);+if(regs)+show_regs(regs);+else+dump_stack();this_cpu_write(printk_func,printk_func_save);cpumask_clear_cpu(cpu,to_cpumask(backtrace_mask));--
From: Thomas Gleixner <hidden> Date: 2015-09-22 11:00:01
On Tue, 15 Sep 2015, Daniel Thompson wrote:
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This can be fixed by detecting that the calling context cannot be
preempted and issuing the backtrace directly in this case. Issuing
directly leaves us without any pt_regs to pass to nmi_cpu_backtrace()
so we also modify the generic code to call dump_stack() when its
argument is NULL.
Signed-off-by: Daniel Thompson <redacted>
For the genric part.
Acked-by: Thomas Gleixner <redacted>
From: Russell King - ARM Linux <hidden> Date: 2015-10-03 15:40:55
On Tue, Sep 15, 2015 at 03:40:05PM +0100, Daniel Thompson wrote:
Currently on ARM when <SysRq-L> is triggered from an interrupt handler
(e.g. a SysRq issued using UART or kbd) the main CPU will wedge for ten
seconds with interrupts masked before issuing a backtrace for every CPU
except itself.
The new backtrace code introduced by commit 96f0e00378d4 ("ARM: add
basic support for on-demand backtrace of other CPUs") does not work
correctly when run from an interrupt handler because IPI_CPU_BACKTRACE
is used to generate the backtrace on all CPUs but cannot preempt the
current calling context.
This can be fixed by detecting that the calling context cannot be
preempted and issuing the backtrace directly in this case. Issuing
directly leaves us without any pt_regs to pass to nmi_cpu_backtrace()
so we also modify the generic code to call dump_stack() when its
argument is NULL.
Signed-off-by: Daniel Thompson <redacted>
When submitting a patch to the patch system, please ensure that you pick
up people's acks _before_ submitting it to there - don't expect me to
search the mailing list, identify which patch version is the one in the
patch system, and then read the entire thread finding all the acks, then
having to amend the commit to add them.
A patch in the patch system with no acks looks like a patch which hasn't
been sent to the mailing lists.
Thanks.
--
FTTC broadband for 0.8mile line: currently at 9.6Mbps down 400kbps up
according to speedtest.net.