1 /*-
2 * SPDX-License-Identifier: BSD-2-Clause
3 *
4 * Copyright (c) 2003 John Baldwin <jhb@FreeBSD.org>
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 * SUCH DAMAGE.
26 */
27
28 /*
29 * PIC driver for the 8259A Master and Slave PICs in PC/AT machines.
30 */
31
32 #include <sys/cdefs.h>
33 #include "opt_auto_eoi.h"
34 #include "opt_isa.h"
35
36 #include <sys/param.h>
37 #include <sys/systm.h>
38 #include <sys/asan.h>
39 #include <sys/bus.h>
40 #include <sys/interrupt.h>
41 #include <sys/kernel.h>
42 #include <sys/lock.h>
43 #include <sys/module.h>
44 #include <sys/msan.h>
45
46 #include <machine/cpufunc.h>
47 #include <machine/frame.h>
48 #include <machine/intr_machdep.h>
49 #include <machine/md_var.h>
50 #include <machine/resource.h>
51 #include <machine/segments.h>
52
53 #include <dev/ic/i8259.h>
54 #include <x86/isa/icu.h>
55 #include <isa/isareg.h>
56 #include <isa/isavar.h>
57
58 #ifdef __amd64__
59 #define SDT_ATPIC SDT_SYSIGT
60 #define GSEL_ATPIC 0
61 #else
62 #define SDT_ATPIC SDT_SYS386IGT
63 #define GSEL_ATPIC GSEL(GCODE_SEL, SEL_KPL)
64 #endif
65
66 #define MASTER 0
67 #define SLAVE 1
68
69 #define IMEN_MASK(ai) (IRQ_MASK((ai)->at_irq))
70
71 #define NUM_ISA_IRQS 16
72
73 static void atpic_init(void *dummy);
74
75 inthand_t
76 IDTVEC(atpic_intr0), IDTVEC(atpic_intr1), IDTVEC(atpic_intr2),
77 IDTVEC(atpic_intr3), IDTVEC(atpic_intr4), IDTVEC(atpic_intr5),
78 IDTVEC(atpic_intr6), IDTVEC(atpic_intr7), IDTVEC(atpic_intr8),
79 IDTVEC(atpic_intr9), IDTVEC(atpic_intr10), IDTVEC(atpic_intr11),
80 IDTVEC(atpic_intr12), IDTVEC(atpic_intr13), IDTVEC(atpic_intr14),
81 IDTVEC(atpic_intr15);
82 /* XXXKIB i386 uses stubs until pti comes */
83 inthand_t
84 IDTVEC(atpic_intr0_pti), IDTVEC(atpic_intr1_pti),
85 IDTVEC(atpic_intr2_pti), IDTVEC(atpic_intr3_pti),
86 IDTVEC(atpic_intr4_pti), IDTVEC(atpic_intr5_pti),
87 IDTVEC(atpic_intr6_pti), IDTVEC(atpic_intr7_pti),
88 IDTVEC(atpic_intr8_pti), IDTVEC(atpic_intr9_pti),
89 IDTVEC(atpic_intr10_pti), IDTVEC(atpic_intr11_pti),
90 IDTVEC(atpic_intr12_pti), IDTVEC(atpic_intr13_pti),
91 IDTVEC(atpic_intr14_pti), IDTVEC(atpic_intr15_pti);
92
93 #define IRQ(ap, ai) ((ap)->at_irqbase + (ai)->at_irq)
94
95 #define ATPIC(io, base, eoi) { \
96 .at_pic = { \
97 .pic_register_sources = atpic_register_sources, \
98 .pic_enable_source = atpic_enable_source, \
99 .pic_disable_source = atpic_disable_source, \
100 .pic_eoi_source = (eoi), \
101 .pic_enable_intr = atpic_enable_intr, \
102 .pic_disable_intr = atpic_disable_intr, \
103 .pic_vector = atpic_vector, \
104 .pic_source_pending = atpic_source_pending, \
105 .pic_resume = atpic_resume, \
106 .pic_config_intr = atpic_config_intr, \
107 .pic_assign_cpu = atpic_assign_cpu \
108 }, \
109 .at_ioaddr = (io), \
110 .at_irqbase = (base), \
111 .at_intbase = IDT_IO_INTS + (base), \
112 .at_imen = 0xff, \
113 }
114
115 #define INTSRC(irq) \
116 { \
117 .at_intsrc = { &atpics[(irq) / 8].at_pic }, \
118 .at_intr = IDTVEC(atpic_intr ## irq ), \
119 .at_intr_pti = IDTVEC(atpic_intr ## irq ## _pti), \
120 .at_irq = (irq) % 8, \
121 }
122
123 struct atpic {
124 struct pic at_pic;
125 int at_ioaddr;
126 int at_irqbase;
127 uint8_t at_intbase;
128 uint8_t at_imen;
129 };
130
131 struct atpic_intsrc {
132 struct intsrc at_intsrc;
133 inthand_t *at_intr, *at_intr_pti;
134 int at_irq; /* Relative to PIC base. */
135 enum intr_trigger at_trigger;
136 u_long at_count;
137 u_long at_straycount;
138 };
139
140 static void atpic_register_sources(struct pic *pic);
141 static void atpic_enable_source(struct intsrc *isrc);
142 static void atpic_disable_source(struct intsrc *isrc, int eoi);
143 static void atpic_eoi_master(struct intsrc *isrc);
144 static void atpic_eoi_slave(struct intsrc *isrc);
145 static void atpic_enable_intr(struct intsrc *isrc);
146 static void atpic_disable_intr(struct intsrc *isrc);
147 static int atpic_vector(struct intsrc *isrc);
148 static void atpic_resume(struct pic *pic, bool suspend_cancelled);
149 static int atpic_source_pending(struct intsrc *isrc);
150 static int atpic_config_intr(struct intsrc *isrc, enum intr_trigger trig,
151 enum intr_polarity pol);
152 static int atpic_assign_cpu(struct intsrc *isrc, u_int apic_id);
153 static void i8259_init(struct atpic *pic, int slave);
154
155 static struct atpic atpics[] = {
156 ATPIC(IO_ICU1, 0, atpic_eoi_master),
157 ATPIC(IO_ICU2, 8, atpic_eoi_slave)
158 };
159
160 static struct atpic_intsrc atintrs[] = {
161 INTSRC(0),
162 INTSRC(1),
163 INTSRC(2),
164 INTSRC(3),
165 INTSRC(4),
166 INTSRC(5),
167 INTSRC(6),
168 INTSRC(7),
169 INTSRC(8),
170 INTSRC(9),
171 INTSRC(10),
172 INTSRC(11),
173 INTSRC(12),
174 INTSRC(13),
175 INTSRC(14),
176 INTSRC(15),
177 };
178
179 CTASSERT(nitems(atintrs) == NUM_ISA_IRQS);
180
181 static __inline void
_atpic_eoi_master(struct intsrc * isrc)182 _atpic_eoi_master(struct intsrc *isrc)
183 {
184
185 KASSERT(isrc->is_pic == &atpics[MASTER].at_pic,
186 ("%s: mismatched pic", __func__));
187 #ifndef AUTO_EOI_1
188 outb(atpics[MASTER].at_ioaddr, OCW2_EOI);
189 #endif
190 }
191
192 /*
193 * The data sheet says no auto-EOI on slave, but it sometimes works.
194 * So, if AUTO_EOI_2 is enabled, we use it.
195 */
196 static __inline void
_atpic_eoi_slave(struct intsrc * isrc)197 _atpic_eoi_slave(struct intsrc *isrc)
198 {
199
200 KASSERT(isrc->is_pic == &atpics[SLAVE].at_pic,
201 ("%s: mismatched pic", __func__));
202 #ifndef AUTO_EOI_2
203 outb(atpics[SLAVE].at_ioaddr, OCW2_EOI);
204 #ifndef AUTO_EOI_1
205 outb(atpics[MASTER].at_ioaddr, OCW2_EOI);
206 #endif
207 #endif
208 }
209
210 static void
atpic_register_sources(struct pic * pic)211 atpic_register_sources(struct pic *pic)
212 {
213 struct atpic *ap = (struct atpic *)pic;
214 struct atpic_intsrc *ai;
215 int i;
216
217 /*
218 * If any of the ISA IRQs have an interrupt source already, then
219 * assume that the I/O APICs are being used and don't register any
220 * of our interrupt sources. This makes sure we don't accidentally
221 * use mixed mode. The "accidental" use could otherwise occur on
222 * machines that route the ACPI SCI interrupt to a different ISA
223 * IRQ (at least one machine routes it to IRQ 13) thus disabling
224 * that APIC ISA routing and allowing the ATPIC source for that IRQ
225 * to leak through. We used to depend on this feature for routing
226 * IRQ0 via mixed mode, but now we don't use mixed mode at all.
227 *
228 * To avoid the slave not register sources after the master
229 * registers its sources, register all IRQs when this function is
230 * called on the master.
231 */
232 if (ap != &atpics[MASTER])
233 return;
234 for (i = 0; i < NUM_ISA_IRQS; i++)
235 if (intr_lookup_source(i) != NULL)
236 return;
237
238 /* Loop through all interrupt sources and add them. */
239 for (i = 0, ai = atintrs; i < NUM_ISA_IRQS; i++, ai++) {
240 if (i == ICU_SLAVEID)
241 continue;
242 intr_register_source(&ai->at_intsrc);
243 }
244 }
245
246 static void
atpic_enable_source(struct intsrc * isrc)247 atpic_enable_source(struct intsrc *isrc)
248 {
249 struct atpic_intsrc *ai = (struct atpic_intsrc *)isrc;
250 struct atpic *ap = (struct atpic *)isrc->is_pic;
251
252 spinlock_enter();
253 if (ap->at_imen & IMEN_MASK(ai)) {
254 ap->at_imen &= ~IMEN_MASK(ai);
255 outb(ap->at_ioaddr + ICU_IMR_OFFSET, ap->at_imen);
256 }
257 spinlock_exit();
258 }
259
260 static void
atpic_disable_source(struct intsrc * isrc,int eoi)261 atpic_disable_source(struct intsrc *isrc, int eoi)
262 {
263 struct atpic_intsrc *ai = (struct atpic_intsrc *)isrc;
264 struct atpic *ap = (struct atpic *)isrc->is_pic;
265
266 spinlock_enter();
267 if (ai->at_trigger != INTR_TRIGGER_EDGE) {
268 ap->at_imen |= IMEN_MASK(ai);
269 outb(ap->at_ioaddr + ICU_IMR_OFFSET, ap->at_imen);
270 }
271
272 /*
273 * Take care to call these functions directly instead of through
274 * a function pointer. All of the referenced variables should
275 * still be hot in the cache.
276 */
277 if (eoi == PIC_EOI) {
278 if (isrc->is_pic == &atpics[MASTER].at_pic)
279 _atpic_eoi_master(isrc);
280 else
281 _atpic_eoi_slave(isrc);
282 }
283
284 spinlock_exit();
285 }
286
287 static void
atpic_eoi_master(struct intsrc * isrc)288 atpic_eoi_master(struct intsrc *isrc)
289 {
290 #ifndef AUTO_EOI_1
291 spinlock_enter();
292 _atpic_eoi_master(isrc);
293 spinlock_exit();
294 #endif
295 }
296
297 static void
atpic_eoi_slave(struct intsrc * isrc)298 atpic_eoi_slave(struct intsrc *isrc)
299 {
300 #ifndef AUTO_EOI_2
301 spinlock_enter();
302 _atpic_eoi_slave(isrc);
303 spinlock_exit();
304 #endif
305 }
306
307 static void
atpic_enable_intr(struct intsrc * isrc)308 atpic_enable_intr(struct intsrc *isrc)
309 {
310 }
311
312 static void
atpic_disable_intr(struct intsrc * isrc)313 atpic_disable_intr(struct intsrc *isrc)
314 {
315 }
316
317 static int
atpic_vector(struct intsrc * isrc)318 atpic_vector(struct intsrc *isrc)
319 {
320 struct atpic_intsrc *ai = (struct atpic_intsrc *)isrc;
321 struct atpic *ap = (struct atpic *)isrc->is_pic;
322
323 return (IRQ(ap, ai));
324 }
325
326 static int
atpic_source_pending(struct intsrc * isrc)327 atpic_source_pending(struct intsrc *isrc)
328 {
329 struct atpic_intsrc *ai = (struct atpic_intsrc *)isrc;
330 struct atpic *ap = (struct atpic *)isrc->is_pic;
331
332 return (inb(ap->at_ioaddr) & IMEN_MASK(ai));
333 }
334
335 static void
atpic_resume(struct pic * pic,bool suspend_cancelled)336 atpic_resume(struct pic *pic, bool suspend_cancelled)
337 {
338 struct atpic *ap = (struct atpic *)pic;
339
340 i8259_init(ap, ap == &atpics[SLAVE]);
341 if (ap == &atpics[SLAVE] && elcr_found)
342 elcr_resume();
343 }
344
345 static int
atpic_config_intr(struct intsrc * isrc,enum intr_trigger trig,enum intr_polarity pol)346 atpic_config_intr(struct intsrc *isrc, enum intr_trigger trig,
347 enum intr_polarity pol)
348 {
349 struct atpic_intsrc *ai = (struct atpic_intsrc *)isrc;
350 u_int vector;
351
352 /* Map conforming values to edge/hi and sanity check the values. */
353 if (trig == INTR_TRIGGER_CONFORM)
354 trig = INTR_TRIGGER_EDGE;
355 if (pol == INTR_POLARITY_CONFORM)
356 pol = INTR_POLARITY_HIGH;
357 vector = atpic_vector(isrc);
358 if ((trig == INTR_TRIGGER_EDGE && pol == INTR_POLARITY_LOW) ||
359 (trig == INTR_TRIGGER_LEVEL && pol == INTR_POLARITY_HIGH)) {
360 printf(
361 "atpic: Mismatched config for IRQ%u: trigger %s, polarity %s\n",
362 vector, trig == INTR_TRIGGER_EDGE ? "edge" : "level",
363 pol == INTR_POLARITY_HIGH ? "high" : "low");
364 return (EINVAL);
365 }
366
367 /* If there is no change, just return. */
368 if (ai->at_trigger == trig)
369 return (0);
370
371 /*
372 * Certain IRQs can never be level/lo, so don't try to set them
373 * that way if asked. At least some ELCR registers ignore setting
374 * these bits as well.
375 */
376 if ((vector == 0 || vector == 1 || vector == 2 || vector == 13) &&
377 trig == INTR_TRIGGER_LEVEL) {
378 if (bootverbose)
379 printf(
380 "atpic: Ignoring invalid level/low configuration for IRQ%u\n",
381 vector);
382 return (EINVAL);
383 }
384 if (!elcr_found) {
385 if (bootverbose)
386 printf("atpic: No ELCR to configure IRQ%u as %s\n",
387 vector, trig == INTR_TRIGGER_EDGE ? "edge/high" :
388 "level/low");
389 return (ENXIO);
390 }
391 if (bootverbose)
392 printf("atpic: Programming IRQ%u as %s\n", vector,
393 trig == INTR_TRIGGER_EDGE ? "edge/high" : "level/low");
394 spinlock_enter();
395 elcr_write_trigger(atpic_vector(isrc), trig);
396 ai->at_trigger = trig;
397 spinlock_exit();
398 return (0);
399 }
400
401 static int
atpic_assign_cpu(struct intsrc * isrc,u_int apic_id)402 atpic_assign_cpu(struct intsrc *isrc, u_int apic_id)
403 {
404
405 /*
406 * 8259A's are only used in UP in which case all interrupts always
407 * go to the sole CPU and this function shouldn't even be called.
408 */
409 panic("%s: bad cookie", __func__);
410 }
411
412 static void
i8259_init(struct atpic * pic,int slave)413 i8259_init(struct atpic *pic, int slave)
414 {
415 int imr_addr;
416
417 /* Reset the PIC and program with next four bytes. */
418 spinlock_enter();
419 outb(pic->at_ioaddr, ICW1_RESET | ICW1_IC4);
420 imr_addr = pic->at_ioaddr + ICU_IMR_OFFSET;
421
422 /* Start vector. */
423 outb(imr_addr, pic->at_intbase);
424
425 /*
426 * Setup slave links. For the master pic, indicate what line
427 * the slave is configured on. For the slave indicate
428 * which line on the master we are connected to.
429 */
430 if (slave)
431 outb(imr_addr, ICU_SLAVEID);
432 else
433 outb(imr_addr, IRQ_MASK(ICU_SLAVEID));
434
435 /* Set mode. */
436 if (slave)
437 outb(imr_addr, SLAVE_MODE);
438 else
439 outb(imr_addr, MASTER_MODE);
440
441 /* Set interrupt enable mask. */
442 outb(imr_addr, pic->at_imen);
443
444 /* Reset is finished, default to IRR on read. */
445 outb(pic->at_ioaddr, OCW3_SEL | OCW3_RR);
446
447 /* OCW2_L1 sets priority order to 3-7, 0-2 (com2 first). */
448 if (!slave)
449 outb(pic->at_ioaddr, OCW2_R | OCW2_SL | OCW2_L1);
450
451 spinlock_exit();
452 }
453
454 void
atpic_startup(void)455 atpic_startup(void)
456 {
457 struct atpic_intsrc *ai;
458 int i;
459
460 /* Start off with all interrupts disabled. */
461 i8259_init(&atpics[MASTER], 0);
462 i8259_init(&atpics[SLAVE], 1);
463 atpic_enable_source((struct intsrc *)&atintrs[ICU_SLAVEID]);
464
465 /* Install low-level interrupt handlers for all of our IRQs. */
466 for (i = 0, ai = atintrs; i < NUM_ISA_IRQS; i++, ai++) {
467 if (i == ICU_SLAVEID)
468 continue;
469 ai->at_intsrc.is_count = &ai->at_count;
470 ai->at_intsrc.is_straycount = &ai->at_straycount;
471 setidt(((struct atpic *)ai->at_intsrc.is_pic)->at_intbase +
472 ai->at_irq, pti ? ai->at_intr_pti : ai->at_intr, SDT_ATPIC,
473 SEL_KPL, GSEL_ATPIC);
474 }
475
476 /*
477 * Look for an ELCR. If we find one, update the trigger modes.
478 * If we don't find one, assume that IRQs 0, 1, 2, and 13 are
479 * edge triggered and that everything else is level triggered.
480 * We only use the trigger information to reprogram the ELCR if
481 * we have one and as an optimization to avoid masking edge
482 * triggered interrupts. For the case that we don't have an ELCR,
483 * it doesn't hurt to mask an edge triggered interrupt, so we
484 * assume level trigger for any interrupt that we aren't sure is
485 * edge triggered.
486 */
487 if (elcr_found) {
488 for (i = 0, ai = atintrs; i < NUM_ISA_IRQS; i++, ai++)
489 ai->at_trigger = elcr_read_trigger(i);
490 } else {
491 for (i = 0, ai = atintrs; i < NUM_ISA_IRQS; i++, ai++)
492 switch (i) {
493 case 0:
494 case 1:
495 case 2:
496 case 8:
497 case 13:
498 ai->at_trigger = INTR_TRIGGER_EDGE;
499 break;
500 default:
501 ai->at_trigger = INTR_TRIGGER_LEVEL;
502 break;
503 }
504 }
505 }
506
507 static void
atpic_init(void * dummy __unused)508 atpic_init(void *dummy __unused)
509 {
510
511 /*
512 * Register our PICs, even if we aren't going to use any of their
513 * pins so that they are suspended and resumed.
514 */
515 if (intr_register_pic(&atpics[0].at_pic) != 0 ||
516 intr_register_pic(&atpics[1].at_pic) != 0)
517 panic("Unable to register ATPICs");
518
519 if (num_io_irqs == 0)
520 num_io_irqs = NUM_ISA_IRQS;
521 }
522 SYSINIT(atpic_init, SI_SUB_INTR, SI_ORDER_FOURTH, atpic_init, NULL);
523
524 void
atpic_handle_intr(u_int vector,struct trapframe * frame)525 atpic_handle_intr(u_int vector, struct trapframe *frame)
526 {
527 struct intsrc *isrc;
528
529 kasan_mark(frame, sizeof(*frame), sizeof(*frame), 0);
530 kmsan_mark(frame, sizeof(*frame), KMSAN_STATE_INITED);
531 trap_check_kstack();
532
533 KASSERT(vector < NUM_ISA_IRQS, ("unknown int %u\n", vector));
534 isrc = &atintrs[vector].at_intsrc;
535
536 /*
537 * If we don't have an event, see if this is a spurious
538 * interrupt.
539 */
540 if (isrc->is_event == NULL && (vector == 7 || vector == 15)) {
541 int port, isr;
542
543 /*
544 * Read the ISR register to see if IRQ 7/15 is really
545 * pending. Reset read register back to IRR when done.
546 */
547 port = ((struct atpic *)isrc->is_pic)->at_ioaddr;
548 spinlock_enter();
549 outb(port, OCW3_SEL | OCW3_RR | OCW3_RIS);
550 isr = inb(port);
551 outb(port, OCW3_SEL | OCW3_RR);
552 spinlock_exit();
553 if ((isr & IRQ_MASK(7)) == 0)
554 return;
555 }
556 intr_execute_handlers(isrc, frame);
557 }
558
559 #ifdef DEV_ISA
560 /*
561 * Bus attachment for the ISA PIC.
562 */
563 static struct isa_pnp_id atpic_ids[] = {
564 { 0x0000d041 /* PNP0000 */, "AT interrupt controller" },
565 { 0 }
566 };
567
568 static int
atpic_probe(device_t dev)569 atpic_probe(device_t dev)
570 {
571 int result;
572
573 result = ISA_PNP_PROBE(device_get_parent(dev), dev, atpic_ids);
574 if (result <= 0)
575 device_quiet(dev);
576 return (result);
577 }
578
579 /*
580 * We might be granted IRQ 2, as this is typically consumed by chaining
581 * between the two PIC components. If we're using the APIC, however,
582 * this may not be the case, and as such we should free the resource.
583 * (XXX untested)
584 *
585 * The generic ISA attachment code will handle allocating any other resources
586 * that we don't explicitly claim here.
587 */
588 static int
atpic_attach(device_t dev)589 atpic_attach(device_t dev)
590 {
591 struct resource *res;
592 int rid;
593
594 /* Try to allocate our IRQ and then free it. */
595 rid = 0;
596 res = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid, 0);
597 if (res != NULL)
598 bus_release_resource(dev, SYS_RES_IRQ, rid, res);
599 return (0);
600 }
601
602 static device_method_t atpic_methods[] = {
603 /* Device interface */
604 DEVMETHOD(device_probe, atpic_probe),
605 DEVMETHOD(device_attach, atpic_attach),
606 { 0, 0 }
607 };
608
609 static driver_t atpic_driver = {
610 "atpic",
611 atpic_methods,
612 1, /* no softc */
613 };
614
615 DRIVER_MODULE(atpic, isa, atpic_driver, 0, 0);
616 DRIVER_MODULE(atpic, acpi, atpic_driver, 0, 0);
617 ISA_PNP_INFO(atpic_ids);
618 #endif /* DEV_ISA */
619