source: xtideuniversalbios/trunk/XTIDE_Universal_BIOS/Src/VariablesAndDPTs/FindDPT.asm @ 621

Last change on this file since 621 was 621, checked in by krille_n_, 2 years ago

Changes:

  • Fixed three different bugs all causing the boot menu to show drives using IRQs even though the BIOS had been built without MODULE_IRQ.
  • Fixed two bugs in XTIDECFG where loading a BIOS from file and then loading the old settings from EEPROM would
    • overwrite ROMVARS.wFlags in the loaded BIOS file (in RAM). The possibly resulting mismatch of module flags could make it impossible to change settings for modules included in the BIOS or allow changing settings for modules not included in the BIOS.
    • not copy the color theme over to the loaded BIOS.
  • Also fixed two very minor bugs in XTIDECFG in BiosFile_LoadFileFromDSSItoRamBuffer and BiosFile_SaveRamBufferToFileInDSSI where the error handling in these routines would close whatever file handle that happened to match the error code returned by DOS in AX.
  • Made significant changes to the new flash ROM programming routines to reduce the size. Also fixed a minor bug that would cause the second verification to be skipped and return success when programming a 64 KB block of data.
  • Changed the custom BIOS build file names to the 8.3 format.
  • Changed some help strings in XTIDECFG to clarify things.
  • Other minor optimizations and fixes.
