1 /* SPDX-License-Identifier: GPL-2.0 */ 2 #ifndef _ASM_X86_IDTENTRY_H 3 #define _ASM_X86_IDTENTRY_H 4 5 /* Interrupts/Exceptions */ 6 #include <asm/trapnr.h> 7 8 #ifndef __ASSEMBLY__ 9 #include <linux/entry-common.h> 10 #include <linux/hardirq.h> 11 12 #include <asm/irq_stack.h> 13 14 bool idtentry_enter_nmi(struct pt_regs *regs); 15 void idtentry_exit_nmi(struct pt_regs *regs, bool irq_state); 16 17 /** 18 * DECLARE_IDTENTRY - Declare functions for simple IDT entry points 19 * No error code pushed by hardware 20 * @vector: Vector number (ignored for C) 21 * @func: Function name of the entry point 22 * 23 * Declares three functions: 24 * - The ASM entry point: asm_##func 25 * - The XEN PV trap entry point: xen_##func (maybe unused) 26 * - The C handler called from the ASM entry point 27 * 28 * Note: This is the C variant of DECLARE_IDTENTRY(). As the name says it 29 * declares the entry points for usage in C code. There is an ASM variant 30 * as well which is used to emit the entry stubs in entry_32/64.S. 31 */ 32 #define DECLARE_IDTENTRY(vector, func) \ 33 asmlinkage void asm_##func(void); \ 34 asmlinkage void xen_asm_##func(void); \ 35 __visible void func(struct pt_regs *regs) 36 37 /** 38 * DEFINE_IDTENTRY - Emit code for simple IDT entry points 39 * @func: Function name of the entry point 40 * 41 * @func is called from ASM entry code with interrupts disabled. 42 * 43 * The macro is written so it acts as function definition. Append the 44 * body with a pair of curly brackets. 45 * 46 * irqentry_enter() contains common code which has to be invoked before 47 * arbitrary code in the body. irqentry_exit() contains common code 48 * which has to run before returning to the low level assembly code. 49 */ 50 #define DEFINE_IDTENTRY(func) \ 51 static __always_inline void __##func(struct pt_regs *regs); \ 52 \ 53 __visible noinstr void func(struct pt_regs *regs) \ 54 { \ 55 irqentry_state_t state = irqentry_enter(regs); \ 56 \ 57 instrumentation_begin(); \ 58 __##func (regs); \ 59 instrumentation_end(); \ 60 irqentry_exit(regs, state); \ 61 } \ 62 \ 63 static __always_inline void __##func(struct pt_regs *regs) 64 65 /* Special case for 32bit IRET 'trap' */ 66 #define DECLARE_IDTENTRY_SW DECLARE_IDTENTRY 67 #define DEFINE_IDTENTRY_SW DEFINE_IDTENTRY 68 69 /** 70 * DECLARE_IDTENTRY_ERRORCODE - Declare functions for simple IDT entry points 71 * Error code pushed by hardware 72 * @vector: Vector number (ignored for C) 73 * @func: Function name of the entry point 74 * 75 * Declares three functions: 76 * - The ASM entry point: asm_##func 77 * - The XEN PV trap entry point: xen_##func (maybe unused) 78 * - The C handler called from the ASM entry point 79 * 80 * Same as DECLARE_IDTENTRY, but has an extra error_code argument for the 81 * C-handler. 82 */ 83 #define DECLARE_IDTENTRY_ERRORCODE(vector, func) \ 84 asmlinkage void asm_##func(void); \ 85 asmlinkage void xen_asm_##func(void); \ 86 __visible void func(struct pt_regs *regs, unsigned long error_code) 87 88 /** 89 * DEFINE_IDTENTRY_ERRORCODE - Emit code for simple IDT entry points 90 * Error code pushed by hardware 91 * @func: Function name of the entry point 92 * 93 * Same as DEFINE_IDTENTRY, but has an extra error_code argument 94 */ 95 #define DEFINE_IDTENTRY_ERRORCODE(func) \ 96 static __always_inline void __##func(struct pt_regs *regs, \ 97 unsigned long error_code); \ 98 \ 99 __visible noinstr void func(struct pt_regs *regs, \ 100 unsigned long error_code) \ 101 { \ 102 irqentry_state_t state = irqentry_enter(regs); \ 103 \ 104 instrumentation_begin(); \ 105 __##func (regs, error_code); \ 106 instrumentation_end(); \ 107 irqentry_exit(regs, state); \ 108 } \ 109 \ 110 static __always_inline void __##func(struct pt_regs *regs, \ 111 unsigned long error_code) 112 113 /** 114 * DECLARE_IDTENTRY_RAW - Declare functions for raw IDT entry points 115 * No error code pushed by hardware 116 * @vector: Vector number (ignored for C) 117 * @func: Function name of the entry point 118 * 119 * Maps to DECLARE_IDTENTRY(). 120 */ 121 #define DECLARE_IDTENTRY_RAW(vector, func) \ 122 DECLARE_IDTENTRY(vector, func) 123 124 /** 125 * DEFINE_IDTENTRY_RAW - Emit code for raw IDT entry points 126 * @func: Function name of the entry point 127 * 128 * @func is called from ASM entry code with interrupts disabled. 129 * 130 * The macro is written so it acts as function definition. Append the 131 * body with a pair of curly brackets. 132 * 133 * Contrary to DEFINE_IDTENTRY() this does not invoke the 134 * idtentry_enter/exit() helpers before and after the body invocation. This 135 * needs to be done in the body itself if applicable. Use if extra work 136 * is required before the enter/exit() helpers are invoked. 137 */ 138 #define DEFINE_IDTENTRY_RAW(func) \ 139 __visible noinstr void func(struct pt_regs *regs) 140 141 /** 142 * DECLARE_IDTENTRY_RAW_ERRORCODE - Declare functions for raw IDT entry points 143 * Error code pushed by hardware 144 * @vector: Vector number (ignored for C) 145 * @func: Function name of the entry point 146 * 147 * Maps to DECLARE_IDTENTRY_ERRORCODE() 148 */ 149 #define DECLARE_IDTENTRY_RAW_ERRORCODE(vector, func) \ 150 DECLARE_IDTENTRY_ERRORCODE(vector, func) 151 152 /** 153 * DEFINE_IDTENTRY_RAW_ERRORCODE - Emit code for raw IDT entry points 154 * @func: Function name of the entry point 155 * 156 * @func is called from ASM entry code with interrupts disabled. 157 * 158 * The macro is written so it acts as function definition. Append the 159 * body with a pair of curly brackets. 160 * 161 * Contrary to DEFINE_IDTENTRY_ERRORCODE() this does not invoke the 162 * irqentry_enter/exit() helpers before and after the body invocation. This 163 * needs to be done in the body itself if applicable. Use if extra work 164 * is required before the enter/exit() helpers are invoked. 165 */ 166 #define DEFINE_IDTENTRY_RAW_ERRORCODE(func) \ 167 __visible noinstr void func(struct pt_regs *regs, unsigned long error_code) 168 169 /** 170 * DECLARE_IDTENTRY_IRQ - Declare functions for device interrupt IDT entry 171 * points (common/spurious) 172 * @vector: Vector number (ignored for C) 173 * @func: Function name of the entry point 174 * 175 * Maps to DECLARE_IDTENTRY_ERRORCODE() 176 */ 177 #define DECLARE_IDTENTRY_IRQ(vector, func) \ 178 DECLARE_IDTENTRY_ERRORCODE(vector, func) 179 180 /** 181 * DEFINE_IDTENTRY_IRQ - Emit code for device interrupt IDT entry points 182 * @func: Function name of the entry point 183 * 184 * The vector number is pushed by the low level entry stub and handed 185 * to the function as error_code argument which needs to be truncated 186 * to an u8 because the push is sign extending. 187 * 188 * irq_enter/exit_rcu() are invoked before the function body and the 189 * KVM L1D flush request is set. Stack switching to the interrupt stack 190 * has to be done in the function body if necessary. 191 */ 192 #define DEFINE_IDTENTRY_IRQ(func) \ 193 static __always_inline void __##func(struct pt_regs *regs, u8 vector); \ 194 \ 195 __visible noinstr void func(struct pt_regs *regs, \ 196 unsigned long error_code) \ 197 { \ 198 irqentry_state_t state = irqentry_enter(regs); \ 199 \ 200 instrumentation_begin(); \ 201 irq_enter_rcu(); \ 202 kvm_set_cpu_l1tf_flush_l1d(); \ 203 __##func (regs, (u8)error_code); \ 204 irq_exit_rcu(); \ 205 instrumentation_end(); \ 206 irqentry_exit(regs, state); \ 207 } \ 208 \ 209 static __always_inline void __##func(struct pt_regs *regs, u8 vector) 210 211 /** 212 * DECLARE_IDTENTRY_SYSVEC - Declare functions for system vector entry points 213 * @vector: Vector number (ignored for C) 214 * @func: Function name of the entry point 215 * 216 * Declares three functions: 217 * - The ASM entry point: asm_##func 218 * - The XEN PV trap entry point: xen_##func (maybe unused) 219 * - The C handler called from the ASM entry point 220 * 221 * Maps to DECLARE_IDTENTRY(). 222 */ 223 #define DECLARE_IDTENTRY_SYSVEC(vector, func) \ 224 DECLARE_IDTENTRY(vector, func) 225 226 /** 227 * DEFINE_IDTENTRY_SYSVEC - Emit code for system vector IDT entry points 228 * @func: Function name of the entry point 229 * 230 * irqentry_enter/exit() and irq_enter/exit_rcu() are invoked before the 231 * function body. KVM L1D flush request is set. 232 * 233 * Runs the function on the interrupt stack if the entry hit kernel mode 234 */ 235 #define DEFINE_IDTENTRY_SYSVEC(func) \ 236 static void __##func(struct pt_regs *regs); \ 237 \ 238 __visible noinstr void func(struct pt_regs *regs) \ 239 { \ 240 irqentry_state_t state = irqentry_enter(regs); \ 241 \ 242 instrumentation_begin(); \ 243 irq_enter_rcu(); \ 244 kvm_set_cpu_l1tf_flush_l1d(); \ 245 run_on_irqstack_cond(__##func, regs, regs); \ 246 irq_exit_rcu(); \ 247 instrumentation_end(); \ 248 irqentry_exit(regs, state); \ 249 } \ 250 \ 251 static noinline void __##func(struct pt_regs *regs) 252 253 /** 254 * DEFINE_IDTENTRY_SYSVEC_SIMPLE - Emit code for simple system vector IDT 255 * entry points 256 * @func: Function name of the entry point 257 * 258 * Runs the function on the interrupted stack. No switch to IRQ stack and 259 * only the minimal __irq_enter/exit() handling. 260 * 261 * Only use for 'empty' vectors like reschedule IPI and KVM posted 262 * interrupt vectors. 263 */ 264 #define DEFINE_IDTENTRY_SYSVEC_SIMPLE(func) \ 265 static __always_inline void __##func(struct pt_regs *regs); \ 266 \ 267 __visible noinstr void func(struct pt_regs *regs) \ 268 { \ 269 irqentry_state_t state = irqentry_enter(regs); \ 270 \ 271 instrumentation_begin(); \ 272 __irq_enter_raw(); \ 273 kvm_set_cpu_l1tf_flush_l1d(); \ 274 __##func (regs); \ 275 __irq_exit_raw(); \ 276 instrumentation_end(); \ 277 irqentry_exit(regs, state); \ 278 } \ 279 \ 280 static __always_inline void __##func(struct pt_regs *regs) 281 282 /** 283 * DECLARE_IDTENTRY_XENCB - Declare functions for XEN HV callback entry point 284 * @vector: Vector number (ignored for C) 285 * @func: Function name of the entry point 286 * 287 * Declares three functions: 288 * - The ASM entry point: asm_##func 289 * - The XEN PV trap entry point: xen_##func (maybe unused) 290 * - The C handler called from the ASM entry point 291 * 292 * Maps to DECLARE_IDTENTRY(). Distinct entry point to handle the 32/64-bit 293 * difference 294 */ 295 #define DECLARE_IDTENTRY_XENCB(vector, func) \ 296 DECLARE_IDTENTRY(vector, func) 297 298 #ifdef CONFIG_X86_64 299 /** 300 * DECLARE_IDTENTRY_IST - Declare functions for IST handling IDT entry points 301 * @vector: Vector number (ignored for C) 302 * @func: Function name of the entry point 303 * 304 * Maps to DECLARE_IDTENTRY_RAW, but declares also the NOIST C handler 305 * which is called from the ASM entry point on user mode entry 306 */ 307 #define DECLARE_IDTENTRY_IST(vector, func) \ 308 DECLARE_IDTENTRY_RAW(vector, func); \ 309 __visible void noist_##func(struct pt_regs *regs) 310 311 /** 312 * DEFINE_IDTENTRY_IST - Emit code for IST entry points 313 * @func: Function name of the entry point 314 * 315 * Maps to DEFINE_IDTENTRY_RAW 316 */ 317 #define DEFINE_IDTENTRY_IST(func) \ 318 DEFINE_IDTENTRY_RAW(func) 319 320 /** 321 * DEFINE_IDTENTRY_NOIST - Emit code for NOIST entry points which 322 * belong to a IST entry point (MCE, DB) 323 * @func: Function name of the entry point. Must be the same as 324 * the function name of the corresponding IST variant 325 * 326 * Maps to DEFINE_IDTENTRY_RAW(). 327 */ 328 #define DEFINE_IDTENTRY_NOIST(func) \ 329 DEFINE_IDTENTRY_RAW(noist_##func) 330 331 /** 332 * DECLARE_IDTENTRY_DF - Declare functions for double fault 333 * @vector: Vector number (ignored for C) 334 * @func: Function name of the entry point 335 * 336 * Maps to DECLARE_IDTENTRY_RAW_ERRORCODE 337 */ 338 #define DECLARE_IDTENTRY_DF(vector, func) \ 339 DECLARE_IDTENTRY_RAW_ERRORCODE(vector, func) 340 341 /** 342 * DEFINE_IDTENTRY_DF - Emit code for double fault 343 * @func: Function name of the entry point 344 * 345 * Maps to DEFINE_IDTENTRY_RAW_ERRORCODE 346 */ 347 #define DEFINE_IDTENTRY_DF(func) \ 348 DEFINE_IDTENTRY_RAW_ERRORCODE(func) 349 350 #else /* CONFIG_X86_64 */ 351 352 /** 353 * DECLARE_IDTENTRY_DF - Declare functions for double fault 32bit variant 354 * @vector: Vector number (ignored for C) 355 * @func: Function name of the entry point 356 * 357 * Declares two functions: 358 * - The ASM entry point: asm_##func 359 * - The C handler called from the C shim 360 */ 361 #define DECLARE_IDTENTRY_DF(vector, func) \ 362 asmlinkage void asm_##func(void); \ 363 __visible void func(struct pt_regs *regs, \ 364 unsigned long error_code, \ 365 unsigned long address) 366 367 /** 368 * DEFINE_IDTENTRY_DF - Emit code for double fault on 32bit 369 * @func: Function name of the entry point 370 * 371 * This is called through the doublefault shim which already provides 372 * cr2 in the address argument. 373 */ 374 #define DEFINE_IDTENTRY_DF(func) \ 375 __visible noinstr void func(struct pt_regs *regs, \ 376 unsigned long error_code, \ 377 unsigned long address) 378 379 #endif /* !CONFIG_X86_64 */ 380 381 /* C-Code mapping */ 382 #define DECLARE_IDTENTRY_NMI DECLARE_IDTENTRY_RAW 383 #define DEFINE_IDTENTRY_NMI DEFINE_IDTENTRY_RAW 384 385 #ifdef CONFIG_X86_64 386 #define DECLARE_IDTENTRY_MCE DECLARE_IDTENTRY_IST 387 #define DEFINE_IDTENTRY_MCE DEFINE_IDTENTRY_IST 388 #define DEFINE_IDTENTRY_MCE_USER DEFINE_IDTENTRY_NOIST 389 390 #define DECLARE_IDTENTRY_DEBUG DECLARE_IDTENTRY_IST 391 #define DEFINE_IDTENTRY_DEBUG DEFINE_IDTENTRY_IST 392 #define DEFINE_IDTENTRY_DEBUG_USER DEFINE_IDTENTRY_NOIST 393 #endif 394 395 #else /* !__ASSEMBLY__ */ 396 397 /* 398 * The ASM variants for DECLARE_IDTENTRY*() which emit the ASM entry stubs. 399 */ 400 #define DECLARE_IDTENTRY(vector, func) \ 401 idtentry vector asm_##func func has_error_code=0 402 403 #define DECLARE_IDTENTRY_ERRORCODE(vector, func) \ 404 idtentry vector asm_##func func has_error_code=1 405 406 /* Special case for 32bit IRET 'trap'. Do not emit ASM code */ 407 #define DECLARE_IDTENTRY_SW(vector, func) 408 409 #define DECLARE_IDTENTRY_RAW(vector, func) \ 410 DECLARE_IDTENTRY(vector, func) 411 412 #define DECLARE_IDTENTRY_RAW_ERRORCODE(vector, func) \ 413 DECLARE_IDTENTRY_ERRORCODE(vector, func) 414 415 /* Entries for common/spurious (device) interrupts */ 416 #define DECLARE_IDTENTRY_IRQ(vector, func) \ 417 idtentry_irq vector func 418 419 /* System vector entries */ 420 #define DECLARE_IDTENTRY_SYSVEC(vector, func) \ 421 idtentry_sysvec vector func 422 423 #ifdef CONFIG_X86_64 424 # define DECLARE_IDTENTRY_MCE(vector, func) \ 425 idtentry_mce_db vector asm_##func func 426 427 # define DECLARE_IDTENTRY_DEBUG(vector, func) \ 428 idtentry_mce_db vector asm_##func func 429 430 # define DECLARE_IDTENTRY_DF(vector, func) \ 431 idtentry_df vector asm_##func func 432 433 # define DECLARE_IDTENTRY_XENCB(vector, func) \ 434 DECLARE_IDTENTRY(vector, func) 435 436 #else 437 # define DECLARE_IDTENTRY_MCE(vector, func) \ 438 DECLARE_IDTENTRY(vector, func) 439 440 /* No ASM emitted for DF as this goes through a C shim */ 441 # define DECLARE_IDTENTRY_DF(vector, func) 442 443 /* No ASM emitted for XEN hypervisor callback */ 444 # define DECLARE_IDTENTRY_XENCB(vector, func) 445 446 #endif 447 448 /* No ASM code emitted for NMI */ 449 #define DECLARE_IDTENTRY_NMI(vector, func) 450 451 /* 452 * ASM code to emit the common vector entry stubs where each stub is 453 * packed into 8 bytes. 454 * 455 * Note, that the 'pushq imm8' is emitted via '.byte 0x6a, vector' because 456 * GCC treats the local vector variable as unsigned int and would expand 457 * all vectors above 0x7F to a 5 byte push. The original code did an 458 * adjustment of the vector number to be in the signed byte range to avoid 459 * this. While clever it's mindboggling counterintuitive and requires the 460 * odd conversion back to a real vector number in the C entry points. Using 461 * .byte achieves the same thing and the only fixup needed in the C entry 462 * point is to mask off the bits above bit 7 because the push is sign 463 * extending. 464 */ 465 .align 8 466 SYM_CODE_START(irq_entries_start) 467 vector=FIRST_EXTERNAL_VECTOR 468 .rept (FIRST_SYSTEM_VECTOR - FIRST_EXTERNAL_VECTOR) 469 UNWIND_HINT_IRET_REGS 470 0 : 471 .byte 0x6a, vector 472 jmp asm_common_interrupt 473 nop 474 /* Ensure that the above is 8 bytes max */ 475 . = 0b + 8 476 vector = vector+1 477 .endr 478 SYM_CODE_END(irq_entries_start) 479 480 #ifdef CONFIG_X86_LOCAL_APIC 481 .align 8 482 SYM_CODE_START(spurious_entries_start) 483 vector=FIRST_SYSTEM_VECTOR 484 .rept (NR_VECTORS - FIRST_SYSTEM_VECTOR) 485 UNWIND_HINT_IRET_REGS 486 0 : 487 .byte 0x6a, vector 488 jmp asm_spurious_interrupt 489 nop 490 /* Ensure that the above is 8 bytes max */ 491 . = 0b + 8 492 vector = vector+1 493 .endr 494 SYM_CODE_END(spurious_entries_start) 495 #endif 496 497 #endif /* __ASSEMBLY__ */ 498 499 /* 500 * The actual entry points. Note that DECLARE_IDTENTRY*() serves two 501 * purposes: 502 * - provide the function declarations when included from C-Code 503 * - emit the ASM stubs when included from entry_32/64.S 504 * 505 * This avoids duplicate defines and ensures that everything is consistent. 506 */ 507 508 /* 509 * Dummy trap number so the low level ASM macro vector number checks do not 510 * match which results in emitting plain IDTENTRY stubs without bells and 511 * whistels. 512 */ 513 #define X86_TRAP_OTHER 0xFFFF 514 515 /* Simple exception entry points. No hardware error code */ 516 DECLARE_IDTENTRY(X86_TRAP_DE, exc_divide_error); 517 DECLARE_IDTENTRY(X86_TRAP_OF, exc_overflow); 518 DECLARE_IDTENTRY(X86_TRAP_BR, exc_bounds); 519 DECLARE_IDTENTRY(X86_TRAP_NM, exc_device_not_available); 520 DECLARE_IDTENTRY(X86_TRAP_OLD_MF, exc_coproc_segment_overrun); 521 DECLARE_IDTENTRY(X86_TRAP_SPURIOUS, exc_spurious_interrupt_bug); 522 DECLARE_IDTENTRY(X86_TRAP_MF, exc_coprocessor_error); 523 DECLARE_IDTENTRY(X86_TRAP_XF, exc_simd_coprocessor_error); 524 525 /* 32bit software IRET trap. Do not emit ASM code */ 526 DECLARE_IDTENTRY_SW(X86_TRAP_IRET, iret_error); 527 528 /* Simple exception entries with error code pushed by hardware */ 529 DECLARE_IDTENTRY_ERRORCODE(X86_TRAP_TS, exc_invalid_tss); 530 DECLARE_IDTENTRY_ERRORCODE(X86_TRAP_NP, exc_segment_not_present); 531 DECLARE_IDTENTRY_ERRORCODE(X86_TRAP_SS, exc_stack_segment); 532 DECLARE_IDTENTRY_ERRORCODE(X86_TRAP_GP, exc_general_protection); 533 DECLARE_IDTENTRY_ERRORCODE(X86_TRAP_AC, exc_alignment_check); 534 535 /* Raw exception entries which need extra work */ 536 DECLARE_IDTENTRY_RAW(X86_TRAP_UD, exc_invalid_op); 537 DECLARE_IDTENTRY_RAW(X86_TRAP_BP, exc_int3); 538 DECLARE_IDTENTRY_RAW_ERRORCODE(X86_TRAP_PF, exc_page_fault); 539 540 #ifdef CONFIG_X86_MCE 541 #ifdef CONFIG_X86_64 542 DECLARE_IDTENTRY_MCE(X86_TRAP_MC, exc_machine_check); 543 #else 544 DECLARE_IDTENTRY_RAW(X86_TRAP_MC, exc_machine_check); 545 #endif 546 #endif 547 548 /* NMI */ 549 DECLARE_IDTENTRY_NMI(X86_TRAP_NMI, exc_nmi); 550 #if defined(CONFIG_XEN_PV) && defined(CONFIG_X86_64) 551 DECLARE_IDTENTRY_RAW(X86_TRAP_NMI, xenpv_exc_nmi); 552 #endif 553 554 /* #DB */ 555 #ifdef CONFIG_X86_64 556 DECLARE_IDTENTRY_DEBUG(X86_TRAP_DB, exc_debug); 557 #else 558 DECLARE_IDTENTRY_RAW(X86_TRAP_DB, exc_debug); 559 #endif 560 #if defined(CONFIG_XEN_PV) && defined(CONFIG_X86_64) 561 DECLARE_IDTENTRY_RAW(X86_TRAP_DB, xenpv_exc_debug); 562 #endif 563 564 /* #DF */ 565 DECLARE_IDTENTRY_DF(X86_TRAP_DF, exc_double_fault); 566 567 #ifdef CONFIG_XEN_PV 568 DECLARE_IDTENTRY_XENCB(X86_TRAP_OTHER, exc_xen_hypervisor_callback); 569 #endif 570 571 /* Device interrupts common/spurious */ 572 DECLARE_IDTENTRY_IRQ(X86_TRAP_OTHER, common_interrupt); 573 #ifdef CONFIG_X86_LOCAL_APIC 574 DECLARE_IDTENTRY_IRQ(X86_TRAP_OTHER, spurious_interrupt); 575 #endif 576 577 /* System vector entry points */ 578 #ifdef CONFIG_X86_LOCAL_APIC 579 DECLARE_IDTENTRY_SYSVEC(ERROR_APIC_VECTOR, sysvec_error_interrupt); 580 DECLARE_IDTENTRY_SYSVEC(SPURIOUS_APIC_VECTOR, sysvec_spurious_apic_interrupt); 581 DECLARE_IDTENTRY_SYSVEC(LOCAL_TIMER_VECTOR, sysvec_apic_timer_interrupt); 582 DECLARE_IDTENTRY_SYSVEC(X86_PLATFORM_IPI_VECTOR, sysvec_x86_platform_ipi); 583 #endif 584 585 #ifdef CONFIG_SMP 586 DECLARE_IDTENTRY(RESCHEDULE_VECTOR, sysvec_reschedule_ipi); 587 DECLARE_IDTENTRY_SYSVEC(IRQ_MOVE_CLEANUP_VECTOR, sysvec_irq_move_cleanup); 588 DECLARE_IDTENTRY_SYSVEC(REBOOT_VECTOR, sysvec_reboot); 589 DECLARE_IDTENTRY_SYSVEC(CALL_FUNCTION_SINGLE_VECTOR, sysvec_call_function_single); 590 DECLARE_IDTENTRY_SYSVEC(CALL_FUNCTION_VECTOR, sysvec_call_function); 591 #endif 592 593 #ifdef CONFIG_X86_LOCAL_APIC 594 # ifdef CONFIG_X86_UV 595 DECLARE_IDTENTRY_SYSVEC(UV_BAU_MESSAGE, sysvec_uv_bau_message); 596 # endif 597 598 # ifdef CONFIG_X86_MCE_THRESHOLD 599 DECLARE_IDTENTRY_SYSVEC(THRESHOLD_APIC_VECTOR, sysvec_threshold); 600 # endif 601 602 # ifdef CONFIG_X86_MCE_AMD 603 DECLARE_IDTENTRY_SYSVEC(DEFERRED_ERROR_VECTOR, sysvec_deferred_error); 604 # endif 605 606 # ifdef CONFIG_X86_THERMAL_VECTOR 607 DECLARE_IDTENTRY_SYSVEC(THERMAL_APIC_VECTOR, sysvec_thermal); 608 # endif 609 610 # ifdef CONFIG_IRQ_WORK 611 DECLARE_IDTENTRY_SYSVEC(IRQ_WORK_VECTOR, sysvec_irq_work); 612 # endif 613 #endif 614 615 #ifdef CONFIG_HAVE_KVM 616 DECLARE_IDTENTRY_SYSVEC(POSTED_INTR_VECTOR, sysvec_kvm_posted_intr_ipi); 617 DECLARE_IDTENTRY_SYSVEC(POSTED_INTR_WAKEUP_VECTOR, sysvec_kvm_posted_intr_wakeup_ipi); 618 DECLARE_IDTENTRY_SYSVEC(POSTED_INTR_NESTED_VECTOR, sysvec_kvm_posted_intr_nested_ipi); 619 #endif 620 621 #if IS_ENABLED(CONFIG_HYPERV) 622 DECLARE_IDTENTRY_SYSVEC(HYPERVISOR_CALLBACK_VECTOR, sysvec_hyperv_callback); 623 DECLARE_IDTENTRY_SYSVEC(HYPERV_REENLIGHTENMENT_VECTOR, sysvec_hyperv_reenlightenment); 624 DECLARE_IDTENTRY_SYSVEC(HYPERV_STIMER0_VECTOR, sysvec_hyperv_stimer0); 625 #endif 626 627 #if IS_ENABLED(CONFIG_ACRN_GUEST) 628 DECLARE_IDTENTRY_SYSVEC(HYPERVISOR_CALLBACK_VECTOR, sysvec_acrn_hv_callback); 629 #endif 630 631 #ifdef CONFIG_XEN_PVHVM 632 DECLARE_IDTENTRY_SYSVEC(HYPERVISOR_CALLBACK_VECTOR, sysvec_xen_hvm_callback); 633 #endif 634 635 #ifdef CONFIG_KVM_GUEST 636 DECLARE_IDTENTRY_SYSVEC(HYPERVISOR_CALLBACK_VECTOR, sysvec_kvm_asyncpf_interrupt); 637 #endif 638 639 #undef X86_TRAP_OTHER 640 641 #endif 642