1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42 #include <machine/i82093reg.h>
43 #include <machine/i82489reg.h>
44
45 #ifdef __ELF__
46 #define XINTR(vec) Xintrvec
47 #else
48 #define XINTR(vec) _Xintrvec
49 #endif
50
51 .globl _C_LABEL(apic_stray)
52
53 #ifdef MULTIPROCESSOR
54 .globl XINTR(ipi)
55 XINTR(ipi):
56 pushl $0
57 pushl $T_ASTFLT
58 INTRENTRY
59 MAKE_FRAME
60 pushl CPL
61 movl _C_LABEL(lapic_ppr),%eax
62 movl %eax,CPL
63 ioapic_asm_ack()
64 sti
65 call _C_LABEL(i386_ipi_handler)
66 cli
67 popl CPL
68 INTRFASTEXIT
69
70 .globl XINTR(ipi_ast)
71 XINTR(ipi_ast):
72 pushl %eax
73 pushl %ds
74 movl $GSEL(GDATA_SEL, SEL_KPL), %eax
75 movl %eax, %ds
76
77 ioapic_asm_ack()
78
79 movl $IPL_SOFTAST, %eax
80 orl $(1 << SIR_AST), _C_LABEL(ipending)
81
82 orl $(LAPIC_DLMODE_FIXED|LAPIC_LVL_ASSERT|LAPIC_DEST_SELF), %eax
83 movl %eax, _C_LABEL(local_apic) + LAPIC_ICRLO
84
85 movl _C_LABEL(local_apic) + LAPIC_ID, %eax
86 popl %ds
87 popl %eax
88 iret
89
90 .globl XINTR(ipi_invltlb)
91 .p2align 4,0x90
92 XINTR(ipi_invltlb):
93 pushl %eax
94 pushl %ds
95 movl $GSEL(GDATA_SEL, SEL_KPL), %eax
96 movl %eax, %ds
97
98 ioapic_asm_ack()
99
100 movl %cr3, %eax
101 movl %eax, %cr3
102
103 lock
104 decl tlb_shoot_wait
105
106 popl %ds
107 popl %eax
108 iret
109
110 .globl XINTR(ipi_invlpg)
111 .p2align 4,0x90
112 XINTR(ipi_invlpg):
113 pushl %eax
114 pushl %ds
115 movl $GSEL(GDATA_SEL, SEL_KPL), %eax
116 movl %eax, %ds
117
118 ioapic_asm_ack()
119
120 movl tlb_shoot_addr1, %eax
121 invlpg (%eax)
122
123 lock
124 decl tlb_shoot_wait
125
126 popl %ds
127 popl %eax
128 iret
129
130 .globl XINTR(ipi_invlrange)
131 .p2align 4,0x90
132 XINTR(ipi_invlrange):
133 pushl %eax
134 pushl %edx
135 pushl %ds
136 movl $GSEL(GDATA_SEL, SEL_KPL), %eax
137 movl %eax, %ds
138
139 ioapic_asm_ack()
140
141 movl tlb_shoot_addr1, %eax
142 movl tlb_shoot_addr2, %edx
143 1: invlpg (%eax)
144 addl $PAGE_SIZE, %eax
145 cmpl %edx, %eax
146 jb 1b
147
148 lock
149 decl tlb_shoot_wait
150
151 popl %ds
152 popl %edx
153 popl %eax
154 iret
155
156 #endif
157
158
159
160
161 .globl XINTR(ltimer)
162 XINTR(ltimer):
163 pushl $0
164 pushl $T_ASTFLT
165 INTRENTRY
166 MAKE_FRAME
167 pushl CPL
168 movl _C_LABEL(lapic_ppr),%eax
169 movl %eax,CPL
170 ioapic_asm_ack()
171 sti
172 #ifdef MULTIPROCESSOR
173 call _C_LABEL(i386_softintlock)
174 #endif
175 movl %esp,%eax
176 pushl %eax
177 call _C_LABEL(lapic_clockintr)
178 addl $4,%esp
179 #ifdef MULTIPROCESSOR
180 call _C_LABEL(i386_softintunlock)
181 #endif
182 jmp _C_LABEL(Xdoreti)
183
184 .globl XINTR(softclock), XINTR(softnet), XINTR(softtty), XINTR(softast)
185 XINTR(softclock):
186 pushl $0
187 pushl $T_ASTFLT
188 INTRENTRY
189 MAKE_FRAME
190 pushl CPL
191 movl $IPL_SOFTCLOCK,CPL
192 andl $~(1<<SIR_CLOCK),_C_LABEL(ipending)
193 ioapic_asm_ack()
194 sti
195 #ifdef MULTIPROCESSOR
196 call _C_LABEL(i386_softintlock)
197 #endif
198 call _C_LABEL(softclock)
199 #ifdef MULTIPROCESSOR
200 call _C_LABEL(i386_softintunlock)
201 #endif
202 jmp _C_LABEL(Xdoreti)
203
204 #define DONETISR(s, c) \
205 .globl _C_LABEL(c) ;\
206 testl $(1 << s),%edi ;\
207 jz 1f ;\
208 call _C_LABEL(c) ;\
209 1:
210
211 XINTR(softnet):
212 pushl $0
213 pushl $T_ASTFLT
214 INTRENTRY
215 MAKE_FRAME
216 pushl CPL
217 movl $IPL_SOFTNET,CPL
218 andl $~(1<<SIR_NET),_C_LABEL(ipending)
219 ioapic_asm_ack()
220 sti
221 #ifdef MULTIPROCESSOR
222 call _C_LABEL(i386_softintlock)
223 #endif
224 xorl %edi,%edi
225 xchgl _C_LABEL(netisr),%edi
226 #include <net/netisr_dispatch.h>
227 #ifdef MULTIPROCESSOR
228 call _C_LABEL(i386_softintunlock)
229 #endif
230 jmp _C_LABEL(Xdoreti)
231 #undef DONETISR
232
233 XINTR(softtty):
234 pushl $0
235 pushl $T_ASTFLT
236 INTRENTRY
237 MAKE_FRAME
238 pushl CPL
239 movl $IPL_SOFTTTY,CPL
240 andl $~(1<<SIR_TTY),_C_LABEL(ipending)
241 ioapic_asm_ack()
242 sti
243 #ifdef MULTIPROCESSOR
244 call _C_LABEL(i386_softintlock)
245 #endif
246 call _C_LABEL(comsoft)
247 #ifdef MULTIPROCESSOR
248 call _C_LABEL(i386_softintunlock)
249 #endif
250 jmp _C_LABEL(Xdoreti)
251
252 XINTR(softast):
253 pushl $0
254 pushl $T_ASTFLT
255 INTRENTRY
256 MAKE_FRAME
257 pushl CPL
258 movl $IPL_SOFTAST,CPL
259 andl $~(1<<SIR_AST),_C_LABEL(ipending)
260 ioapic_asm_ack()
261 sti
262 jmp _C_LABEL(Xdoreti)
263
264 #if NIOAPIC > 0
265
266 #define voidop(num)
267
268
269
270
271
272
273
274
275
276 #define APICINTR(name, num, early_ack, late_ack, mask, unmask, level_mask) \
277 _C_LABEL(Xintr_namenum): \
278 pushl $0 ;\
279 pushl $T_ASTFLT ;\
280 INTRENTRY ;\
281 MAKE_FRAME ;\
282 pushl CPL ;\
283 movl _C_LABEL(lapic_ppr),%eax ;\
284 orl $num,%eax ;\
285 movl _C_LABEL(apic_maxlevel)(,%eax,4),%ebx ;\
286 movl %ebx,CPL ;\
287 mask(num) ;\
288 early_ack(num) ;\
289 incl MY_COUNT+V_INTR ;\
290 sti ;\
291 incl _C_LABEL(apic_intrcount)(,%eax,4) ;\
292 movl _C_LABEL(apic_intrhand)(,%eax,4),%ebx ;\
293 testl %ebx,%ebx ;\
294 jz _C_LABEL(Xstray_namenum) ;\
295 APIC_STRAY_INIT ;\
296 7: \
297 LOCK_KERNEL(IF_PPL(%esp)) ;\
298 movl IH_ARG(%ebx),%eax ;\
299 testl %eax,%eax ;\
300 jnz 6f ;\
301 movl %esp,%eax ;\
302 6: \
303 pushl %eax ;\
304 call *IH_FUN(%ebx) ;\
305 addl $4,%esp ;\
306 APIC_STRAY_INTEGRATE ;\
307 orl %eax,%eax ;\
308 jz 4f ;\
309 addl $1,IH_COUNT(%ebx) ;\
310 adcl $0,IH_COUNT+4(%ebx) ;\
311 4: \
312 UNLOCK_KERNEL(IF_PPL(%esp)) ;\
313 movl IH_NEXT(%ebx),%ebx ;\
314 testl %ebx,%ebx ;\
315 jnz 7b ;\
316 APIC_STRAY_TEST(name,num) ;\
317 8: \
318 unmask(num) ;\
319 late_ack(num) ;\
320 jmp _C_LABEL(Xdoreti) ;\
321 _C_LABEL(Xstray_namenum): \
322 pushl $num ;\
323 call _C_LABEL(apic_stray) ;\
324 addl $4,%esp ;\
325 jmp 8b ;\
326
327 #if defined(DEBUG)
328 #define APIC_STRAY_INIT \
329 xorl %esi,%esi
330 #define APIC_STRAY_INTEGRATE \
331 orl %eax,%esi
332 #define APIC_STRAY_TEST(name,num) \
333 testl %esi,%esi ;\
334 jz _C_LABEL(Xstray_namenum)
335 #else
336 #define APIC_STRAY_INIT
337 #define APIC_STRAY_INTEGRATE
338 #define APIC_STRAY_TEST(name,num)
339 #endif
340
341 APICINTR(ioapic,0, voidop, ioapic_asm_ack, voidop, voidop, voidop)
342 APICINTR(ioapic,1, voidop, ioapic_asm_ack, voidop, voidop, voidop)
343 APICINTR(ioapic,2, voidop, ioapic_asm_ack, voidop, voidop, voidop)
344 APICINTR(ioapic,3, voidop, ioapic_asm_ack, voidop, voidop, voidop)
345 APICINTR(ioapic,4, voidop, ioapic_asm_ack, voidop, voidop, voidop)
346 APICINTR(ioapic,5, voidop, ioapic_asm_ack, voidop, voidop, voidop)
347 APICINTR(ioapic,6, voidop, ioapic_asm_ack, voidop, voidop, voidop)
348 APICINTR(ioapic,7, voidop, ioapic_asm_ack, voidop, voidop, voidop)
349 APICINTR(ioapic,8, voidop, ioapic_asm_ack, voidop, voidop, voidop)
350 APICINTR(ioapic,9, voidop, ioapic_asm_ack, voidop, voidop, voidop)
351 APICINTR(ioapic,10, voidop, ioapic_asm_ack, voidop, voidop, voidop)
352 APICINTR(ioapic,11, voidop, ioapic_asm_ack, voidop, voidop, voidop)
353 APICINTR(ioapic,12, voidop, ioapic_asm_ack, voidop, voidop, voidop)
354 APICINTR(ioapic,13, voidop, ioapic_asm_ack, voidop, voidop, voidop)
355 APICINTR(ioapic,14, voidop, ioapic_asm_ack, voidop, voidop, voidop)
356 APICINTR(ioapic,15, voidop, ioapic_asm_ack, voidop, voidop, voidop)
357
358 .globl _C_LABEL(Xintr_ioapic0),_C_LABEL(Xintr_ioapic1)
359 .globl _C_LABEL(Xintr_ioapic2),_C_LABEL(Xintr_ioapic3)
360 .globl _C_LABEL(Xintr_ioapic4),_C_LABEL(Xintr_ioapic5)
361 .globl _C_LABEL(Xintr_ioapic6),_C_LABEL(Xintr_ioapic7)
362 .globl _C_LABEL(Xintr_ioapic8),_C_LABEL(Xintr_ioapic9)
363 .globl _C_LABEL(Xintr_ioapic10),_C_LABEL(Xintr_ioapic11)
364 .globl _C_LABEL(Xintr_ioapic12),_C_LABEL(Xintr_ioapic13)
365 .globl _C_LABEL(Xintr_ioapic14),_C_LABEL(Xintr_ioapic15)
366 .globl _C_LABEL(apichandler)
367
368 _C_LABEL(apichandler):
369 .long _C_LABEL(Xintr_ioapic0),_C_LABEL(Xintr_ioapic1)
370 .long _C_LABEL(Xintr_ioapic2),_C_LABEL(Xintr_ioapic3)
371 .long _C_LABEL(Xintr_ioapic4),_C_LABEL(Xintr_ioapic5)
372 .long _C_LABEL(Xintr_ioapic6),_C_LABEL(Xintr_ioapic7)
373 .long _C_LABEL(Xintr_ioapic8),_C_LABEL(Xintr_ioapic9)
374 .long _C_LABEL(Xintr_ioapic10),_C_LABEL(Xintr_ioapic11)
375 .long _C_LABEL(Xintr_ioapic12),_C_LABEL(Xintr_ioapic13)
376 .long _C_LABEL(Xintr_ioapic14),_C_LABEL(Xintr_ioapic15)
377
378 #endif
379