162306a36Sopenharmony_ciObjtool 262306a36Sopenharmony_ci======= 362306a36Sopenharmony_ci 462306a36Sopenharmony_ciThe kernel CONFIG_OBJTOOL option enables a host tool named 'objtool' 562306a36Sopenharmony_ciwhich runs at compile time. It can do various validations and 662306a36Sopenharmony_citransformations on .o files. 762306a36Sopenharmony_ci 862306a36Sopenharmony_ciObjtool has become an integral part of the x86-64 kernel toolchain. The 962306a36Sopenharmony_cikernel depends on it for a variety of security and performance features 1062306a36Sopenharmony_ci(and other types of features as well). 1162306a36Sopenharmony_ci 1262306a36Sopenharmony_ci 1362306a36Sopenharmony_ciFeatures 1462306a36Sopenharmony_ci-------- 1562306a36Sopenharmony_ci 1662306a36Sopenharmony_ciObjtool has the following features: 1762306a36Sopenharmony_ci 1862306a36Sopenharmony_ci- Stack unwinding metadata validation -- useful for helping to ensure 1962306a36Sopenharmony_ci stack traces are reliable for live patching 2062306a36Sopenharmony_ci 2162306a36Sopenharmony_ci- ORC unwinder metadata generation -- a faster and more precise 2262306a36Sopenharmony_ci alternative to frame pointer based unwinding 2362306a36Sopenharmony_ci 2462306a36Sopenharmony_ci- Retpoline validation -- ensures that all indirect calls go through 2562306a36Sopenharmony_ci retpoline thunks, for Spectre v2 mitigations 2662306a36Sopenharmony_ci 2762306a36Sopenharmony_ci- Retpoline call site annotation -- annotates all retpoline thunk call 2862306a36Sopenharmony_ci sites, enabling the kernel to patch them inline, to prevent "thunk 2962306a36Sopenharmony_ci funneling" for both security and performance reasons 3062306a36Sopenharmony_ci 3162306a36Sopenharmony_ci- Non-instrumentation validation -- validates non-instrumentable 3262306a36Sopenharmony_ci ("noinstr") code rules, preventing instrumentation in low-level C 3362306a36Sopenharmony_ci entry code 3462306a36Sopenharmony_ci 3562306a36Sopenharmony_ci- Static call annotation -- annotates static call sites, enabling the 3662306a36Sopenharmony_ci kernel to implement inline static calls, a faster alternative to some 3762306a36Sopenharmony_ci indirect branches 3862306a36Sopenharmony_ci 3962306a36Sopenharmony_ci- Uaccess validation -- validates uaccess rules for a proper 4062306a36Sopenharmony_ci implementation of Supervisor Mode Access Protection (SMAP) 4162306a36Sopenharmony_ci 4262306a36Sopenharmony_ci- Straight Line Speculation validation -- validates certain SLS 4362306a36Sopenharmony_ci mitigations 4462306a36Sopenharmony_ci 4562306a36Sopenharmony_ci- Indirect Branch Tracking validation -- validates Intel CET IBT rules 4662306a36Sopenharmony_ci to ensure that all functions referenced by function pointers have 4762306a36Sopenharmony_ci corresponding ENDBR instructions 4862306a36Sopenharmony_ci 4962306a36Sopenharmony_ci- Indirect Branch Tracking annotation -- annotates unused ENDBR 5062306a36Sopenharmony_ci instruction sites, enabling the kernel to "seal" them (replace them 5162306a36Sopenharmony_ci with NOPs) to further harden IBT 5262306a36Sopenharmony_ci 5362306a36Sopenharmony_ci- Function entry annotation -- annotates function entries, enabling 5462306a36Sopenharmony_ci kernel function tracing 5562306a36Sopenharmony_ci 5662306a36Sopenharmony_ci- Other toolchain hacks which will go unmentioned at this time... 5762306a36Sopenharmony_ci 5862306a36Sopenharmony_ciEach feature can be enabled individually or in combination using the 5962306a36Sopenharmony_ciobjtool cmdline. 6062306a36Sopenharmony_ci 6162306a36Sopenharmony_ci 6262306a36Sopenharmony_ciObjects 6362306a36Sopenharmony_ci------- 6462306a36Sopenharmony_ci 6562306a36Sopenharmony_ciTypically, objtool runs on every translation unit (TU, aka ".o file") in 6662306a36Sopenharmony_cithe kernel. If a TU is part of a kernel module, the '--module' option 6762306a36Sopenharmony_ciis added. 6862306a36Sopenharmony_ci 6962306a36Sopenharmony_ciHowever: 7062306a36Sopenharmony_ci 7162306a36Sopenharmony_ci- If noinstr validation is enabled, it also runs on vmlinux.o, with all 7262306a36Sopenharmony_ci options removed and '--noinstr' added. 7362306a36Sopenharmony_ci 7462306a36Sopenharmony_ci- If IBT or LTO is enabled, it doesn't run on TUs at all. Instead it 7562306a36Sopenharmony_ci runs on vmlinux.o and linked modules, with all options. 7662306a36Sopenharmony_ci 7762306a36Sopenharmony_ciIn summary: 7862306a36Sopenharmony_ci 7962306a36Sopenharmony_ci A) Legacy mode: 8062306a36Sopenharmony_ci TU: objtool [--module] <options> 8162306a36Sopenharmony_ci vmlinux: N/A 8262306a36Sopenharmony_ci module: N/A 8362306a36Sopenharmony_ci 8462306a36Sopenharmony_ci B) CONFIG_NOINSTR_VALIDATION=y && !(CONFIG_X86_KERNEL_IBT=y || CONFIG_LTO=y): 8562306a36Sopenharmony_ci TU: objtool [--module] <options> // no --noinstr 8662306a36Sopenharmony_ci vmlinux: objtool --noinstr // other options removed 8762306a36Sopenharmony_ci module: N/A 8862306a36Sopenharmony_ci 8962306a36Sopenharmony_ci C) CONFIG_X86_KERNEL_IBT=y || CONFIG_LTO=y: 9062306a36Sopenharmony_ci TU: N/A 9162306a36Sopenharmony_ci vmlinux: objtool --noinstr <options> 9262306a36Sopenharmony_ci module: objtool --module --noinstr <options> 9362306a36Sopenharmony_ci 9462306a36Sopenharmony_ci 9562306a36Sopenharmony_ciStack validation 9662306a36Sopenharmony_ci---------------- 9762306a36Sopenharmony_ci 9862306a36Sopenharmony_ciObjtool's stack validation feature analyzes every .o file and ensures 9962306a36Sopenharmony_cithe validity of its stack metadata. It enforces a set of rules on asm 10062306a36Sopenharmony_cicode and C inline assembly code so that stack traces can be reliable. 10162306a36Sopenharmony_ci 10262306a36Sopenharmony_ciFor each function, it recursively follows all possible code paths and 10362306a36Sopenharmony_civalidates the correct frame pointer state at each instruction. 10462306a36Sopenharmony_ci 10562306a36Sopenharmony_ciIt also follows code paths involving special sections, like 10662306a36Sopenharmony_ci.altinstructions, __jump_table, and __ex_table, which can add 10762306a36Sopenharmony_cialternative execution paths to a given instruction (or set of 10862306a36Sopenharmony_ciinstructions). Similarly, it knows how to follow switch statements, for 10962306a36Sopenharmony_ciwhich gcc sometimes uses jump tables. 11062306a36Sopenharmony_ci 11162306a36Sopenharmony_ciHere are some of the benefits of validating stack metadata: 11262306a36Sopenharmony_ci 11362306a36Sopenharmony_cia) More reliable stack traces for frame pointer enabled kernels 11462306a36Sopenharmony_ci 11562306a36Sopenharmony_ci Frame pointers are used for debugging purposes. They allow runtime 11662306a36Sopenharmony_ci code and debug tools to be able to walk the stack to determine the 11762306a36Sopenharmony_ci chain of function call sites that led to the currently executing 11862306a36Sopenharmony_ci code. 11962306a36Sopenharmony_ci 12062306a36Sopenharmony_ci For some architectures, frame pointers are enabled by 12162306a36Sopenharmony_ci CONFIG_FRAME_POINTER. For some other architectures they may be 12262306a36Sopenharmony_ci required by the ABI (sometimes referred to as "backchain pointers"). 12362306a36Sopenharmony_ci 12462306a36Sopenharmony_ci For C code, gcc automatically generates instructions for setting up 12562306a36Sopenharmony_ci frame pointers when the -fno-omit-frame-pointer option is used. 12662306a36Sopenharmony_ci 12762306a36Sopenharmony_ci But for asm code, the frame setup instructions have to be written by 12862306a36Sopenharmony_ci hand, which most people don't do. So the end result is that 12962306a36Sopenharmony_ci CONFIG_FRAME_POINTER is honored for C code but not for most asm code. 13062306a36Sopenharmony_ci 13162306a36Sopenharmony_ci For stack traces based on frame pointers to be reliable, all 13262306a36Sopenharmony_ci functions which call other functions must first create a stack frame 13362306a36Sopenharmony_ci and update the frame pointer. If a first function doesn't properly 13462306a36Sopenharmony_ci create a stack frame before calling a second function, the *caller* 13562306a36Sopenharmony_ci of the first function will be skipped on the stack trace. 13662306a36Sopenharmony_ci 13762306a36Sopenharmony_ci For example, consider the following example backtrace with frame 13862306a36Sopenharmony_ci pointers enabled: 13962306a36Sopenharmony_ci 14062306a36Sopenharmony_ci [<ffffffff81812584>] dump_stack+0x4b/0x63 14162306a36Sopenharmony_ci [<ffffffff812d6dc2>] cmdline_proc_show+0x12/0x30 14262306a36Sopenharmony_ci [<ffffffff8127f568>] seq_read+0x108/0x3e0 14362306a36Sopenharmony_ci [<ffffffff812cce62>] proc_reg_read+0x42/0x70 14462306a36Sopenharmony_ci [<ffffffff81256197>] __vfs_read+0x37/0x100 14562306a36Sopenharmony_ci [<ffffffff81256b16>] vfs_read+0x86/0x130 14662306a36Sopenharmony_ci [<ffffffff81257898>] SyS_read+0x58/0xd0 14762306a36Sopenharmony_ci [<ffffffff8181c1f2>] entry_SYSCALL_64_fastpath+0x12/0x76 14862306a36Sopenharmony_ci 14962306a36Sopenharmony_ci It correctly shows that the caller of cmdline_proc_show() is 15062306a36Sopenharmony_ci seq_read(). 15162306a36Sopenharmony_ci 15262306a36Sopenharmony_ci If we remove the frame pointer logic from cmdline_proc_show() by 15362306a36Sopenharmony_ci replacing the frame pointer related instructions with nops, here's 15462306a36Sopenharmony_ci what it looks like instead: 15562306a36Sopenharmony_ci 15662306a36Sopenharmony_ci [<ffffffff81812584>] dump_stack+0x4b/0x63 15762306a36Sopenharmony_ci [<ffffffff812d6dc2>] cmdline_proc_show+0x12/0x30 15862306a36Sopenharmony_ci [<ffffffff812cce62>] proc_reg_read+0x42/0x70 15962306a36Sopenharmony_ci [<ffffffff81256197>] __vfs_read+0x37/0x100 16062306a36Sopenharmony_ci [<ffffffff81256b16>] vfs_read+0x86/0x130 16162306a36Sopenharmony_ci [<ffffffff81257898>] SyS_read+0x58/0xd0 16262306a36Sopenharmony_ci [<ffffffff8181c1f2>] entry_SYSCALL_64_fastpath+0x12/0x76 16362306a36Sopenharmony_ci 16462306a36Sopenharmony_ci Notice that cmdline_proc_show()'s caller, seq_read(), has been 16562306a36Sopenharmony_ci skipped. Instead the stack trace seems to show that 16662306a36Sopenharmony_ci cmdline_proc_show() was called by proc_reg_read(). 16762306a36Sopenharmony_ci 16862306a36Sopenharmony_ci The benefit of objtool here is that because it ensures that *all* 16962306a36Sopenharmony_ci functions honor CONFIG_FRAME_POINTER, no functions will ever[*] be 17062306a36Sopenharmony_ci skipped on a stack trace. 17162306a36Sopenharmony_ci 17262306a36Sopenharmony_ci [*] unless an interrupt or exception has occurred at the very 17362306a36Sopenharmony_ci beginning of a function before the stack frame has been created, 17462306a36Sopenharmony_ci or at the very end of the function after the stack frame has been 17562306a36Sopenharmony_ci destroyed. This is an inherent limitation of frame pointers. 17662306a36Sopenharmony_ci 17762306a36Sopenharmony_cib) ORC (Oops Rewind Capability) unwind table generation 17862306a36Sopenharmony_ci 17962306a36Sopenharmony_ci An alternative to frame pointers and DWARF, ORC unwind data can be 18062306a36Sopenharmony_ci used to walk the stack. Unlike frame pointers, ORC data is out of 18162306a36Sopenharmony_ci band. So it doesn't affect runtime performance and it can be 18262306a36Sopenharmony_ci reliable even when interrupts or exceptions are involved. 18362306a36Sopenharmony_ci 18462306a36Sopenharmony_ci For more details, see Documentation/arch/x86/orc-unwinder.rst. 18562306a36Sopenharmony_ci 18662306a36Sopenharmony_cic) Higher live patching compatibility rate 18762306a36Sopenharmony_ci 18862306a36Sopenharmony_ci Livepatch has an optional "consistency model", which is needed for 18962306a36Sopenharmony_ci more complex patches. In order for the consistency model to work, 19062306a36Sopenharmony_ci stack traces need to be reliable (or an unreliable condition needs to 19162306a36Sopenharmony_ci be detectable). Objtool makes that possible. 19262306a36Sopenharmony_ci 19362306a36Sopenharmony_ci For more details, see the livepatch documentation in the Linux kernel 19462306a36Sopenharmony_ci source tree at Documentation/livepatch/livepatch.rst. 19562306a36Sopenharmony_ci 19662306a36Sopenharmony_ciTo achieve the validation, objtool enforces the following rules: 19762306a36Sopenharmony_ci 19862306a36Sopenharmony_ci1. Each callable function must be annotated as such with the ELF 19962306a36Sopenharmony_ci function type. In asm code, this is typically done using the 20062306a36Sopenharmony_ci ENTRY/ENDPROC macros. If objtool finds a return instruction 20162306a36Sopenharmony_ci outside of a function, it flags an error since that usually indicates 20262306a36Sopenharmony_ci callable code which should be annotated accordingly. 20362306a36Sopenharmony_ci 20462306a36Sopenharmony_ci This rule is needed so that objtool can properly identify each 20562306a36Sopenharmony_ci callable function in order to analyze its stack metadata. 20662306a36Sopenharmony_ci 20762306a36Sopenharmony_ci2. Conversely, each section of code which is *not* callable should *not* 20862306a36Sopenharmony_ci be annotated as an ELF function. The ENDPROC macro shouldn't be used 20962306a36Sopenharmony_ci in this case. 21062306a36Sopenharmony_ci 21162306a36Sopenharmony_ci This rule is needed so that objtool can ignore non-callable code. 21262306a36Sopenharmony_ci Such code doesn't have to follow any of the other rules. 21362306a36Sopenharmony_ci 21462306a36Sopenharmony_ci3. Each callable function which calls another function must have the 21562306a36Sopenharmony_ci correct frame pointer logic, if required by CONFIG_FRAME_POINTER or 21662306a36Sopenharmony_ci the architecture's back chain rules. This can by done in asm code 21762306a36Sopenharmony_ci with the FRAME_BEGIN/FRAME_END macros. 21862306a36Sopenharmony_ci 21962306a36Sopenharmony_ci This rule ensures that frame pointer based stack traces will work as 22062306a36Sopenharmony_ci designed. If function A doesn't create a stack frame before calling 22162306a36Sopenharmony_ci function B, the _caller_ of function A will be skipped on the stack 22262306a36Sopenharmony_ci trace. 22362306a36Sopenharmony_ci 22462306a36Sopenharmony_ci4. Dynamic jumps and jumps to undefined symbols are only allowed if: 22562306a36Sopenharmony_ci 22662306a36Sopenharmony_ci a) the jump is part of a switch statement; or 22762306a36Sopenharmony_ci 22862306a36Sopenharmony_ci b) the jump matches sibling call semantics and the frame pointer has 22962306a36Sopenharmony_ci the same value it had on function entry. 23062306a36Sopenharmony_ci 23162306a36Sopenharmony_ci This rule is needed so that objtool can reliably analyze all of a 23262306a36Sopenharmony_ci function's code paths. If a function jumps to code in another file, 23362306a36Sopenharmony_ci and it's not a sibling call, objtool has no way to follow the jump 23462306a36Sopenharmony_ci because it only analyzes a single file at a time. 23562306a36Sopenharmony_ci 23662306a36Sopenharmony_ci5. A callable function may not execute kernel entry/exit instructions. 23762306a36Sopenharmony_ci The only code which needs such instructions is kernel entry code, 23862306a36Sopenharmony_ci which shouldn't be be in callable functions anyway. 23962306a36Sopenharmony_ci 24062306a36Sopenharmony_ci This rule is just a sanity check to ensure that callable functions 24162306a36Sopenharmony_ci return normally. 24262306a36Sopenharmony_ci 24362306a36Sopenharmony_ci 24462306a36Sopenharmony_ciObjtool warnings 24562306a36Sopenharmony_ci---------------- 24662306a36Sopenharmony_ci 24762306a36Sopenharmony_ciNOTE: When requesting help with an objtool warning, please recreate with 24862306a36Sopenharmony_ciOBJTOOL_VERBOSE=1 (e.g., "make OBJTOOL_VERBOSE=1") and send the full 24962306a36Sopenharmony_cioutput, including any disassembly or backtrace below the warning, to the 25062306a36Sopenharmony_ciobjtool maintainers. 25162306a36Sopenharmony_ci 25262306a36Sopenharmony_ciFor asm files, if you're getting an error which doesn't make sense, 25362306a36Sopenharmony_cifirst make sure that the affected code follows the above rules. 25462306a36Sopenharmony_ci 25562306a36Sopenharmony_ciFor C files, the common culprits are inline asm statements and calls to 25662306a36Sopenharmony_ci"noreturn" functions. See below for more details. 25762306a36Sopenharmony_ci 25862306a36Sopenharmony_ciAnother possible cause for errors in C code is if the Makefile removes 25962306a36Sopenharmony_ci-fno-omit-frame-pointer or adds -fomit-frame-pointer to the gcc options. 26062306a36Sopenharmony_ci 26162306a36Sopenharmony_ciHere are some examples of common warnings reported by objtool, what 26262306a36Sopenharmony_cithey mean, and suggestions for how to fix them. When in doubt, ping 26362306a36Sopenharmony_cithe objtool maintainers. 26462306a36Sopenharmony_ci 26562306a36Sopenharmony_ci 26662306a36Sopenharmony_ci1. file.o: warning: objtool: func()+0x128: call without frame pointer save/setup 26762306a36Sopenharmony_ci 26862306a36Sopenharmony_ci The func() function made a function call without first saving and/or 26962306a36Sopenharmony_ci updating the frame pointer, and CONFIG_FRAME_POINTER is enabled. 27062306a36Sopenharmony_ci 27162306a36Sopenharmony_ci If the error is for an asm file, and func() is indeed a callable 27262306a36Sopenharmony_ci function, add proper frame pointer logic using the FRAME_BEGIN and 27362306a36Sopenharmony_ci FRAME_END macros. Otherwise, if it's not a callable function, remove 27462306a36Sopenharmony_ci its ELF function annotation by changing ENDPROC to END, and instead 27562306a36Sopenharmony_ci use the manual unwind hint macros in asm/unwind_hints.h. 27662306a36Sopenharmony_ci 27762306a36Sopenharmony_ci If it's a GCC-compiled .c file, the error may be because the function 27862306a36Sopenharmony_ci uses an inline asm() statement which has a "call" instruction. An 27962306a36Sopenharmony_ci asm() statement with a call instruction must declare the use of the 28062306a36Sopenharmony_ci stack pointer in its output operand. On x86_64, this means adding 28162306a36Sopenharmony_ci the ASM_CALL_CONSTRAINT as an output constraint: 28262306a36Sopenharmony_ci 28362306a36Sopenharmony_ci asm volatile("call func" : ASM_CALL_CONSTRAINT); 28462306a36Sopenharmony_ci 28562306a36Sopenharmony_ci Otherwise the stack frame may not get created before the call. 28662306a36Sopenharmony_ci 28762306a36Sopenharmony_ci 28862306a36Sopenharmony_ci2. file.o: warning: objtool: .text+0x53: unreachable instruction 28962306a36Sopenharmony_ci 29062306a36Sopenharmony_ci Objtool couldn't find a code path to reach the instruction. 29162306a36Sopenharmony_ci 29262306a36Sopenharmony_ci If the error is for an asm file, and the instruction is inside (or 29362306a36Sopenharmony_ci reachable from) a callable function, the function should be annotated 29462306a36Sopenharmony_ci with the ENTRY/ENDPROC macros (ENDPROC is the important one). 29562306a36Sopenharmony_ci Otherwise, the code should probably be annotated with the unwind hint 29662306a36Sopenharmony_ci macros in asm/unwind_hints.h so objtool and the unwinder can know the 29762306a36Sopenharmony_ci stack state associated with the code. 29862306a36Sopenharmony_ci 29962306a36Sopenharmony_ci If you're 100% sure the code won't affect stack traces, or if you're 30062306a36Sopenharmony_ci a just a bad person, you can tell objtool to ignore it. See the 30162306a36Sopenharmony_ci "Adding exceptions" section below. 30262306a36Sopenharmony_ci 30362306a36Sopenharmony_ci If it's not actually in a callable function (e.g. kernel entry code), 30462306a36Sopenharmony_ci change ENDPROC to END. 30562306a36Sopenharmony_ci 30662306a36Sopenharmony_ci3. file.o: warning: objtool: foo+0x48c: bar() is missing a __noreturn annotation 30762306a36Sopenharmony_ci 30862306a36Sopenharmony_ci The call from foo() to bar() doesn't return, but bar() is missing the 30962306a36Sopenharmony_ci __noreturn annotation. NOTE: In addition to annotating the function 31062306a36Sopenharmony_ci with __noreturn, please also add it to tools/objtool/noreturns.h. 31162306a36Sopenharmony_ci 31262306a36Sopenharmony_ci4. file.o: warning: objtool: func(): can't find starting instruction 31362306a36Sopenharmony_ci or 31462306a36Sopenharmony_ci file.o: warning: objtool: func()+0x11dd: can't decode instruction 31562306a36Sopenharmony_ci 31662306a36Sopenharmony_ci Does the file have data in a text section? If so, that can confuse 31762306a36Sopenharmony_ci objtool's instruction decoder. Move the data to a more appropriate 31862306a36Sopenharmony_ci section like .data or .rodata. 31962306a36Sopenharmony_ci 32062306a36Sopenharmony_ci 32162306a36Sopenharmony_ci5. file.o: warning: objtool: func()+0x6: unsupported instruction in callable function 32262306a36Sopenharmony_ci 32362306a36Sopenharmony_ci This is a kernel entry/exit instruction like sysenter or iret. Such 32462306a36Sopenharmony_ci instructions aren't allowed in a callable function, and are most 32562306a36Sopenharmony_ci likely part of the kernel entry code. They should usually not have 32662306a36Sopenharmony_ci the callable function annotation (ENDPROC) and should always be 32762306a36Sopenharmony_ci annotated with the unwind hint macros in asm/unwind_hints.h. 32862306a36Sopenharmony_ci 32962306a36Sopenharmony_ci 33062306a36Sopenharmony_ci6. file.o: warning: objtool: func()+0x26: sibling call from callable instruction with modified stack frame 33162306a36Sopenharmony_ci 33262306a36Sopenharmony_ci This is a dynamic jump or a jump to an undefined symbol. Objtool 33362306a36Sopenharmony_ci assumed it's a sibling call and detected that the frame pointer 33462306a36Sopenharmony_ci wasn't first restored to its original state. 33562306a36Sopenharmony_ci 33662306a36Sopenharmony_ci If it's not really a sibling call, you may need to move the 33762306a36Sopenharmony_ci destination code to the local file. 33862306a36Sopenharmony_ci 33962306a36Sopenharmony_ci If the instruction is not actually in a callable function (e.g. 34062306a36Sopenharmony_ci kernel entry code), change ENDPROC to END and annotate manually with 34162306a36Sopenharmony_ci the unwind hint macros in asm/unwind_hints.h. 34262306a36Sopenharmony_ci 34362306a36Sopenharmony_ci 34462306a36Sopenharmony_ci7. file: warning: objtool: func()+0x5c: stack state mismatch 34562306a36Sopenharmony_ci 34662306a36Sopenharmony_ci The instruction's frame pointer state is inconsistent, depending on 34762306a36Sopenharmony_ci which execution path was taken to reach the instruction. 34862306a36Sopenharmony_ci 34962306a36Sopenharmony_ci Make sure that, when CONFIG_FRAME_POINTER is enabled, the function 35062306a36Sopenharmony_ci pushes and sets up the frame pointer (for x86_64, this means rbp) at 35162306a36Sopenharmony_ci the beginning of the function and pops it at the end of the function. 35262306a36Sopenharmony_ci Also make sure that no other code in the function touches the frame 35362306a36Sopenharmony_ci pointer. 35462306a36Sopenharmony_ci 35562306a36Sopenharmony_ci Another possibility is that the code has some asm or inline asm which 35662306a36Sopenharmony_ci does some unusual things to the stack or the frame pointer. In such 35762306a36Sopenharmony_ci cases it's probably appropriate to use the unwind hint macros in 35862306a36Sopenharmony_ci asm/unwind_hints.h. 35962306a36Sopenharmony_ci 36062306a36Sopenharmony_ci 36162306a36Sopenharmony_ci8. file.o: warning: objtool: funcA() falls through to next function funcB() 36262306a36Sopenharmony_ci 36362306a36Sopenharmony_ci This means that funcA() doesn't end with a return instruction or an 36462306a36Sopenharmony_ci unconditional jump, and that objtool has determined that the function 36562306a36Sopenharmony_ci can fall through into the next function. There could be different 36662306a36Sopenharmony_ci reasons for this: 36762306a36Sopenharmony_ci 36862306a36Sopenharmony_ci 1) funcA()'s last instruction is a call to a "noreturn" function like 36962306a36Sopenharmony_ci panic(). In this case the noreturn function needs to be added to 37062306a36Sopenharmony_ci objtool's hard-coded global_noreturns array. Feel free to bug the 37162306a36Sopenharmony_ci objtool maintainer, or you can submit a patch. 37262306a36Sopenharmony_ci 37362306a36Sopenharmony_ci 2) funcA() uses the unreachable() annotation in a section of code 37462306a36Sopenharmony_ci that is actually reachable. 37562306a36Sopenharmony_ci 37662306a36Sopenharmony_ci 3) If funcA() calls an inline function, the object code for funcA() 37762306a36Sopenharmony_ci might be corrupt due to a gcc bug. For more details, see: 37862306a36Sopenharmony_ci https://gcc.gnu.org/bugzilla/show_bug.cgi?id=70646 37962306a36Sopenharmony_ci 38062306a36Sopenharmony_ci9. file.o: warning: objtool: funcA() call to funcB() with UACCESS enabled 38162306a36Sopenharmony_ci 38262306a36Sopenharmony_ci This means that an unexpected call to a non-whitelisted function exists 38362306a36Sopenharmony_ci outside of arch-specific guards. 38462306a36Sopenharmony_ci X86: SMAP (stac/clac): __uaccess_begin()/__uaccess_end() 38562306a36Sopenharmony_ci ARM: PAN: uaccess_enable()/uaccess_disable() 38662306a36Sopenharmony_ci 38762306a36Sopenharmony_ci These functions should be called to denote a minimal critical section around 38862306a36Sopenharmony_ci access to __user variables. See also: https://lwn.net/Articles/517475/ 38962306a36Sopenharmony_ci 39062306a36Sopenharmony_ci The intention of the warning is to prevent calls to funcB() from eventually 39162306a36Sopenharmony_ci calling schedule(), potentially leaking the AC flags state, and not 39262306a36Sopenharmony_ci restoring them correctly. 39362306a36Sopenharmony_ci 39462306a36Sopenharmony_ci It also helps verify that there are no unexpected calls to funcB() which may 39562306a36Sopenharmony_ci access user space pages with protections against doing so disabled. 39662306a36Sopenharmony_ci 39762306a36Sopenharmony_ci To fix, either: 39862306a36Sopenharmony_ci 1) remove explicit calls to funcB() from funcA(). 39962306a36Sopenharmony_ci 2) add the correct guards before and after calls to low level functions like 40062306a36Sopenharmony_ci __get_user_size()/__put_user_size(). 40162306a36Sopenharmony_ci 3) add funcB to uaccess_safe_builtin whitelist in tools/objtool/check.c, if 40262306a36Sopenharmony_ci funcB obviously does not call schedule(), and is marked notrace (since 40362306a36Sopenharmony_ci function tracing inserts additional calls, which is not obvious from the 40462306a36Sopenharmony_ci sources). 40562306a36Sopenharmony_ci 40662306a36Sopenharmony_ci10. file.o: warning: func()+0x5c: stack layout conflict in alternatives 40762306a36Sopenharmony_ci 40862306a36Sopenharmony_ci This means that in the use of the alternative() or ALTERNATIVE() 40962306a36Sopenharmony_ci macro, the code paths have conflicting modifications to the stack. 41062306a36Sopenharmony_ci The problem is that there is only one ORC unwind table, which means 41162306a36Sopenharmony_ci that the ORC unwind entries must be consistent for all possible 41262306a36Sopenharmony_ci instruction boundaries regardless of which code has been patched. 41362306a36Sopenharmony_ci This limitation can be overcome by massaging the alternatives with 41462306a36Sopenharmony_ci NOPs to shift the stack changes around so they no longer conflict. 41562306a36Sopenharmony_ci 41662306a36Sopenharmony_ci11. file.o: warning: unannotated intra-function call 41762306a36Sopenharmony_ci 41862306a36Sopenharmony_ci This warning means that a direct call is done to a destination which 41962306a36Sopenharmony_ci is not at the beginning of a function. If this is a legit call, you 42062306a36Sopenharmony_ci can remove this warning by putting the ANNOTATE_INTRA_FUNCTION_CALL 42162306a36Sopenharmony_ci directive right before the call. 42262306a36Sopenharmony_ci 42362306a36Sopenharmony_ci12. file.o: warning: func(): not an indirect call target 42462306a36Sopenharmony_ci 42562306a36Sopenharmony_ci This means that objtool is running with --ibt and a function expected 42662306a36Sopenharmony_ci to be an indirect call target is not. In particular, this happens for 42762306a36Sopenharmony_ci init_module() or cleanup_module() if a module relies on these special 42862306a36Sopenharmony_ci names and does not use module_init() / module_exit() macros to create 42962306a36Sopenharmony_ci them. 43062306a36Sopenharmony_ci 43162306a36Sopenharmony_ci 43262306a36Sopenharmony_ciIf the error doesn't seem to make sense, it could be a bug in objtool. 43362306a36Sopenharmony_ciFeel free to ask the objtool maintainer for help. 43462306a36Sopenharmony_ci 43562306a36Sopenharmony_ci 43662306a36Sopenharmony_ciAdding exceptions 43762306a36Sopenharmony_ci----------------- 43862306a36Sopenharmony_ci 43962306a36Sopenharmony_ciIf you _really_ need objtool to ignore something, and are 100% sure 44062306a36Sopenharmony_cithat it won't affect kernel stack traces, you can tell objtool to 44162306a36Sopenharmony_ciignore it: 44262306a36Sopenharmony_ci 44362306a36Sopenharmony_ci- To skip validation of a function, use the STACK_FRAME_NON_STANDARD 44462306a36Sopenharmony_ci macro. 44562306a36Sopenharmony_ci 44662306a36Sopenharmony_ci- To skip validation of a file, add 44762306a36Sopenharmony_ci 44862306a36Sopenharmony_ci OBJECT_FILES_NON_STANDARD_filename.o := y 44962306a36Sopenharmony_ci 45062306a36Sopenharmony_ci to the Makefile. 45162306a36Sopenharmony_ci 45262306a36Sopenharmony_ci- To skip validation of a directory, add 45362306a36Sopenharmony_ci 45462306a36Sopenharmony_ci OBJECT_FILES_NON_STANDARD := y 45562306a36Sopenharmony_ci 45662306a36Sopenharmony_ci to the Makefile. 45762306a36Sopenharmony_ci 45862306a36Sopenharmony_ciNOTE: OBJECT_FILES_NON_STANDARD doesn't work for link time validation of 45962306a36Sopenharmony_civmlinux.o or a linked module. So it should only be used for files which 46062306a36Sopenharmony_ciaren't linked into vmlinux or a module. 461