Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

818 lines
28 KiB

  1. ;++
  2. ;
  3. ;Copyright (c) 1991 Microsoft Corporation
  4. ;
  5. ;Module Name:
  6. ;
  7. ; ixsysint.asm
  8. ;
  9. ;Abstract:
  10. ;
  11. ; This module implements the HAL routines to enable/disable system
  12. ; interrupts.
  13. ;
  14. ;Author:
  15. ;
  16. ; John Vert (jvert) 22-Jul-1991
  17. ;
  18. ;Environment:
  19. ;
  20. ; Kernel Mode
  21. ;
  22. ;Revision History:
  23. ;
  24. ;--
  25. .386p
  26. .xlist
  27. include hal386.inc
  28. include callconv.inc ; calling convention macros
  29. include i386\ix8259.inc
  30. include i386\kimacro.inc
  31. include mac386.inc
  32. .list
  33. extrn KiI8259MaskTable:DWORD
  34. EXTRNP _KeBugCheck,1,IMPORT
  35. ifdef IRQL_METRICS
  36. extrn HalPostponedIntCount:dword
  37. endif
  38. extrn _HalpEisaELCR:dword ; Set bit indicates LEVEL
  39. extrn _HalpEisaIrqIgnore:dword
  40. extrn SWInterruptHandlerTable:dword
  41. extrn _HalpIrqMiniportInitialized:dword
  42. extrn HalpHardwareInterruptLevel:proc
  43. extrn _PciirqmpGetTrigger@4:proc
  44. extrn _PciirqmpSetTrigger@4:proc
  45. ;
  46. ; Constants used to initialize CMOS/Real Time Clock
  47. ;
  48. CMOS_CONTROL_PORT EQU 70h ; command port for cmos
  49. CMOS_DATA_PORT EQU 71h ; cmos data port
  50. ;
  51. ; Macros to Read/Write/Reset CMOS to initialize RTC
  52. ;
  53. ; CMOS_READ
  54. ;
  55. ; Description: This macro read a byte from the CMOS register specified
  56. ; in (AL).
  57. ;
  58. ; Parameter: (AL) = address/register to read
  59. ; Return: (AL) = data
  60. ;
  61. CMOS_READ MACRO
  62. OUT CMOS_CONTROL_PORT,al ; ADDRESS LOCATION AND DISABLE NMI
  63. IODelay ; I/O DELAY
  64. IN AL,CMOS_DATA_PORT ; READ IN REQUESTED CMOS DATA
  65. IODelay ; I/O DELAY
  66. ENDM
  67. _DATA SEGMENT DWORD PUBLIC 'DATA'
  68. align dword
  69. ;
  70. ; HalDismissSystemInterrupt does an indirect jump through this table so it
  71. ; can quickly execute specific code for different interrupts.
  72. ;
  73. public HalpSpecialDismissTable
  74. HalpSpecialDismissTable label dword
  75. dd offset FLAT:HalpDismissNormal ; irq 0
  76. dd offset FLAT:HalpDismissNormal ; irq 1
  77. dd offset FLAT:HalpDismissNormal ; irq 2
  78. dd offset FLAT:HalpDismissNormal ; irq 3
  79. dd offset FLAT:HalpDismissNormal ; irq 4
  80. dd offset FLAT:HalpDismissNormal ; irq 5
  81. dd offset FLAT:HalpDismissNormal ; irq 6
  82. dd offset FLAT:HalpDismissIrq07 ; irq 7
  83. dd offset FLAT:HalpDismissNormal ; irq 8
  84. dd offset FLAT:HalpDismissNormal ; irq 9
  85. dd offset FLAT:HalpDismissNormal ; irq A
  86. dd offset FLAT:HalpDismissNormal ; irq B
  87. dd offset FLAT:HalpDismissNormal ; irq C
  88. dd offset FLAT:HalpDismissIrq0d ; irq D
  89. dd offset FLAT:HalpDismissNormal ; irq E
  90. dd offset FLAT:HalpDismissIrq0f ; irq F
  91. dd offset FLAT:HalpDismissNormal ; irq 10
  92. dd offset FLAT:HalpDismissNormal ; irq 11
  93. dd offset FLAT:HalpDismissNormal ; irq 12
  94. dd offset FLAT:HalpDismissNormal ; irq 13
  95. dd offset FLAT:HalpDismissNormal ; irq 14
  96. dd offset FLAT:HalpDismissNormal ; irq 15
  97. dd offset FLAT:HalpDismissNormal ; irq 16
  98. dd offset FLAT:HalpDismissNormal ; irq 17
  99. dd offset FLAT:HalpDismissNormal ; irq 18
  100. dd offset FLAT:HalpDismissNormal ; irq 19
  101. dd offset FLAT:HalpDismissNormal ; irq 1A
  102. dd offset FLAT:HalpDismissNormal ; irq 1B
  103. dd offset FLAT:HalpDismissNormal ; irq 1C
  104. dd offset FLAT:HalpDismissNormal ; irq 1D
  105. dd offset FLAT:HalpDismissNormal ; irq 1E
  106. dd offset FLAT:HalpDismissNormal ; irq 1F
  107. dd offset FLAT:HalpDismissNormal ; irq 20
  108. dd offset FLAT:HalpDismissNormal ; irq 21
  109. dd offset FLAT:HalpDismissNormal ; irq 22
  110. dd offset FLAT:HalpDismissNormal ; irq 23
  111. dd offset FLAT:HalpDismissInvalidVector ;24
  112. dd offset FLAT:HalpDismissInvalidVector ;25
  113. dd offset FLAT:HalpDismissInvalidVector ;26
  114. dd offset FLAT:HalpDismissInvalidVector ;27
  115. dd offset FLAT:HalpDismissInvalidVector ;28
  116. dd offset FLAT:HalpDismissInvalidVector ;29
  117. dd offset FLAT:HalpDismissInvalidVector ;2a
  118. dd offset FLAT:HalpDismissInvalidVector ;2b
  119. dd offset FLAT:HalpDismissInvalidVector ;2c
  120. dd offset FLAT:HalpDismissInvalidVector ;2d
  121. dd offset FLAT:HalpDismissInvalidVector ;2e
  122. dd offset FLAT:HalpDismissInvalidVector ;2f
  123. dd offset FLAT:HalpDismissInvalidVector ;30
  124. dd offset FLAT:HalpDismissInvalidVector ;31
  125. dd offset FLAT:HalpDismissInvalidVector ;32
  126. dd offset FLAT:HalpDismissInvalidVector ;33
  127. dd offset FLAT:HalpDismissInvalidVector ;34
  128. dd offset FLAT:HalpDismissInvalidVector ;35
  129. dd offset FLAT:HalpDismissInvalidVector ;36
  130. dd offset FLAT:HalpDismissInvalidVector ;37
  131. dd offset FLAT:HalpDismissInvalidVector ;38
  132. dd offset FLAT:HalpDismissInvalidVector ;39
  133. dd offset FLAT:HalpDismissInvalidVector ;3a
  134. dd offset FLAT:HalpDismissInvalidVector ;3b
  135. dd offset FLAT:HalpDismissInvalidVector ;3c
  136. dd offset FLAT:HalpDismissInvalidVector ;3d
  137. dd offset FLAT:HalpDismissInvalidVector ;3e
  138. dd offset FLAT:HalpDismissInvalidVector ;3f
  139. dd offset FLAT:HalpDismissInvalidVector ;40
  140. dd offset FLAT:HalpDismissInvalidVector ;41
  141. dd offset FLAT:HalpDismissInvalidVector ;42
  142. dd offset FLAT:HalpDismissInvalidVector ;43
  143. dd offset FLAT:HalpDismissInvalidVector ;44
  144. dd offset FLAT:HalpDismissInvalidVector ;45
  145. dd offset FLAT:HalpDismissInvalidVector ;46
  146. dd offset FLAT:HalpDismissInvalidVector ;47
  147. dd offset FLAT:HalpDismissInvalidVector ;48
  148. dd offset FLAT:HalpDismissInvalidVector ;49
  149. dd offset FLAT:HalpDismissInvalidVector ;4a
  150. dd offset FLAT:HalpDismissInvalidVector ;4b
  151. dd offset FLAT:HalpDismissInvalidVector ;4c
  152. dd offset FLAT:HalpDismissInvalidVector ;4d
  153. dd offset FLAT:HalpDismissInvalidVector ;4e
  154. dd offset FLAT:HalpDismissInvalidVector ;4f
  155. dd offset FLAT:HalpDismissInvalidVector ;50
  156. dd offset FLAT:HalpDismissInvalidVector ;51
  157. dd offset FLAT:HalpDismissInvalidVector ;52
  158. dd offset FLAT:HalpDismissInvalidVector ;53
  159. dd offset FLAT:HalpDismissInvalidVector ;54
  160. dd offset FLAT:HalpDismissInvalidVector ;55
  161. dd offset FLAT:HalpDismissInvalidVector ;56
  162. dd offset FLAT:HalpDismissInvalidVector ;57
  163. dd offset FLAT:HalpDismissInvalidVector ;58
  164. dd offset FLAT:HalpDismissInvalidVector ;59
  165. dd offset FLAT:HalpDismissInvalidVector ;5a
  166. dd offset FLAT:HalpDismissInvalidVector ;5b
  167. dd offset FLAT:HalpDismissInvalidVector ;5c
  168. dd offset FLAT:HalpDismissInvalidVector ;5d
  169. dd offset FLAT:HalpDismissInvalidVector ;5e
  170. dd offset FLAT:HalpDismissInvalidVector ;5f
  171. dd offset FLAT:HalpDismissInvalidVector ;60
  172. dd offset FLAT:HalpDismissInvalidVector ;61
  173. dd offset FLAT:HalpDismissInvalidVector ;62
  174. dd offset FLAT:HalpDismissInvalidVector ;63
  175. dd offset FLAT:HalpDismissInvalidVector ;64
  176. dd offset FLAT:HalpDismissInvalidVector ;65
  177. dd offset FLAT:HalpDismissInvalidVector ;66
  178. dd offset FLAT:HalpDismissInvalidVector ;67
  179. dd offset FLAT:HalpDismissInvalidVector ;68
  180. dd offset FLAT:HalpDismissInvalidVector ;69
  181. dd offset FLAT:HalpDismissInvalidVector ;6a
  182. dd offset FLAT:HalpDismissInvalidVector ;6b
  183. dd offset FLAT:HalpDismissInvalidVector ;6c
  184. dd offset FLAT:HalpDismissInvalidVector ;6d
  185. dd offset FLAT:HalpDismissInvalidVector ;6e
  186. dd offset FLAT:HalpDismissInvalidVector ;6f
  187. dd offset FLAT:HalpDismissInvalidVector ;70
  188. dd offset FLAT:HalpDismissInvalidVector ;71
  189. dd offset FLAT:HalpDismissInvalidVector ;72
  190. dd offset FLAT:HalpDismissInvalidVector ;73
  191. dd offset FLAT:HalpDismissInvalidVector ;74
  192. dd offset FLAT:HalpDismissInvalidVector ;75
  193. dd offset FLAT:HalpDismissInvalidVector ;76
  194. dd offset FLAT:HalpDismissInvalidVector ;77
  195. dd offset FLAT:HalpDismissInvalidVector ;78
  196. dd offset FLAT:HalpDismissInvalidVector ;79
  197. dd offset FLAT:HalpDismissInvalidVector ;7a
  198. dd offset FLAT:HalpDismissInvalidVector ;7b
  199. dd offset FLAT:HalpDismissInvalidVector ;7c
  200. dd offset FLAT:HalpDismissInvalidVector ;7d
  201. dd offset FLAT:HalpDismissInvalidVector ;7e
  202. dd offset FLAT:HalpDismissInvalidVector ;7f
  203. dd offset FLAT:HalpDismissInvalidVector ;80
  204. dd offset FLAT:HalpDismissInvalidVector ;81
  205. dd offset FLAT:HalpDismissInvalidVector ;82
  206. dd offset FLAT:HalpDismissInvalidVector ;83
  207. dd offset FLAT:HalpDismissInvalidVector ;84
  208. dd offset FLAT:HalpDismissInvalidVector ;85
  209. dd offset FLAT:HalpDismissInvalidVector ;86
  210. dd offset FLAT:HalpDismissInvalidVector ;87
  211. dd offset FLAT:HalpDismissInvalidVector ;88
  212. dd offset FLAT:HalpDismissInvalidVector ;89
  213. dd offset FLAT:HalpDismissInvalidVector ;8a
  214. dd offset FLAT:HalpDismissInvalidVector ;8b
  215. dd offset FLAT:HalpDismissInvalidVector ;8c
  216. dd offset FLAT:HalpDismissInvalidVector ;8d
  217. dd offset FLAT:HalpDismissInvalidVector ;8e
  218. dd offset FLAT:HalpDismissInvalidVector ;8f
  219. dd offset FLAT:HalpDismissInvalidVector ;90
  220. dd offset FLAT:HalpDismissInvalidVector ;91
  221. dd offset FLAT:HalpDismissInvalidVector ;92
  222. dd offset FLAT:HalpDismissInvalidVector ;93
  223. dd offset FLAT:HalpDismissInvalidVector ;94
  224. dd offset FLAT:HalpDismissInvalidVector ;95
  225. dd offset FLAT:HalpDismissInvalidVector ;96
  226. dd offset FLAT:HalpDismissInvalidVector ;97
  227. dd offset FLAT:HalpDismissInvalidVector ;98
  228. dd offset FLAT:HalpDismissInvalidVector ;99
  229. dd offset FLAT:HalpDismissInvalidVector ;9a
  230. dd offset FLAT:HalpDismissInvalidVector ;9b
  231. dd offset FLAT:HalpDismissInvalidVector ;9c
  232. dd offset FLAT:HalpDismissInvalidVector ;9d
  233. dd offset FLAT:HalpDismissInvalidVector ;9e
  234. dd offset FLAT:HalpDismissInvalidVector ;9f
  235. dd offset FLAT:HalpDismissInvalidVector ;a0
  236. dd offset FLAT:HalpDismissInvalidVector ;a1
  237. dd offset FLAT:HalpDismissInvalidVector ;a2
  238. dd offset FLAT:HalpDismissInvalidVector ;a3
  239. dd offset FLAT:HalpDismissInvalidVector ;a4
  240. dd offset FLAT:HalpDismissInvalidVector ;a5
  241. dd offset FLAT:HalpDismissInvalidVector ;a6
  242. dd offset FLAT:HalpDismissInvalidVector ;a7
  243. dd offset FLAT:HalpDismissInvalidVector ;a8
  244. dd offset FLAT:HalpDismissInvalidVector ;a9
  245. dd offset FLAT:HalpDismissInvalidVector ;aa
  246. dd offset FLAT:HalpDismissInvalidVector ;ab
  247. dd offset FLAT:HalpDismissInvalidVector ;ac
  248. dd offset FLAT:HalpDismissInvalidVector ;ad
  249. dd offset FLAT:HalpDismissInvalidVector ;ae
  250. dd offset FLAT:HalpDismissInvalidVector ;af
  251. dd offset FLAT:HalpDismissInvalidVector ;b0
  252. dd offset FLAT:HalpDismissInvalidVector ;b1
  253. dd offset FLAT:HalpDismissInvalidVector ;b2
  254. dd offset FLAT:HalpDismissInvalidVector ;b3
  255. dd offset FLAT:HalpDismissInvalidVector ;b4
  256. dd offset FLAT:HalpDismissInvalidVector ;b5
  257. dd offset FLAT:HalpDismissInvalidVector ;b6
  258. dd offset FLAT:HalpDismissInvalidVector ;b7
  259. dd offset FLAT:HalpDismissInvalidVector ;b8
  260. dd offset FLAT:HalpDismissInvalidVector ;b9
  261. dd offset FLAT:HalpDismissInvalidVector ;ba
  262. dd offset FLAT:HalpDismissInvalidVector ;bb
  263. dd offset FLAT:HalpDismissInvalidVector ;bc
  264. dd offset FLAT:HalpDismissInvalidVector ;bd
  265. dd offset FLAT:HalpDismissInvalidVector ;be
  266. dd offset FLAT:HalpDismissInvalidVector ;bf
  267. dd offset FLAT:HalpDismissInvalidVector ;c0
  268. dd offset FLAT:HalpDismissInvalidVector ;c1
  269. dd offset FLAT:HalpDismissInvalidVector ;c2
  270. dd offset FLAT:HalpDismissInvalidVector ;c3
  271. dd offset FLAT:HalpDismissInvalidVector ;c4
  272. dd offset FLAT:HalpDismissInvalidVector ;c5
  273. dd offset FLAT:HalpDismissInvalidVector ;c6
  274. dd offset FLAT:HalpDismissInvalidVector ;c7
  275. dd offset FLAT:HalpDismissInvalidVector ;c8
  276. dd offset FLAT:HalpDismissInvalidVector ;c9
  277. dd offset FLAT:HalpDismissInvalidVector ;ca
  278. dd offset FLAT:HalpDismissInvalidVector ;cb
  279. dd offset FLAT:HalpDismissInvalidVector ;cc
  280. dd offset FLAT:HalpDismissInvalidVector ;cd
  281. dd offset FLAT:HalpDismissInvalidVector ;ce
  282. dd offset FLAT:HalpDismissInvalidVector ;cf
  283. _DATA ENDS
  284. _TEXT SEGMENT DWORD PUBLIC 'DATA'
  285. public HalpSpecialDismissLevelTable
  286. HalpSpecialDismissLevelTable label dword
  287. dd offset FLAT:HalpDismissLevel ; irq 0
  288. dd offset FLAT:HalpDismissLevel ; irq 1
  289. dd offset FLAT:HalpDismissLevel ; irq 2
  290. dd offset FLAT:HalpDismissLevel ; irq 3
  291. dd offset FLAT:HalpDismissLevel ; irq 4
  292. dd offset FLAT:HalpDismissLevel ; irq 5
  293. dd offset FLAT:HalpDismissLevel ; irq 6
  294. dd offset FLAT:HalpDismissIrq07Level ; irq 7
  295. dd offset FLAT:HalpDismissLevel ; irq 8
  296. dd offset FLAT:HalpDismissLevel ; irq 9
  297. dd offset FLAT:HalpDismissLevel ; irq A
  298. dd offset FLAT:HalpDismissLevel ; irq B
  299. dd offset FLAT:HalpDismissLevel ; irq C
  300. dd offset FLAT:HalpDismissIrq0dLevel ; irq D
  301. dd offset FLAT:HalpDismissLevel ; irq E
  302. dd offset FLAT:HalpDismissIrq0fLevel ; irq F
  303. _TEXT ENDS
  304. _TEXT$01 SEGMENT DWORD PUBLIC 'CODE'
  305. ASSUME DS:FLAT, ES:FLAT, SS:NOTHING, FS:NOTHING, GS:NOTHING
  306. ;++
  307. ;BOOLEAN
  308. ;HalBeginSystemInterrupt(
  309. ; IN KIRQL Irql
  310. ; IN CCHAR Vector,
  311. ; OUT PKIRQL OldIrql
  312. ; )
  313. ;
  314. ;
  315. ;
  316. ;Routine Description:
  317. ;
  318. ; This routine is used to dismiss the specified vector number. It is called
  319. ; before any interrupt service routine code is executed.
  320. ;
  321. ; N.B. This routine does NOT preserve EAX or EBX
  322. ;
  323. ; On a UP machine the interrupt dismissed at BeginSystemInterrupt time.
  324. ; This is fine since the irql is being raise to mask it off.
  325. ; HalEndSystemInterrupt is simply a LowerIrql request.
  326. ;
  327. ;
  328. ;Arguments:
  329. ;
  330. ; Irql - Supplies the IRQL to raise to
  331. ;
  332. ; Vector - Supplies the vector of the interrupt to be dismissed
  333. ;
  334. ; OldIrql- Location to return OldIrql
  335. ;
  336. ;
  337. ;Return Value:
  338. ;
  339. ; FALSE - Interrupt is spurious and should be ignored
  340. ;
  341. ; TRUE - Interrupt successfully dismissed and Irql raised.
  342. ;
  343. ;--
  344. align dword
  345. HbsiIrql equ byte ptr [esp+4]
  346. HbsiVector equ byte ptr [esp+8]
  347. HbsiOldIrql equ dword ptr [esp+12]
  348. cPublicProc _HalBeginSystemInterrupt ,3
  349. .FPO ( 0, 3, 0, 0, 0, 0 )
  350. xor ecx, ecx
  351. mov cl, HbsiVector ; (ecx) = System Vector
  352. sub ecx, PRIMARY_VECTOR_BASE ; (ecx) = 8259 IRQ #
  353. if DBG
  354. cmp ecx, 1fh
  355. jbe hbsi00
  356. int 3
  357. hbsi00:
  358. endif
  359. jmp HalpSpecialDismissTable[ecx*4]
  360. HalpDismissIrq0f:
  361. ;
  362. ; Check to see if this is a spurious interrupt
  363. ;
  364. mov al, OCW3_READ_ISR ; tell 8259 we want to read ISR
  365. out PIC2_PORT0, al
  366. IODelay ; delay
  367. in al, PIC2_PORT0 ; (al) = content of PIC 1 ISR
  368. test al, 10000000B ; Is In-Service register set?
  369. jnz short HalpDismissNormal ; No, this is NOT a spurious int,
  370. ; go do the normal interrupt stuff
  371. HalpIrq0fSpurious:
  372. ;
  373. ; This is a spurious interrupt.
  374. ; Because the slave PIC is cascaded to irq2 of master PIC, we need to
  375. ; dismiss the interupt on master PIC's irq2.
  376. ;
  377. mov al, PIC2_EOI ; Specific eoi to master for pic2 eoi
  378. out PIC1_PORT0, al ; send irq2 specific eoi to master
  379. mov eax,0 ; return FALSE
  380. stdRET _HalBeginSystemInterrupt
  381. HalpDismissIrq07:
  382. ;
  383. ; Check to see if this is a spurious interrupt
  384. ;
  385. mov al, OCW3_READ_ISR ; tell 8259 we want to read ISR
  386. out PIC1_PORT0, al
  387. IODelay ; delay
  388. in al, PIC1_PORT0 ; (al) = content of PIC 1 ISR
  389. test al, 10000000B ; Is In-Service register set?
  390. jnz HalpDismissNormal ; No, so this is NOT a spurious int
  391. mov eax, 0 ; return FALSE
  392. stdRET _HalBeginSystemInterrupt
  393. HalpDismissIrq0d:
  394. ;
  395. ; Clear the NPX busy latch.
  396. ;
  397. xor al,al
  398. out I386_80387_BUSY_PORT, al
  399. align 4
  400. HalpDismissNormal:
  401. ;
  402. ; Raise IRQL to requested level
  403. ;
  404. xor eax, eax
  405. mov al, HbsiIrql ; (al) = New irql
  406. ; (ecx) = IRQ #
  407. mov ebx, PCR[PcIrql] ; (ebx) = Current Irql
  408. ;
  409. ; Now we check to make sure the Irql of this interrupt > current Irql.
  410. ; If it is not, we dismiss it as spurious and set the appropriate bit
  411. ; in the IRR so we can dispatch the interrupt when Irql is lowered
  412. ;
  413. cmp al, bl
  414. jbe Hdsi300
  415. mov PCR[PcIrql], eax ; set new Irql
  416. mov edx, HbsiOldIrql ; save current irql to OldIrql variable
  417. mov byte ptr [edx], bl
  418. ;
  419. ; Dismiss interrupt.
  420. ;
  421. mov eax, ecx ; (eax) = IRQ #
  422. cmp eax, 8 ; EOI to master or slave?
  423. jae short Hbsi100 ; EIO to both master and slave
  424. or al, PIC1_EOI_MASK ; create specific eoi mask for master
  425. out PIC1_PORT0, al ; dismiss the interrupt
  426. sti
  427. mov eax, 1 ; return TRUE
  428. stdRET _HalBeginSystemInterrupt
  429. align 4
  430. Hbsi100:
  431. add al, OCW2_SPECIFIC_EOI - 8 ; specific eoi to slave
  432. out PIC2_PORT0, al
  433. mov al, PIC2_EOI ; specific eoi to master for pic2 eoi
  434. out PIC1_PORT0, al ; send irq2 specific eoi to master
  435. sti
  436. mov eax, 1 ; return TRUE
  437. stdRET _HalBeginSystemInterrupt
  438. align 4
  439. HalpDismissInvalidVector:
  440. mov eax,0 ; return FALSE
  441. stdRET _HalBeginSystemInterrupt
  442. align 4
  443. Hdsi300:
  444. ;
  445. ; An interrupt has come in at a lower Irql, so we dismiss it as spurious and
  446. ; set the appropriate bit in the IRR so that KeLowerIrql knows to dispatch
  447. ; it when Irql is lowered.
  448. ;
  449. ; (ecx) = 8259 IRQ#
  450. ; (al) = New Irql
  451. ; (ebx) = Current Irql
  452. ;
  453. mov eax, 1
  454. add ecx, 4 ; (ecx) = Irq # + 4
  455. shl eax, cl
  456. or PCR[PcIRR], eax
  457. ;
  458. ; Raise Irql to prevent it from happening again
  459. ;
  460. ;
  461. ; Get the PIC masks for Irql
  462. ;
  463. mov eax, KiI8259MaskTable[ebx*4]
  464. or eax, PCR[PcIDR]
  465. ;
  466. ; Write the new interrupt mask register back to the 8259
  467. ;
  468. SET_8259_MASK
  469. Hbsi390:
  470. ifdef IRQL_METRICS
  471. lock inc HalPostponedIntCount
  472. endif
  473. xor eax, eax ; return FALSE, spurious interrupt
  474. stdRET _HalBeginSystemInterrupt
  475. HalpDismissIrq0fLevel:
  476. ;
  477. ; Check to see if this is a spurious interrupt
  478. ;
  479. mov al, OCW3_READ_ISR ; tell 8259 we want to read ISR
  480. out PIC2_PORT0, al
  481. IODelay ; delay
  482. in al, PIC2_PORT0 ; (al) = content of PIC 1 ISR
  483. test al, 10000000B ; Is In-Service register set?
  484. jnz short HalpDismissLevel ; No, this is NOT a spurious int,
  485. ; go do the normal interrupt stuff
  486. jmp HalpIrq0fSpurious
  487. HalpDismissIrq07Level:
  488. ;
  489. ; Check to see if this is a spurious interrupt
  490. ;
  491. mov al, OCW3_READ_ISR ; tell 8259 we want to read ISR
  492. out PIC1_PORT0, al
  493. IODelay ; delay
  494. in al, PIC1_PORT0 ; (al) = content of PIC 1 ISR
  495. test al, 10000000B ; Is In-Service register set?
  496. jnz short HalpDismissLevel ; No, so this is NOT a spurious int
  497. mov eax, 0 ; return FALSE
  498. stdRET _HalBeginSystemInterrupt
  499. HalpDismissIrq0dLevel:
  500. ;
  501. ; Clear the NPX busy latch.
  502. ;
  503. xor al,al
  504. out I386_80387_BUSY_PORT, al
  505. align 4
  506. HalpDismissLevel:
  507. ;
  508. ; Mask this level interrupt off
  509. ; (ecx) = 8259 IRQ#
  510. ;
  511. mov al, HbsiIrql ; (al) = New irql
  512. mov eax, KiI8259MaskTable[eax*4] ; get 8259's masks
  513. or eax, PCR[PcIDR] ; mask disabled irqs
  514. SET_8259_MASK ; send mask to 8259s
  515. ;
  516. ; The SWInterruptHandler for this vector has been set to a NOP.
  517. ; Set the vector's IRR so that Lower Irql will clear the 8259 mask for this
  518. ; Irq when the irql is lowered below this level.
  519. ;
  520. mov eax, ecx ; (eax) = Irq #
  521. mov ebx, 1
  522. add ecx, 4 ; (ecx) = Irq # + 4
  523. shl ebx, cl
  524. or PCR[PcIRR], ebx
  525. ;
  526. ; Dismiss interrupt. Current interrupt is already masked off.
  527. ; Then check to make sure the Irql of this interrupt > current Irql.
  528. ; If it is not, we dismiss it as spurious - since this is a level interrupt
  529. ; when the 8259's are unmasked the interrupt will reoccur
  530. ;
  531. mov cl, HbsiIrql
  532. mov bl, PCR[PcIrql]
  533. mov edx, HbsiOldIrql
  534. cmp eax, 8 ; EOI to master or slave?
  535. jae short Hbsi450 ; EIO to both master and slave
  536. or al, PIC1_EOI_MASK ; create specific eoi mask for master
  537. out PIC1_PORT0, al ; dismiss the interrupt
  538. cmp cl, bl
  539. jbe short Hbsi390 ; Spurious?
  540. movzx ecx, cl
  541. mov PCR[PcIrql], ecx ; raise to new irql
  542. mov byte ptr [edx], bl ; return old irql
  543. sti
  544. mov eax, 1 ; return TRUE
  545. stdRET _HalBeginSystemInterrupt
  546. align 4
  547. Hbsi450:
  548. add al, OCW2_SPECIFIC_EOI - 8 ; specific eoi to slave
  549. out PIC2_PORT0, al
  550. mov al, PIC2_EOI ; specific eoi to master for pic2 eoi
  551. out PIC1_PORT0, al ; send irq2 specific eoi to master
  552. cmp cl, bl
  553. jbe Hbsi390 ; Spurious?
  554. movzx ecx, cl
  555. mov PCR[PcIrql], ecx ; raise to new irql
  556. mov byte ptr [edx], bl ; return old irql
  557. sti
  558. mov eax, 1 ; return TRUE
  559. stdRET _HalBeginSystemInterrupt
  560. stdENDP _HalBeginSystemInterrupt
  561. ;++
  562. ;VOID
  563. ;HalDisableSystemInterrupt(
  564. ; IN CCHAR Vector,
  565. ; IN KIRQL Irql
  566. ; )
  567. ;
  568. ;
  569. ;
  570. ;Routine Description:
  571. ;
  572. ; Disables a system interrupt.
  573. ;
  574. ;Arguments:
  575. ;
  576. ; Vector - Supplies the vector of the interrupt to be disabled
  577. ;
  578. ; Irql - Supplies the interrupt level of the interrupt to be disabled
  579. ;
  580. ;Return Value:
  581. ;
  582. ; None.
  583. ;
  584. ;--
  585. cPublicProc _HalDisableSystemInterrupt ,2
  586. .FPO ( 0, 2, 0, 0, 0, 0 )
  587. ;
  588. movzx ecx, byte ptr [esp+4] ; (ecx) = Vector
  589. sub ecx, PRIMARY_VECTOR_BASE ; (ecx) = 8259 irq #
  590. mov edx, 1
  591. shl edx, cl ; (ebx) = bit in IMR to disable
  592. cli
  593. or PCR[PcIDR], edx
  594. xor eax, eax
  595. ;
  596. ; Get the current interrupt mask register from the 8259
  597. ;
  598. in al, PIC2_PORT1
  599. shl eax, 8
  600. in al, PIC1_PORT1
  601. ;
  602. ; Mask off the interrupt to be disabled
  603. ;
  604. or eax, edx
  605. ;
  606. ; Write the new interrupt mask register back to the 8259
  607. ;
  608. out PIC1_PORT1, al
  609. shr eax, 8
  610. out PIC2_PORT1, al
  611. PIC2DELAY
  612. sti
  613. stdRET _HalDisableSystemInterrupt
  614. stdENDP _HalDisableSystemInterrupt
  615. ;++
  616. ;
  617. ;BOOLEAN
  618. ;HalEnableSystemInterrupt(
  619. ; IN ULONG Vector,
  620. ; IN KIRQL Irql,
  621. ; IN KINTERRUPT_MODE InterruptMode
  622. ; )
  623. ;
  624. ;
  625. ;Routine Description:
  626. ;
  627. ; Enables a system interrupt
  628. ;
  629. ;Arguments:
  630. ;
  631. ; Vector - Supplies the vector of the interrupt to be enabled
  632. ;
  633. ; Irql - Supplies the interrupt level of the interrupt to be enabled.
  634. ;
  635. ;Return Value:
  636. ;
  637. ; None.
  638. ;
  639. ;--
  640. cPublicProc _HalEnableSystemInterrupt ,3
  641. .FPO ( 0, 3, 0, 0, 0, 0 )
  642. movzx ecx, byte ptr [esp+4] ; (ecx) = vector
  643. sub ecx, PRIMARY_VECTOR_BASE
  644. jc hes_error
  645. cmp ecx, CLOCK2_LEVEL
  646. jnc hes_error
  647. ;
  648. ; Use the IRQ miniport to get the HW state.
  649. ;
  650. cmp _HalpIrqMiniportInitialized, 0
  651. jz hes_noMPGet
  652. push ecx
  653. lea eax, _HalpEisaELCR
  654. push eax
  655. call _PciirqmpGetTrigger@4
  656. pop ecx
  657. hes_noMPGet:
  658. bt _HalpEisaIrqIgnore,ecx ;;Is this Eisa Ignore bit set?
  659. jc short hes_ProgPic
  660. ;
  661. ; Clear or set the edge\level mask bit depending on what the caller wants.
  662. ;
  663. btr _HalpEisaELCR, ecx
  664. mov al, [esp+12]
  665. cmp al, 0
  666. jnz short hes_edge
  667. bt _HalpEisaELCR, ecx
  668. jc short @F
  669. ; Caller wants level triggered interrupts
  670. ; if IRQ routing is turned on, try and provide it
  671. cmp _HalpIrqMiniportInitialized, 0
  672. jz short @F
  673. bts _HalpEisaELCR, ecx
  674. @@:
  675. mov SWInterruptHandlerTable+4*4[ecx*4], offset HalpHardwareInterruptLevel
  676. mov edx, HalpSpecialDismissLevelTable[ecx*4]
  677. mov HalpSpecialDismissTable[ecx*4], edx
  678. hes_edge:
  679. cmp _HalpIrqMiniportInitialized, 0
  680. jz hes_ProgPIC
  681. ;
  682. ; Program the HW to make it match the callers request.
  683. ;
  684. mov eax, _HalpEisaELCR
  685. push ecx
  686. push eax
  687. call _PciirqmpSetTrigger@4
  688. pop ecx
  689. if 0
  690. .err
  691. ;;
  692. ;; We can't just arbitrarily blast ports. This makes machines do really weird things
  693. ;;
  694. hes_noMPSet:
  695. mov edx, 4d0h
  696. out dx, al
  697. inc edx
  698. mov al, ah
  699. out dx, al
  700. endif
  701. hes_ProgPIC:
  702. mov eax, 1
  703. shl eax, cl ; (ebx) = bit in IMR to enable
  704. not eax
  705. cli
  706. and PCR[PcIDR], eax
  707. ;
  708. ; Get the PIC masks for Irql 0
  709. ;
  710. mov eax, KiI8259MaskTable[0]
  711. or eax, PCR[PcIDR]
  712. ;
  713. ; Write the new interrupt mask register back to the 8259
  714. ;
  715. SET_8259_MASK
  716. sti
  717. mov eax, 1 ; return TRUE
  718. stdRET _HalEnableSystemInterrupt
  719. hes_error:
  720. if DBG
  721. int 3
  722. endif
  723. xor eax, eax ; FALSE
  724. stdRET _HalEnableSystemInterrupt
  725. stdENDP _HalEnableSystemInterrupt
  726. _TEXT$01 ENDS
  727. END