~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/arch/x86/entry/entry_64_fred.S

Version: ~ [ linux-6.12-rc7 ] ~ [ linux-6.11.7 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.60 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.116 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.171 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.229 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.285 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.323 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.12 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 /* SPDX-License-Identifier: GPL-2.0 */
  2 /*
  3  * The actual FRED entry points.
  4  */
  5 
  6 #include <linux/export.h>
  7 
  8 #include <asm/asm.h>
  9 #include <asm/fred.h>
 10 #include <asm/segment.h>
 11 
 12 #include "calling.h"
 13 
 14         .code64
 15         .section .noinstr.text, "ax"
 16 
 17 .macro FRED_ENTER
 18         UNWIND_HINT_END_OF_STACK
 19         ENDBR
 20         PUSH_AND_CLEAR_REGS
 21         movq    %rsp, %rdi      /* %rdi -> pt_regs */
 22 .endm
 23 
 24 .macro FRED_EXIT
 25         UNWIND_HINT_REGS
 26         POP_REGS
 27 .endm
 28 
 29 /*
 30  * The new RIP value that FRED event delivery establishes is
 31  * IA32_FRED_CONFIG & ~FFFH for events that occur in ring 3.
 32  * Thus the FRED ring 3 entry point must be 4K page aligned.
 33  */
 34         .align 4096
 35 
 36 SYM_CODE_START_NOALIGN(asm_fred_entrypoint_user)
 37         FRED_ENTER
 38         call    fred_entry_from_user
 39 SYM_INNER_LABEL(asm_fred_exit_user, SYM_L_GLOBAL)
 40         FRED_EXIT
 41 1:      ERETU
 42 
 43         _ASM_EXTABLE_TYPE(1b, asm_fred_entrypoint_user, EX_TYPE_ERETU)
 44 SYM_CODE_END(asm_fred_entrypoint_user)
 45 
 46 /*
 47  * The new RIP value that FRED event delivery establishes is
 48  * (IA32_FRED_CONFIG & ~FFFH) + 256 for events that occur in
 49  * ring 0, i.e., asm_fred_entrypoint_user + 256.
 50  */
 51         .org asm_fred_entrypoint_user + 256, 0xcc
 52 SYM_CODE_START_NOALIGN(asm_fred_entrypoint_kernel)
 53         FRED_ENTER
 54         call    fred_entry_from_kernel
 55         FRED_EXIT
 56         ERETS
 57 SYM_CODE_END(asm_fred_entrypoint_kernel)
 58 
 59 #if IS_ENABLED(CONFIG_KVM_INTEL)
 60 SYM_FUNC_START(asm_fred_entry_from_kvm)
 61         push %rbp
 62         mov %rsp, %rbp
 63 
 64         UNWIND_HINT_SAVE
 65 
 66         /*
 67          * Both IRQ and NMI from VMX can be handled on current task stack
 68          * because there is no need to protect from reentrancy and the call
 69          * stack leading to this helper is effectively constant and shallow
 70          * (relatively speaking). Do the same when FRED is active, i.e., no
 71          * need to check current stack level for a stack switch.
 72          *
 73          * Emulate the FRED-defined redzone and stack alignment.
 74          */
 75         sub $(FRED_CONFIG_REDZONE_AMOUNT << 6), %rsp
 76         and $FRED_STACK_FRAME_RSP_MASK, %rsp
 77 
 78         /*
 79          * Start to push a FRED stack frame, which is always 64 bytes:
 80          *
 81          * +--------+-----------------+
 82          * | Bytes  | Usage           |
 83          * +--------+-----------------+
 84          * | 63:56  | Reserved        |
 85          * | 55:48  | Event Data      |
 86          * | 47:40  | SS + Event Info |
 87          * | 39:32  | RSP             |
 88          * | 31:24  | RFLAGS          |
 89          * | 23:16  | CS + Aux Info   |
 90          * |  15:8  | RIP             |
 91          * |   7:0  | Error Code      |
 92          * +--------+-----------------+
 93          */
 94         push $0                         /* Reserved, must be 0 */
 95         push $0                         /* Event data, 0 for IRQ/NMI */
 96         push %rdi                       /* fred_ss handed in by the caller */
 97         push %rbp
 98         pushf
 99         mov $__KERNEL_CS, %rax
100         push %rax
101 
102         /*
103          * Unlike the IDT event delivery, FRED _always_ pushes an error code
104          * after pushing the return RIP, thus the CALL instruction CANNOT be
105          * used here to push the return RIP, otherwise there is no chance to
106          * push an error code before invoking the IRQ/NMI handler.
107          *
108          * Use LEA to get the return RIP and push it, then push an error code.
109          */
110         lea 1f(%rip), %rax
111         push %rax                               /* Return RIP */
112         push $0                                 /* Error code, 0 for IRQ/NMI */
113 
114         PUSH_AND_CLEAR_REGS clear_bp=0 unwind_hint=0
115         movq %rsp, %rdi                         /* %rdi -> pt_regs */
116         call __fred_entry_from_kvm              /* Call the C entry point */
117         POP_REGS
118         ERETS
119 1:
120         /*
121          * Objtool doesn't understand what ERETS does, this hint tells it that
122          * yes, we'll reach here and with what stack state. A save/restore pair
123          * isn't strictly needed, but it's the simplest form.
124          */
125         UNWIND_HINT_RESTORE
126         pop %rbp
127         RET
128 
129 SYM_FUNC_END(asm_fred_entry_from_kvm)
130 EXPORT_SYMBOL_GPL(asm_fred_entry_from_kvm);
131 #endif

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php