Skip to content

Commit 85e3e7f

Browse files
jognesspmladek
authored andcommitted
printk: remove NMI tracking
All NMI contexts are handled the same as the safe context: store the message and defer printing. There is no need to have special NMI context tracking for this. Using in_nmi() is enough. There are several parts of the kernel that are manually calling into the printk NMI context tracking in order to cause general printk deferred printing: arch/arm/kernel/smp.c arch/powerpc/kexec/crash.c kernel/trace/trace.c For arm/kernel/smp.c and powerpc/kexec/crash.c, provide a new function pair printk_deferred_enter/exit that explicitly achieves the same objective. For ftrace, remove the printk context manipulation completely. It was added in commit 03fc7f9 ("printk/nmi: Prevent deadlock when accessing the main log buffer in NMI"). The purpose was to enforce storing messages directly into the ring buffer even in NMI context. It really should have only modified the behavior in NMI context. There is no need for a special behavior any longer. All messages are always stored directly now. The console deferring is handled transparently in vprintk(). Signed-off-by: John Ogness <[email protected]> [[email protected]: Remove special handling in ftrace.c completely. Signed-off-by: Petr Mladek <[email protected]> Link: https://lore.kernel.org/r/[email protected]
1 parent 93d102f commit 85e3e7f

File tree

8 files changed

+23
-68
lines changed

8 files changed

+23
-68
lines changed

arch/arm/kernel/smp.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -667,9 +667,9 @@ static void do_handle_IPI(int ipinr)
667667
break;
668668

669669
case IPI_CPU_BACKTRACE:
670-
printk_nmi_enter();
670+
printk_deferred_enter();
671671
nmi_cpu_backtrace(get_irq_regs());
672-
printk_nmi_exit();
672+
printk_deferred_exit();
673673
break;
674674

675675
default:

arch/powerpc/kexec/crash.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -313,7 +313,7 @@ void default_machine_crash_shutdown(struct pt_regs *regs)
313313
int (*old_handler)(struct pt_regs *regs);
314314

315315
/* Avoid hardlocking with irresponsive CPU holding logbuf_lock */
316-
printk_nmi_enter();
316+
printk_deferred_enter();
317317

318318
/*
319319
* This function is only called after the system

include/linux/hardirq.h

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,6 @@ extern void rcu_nmi_exit(void);
116116
do { \
117117
lockdep_off(); \
118118
arch_nmi_enter(); \
119-
printk_nmi_enter(); \
120119
BUG_ON(in_nmi() == NMI_MASK); \
121120
__preempt_count_add(NMI_OFFSET + HARDIRQ_OFFSET); \
122121
} while (0)
@@ -135,7 +134,6 @@ extern void rcu_nmi_exit(void);
135134
do { \
136135
BUG_ON(!in_nmi()); \
137136
__preempt_count_sub(NMI_OFFSET + HARDIRQ_OFFSET); \
138-
printk_nmi_exit(); \
139137
arch_nmi_exit(); \
140138
lockdep_on(); \
141139
} while (0)

include/linux/printk.h

Lines changed: 19 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -149,18 +149,6 @@ static inline __printf(1, 2) __cold
149149
void early_printk(const char *s, ...) { }
150150
#endif
151151

152-
#ifdef CONFIG_PRINTK_NMI
153-
extern void printk_nmi_enter(void);
154-
extern void printk_nmi_exit(void);
155-
extern void printk_nmi_direct_enter(void);
156-
extern void printk_nmi_direct_exit(void);
157-
#else
158-
static inline void printk_nmi_enter(void) { }
159-
static inline void printk_nmi_exit(void) { }
160-
static inline void printk_nmi_direct_enter(void) { }
161-
static inline void printk_nmi_direct_exit(void) { }
162-
#endif /* PRINTK_NMI */
163-
164152
struct dev_printk_info;
165153

166154
#ifdef CONFIG_PRINTK
@@ -180,6 +168,16 @@ int printk(const char *fmt, ...);
180168
*/
181169
__printf(1, 2) __cold int printk_deferred(const char *fmt, ...);
182170

171+
extern void __printk_safe_enter(void);
172+
extern void __printk_safe_exit(void);
173+
/*
174+
* The printk_deferred_enter/exit macros are available only as a hack for
175+
* some code paths that need to defer all printk console printing. Interrupts
176+
* must be disabled for the deferred duration.
177+
*/
178+
#define printk_deferred_enter __printk_safe_enter
179+
#define printk_deferred_exit __printk_safe_exit
180+
183181
/*
184182
* Please don't use printk_ratelimit(), because it shares ratelimiting state
185183
* with all other unrelated printk_ratelimit() callsites. Instead use
@@ -224,6 +222,15 @@ int printk_deferred(const char *s, ...)
224222
{
225223
return 0;
226224
}
225+
226+
static inline void printk_deferred_enter(void)
227+
{
228+
}
229+
230+
static inline void printk_deferred_exit(void)
231+
{
232+
}
233+
227234
static inline int printk_ratelimit(void)
228235
{
229236
return 0;

init/Kconfig

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1506,11 +1506,6 @@ config PRINTK
15061506
very difficult to diagnose system problems, saying N here is
15071507
strongly discouraged.
15081508

1509-
config PRINTK_NMI
1510-
def_bool y
1511-
depends on PRINTK
1512-
depends on HAVE_NMI
1513-
15141509
config BUG
15151510
bool "BUG() support" if EXPERT
15161511
default y

kernel/printk/internal.h

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,21 +6,13 @@
66

77
#ifdef CONFIG_PRINTK
88

9-
#define PRINTK_SAFE_CONTEXT_MASK 0x007ffffff
10-
#define PRINTK_NMI_DIRECT_CONTEXT_MASK 0x008000000
11-
#define PRINTK_NMI_CONTEXT_MASK 0xff0000000
12-
13-
#define PRINTK_NMI_CONTEXT_OFFSET 0x010000000
14-
159
__printf(4, 0)
1610
int vprintk_store(int facility, int level,
1711
const struct dev_printk_info *dev_info,
1812
const char *fmt, va_list args);
1913

2014
__printf(1, 0) int vprintk_default(const char *fmt, va_list args);
2115
__printf(1, 0) int vprintk_deferred(const char *fmt, va_list args);
22-
void __printk_safe_enter(void);
23-
void __printk_safe_exit(void);
2416

2517
bool printk_percpu_data_ready(void);
2618

kernel/printk/printk_safe.c

Lines changed: 1 addition & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -4,48 +4,16 @@
44
*/
55

66
#include <linux/preempt.h>
7-
#include <linux/spinlock.h>
8-
#include <linux/debug_locks.h>
97
#include <linux/kdb.h>
108
#include <linux/smp.h>
119
#include <linux/cpumask.h>
12-
#include <linux/irq_work.h>
1310
#include <linux/printk.h>
1411
#include <linux/kprobes.h>
1512

1613
#include "internal.h"
1714

1815
static DEFINE_PER_CPU(int, printk_context);
1916

20-
#ifdef CONFIG_PRINTK_NMI
21-
void noinstr printk_nmi_enter(void)
22-
{
23-
this_cpu_add(printk_context, PRINTK_NMI_CONTEXT_OFFSET);
24-
}
25-
26-
void noinstr printk_nmi_exit(void)
27-
{
28-
this_cpu_sub(printk_context, PRINTK_NMI_CONTEXT_OFFSET);
29-
}
30-
31-
/*
32-
* Marks a code that might produce many messages in NMI context
33-
* and the risk of losing them is more critical than eventual
34-
* reordering.
35-
*/
36-
void printk_nmi_direct_enter(void)
37-
{
38-
if (this_cpu_read(printk_context) & PRINTK_NMI_CONTEXT_MASK)
39-
this_cpu_or(printk_context, PRINTK_NMI_DIRECT_CONTEXT_MASK);
40-
}
41-
42-
void printk_nmi_direct_exit(void)
43-
{
44-
this_cpu_and(printk_context, ~PRINTK_NMI_DIRECT_CONTEXT_MASK);
45-
}
46-
47-
#endif /* CONFIG_PRINTK_NMI */
48-
4917
/* Can be preempted by NMI. */
5018
void __printk_safe_enter(void)
5119
{
@@ -70,10 +38,7 @@ asmlinkage int vprintk(const char *fmt, va_list args)
7038
* Use the main logbuf even in NMI. But avoid calling console
7139
* drivers that might have their own locks.
7240
*/
73-
if (this_cpu_read(printk_context) &
74-
(PRINTK_NMI_DIRECT_CONTEXT_MASK |
75-
PRINTK_NMI_CONTEXT_MASK |
76-
PRINTK_SAFE_CONTEXT_MASK)) {
41+
if (this_cpu_read(printk_context) || in_nmi()) {
7742
int len;
7843

7944
len = vprintk_store(0, LOGLEVEL_DEFAULT, NULL, fmt, args);

kernel/trace/trace.c

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9647,7 +9647,6 @@ void ftrace_dump(enum ftrace_dump_mode oops_dump_mode)
96479647
tracing_off();
96489648

96499649
local_irq_save(flags);
9650-
printk_nmi_direct_enter();
96519650

96529651
/* Simulate the iterator */
96539652
trace_init_global_iter(&iter);
@@ -9729,7 +9728,6 @@ void ftrace_dump(enum ftrace_dump_mode oops_dump_mode)
97299728
atomic_dec(&per_cpu_ptr(iter.array_buffer->data, cpu)->disabled);
97309729
}
97319730
atomic_dec(&dump_running);
9732-
printk_nmi_direct_exit();
97339731
local_irq_restore(flags);
97349732
}
97359733
EXPORT_SYMBOL_GPL(ftrace_dump);

0 commit comments

Comments
 (0)