source: xtideuniversalbios/trunk/XTIDE_Universal_BIOS/Src/Initialization/Interrupts.asm @ 580

Last change on this file since 580 was 580, checked in by krille_n_@…, 9 years ago

Changes:

  • XTIDECFG: Fixed a bug from r459 where the menu option for selection of default boot drive would be missing if the BIOS had been built without MODULE_HOTKEYS. The menu option is now visible if either or both of MODULE_HOTKEYS and MODULE_BOOT_MENU is available.
  • BIOS: Disabled ATA-ID validation by adding a new define (NO_ATAID_VALIDATION) and making it the default for all builds since at least two WD Caviar drive models are incompatible with it.
  • Fixed the "No Fixed Disk Present in FDISK"-bug introduced in r551 which means the Tiny build now works without including MODULE_DRIVEXLATE.
  • Fixed a bug from r528 where pressing hotkey F6 would not initiate detection of serial drives.
  • Fixed a bug from r186 in DisplayFormatCompressed.asm where the boot menu would print the IRQ in hexadecimal format when it should be in decimal format.
  • Optimizations and fixes.
File size: 8.3 KB
RevLine 
[90]1; Project name  :   XTIDE Universal BIOS
[33]2; Description   :   Functions for initializing the BIOS.
3
[376]4;
[491]5; XTIDE Universal BIOS and Associated Tools
[526]6; Copyright (C) 2009-2010 by Tomi Tilli, 2011-2013 by XTIDE Universal BIOS Team.
[376]7;
8; This program is free software; you can redistribute it and/or modify
9; it under the terms of the GNU General Public License as published by
10; the Free Software Foundation; either version 2 of the License, or
11; (at your option) any later version.
[491]12;
[376]13; This program is distributed in the hope that it will be useful,
14; but WITHOUT ANY WARRANTY; without even the implied warranty of
15; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
[491]16; GNU General Public License for more details.
[376]17; Visit http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
[491]18;
[376]19
[33]20; Section containing code
21SECTION .text
22
23;--------------------------------------------------------------------
[580]24; Drives must be detected before this function is called unless
25; MODULE_DRIVEXLATE has been included in the BIOS.
[431]26;
[33]27; Interrupts_InitializeInterruptVectors
28;   Parameters:
29;       DS:     RAMVARS segment
30;       ES:     BDA and Interrupt Vector segment (zero)
31;   Returns:
32;       Nothing
33;   Corrupts registers:
34;       All except segments
[86]35;--------------------------------------------------------------------
[33]36Interrupts_InitializeInterruptVectors:
[431]37    ; Install INT 19h handler to properly reset the system
38    mov     al, BIOS_BOOT_LOADER_INTERRUPT_19h  ; INT 19h interrupt vector offset
39    mov     si, Int19hReset_Handler             ; INT 19h handler to reboot the system
40    call    Interrupts_InstallHandlerToVectorInALFromCSSI
41
42    ; If no drives detected, leave system INT 13h and 40h handlers
43    ; in place. We need our INT 13h handler to swap drive letters.
[492]44%ifndef MODULE_DRIVEXLATE
[431]45    cmp     BYTE [RAMVARS.bDrvCnt], 0
[489]46    je      SHORT Interrupts_InstallHandlerToVectorInALFromCSSI.Interrupts_Return
[431]47%endif
[97]48    ; Fall to .InitializeInt13hAnd40h
[33]49
50;--------------------------------------------------------------------
[97]51; .InitializeInt13hAnd40h
[33]52;   Parameters:
53;       DS:     RAMVARS segment
54;       ES:     BDA and Interrupt Vector segment (zero)
55;   Returns:
56;       Nothing
57;   Corrupts registers:
58;       AX, BX, CX, DX, SI, DI
[86]59;--------------------------------------------------------------------
[97]60.InitializeInt13hAnd40h:
[181]61    mov     ax, [es:BIOS_DISK_INTERRUPT_13h*4+2]; Load old INT 13h segment
62    mov     [RAMVARS.fpOldI13h+2], ax           ; Store old INT 13h segment
63    xchg    dx, ax
[152]64    mov     ax, [es:BIOS_DISK_INTERRUPT_13h*4]  ; Load old INT 13h offset
[33]65    mov     [RAMVARS.fpOldI13h], ax             ; Store old INT 13h offset
[181]66
[33]67    ; Only store INT 13h handler to 40h if 40h is not already installed.
68    ; At least AMI BIOS for 286 stores 40h handler by itself and calls
[530]69    ; 40h from 13h. That system locks to infinite loop if we blindly copy 13h to 40h.
[33]70    call    FloppyDrive_IsInt40hInstalled
[243]71    jc      SHORT .Int40hAlreadyInstalled
[152]72    mov     [es:BIOS_DISKETTE_INTERRUPT_40h*4], ax      ; Store old INT 13h offset
73    mov     [es:BIOS_DISKETTE_INTERRUPT_40h*4+2], dx    ; Store old INT 13h segment
[243]74.Int40hAlreadyInstalled:
[258]75
76    mov     al, BIOS_DISK_INTERRUPT_13h         ; INT 13h interrupt vector offset
[522]77%ifdef RELOCATE_INT13H_STACK
78    mov     si, Int13h_DiskFunctionsHandlerWithStackChange
79%else
[417]80    mov     si, Int13h_DiskFunctionsHandler
81%endif
[392]82
[398]83%ifndef MODULE_IRQ
84    ; Fall to Interrupts_InstallHandlerToVectorInALFromCSSI
85%else
[392]86    call    Interrupts_InstallHandlerToVectorInALFromCSSI
[97]87    ; Fall to .InitializeHardwareIrqHandlers
[33]88
89;--------------------------------------------------------------------
[97]90; .InitializeHardwareIrqHandlers
[33]91;   Parameters:
92;       ES:     BDA and Interrupt Vector segment (zero)
93;   Returns:
94;       Nothing
95;   Corrupts registers:
[258]96;       BX, CX, DX, SI, DI, AX
[86]97;--------------------------------------------------------------------
[97]98.InitializeHardwareIrqHandlers:
[33]99    call    RamVars_GetIdeControllerCountToCX
[558]100    mov     di, ROMVARS.ideVars0+IDEVARS.bIRQ
[33]101.IdeControllerLoop:
[491]102    mov     al, [cs:di]
[33]103    add     di, BYTE IDEVARS_size           ; Increment to next controller
104    call    .InstallLowOrHighIrqHandler
105    loop    .IdeControllerLoop
[86]106.Return:
107    ret     ; This ret is shared with .InstallLowOrHighIrqHandler
[33]108
109;--------------------------------------------------------------------
110; .InstallLowOrHighIrqHandler
111;   Parameters:
[258]112;       AL:     IRQ number, 0 if IRQ disabled
[33]113;       ES:     BDA and Interrupt Vector segment (zero)
114;   Returns:
115;       Nothing
116;   Corrupts registers:
117;       BX, SI
[86]118;--------------------------------------------------------------------
[33]119.InstallLowOrHighIrqHandler:
[258]120    test    al, al
[86]121    jz      SHORT .Return   ; IRQ not used
[540]122%ifdef USE_AT
[258]123    cmp     al, 8
[86]124    jb      SHORT .InstallLowIrqHandler
[162]125    ; Fall to .InstallHighIrqHandler
[33]126
127;--------------------------------------------------------------------
128; .InstallHighIrqHandler
129;   Parameters:
130;       BX:     IRQ number (8...15)
131;       ES:     BDA and Interrupt Vector segment (zero)
132;   Returns:
133;       Nothing
134;   Corrupts registers:
[258]135;       AL, BX, SI
[86]136;--------------------------------------------------------------------
[97]137.InstallHighIrqHandler:
[258]138    add     al, BYTE HARDWARE_IRQ_8_INTERRUPT_70h - 8   ; Interrupt vector number
[150]139    mov     si, IdeIrq_InterruptServiceRoutineForIrqs8to15
[258]140    jmp     SHORT Interrupts_InstallHandlerToVectorInALFromCSSI
[540]141%endif ; USE_AT
[33]142
143;--------------------------------------------------------------------
144; .InstallLowIrqHandler
145;   Parameters:
[258]146;       AL:     IRQ number (0...7)
[33]147;       ES:     BDA and Interrupt Vector segment (zero)
148;   Returns:
149;       Nothing
150;   Corrupts registers:
[258]151;       AL, BX, SI
[86]152;--------------------------------------------------------------------
[33]153.InstallLowIrqHandler:
[258]154    add     al, BYTE HARDWARE_IRQ_0_INTERRUPT_08h       ; Interrupt vector number
[150]155    mov     si, IdeIrq_InterruptServiceRoutineForIrqs2to7
[258]156    ; Fall to Interrupts_InstallHandlerToVectorInALFromCSSI
[398]157%endif ; MODULE_IRQ
[33]158
159
160;--------------------------------------------------------------------
[258]161; Interrupts_InstallHandlerToVectorInALFromCSSI
[33]162;   Parameters:
[258]163;       AL:     Interrupt vector number (for example 13h)
[33]164;       ES:     BDA and Interrupt Vector segment (zero)
165;       CS:SI:  Ptr to interrupt handler
166;   Returns:
167;       Nothing
168;   Corrupts registers:
[258]169;       AX, BX
[86]170;--------------------------------------------------------------------
[258]171Interrupts_InstallHandlerToVectorInALFromCSSI:
172    mov     bl, 4                   ; Shift for DWORD offset, MUL smaller than other alternatives
173    mul     bl
174    xchg    ax, bx
[33]175    mov     [es:bx], si             ; Store offset
176    mov     [es:bx+2], cs           ; Store segment
[489]177.Interrupts_Return:
[33]178    ret
179
180
[398]181%ifdef MODULE_IRQ
[33]182;--------------------------------------------------------------------
183; Interrupts_UnmaskInterruptControllerForDriveInDSDI
184;   Parameters:
185;       DS:DI:  Ptr to DPT
186;   Returns:
187;       Nothing
188;   Corrupts registers:
189;       AX, BX, DX
190;--------------------------------------------------------------------
191Interrupts_UnmaskInterruptControllerForDriveInDSDI:
[294]192    eMOVZX  bx, [di+DPT.bIdevarsOffset]
[33]193    mov     al, [cs:bx+IDEVARS.bIRQ]
[86]194    test    al, al
195    jz      SHORT .Return   ; Interrupts disabled
[33]196    cmp     al, 8
[86]197    jb      SHORT .UnmaskLowIrqController
[162]198    ; Fall to .UnmaskHighIrqController
[33]199
200;--------------------------------------------------------------------
201; .UnmaskHighIrqController
202;   Parameters:
203;       AL:     IRQ number (8...15)
204;   Returns:
205;       Nothing
206;   Corrupts registers:
207;       AX, DX
208;--------------------------------------------------------------------
[97]209.UnmaskHighIrqController:
[33]210    sub     al, 8               ; Slave interrupt number
[152]211    mov     dx, SLAVE_8259_IMR
[33]212    call    .ClearBitFrom8259MaskRegister
213    mov     al, 2               ; Master IRQ 2 to allow slave IRQs
214    ; Fall to .UnmaskLowIrqController
215
216;--------------------------------------------------------------------
217; .UnmaskLowIrqController
218;   Parameters:
219;       AL:     IRQ number (0...7)
220;   Returns:
221;       Nothing
222;   Corrupts registers:
223;       AX, DX
224;--------------------------------------------------------------------
225.UnmaskLowIrqController:
[152]226    mov     dx, MASTER_8259_IMR
[33]227    ; Fall to .ClearBitFrom8259MaskRegister
228
229;--------------------------------------------------------------------
230; .ClearBitFrom8259MaskRegister
231;   Parameters:
232;       AL:     8259 interrupt index (0...7)
233;       DX:     Port address to Interrupt Mask Register
234;   Returns:
235;       Nothing
236;   Corrupts registers:
237;       AX
238;--------------------------------------------------------------------
239.ClearBitFrom8259MaskRegister:
240    push    cx
241    xchg    ax, cx              ; IRQ index to CL
242    mov     ch, 1               ; Load 1 to be shifted
243    shl     ch, cl              ; Shift bit to correct position
244    not     ch                  ; Invert to create bit mask for clearing
245    in      al, dx              ; Read Interrupt Mask Register
246    and     al, ch              ; Clear wanted bit
247    out     dx, al              ; Write modified Interrupt Mask Register
248    pop     cx
[86]249.Return:
[33]250    ret
[398]251
252%endif ; MODULE_IRQ
Note: See TracBrowser for help on using the repository browser.