File size: 9.4 KB
RevLine 
[150]1; Project name  :   XTIDE Universal BIOS
[3]2; Description   :   Functions for finding Disk Parameter Table.
3
[376]4;
[526]5; XTIDE Universal BIOS and Associated Tools
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.
[526]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
[526]16; GNU General Public License for more details.
[376]17; Visit http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
[526]18;
[376]19
[3]20; Section containing code
21SECTION .text
22
23;--------------------------------------------------------------------
[262]24; Checks if drive is handled by this BIOS, and return DPT pointer.
[3]25;
[294]26; FindDPT_ForDriveNumberInDL
[3]27;   Parameters:
[262]28;       DL:     Drive number
[3]29;       DS:     RAMVARS segment
30;   Returns:
[262]31;       CF:     Cleared if drive is handled by this BIOS
32;               Set if drive belongs to some other BIOS
33;       DI:     DPT Pointer if drive is handled by this BIOS
34;               Zero if drive belongs to some other BIOS
[3]35;   Corrupts registers:
[262]36;       Nothing
[150]37;--------------------------------------------------------------------
38ALIGN JUMP_ALIGN
[294]39FindDPT_ForDriveNumberInDL:
[262]40    xchg    di, ax                              ; Save the contents of AX in DI
41
[294]42;
[262]43; Check Our Hard Disks
44;
[433]45    mov     ax, [RAMVARS.wFirstDrvAndCount]     ; Drive count to AH, First number to AL
[262]46    add     ah, al                              ; One past last drive to AH
47
[258]48%ifdef MODULE_SERIAL_FLOPPY
[262]49    cmp     dl, ah                              ; Above last supported?
50    jae     SHORT .HardDiskNotHandledByThisBIOS
[294]51
[262]52    cmp     dl, al                              ; Below first supported?
53    jae     SHORT .CalcDPTForDriveNumber
54
[294]55ALIGN JUMP_ALIGN
56.HardDiskNotHandledByThisBIOS:
[262]57;
58; Check Our Floppy Disks
[294]59;
[262]60    call    RamVars_UnpackFlopCntAndFirstToAL
61    js      SHORT .DiskIsNotHandledByThisBIOS
[294]62
[277]63    cbw                                         ; Always 0h (no floppy drive covered above)
64    adc     ah, al                              ; Add in first drive number and number of drives
65
[262]66    cmp     ah, dl                              ; Check second drive if two, first drive if only one
67    jz      SHORT .CalcDPTForDriveNumber
68    cmp     al, dl                              ; Check first drive in all cases, redundant but OK to repeat
[294]69    jnz     SHORT .DiskIsNotHandledByThisBIOS
[262]70%else
[294]71    cmp     dl, ah                              ; Above last supported?
[262]72    jae     SHORT .DiskIsNotHandledByThisBIOS
[294]73
[262]74    cmp     dl, al                              ; Below first supported?
[294]75    jb      SHORT .DiskIsNotHandledByThisBIOS
[258]76%endif
[567]77    ; Fall to .CalcDPTForDriveNumber
[150]78
79;--------------------------------------------------------------------
80; Finds Disk Parameter Table for drive number.
[294]81; Not intended to be called except by FindDPT_ForDriveNumberInDL
[150]82;
[567]83; .CalcDPTForDriveNumber
[150]84;   Parameters:
85;       DL:     Drive number
86;       DS:     RAMVARS segment
[567]87;       DI:     Saved copy of AX from entry at FindDPT_ForDriveNumberInDL
[150]88;   Returns:
89;       DS:DI:  Ptr to DPT
[567]90;       CF:     Clear
[150]91;   Corrupts registers:
[3]92;       Nothing
93;--------------------------------------------------------------------
94ALIGN JUMP_ALIGN
[262]95.CalcDPTForDriveNumber:
[150]96    push    dx
[3]97
[258]98%ifdef MODULE_SERIAL_FLOPPY
[433]99    mov     ax, [RAMVARS.wFirstDrvAndCount]
[294]100
[258]101    test    dl, dl
102    js      .harddisk
103
104    call    RamVars_UnpackFlopCntAndFirstToAL
105    add     dl, ah                      ; add in end of hard disk DPT list, floppies start immediately after
[294]106
107ALIGN JUMP_ALIGN
[258]108.harddisk:
109    sub     dl, al                      ; subtract off beginning of either hard disk or floppy list (as appropriate)
110%else
111    sub     dl, [RAMVARS.bFirstDrv]     ; subtract off beginning of hard disk list
112%endif
[262]113
[294]114.CalcDPTForNewDrive:
[150]115    mov     al, LARGEST_DPT_SIZE
[294]116
[150]117    mul     dl
[522]118    add     ax, RAMVARS_size            ; Clears CF (will not overflow)
[3]119
[150]120    pop     dx
[262]121
122    xchg    di, ax                      ; Restore AX from entry at FindDPT_ForDriveNumber, put DPT pointer in DI
[150]123    ret
124
[294]125ALIGN JUMP_ALIGN
126.DiskIsNotHandledByThisBIOS:
[259]127;
[262]128; Drive not found...
129;
130    xor     ax, ax                              ; Clear DPT pointer
[294]131    stc                                         ; Is not supported by our BIOS
132
[262]133    xchg    di, ax                              ; Restore AX from save at top
[259]134    ret
135
[271]136
[259]137;--------------------------------------------------------------------
[521]138; Iteration routines for FindDPT_MasterOrSingleForIdevarsOffsetInDL and
[621]139; FindDPT_SlaveForIdevarsOffsetInDL, for use with FindDPT_IterateAllDPTs
[294]140;
[271]141; Returns when DPT is found on the controller with Idevars offset in DL
142;
[521]143; IterateFindSecondDPTforIdevars
[271]144; IterateFindFirstDPTforIdevars
[567]145;       DL:     Offset to IDEVARS to search from DPTs
[524]146;       SI:     Offset to this callback function
[271]147;       DS:DI:  Ptr to DPT to examine
148;   Returns:
[567]149;       CF:     Cleared if wanted DPT found
[271]150;               Set if wrong DPT
151;--------------------------------------------------------------------
[521]152IterateFindSecondDPTforIdevars:
153    call    IterateFindFirstDPTforIdevars
[621]154    jc      SHORT WrongController
[524]155    mov     si, IterateFindFirstDPTforIdevars
[621]156SetCFandReturn:
[524]157    stc
[621]158WrongController:
[524]159    ret
[521]160
[294]161IterateFindFirstDPTforIdevars:
[271]162    cmp     dl, [di+DPT.bIdevarsOffset]         ; Clears CF if matched
[621]163    jne     SHORT SetCFandReturn
[271]164    ret
165
166
167;--------------------------------------------------------------------
[262]168; Finds pointer to first unused Disk Parameter Table.
169; Should only be used before DetectDrives is complete (not valid after this time).
[3]170;
[262]171; FindDPT_ForNewDriveToDSDI
[3]172;   Parameters:
173;       DS:     RAMVARS segment
174;   Returns:
[262]175;       DS:DI:  Ptr to first unused DPT
[3]176;   Corrupts registers:
[262]177;       AX
[3]178;--------------------------------------------------------------------
[262]179ALIGN JUMP_ALIGN
180FindDPT_ForNewDriveToDSDI:
181    push    dx
[294]182
[262]183%ifdef MODULE_SERIAL_FLOPPY
184    mov     dx, [RAMVARS.wDrvCntAndFlopCnt]
185    add     dl, dh
186%else
187    mov     dl, [RAMVARS.bDrvCnt]
188%endif
[294]189
[567]190    jmp     SHORT FindDPT_ForDriveNumberInDL.CalcDPTForNewDrive
[3]191
[152]192;--------------------------------------------------------------------
[233]193; IterateToDptWithFlagsHighInBL
[152]194;   Parameters:
195;       DS:DI:  Ptr to DPT to examine
[567]196;       BL:     Bit(s) to test in DPT.bFlagsHigh
[152]197;   Returns:
[567]198;       CF:     Cleared if wanted DPT found
[262]199;               Set if wrong DPT
[152]200;   Corrupts registers:
201;       Nothing
202;--------------------------------------------------------------------
[567]203%ifdef MODULE_SERIAL
[152]204ALIGN JUMP_ALIGN
[294]205IterateToDptWithFlagsHighInBL:
206    test    [di+DPT.bFlagsHigh], bl             ; Clears CF
[262]207    jnz     SHORT .ReturnRightDPT
208    stc
[294]209.ReturnRightDPT:
[3]210    ret
[567]211%endif
[3]212
213;--------------------------------------------------------------------
[233]214; FindDPT_ToDSDIforSerialDevice
[161]215;   Parameters:
216;       DS:     RAMVARS segment
217;   Returns:
218;       DS:DI:  Ptr to DPT
[567]219;       CF:     Cleared if wanted DPT found
220;               Set if DPT not found, or no DPTs present
[161]221;   Corrupts registers:
[621]222;       BL, SI
[161]223;--------------------------------------------------------------------
[265]224%ifdef MODULE_SERIAL
[294]225ALIGN JUMP_ALIGN
226FindDPT_ToDSDIforSerialDevice:
[233]227    mov     bl, FLGH_DPT_SERIAL_DEVICE
[567]228    ; Fall to FindDPT_ToDSDIforFlagsHighInBL
[265]229%endif
[294]230
[233]231;--------------------------------------------------------------------
[567]232; FindDPT_ToDSDIforFlagsHighInBL
[233]233;   Parameters:
234;       DS:     RAMVARS segment
[567]235;       BL:     Bit(s) to test in DPT.bFlagsHigh
[233]236;   Returns:
237;       DS:DI:  Ptr to DPT
[567]238;       CF:     Cleared if wanted DPT found
239;               Set if DPT not found, or no DPTs present
[233]240;   Corrupts registers:
241;       SI
242;--------------------------------------------------------------------
[567]243%ifdef MODULE_SERIAL
244;%ifdef MODULE_IRQ
245;ALIGN JUMP_ALIGN
246;FindDPT_ToDSDIforFlagsHighInBL:    ; This label is unused
247;%endif
248    mov     si, IterateToDptWithFlagsHighInBL
249    jmp     SHORT FindDPT_IterateAllDPTs
[489]250%endif
[161]251
252;--------------------------------------------------------------------
[567]253; FindDPT_MasterOrSingleForIdevarsOffsetInDL
254;   Parameters:
255;       DL:     Offset to IDEVARS to search for
256;       DS:     RAMVARS segment
257;   Returns:
258;       DS:DI:  Ptr to first DPT with same IDEVARS as in DL
259;       CF:     Cleared if wanted DPT found
260;               Set if DPT not found, or no DPTs present
261;   Corrupts registers:
262;       SI
263;--------------------------------------------------------------------
264FindDPT_MasterOrSingleForIdevarsOffsetInDL:
265    mov     si, IterateFindFirstDPTforIdevars
266    jmp     SHORT FindDPT_IterateAllDPTs
267
268;--------------------------------------------------------------------
269; FindDPT_SlaveForIdevarsOffsetInDL
270;   Parameters:
271;       DL:     Offset to IDEVARS to search for
272;       DS:     RAMVARS segment
273;   Returns:
274;       DS:DI:  Ptr to second DPT with same IDEVARS as in DL
275;       CF:     Cleared if wanted DPT found
276;               Set if DPT not found, or no DPTs present
277;   Corrupts registers:
278;       SI
279;--------------------------------------------------------------------
280FindDPT_SlaveForIdevarsOffsetInDL:
281    mov     si, IterateFindSecondDPTforIdevars
282    ; Fall to FindDPT_IterateAllDPTs
283
284;--------------------------------------------------------------------
[3]285; Iterates all Disk Parameter Tables.
286;
[271]287; FindDPT_IterateAllDPTs
[3]288;   Parameters:
[152]289;       AX,BX,DX:   Parameters to callback function
290;       CS:SI:      Ptr to callback function
[567]291;                   Callback routine should return CF=clear if found
[152]292;       DS:         RAMVARS segment
[3]293;   Returns:
[152]294;       DS:DI:      Ptr to wanted DPT (if found)
[258]295;                   If not found, points to first empty DPT
[567]296;       CF:         Cleared if wanted DPT found
[262]297;                   Set if DPT not found, or no DPTs present
[3]298;   Corrupts registers:
[150]299;       Nothing unless corrupted by callback function
[3]300;--------------------------------------------------------------------
301ALIGN JUMP_ALIGN
[271]302FindDPT_IterateAllDPTs:
[3]303    push    cx
[258]304
305    mov     di, RAMVARS_size            ; Point DS:DI to first DPT
[294]306    eMOVZX  cx, [RAMVARS.bDrvCnt]
[262]307    jcxz    .NotFound                   ; Return if no drives
[294]308
[3]309ALIGN JUMP_ALIGN
310.LoopWhileDPTsLeft:
311    call    si                          ; Is wanted DPT?
[262]312    jnc     SHORT .Found                ;  If so, return
313    add     di, BYTE LARGEST_DPT_SIZE   ; Point to next DPT
[258]314    loop    .LoopWhileDPTsLeft
[262]315
316.NotFound:
317    stc
318
319ALIGN JUMP_ALIGN
320.Found:
[3]321    pop     cx
322    ret
Note: See TracBrowser for help on using the repository browser.