2 * Interrupt descriptor table related code
4 * This file is licensed under the GPL V2
6 #include <linux/interrupt.h>
11 #include <asm/hw_irq.h>
23 #define DEFAULT_STACK 0
25 #define G(_vector, _addr, _ist, _type, _dpl, _segment) \
33 .segment = _segment, \
37 #define INTG(_vector, _addr) \
38 G(_vector, _addr, DEFAULT_STACK, GATE_INTERRUPT, DPL0, __KERNEL_CS)
40 /* System interrupt gate */
41 #define SYSG(_vector, _addr) \
42 G(_vector, _addr, DEFAULT_STACK, GATE_INTERRUPT, DPL3, __KERNEL_CS)
44 /* Interrupt gate with interrupt stack */
45 #define ISTG(_vector, _addr, _ist) \
46 G(_vector, _addr, _ist, GATE_INTERRUPT, DPL0, __KERNEL_CS)
48 /* System interrupt gate with interrupt stack */
49 #define SISTG(_vector, _addr, _ist) \
50 G(_vector, _addr, _ist, GATE_INTERRUPT, DPL3, __KERNEL_CS)
53 #define TSKG(_vector, _gdt) \
54 G(_vector, NULL, DEFAULT_STACK, GATE_TASK, DPL0, _gdt << 3)
57 * Early traps running on the DEFAULT_STACK because the other interrupt
58 * stacks work only after cpu_init().
60 static const __initconst
struct idt_data early_idts
[] = {
61 INTG(X86_TRAP_DB
, debug
),
62 SYSG(X86_TRAP_BP
, int3
),
64 INTG(X86_TRAP_PF
, page_fault
),
69 * The default IDT entries which are set up in trap_init() before
70 * cpu_init() is invoked. Interrupt stacks cannot be used at that point and
71 * the traps which use them are reinitialized with IST after cpu_init() has
74 static const __initconst
struct idt_data def_idts
[] = {
75 INTG(X86_TRAP_DE
, divide_error
),
76 INTG(X86_TRAP_NMI
, nmi
),
77 INTG(X86_TRAP_BR
, bounds
),
78 INTG(X86_TRAP_UD
, invalid_op
),
79 INTG(X86_TRAP_NM
, device_not_available
),
80 INTG(X86_TRAP_OLD_MF
, coprocessor_segment_overrun
),
81 INTG(X86_TRAP_TS
, invalid_TSS
),
82 INTG(X86_TRAP_NP
, segment_not_present
),
83 INTG(X86_TRAP_SS
, stack_segment
),
84 INTG(X86_TRAP_GP
, general_protection
),
85 INTG(X86_TRAP_SPURIOUS
, spurious_interrupt_bug
),
86 INTG(X86_TRAP_MF
, coprocessor_error
),
87 INTG(X86_TRAP_AC
, alignment_check
),
88 INTG(X86_TRAP_XF
, simd_coprocessor_error
),
91 TSKG(X86_TRAP_DF
, GDT_ENTRY_DOUBLEFAULT_TSS
),
93 INTG(X86_TRAP_DF
, double_fault
),
95 INTG(X86_TRAP_DB
, debug
),
98 INTG(X86_TRAP_MC
, &machine_check
),
101 SYSG(X86_TRAP_OF
, overflow
),
102 #if defined(CONFIG_IA32_EMULATION)
103 SYSG(IA32_SYSCALL_VECTOR
, entry_INT80_compat
),
104 #elif defined(CONFIG_X86_32)
105 SYSG(IA32_SYSCALL_VECTOR
, entry_INT80_32
),
110 * The APIC and SMP idt entries
112 static const __initconst
struct idt_data apic_idts
[] = {
114 INTG(RESCHEDULE_VECTOR
, reschedule_interrupt
),
115 INTG(CALL_FUNCTION_VECTOR
, call_function_interrupt
),
116 INTG(CALL_FUNCTION_SINGLE_VECTOR
, call_function_single_interrupt
),
117 INTG(IRQ_MOVE_CLEANUP_VECTOR
, irq_move_cleanup_interrupt
),
118 INTG(REBOOT_VECTOR
, reboot_interrupt
),
121 #ifdef CONFIG_X86_THERMAL_VECTOR
122 INTG(THERMAL_APIC_VECTOR
, thermal_interrupt
),
125 #ifdef CONFIG_X86_MCE_THRESHOLD
126 INTG(THRESHOLD_APIC_VECTOR
, threshold_interrupt
),
129 #ifdef CONFIG_X86_MCE_AMD
130 INTG(DEFERRED_ERROR_VECTOR
, deferred_error_interrupt
),
133 #ifdef CONFIG_X86_LOCAL_APIC
134 INTG(LOCAL_TIMER_VECTOR
, apic_timer_interrupt
),
135 INTG(X86_PLATFORM_IPI_VECTOR
, x86_platform_ipi
),
136 # ifdef CONFIG_HAVE_KVM
137 INTG(POSTED_INTR_VECTOR
, kvm_posted_intr_ipi
),
138 INTG(POSTED_INTR_WAKEUP_VECTOR
, kvm_posted_intr_wakeup_ipi
),
139 INTG(POSTED_INTR_NESTED_VECTOR
, kvm_posted_intr_nested_ipi
),
141 # ifdef CONFIG_IRQ_WORK
142 INTG(IRQ_WORK_VECTOR
, irq_work_interrupt
),
145 INTG(UV_BAU_MESSAGE
, uv_bau_message_intr1
),
147 INTG(SPURIOUS_APIC_VECTOR
, spurious_interrupt
),
148 INTG(ERROR_APIC_VECTOR
, error_interrupt
),
154 * Early traps running on the DEFAULT_STACK because the other interrupt
155 * stacks work only after cpu_init().
157 static const __initconst
struct idt_data early_pf_idts
[] = {
158 INTG(X86_TRAP_PF
, page_fault
),
162 * Override for the debug_idt. Same as the default, but with interrupt
163 * stack set to DEFAULT_STACK (0). Required for NMI trap handling.
165 static const __initconst
struct idt_data dbg_idts
[] = {
166 INTG(X86_TRAP_DB
, debug
),
170 /* Must be page-aligned because the real IDT is used in a fixmap. */
171 gate_desc idt_table
[IDT_ENTRIES
] __page_aligned_bss
;
173 struct desc_ptr idt_descr __ro_after_init
= {
174 .size
= (IDT_ENTRIES
* 2 * sizeof(unsigned long)) - 1,
175 .address
= (unsigned long) idt_table
,
179 /* No need to be aligned, but done to keep all IDTs defined the same way. */
180 gate_desc debug_idt_table
[IDT_ENTRIES
] __page_aligned_bss
;
183 * The exceptions which use Interrupt stacks. They are setup after
184 * cpu_init() when the TSS has been initialized.
186 static const __initconst
struct idt_data ist_idts
[] = {
187 ISTG(X86_TRAP_DB
, debug
, DEBUG_STACK
),
188 ISTG(X86_TRAP_NMI
, nmi
, NMI_STACK
),
189 ISTG(X86_TRAP_DF
, double_fault
, DOUBLEFAULT_STACK
),
190 #ifdef CONFIG_X86_MCE
191 ISTG(X86_TRAP_MC
, &machine_check
, MCE_STACK
),
196 * Override for the debug_idt. Same as the default, but with interrupt
197 * stack set to DEFAULT_STACK (0). Required for NMI trap handling.
199 const struct desc_ptr debug_idt_descr
= {
200 .size
= IDT_ENTRIES
* 16 - 1,
201 .address
= (unsigned long) debug_idt_table
,
205 static inline void idt_init_desc(gate_desc
*gate
, const struct idt_data
*d
)
207 unsigned long addr
= (unsigned long) d
->addr
;
209 gate
->offset_low
= (u16
) addr
;
210 gate
->segment
= (u16
) d
->segment
;
211 gate
->bits
= d
->bits
;
212 gate
->offset_middle
= (u16
) (addr
>> 16);
214 gate
->offset_high
= (u32
) (addr
>> 32);
220 idt_setup_from_table(gate_desc
*idt
, const struct idt_data
*t
, int size
, bool sys
)
224 for (; size
> 0; t
++, size
--) {
225 idt_init_desc(&desc
, t
);
226 write_idt_entry(idt
, t
->vector
, &desc
);
228 set_bit(t
->vector
, system_vectors
);
232 static void set_intr_gate(unsigned int n
, const void *addr
)
234 struct idt_data data
;
238 memset(&data
, 0, sizeof(data
));
241 data
.segment
= __KERNEL_CS
;
242 data
.bits
.type
= GATE_INTERRUPT
;
245 idt_setup_from_table(idt_table
, &data
, 1, false);
249 * idt_setup_early_traps - Initialize the idt table with early traps
251 * On X8664 these traps do not use interrupt stacks as they can't work
252 * before cpu_init() is invoked and sets up TSS. The IST variants are
253 * installed after that.
255 void __init
idt_setup_early_traps(void)
257 idt_setup_from_table(idt_table
, early_idts
, ARRAY_SIZE(early_idts
),
259 load_idt(&idt_descr
);
263 * idt_setup_traps - Initialize the idt table with default traps
265 void __init
idt_setup_traps(void)
267 idt_setup_from_table(idt_table
, def_idts
, ARRAY_SIZE(def_idts
), true);
272 * idt_setup_early_pf - Initialize the idt table with early pagefault handler
274 * On X8664 this does not use interrupt stacks as they can't work before
275 * cpu_init() is invoked and sets up TSS. The IST variant is installed
278 * FIXME: Why is 32bit and 64bit installing the PF handler at different
279 * places in the early setup code?
281 void __init
idt_setup_early_pf(void)
283 idt_setup_from_table(idt_table
, early_pf_idts
,
284 ARRAY_SIZE(early_pf_idts
), true);
288 * idt_setup_ist_traps - Initialize the idt table with traps using IST
290 void __init
idt_setup_ist_traps(void)
292 idt_setup_from_table(idt_table
, ist_idts
, ARRAY_SIZE(ist_idts
), true);
296 * idt_setup_debugidt_traps - Initialize the debug idt table with debug traps
298 void __init
idt_setup_debugidt_traps(void)
300 memcpy(&debug_idt_table
, &idt_table
, IDT_ENTRIES
* 16);
302 idt_setup_from_table(debug_idt_table
, dbg_idts
, ARRAY_SIZE(dbg_idts
), false);
307 * idt_setup_apic_and_irq_gates - Setup APIC/SMP and normal interrupt gates
309 void __init
idt_setup_apic_and_irq_gates(void)
311 int i
= FIRST_EXTERNAL_VECTOR
;
314 idt_setup_from_table(idt_table
, apic_idts
, ARRAY_SIZE(apic_idts
), true);
316 for_each_clear_bit_from(i
, system_vectors
, FIRST_SYSTEM_VECTOR
) {
317 entry
= irq_entries_start
+ 8 * (i
- FIRST_EXTERNAL_VECTOR
);
318 set_intr_gate(i
, entry
);
321 #ifdef CONFIG_X86_LOCAL_APIC
322 for_each_clear_bit_from(i
, system_vectors
, NR_VECTORS
) {
323 set_bit(i
, system_vectors
);
324 entry
= spurious_entries_start
+ 8 * (i
- FIRST_SYSTEM_VECTOR
);
325 set_intr_gate(i
, entry
);
331 * idt_setup_early_handler - Initializes the idt table with early handlers
333 void __init
idt_setup_early_handler(void)
337 for (i
= 0; i
< NUM_EXCEPTION_VECTORS
; i
++)
338 set_intr_gate(i
, early_idt_handler_array
[i
]);
340 for ( ; i
< NR_VECTORS
; i
++)
341 set_intr_gate(i
, early_ignore_irq
);
343 load_idt(&idt_descr
);
347 * idt_invalidate - Invalidate interrupt descriptor table
348 * @addr: The virtual address of the 'invalid' IDT
350 void idt_invalidate(void *addr
)
352 struct desc_ptr idt
= { .address
= (unsigned long) addr
, .size
= 0 };
357 void __init
update_intr_gate(unsigned int n
, const void *addr
)
359 if (WARN_ON_ONCE(!test_bit(n
, system_vectors
)))
361 set_intr_gate(n
, addr
);
364 void alloc_intr_gate(unsigned int n
, const void *addr
)
366 BUG_ON(n
< FIRST_SYSTEM_VECTOR
);
367 if (!test_and_set_bit(n
, system_vectors
))
368 set_intr_gate(n
, addr
);