Skip to content

Commit

Permalink
x86/kconfig: Consolidate unwinders into multiple choice selection
Browse files Browse the repository at this point in the history
There are three mutually exclusive unwinders.  Make that more obvious by
combining them into a multiple-choice selection:

  CONFIG_FRAME_POINTER_UNWINDER
  CONFIG_ORC_UNWINDER
  CONFIG_GUESS_UNWINDER (if CONFIG_EXPERT=y)

Frame pointers are still the default (for now).

The old CONFIG_FRAME_POINTER option is still used in some
arch-independent places, so keep it around, but make it
invisible to the user on x86 - it's now selected by
CONFIG_FRAME_POINTER_UNWINDER=y.

Suggested-by: Ingo Molnar <[email protected]>
Signed-off-by: Josh Poimboeuf <[email protected]>
Cc: Andy Lutomirski <[email protected]>
Cc: Borislav Petkov <[email protected]>
Cc: Brian Gerst <[email protected]>
Cc: Denys Vlasenko <[email protected]>
Cc: H. Peter Anvin <[email protected]>
Cc: Jiri Slaby <[email protected]>
Cc: Linus Torvalds <[email protected]>
Cc: Mike Galbraith <[email protected]>
Cc: Peter Zijlstra <[email protected]>
Cc: Thomas Gleixner <[email protected]>
Cc: [email protected]
Link: http://lkml.kernel.org/r/20170725135424.zukjmgpz3plf5pmt@treble
Signed-off-by: Ingo Molnar <[email protected]>
  • Loading branch information
jpoimboe authored and Ingo Molnar committed Jul 26, 2017
1 parent a34a766 commit 81d3871
Show file tree
Hide file tree
Showing 4 changed files with 45 additions and 11 deletions.
3 changes: 1 addition & 2 deletions arch/x86/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,6 @@ config X86
select ARCH_USE_QUEUED_RWLOCKS
select ARCH_USE_QUEUED_SPINLOCKS
select ARCH_WANT_BATCHED_UNMAP_TLB_FLUSH
select ARCH_WANT_FRAME_POINTERS
select ARCH_WANTS_DYNAMIC_TASK_STRUCT
select ARCH_WANTS_THP_SWAP if X86_64
select BUILDTIME_EXTABLE_SORT
Expand Down Expand Up @@ -168,7 +167,7 @@ config X86
select HAVE_PERF_REGS
select HAVE_PERF_USER_STACK_DUMP
select HAVE_REGS_AND_STACK_ACCESS_API
select HAVE_RELIABLE_STACKTRACE if X86_64 && FRAME_POINTER && STACK_VALIDATION
select HAVE_RELIABLE_STACKTRACE if X86_64 && FRAME_POINTER_UNWINDER && STACK_VALIDATION
select HAVE_STACK_VALIDATION if X86_64
select HAVE_SYSCALL_TRACEPOINTS
select HAVE_UNSTABLE_SCHED_CLOCK
Expand Down
47 changes: 40 additions & 7 deletions arch/x86/Kconfig.debug
Original file line number Diff line number Diff line change
Expand Up @@ -355,9 +355,32 @@ config PUNIT_ATOM_DEBUG
The current power state can be read from
/sys/kernel/debug/punit_atom/dev_power_state

choice
prompt "Choose kernel unwinder"
default FRAME_POINTER_UNWINDER
---help---
This determines which method will be used for unwinding kernel stack
traces for panics, oopses, bugs, warnings, perf, /proc/<pid>/stack,
livepatch, lockdep, and more.

config FRAME_POINTER_UNWINDER
bool "Frame pointer unwinder"
select FRAME_POINTER
---help---
This option enables the frame pointer unwinder for unwinding kernel
stack traces.

The unwinder itself is fast and it uses less RAM than the ORC
unwinder, but the kernel text size will grow by ~3% and the kernel's
overall performance will degrade by roughly 5-10%.

This option is recommended if you want to use the livepatch
consistency model, as this is currently the only way to get a
reliable stack trace (CONFIG_HAVE_RELIABLE_STACKTRACE).

config ORC_UNWINDER
bool "ORC unwinder"
depends on X86_64 && !FRAME_POINTER
depends on X86_64
select STACK_VALIDATION
---help---
This option enables the ORC (Oops Rewind Capability) unwinder for
Expand All @@ -371,12 +394,22 @@ config ORC_UNWINDER
Enabling this option will increase the kernel's runtime memory usage
by roughly 2-4MB, depending on your kernel config.

config FRAME_POINTER_UNWINDER
def_bool y
depends on !ORC_UNWINDER && FRAME_POINTER

config GUESS_UNWINDER
def_bool y
depends on !ORC_UNWINDER && !FRAME_POINTER
bool "Guess unwinder"
depends on EXPERT
---help---
This option enables the "guess" unwinder for unwinding kernel stack
traces. It scans the stack and reports every kernel text address it
finds. Some of the addresses it reports may be incorrect.

While this option often produces false positives, it can still be
useful in many cases. Unlike the other unwinders, it has no runtime
overhead.

endchoice

config FRAME_POINTER
depends on !ORC_UNWINDER && !GUESS_UNWINDER
bool

endmenu
2 changes: 2 additions & 0 deletions arch/x86/configs/tiny.config
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
CONFIG_NOHIGHMEM=y
# CONFIG_HIGHMEM4G is not set
# CONFIG_HIGHMEM64G is not set
CONFIG_GUESS_UNWINDER=y
# CONFIG_FRAME_POINTER_UNWINDER is not set
4 changes: 2 additions & 2 deletions arch/x86/include/asm/unwind.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ struct unwind_state {
bool signal, full_regs;
unsigned long sp, bp, ip;
struct pt_regs *regs;
#elif defined(CONFIG_FRAME_POINTER)
#elif defined(CONFIG_FRAME_POINTER_UNWINDER)
bool got_irq;
unsigned long *bp, *orig_sp, ip;
struct pt_regs *regs;
Expand Down Expand Up @@ -50,7 +50,7 @@ void unwind_start(struct unwind_state *state, struct task_struct *task,
__unwind_start(state, task, regs, first_frame);
}

#if defined(CONFIG_ORC_UNWINDER) || defined(CONFIG_FRAME_POINTER)
#if defined(CONFIG_ORC_UNWINDER) || defined(CONFIG_FRAME_POINTER_UNWINDER)
static inline struct pt_regs *unwind_get_entry_regs(struct unwind_state *state)
{
if (unwind_done(state))
Expand Down

0 comments on commit 81d3871

Please sign in to comment.