LCOV - code coverage report
Current view: top level - arch/x86/include/asm - frame.h (source / functions) Hit Total Coverage
Test: landlock.info Lines: 2 2 100.0 %
Date: 2021-04-22 12:43:58 Functions: 0 0 -

          Line data    Source code
       1             : /* SPDX-License-Identifier: GPL-2.0 */
       2             : #ifndef _ASM_X86_FRAME_H
       3             : #define _ASM_X86_FRAME_H
       4             : 
       5             : #include <asm/asm.h>
       6             : 
       7             : /*
       8             :  * These are stack frame creation macros.  They should be used by every
       9             :  * callable non-leaf asm function to make kernel stack traces more reliable.
      10             :  */
      11             : 
      12             : #ifdef CONFIG_FRAME_POINTER
      13             : 
      14             : #ifdef __ASSEMBLY__
      15             : 
      16             : .macro FRAME_BEGIN
      17             :         push %_ASM_BP
      18             :         _ASM_MOV %_ASM_SP, %_ASM_BP
      19             : .endm
      20             : 
      21             : .macro FRAME_END
      22             :         pop %_ASM_BP
      23             : .endm
      24             : 
      25             : #ifdef CONFIG_X86_64
      26             : /*
      27             :  * This is a sneaky trick to help the unwinder find pt_regs on the stack.  The
      28             :  * frame pointer is replaced with an encoded pointer to pt_regs.  The encoding
      29             :  * is just setting the LSB, which makes it an invalid stack address and is also
      30             :  * a signal to the unwinder that it's a pt_regs pointer in disguise.
      31             :  *
      32             :  * NOTE: This macro must be used *after* PUSH_AND_CLEAR_REGS because it corrupts
      33             :  * the original rbp.
      34             :  */
      35             : .macro ENCODE_FRAME_POINTER ptregs_offset=0
      36             :         leaq 1+\ptregs_offset(%rsp), %rbp
      37             : .endm
      38             : #else /* !CONFIG_X86_64 */
      39             : /*
      40             :  * This is a sneaky trick to help the unwinder find pt_regs on the stack.  The
      41             :  * frame pointer is replaced with an encoded pointer to pt_regs.  The encoding
      42             :  * is just clearing the MSB, which makes it an invalid stack address and is also
      43             :  * a signal to the unwinder that it's a pt_regs pointer in disguise.
      44             :  *
      45             :  * NOTE: This macro must be used *after* SAVE_ALL because it corrupts the
      46             :  * original ebp.
      47             :  */
      48             : .macro ENCODE_FRAME_POINTER
      49             :         mov %esp, %ebp
      50             :         andl $0x7fffffff, %ebp
      51             : .endm
      52             : #endif /* CONFIG_X86_64 */
      53             : 
      54             : #else /* !__ASSEMBLY__ */
      55             : 
      56             : #define FRAME_BEGIN                             \
      57             :         "push %" _ASM_BP "\n"                       \
      58             :         _ASM_MOV "%" _ASM_SP ", %" _ASM_BP "\n"
      59             : 
      60             : #define FRAME_END "pop %" _ASM_BP "\n"
      61             : 
      62             : #ifdef CONFIG_X86_64
      63             : 
      64             : #define ENCODE_FRAME_POINTER                    \
      65             :         "lea 1(%rsp), %rbp\n\t"
      66             : 
      67             : static inline unsigned long encode_frame_pointer(struct pt_regs *regs)
      68             : {
      69             :         return (unsigned long)regs + 1;
      70             : }
      71             : 
      72             : #else /* !CONFIG_X86_64 */
      73             : 
      74             : #define ENCODE_FRAME_POINTER                    \
      75             :         "movl %esp, %ebp\n\t"                 \
      76             :         "andl $0x7fffffff, %ebp\n\t"
      77             : 
      78             : static inline unsigned long encode_frame_pointer(struct pt_regs *regs)
      79             : {
      80             :         return (unsigned long)regs & 0x7fffffff;
      81             : }
      82             : 
      83             : #endif /* CONFIG_X86_64 */
      84             : 
      85             : #endif /* __ASSEMBLY__ */
      86             : 
      87             : #define FRAME_OFFSET __ASM_SEL(4, 8)
      88             : 
      89             : #else /* !CONFIG_FRAME_POINTER */
      90             : 
      91             : #ifdef __ASSEMBLY__
      92             : 
      93             : .macro ENCODE_FRAME_POINTER ptregs_offset=0
      94             : .endm
      95             : 
      96             : #else /* !__ASSEMBLY */
      97             : 
      98             : #define ENCODE_FRAME_POINTER
      99             : 
     100        2616 : static inline unsigned long encode_frame_pointer(struct pt_regs *regs)
     101             : {
     102        2616 :         return 0;
     103             : }
     104             : 
     105             : #endif
     106             : 
     107             : #define FRAME_BEGIN
     108             : #define FRAME_END
     109             : #define FRAME_OFFSET 0
     110             : 
     111             : #endif /* CONFIG_FRAME_POINTER */
     112             : 
     113             : #endif /* _ASM_X86_FRAME_H */

Generated by: LCOV version 1.14