source: xtideuniversalbios/trunk/XTIDE_Universal_BIOS/Src/VariablesAndDPTs/CreateDPT.asm @ 500

Last change on this file since 500 was 493, checked in by gregli@…, 11 years ago

Separated MODULE_8BIT_IDE into the basic part used by XTIDE rev 1 and rev 2 which is PIO based, and MODULE_8BIT_IDE_ADVANCED for JRIDE and XTCF support which requires memory mapping and/or DMA. This allows for creating an 8KB image with boot menu support (but no hotkeys) for the XTIDE rev 1. Cleaned up how we reset the drive translation information, ensuring it is properly set between boot attempt on a primary and secondary drive - as a result we clean it when needed, rather than trying to always keep it clean. Also fixed translation bugs in int13h.asm where I had previously missed converting some MODULE_HOTKEYS into MODULE_DRIVEXLATE.

File size: 11.1 KB
Line 
1; Project name  :   XTIDE Universal BIOS
2; Description   :   Functions for creating Disk Parameter Table.
3
4;
5; XTIDE Universal BIOS and Associated Tools
6; Copyright (C) 2009-2010 by Tomi Tilli, 2011-2012 by XTIDE Universal BIOS Team.
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.
12;
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
16; GNU General Public License for more details.
17; Visit http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
18;
19
20; Section containing code
21SECTION .text
22
23;--------------------------------------------------------------------
24; Creates new Disk Parameter Table for detected hard disk.
25; Drive is then fully accessible using any BIOS function.
26;
27; CreateDPT_FromAtaInformation
28;   Parameters:
29;       BH:     Drive Select byte for Drive and Head Register
30;       DX:     Autodetected port (for devices that support autodetection)
31;       ES:SI:  Ptr to 512-byte ATA information read from the drive
32;       CS:BP:  Ptr to IDEVARS for the controller
33;       DS:     RAMVARS segment
34;       ES:     BDA Segment
35;   Returns:
36;       DS:DI:  Ptr to Disk Parameter Table (if successful)
37;       CF:     Cleared if DPT created successfully
38;               Set if any error
39;   Corrupts registers:
40;       AX, BX, CX, DH
41;--------------------------------------------------------------------
42CreateDPT_FromAtaInformation:
43    call    FindDPT_ForNewDriveToDSDI
44    ; Fall to .InitializeDPT
45
46;--------------------------------------------------------------------
47; .InitializeDPT
48;   Parameters:
49;       BH:     Drive Select byte for Drive and Head Register
50;       DX:     Autodetected port (for devices that support autodetection)
51;       DS:DI:  Ptr to Disk Parameter Table
52;       CS:BP:  Ptr to IDEVARS for the controller
53;   Returns:
54;       Nothing
55;   Corrupts registers:
56;       AX
57;--------------------------------------------------------------------
58.InitializeDPT:
59    call    CreateDPT_StoreIdevarsOffsetAndBasePortFromCSBPtoDPTinDSDI
60    ; Fall to .StoreDriveSelectAndDriveControlByte
61
62;--------------------------------------------------------------------
63; .StoreDriveSelectAndDriveControlByte
64;   Parameters:
65;       BH:     Drive Select byte for Drive and Head Register
66;       DS:DI:  Ptr to Disk Parameter Table
67;       ES:SI:  Ptr to 512-byte ATA information read from the drive
68;       CS:BP:  Ptr to IDEVARS for the controller
69;   Returns:
70;       Nothing
71;   Corrupts registers:
72;       AX
73;--------------------------------------------------------------------
74.StoreDriveSelectAndDriveControlByte:
75    mov     al, bh
76    and     ax, BYTE FLG_DRVNHEAD_DRV       ; AL now has Master/Slave bit
77%ifdef MODULE_IRQ
78    cmp     [cs:bp+IDEVARS.bIRQ], ah        ; Interrupts enabled?
79    jz      SHORT .StoreFlags               ;  If not, do not set interrupt flag
80    or      al, FLGL_DPT_ENABLE_IRQ
81.StoreFlags:
82%endif
83    mov     [di+DPT.wFlags], ax
84    ; Fall to .StoreCHSparametersAndAddressingMode
85
86;--------------------------------------------------------------------
87; .StoreCHSparametersAndAddressingMode
88;   Parameters:
89;       DS:DI:  Ptr to Disk Parameter Table
90;       ES:SI:  Ptr to 512-byte ATA information read from the drive
91;       CS:BP:  Ptr to IDEVARS for the controller
92;   Returns:
93;       Nothing
94;   Corrupts registers:
95;       AX, BX, CX, DX
96;--------------------------------------------------------------------
97.StoreCHSparametersAndAddressingMode:
98    ; Check if CHS defined in ROMVARS
99    call    GetUserDefinedCapacityToBXAXandFlagsToCXandModeToDXfromROMVARS
100    test    cl, FLG_DRVPARAMS_USERCHS
101    jz      SHORT .AutodetectPCHSvalues
102
103    ; Translate P-CHS to L-CHS
104    call    AtaGeometry_GetLCHStoAXBLBHfromPCHSinAXBLBHandTranslateModeInDX
105    jmp     SHORT .StoreLCHStoDPT
106.AutodetectPCHSvalues:
107    call    AtaGeometry_GetLCHStoAXBLBHfromAtaInfoInESSIandTranslateModeInDX
108
109.StoreLCHStoDPT:
110    eSHL_IM dl, TRANSLATEMODE_FIELD_POSITION
111    or      cl, dl
112    or      [di+DPT.bFlagsLow], cl      ; Shift count and addressing mode
113    mov     [di+DPT.wLchsCylinders], ax
114    mov     [di+DPT.wLchsHeadsAndSectors], bx
115
116    ; Store P-CHS to DPT
117    call    AtaGeometry_GetPCHStoAXBLBHfromAtaInfoInESSI
118    mov     [di+DPT.bPchsHeads], bl
119%ifdef MODULE_EBIOS
120    mov     [di+DPT.wPchsCylinders], ax
121    mov     [di+DPT.bPchsSectorsPerTrack], bh
122    ; Fall to .StoreNumberOfLbaSectors
123
124;--------------------------------------------------------------------
125; .StoreNumberOfLbaSectors
126;   Parameters:
127;       DS:DI:  Ptr to Disk Parameter Table
128;       ES:SI:  Ptr to 512-byte ATA information read from the drive
129;       CS:BP:  Ptr to IDEVARS for the controller
130;   Returns:
131;       Nothing
132;   Corrupts registers:
133;       AX, BX, CX, DX
134;--------------------------------------------------------------------
135    ; Check if LBA supported
136    test    BYTE [es:si+ATA1.wCaps+1], A1_wCaps_LBA>>8
137    jz      SHORT .NoLbaSupportedSoNoEBIOS
138
139    ; Store LBA 28/48 total sector count
140    call    AtaGeometry_GetLbaSectorCountToBXDXAXfromAtaInfoInESSI
141    call    StoreLba48AddressingFromCLandTotalSectorCountFromBXDXAX
142
143    ; Load user defined LBA
144    call    GetUserDefinedCapacityToBXAXandFlagsToCXandModeToDXfromROMVARS
145    test    cl, FLG_DRVPARAMS_USERLBA
146    jz      SHORT .KeepTotalSectorsFromAtaID
147
148    ; Compare user defined and ATA-ID sector count and select smaller
149    mov     dx, bx
150    xor     bx, bx      ; User defined LBA now in BX:DX:AX
151    cmp     bx, [di+DPT.twLbaSectors+4]
152    jb      SHORT .StoreUserDefinedSectorCountToDPT
153    cmp     dx, [di+DPT.twLbaSectors+2]
154    jb      SHORT .StoreUserDefinedSectorCountToDPT
155    ja      SHORT .KeepTotalSectorsFromAtaID
156    cmp     ax, [di+DPT.twLbaSectors]
157    jae     SHORT .KeepTotalSectorsFromAtaID
158.StoreUserDefinedSectorCountToDPT:
159    ; CL bit FLGL_DPT_LBA48 is clear at this point
160    call    StoreLba48AddressingFromCLandTotalSectorCountFromBXDXAX
161
162.KeepTotalSectorsFromAtaID:
163.NoLbaSupportedSoNoEBIOS:
164%endif ; MODULE_EBIOS
165    ; Fall to .StoreBlockMode
166
167;--------------------------------------------------------------------
168; .StoreBlockMode
169;   Parameters:
170;       DS:DI:  Ptr to Disk Parameter Table
171;       ES:SI:  Ptr to 512-byte ATA information read from the drive
172;       CS:BP:  Ptr to IDEVARS for the controller
173;   Returns:
174;       Nothing
175;   Corrupts registers:
176;       Nothing
177;--------------------------------------------------------------------
178.StoreBlockMode:
179    cmp     BYTE [es:si+ATA1.bBlckSize], 1  ; Max block size in sectors
180    jbe     SHORT .BlockModeTransfersNotSupported
181    or      BYTE [di+DPT.bFlagsHigh], FLGH_DPT_BLOCK_MODE_SUPPORTED
182.BlockModeTransfersNotSupported:
183    ; Fall to .StoreDeviceSpecificParameters
184
185;--------------------------------------------------------------------
186; .StoreDeviceSpecificParameters
187;   Parameters:
188;       DS:DI:  Ptr to Disk Parameter Table
189;       ES:SI:  Ptr to 512-byte ATA information read from the drive
190;       CS:BP:  Ptr to IDEVARS for the controller
191;   Returns:
192;       Nothing
193;   Corrupts registers:
194;       AX, BX, CX, DX
195;--------------------------------------------------------------------
196.StoreDeviceSpecificParameters:
197    call    Device_FinalizeDPT
198
199;----------------------------------------------------------------------
200; Update drive counts (hard and floppy)
201;----------------------------------------------------------------------
202
203%ifdef MODULE_SERIAL_FLOPPY
204;
205; These two instructions serve two purposes:
206; 1. If the drive is a floppy drive (CF set), then we effectively increment the counter.
207; 2. If this is a hard disk, and there have been any floppy drives previously added, then the hard disk is
208;    effectively discarded.  This is more of a safety check then code that should ever normally be hit (see below).
209;    Since the floppy DPT's come after the hard disk DPT's, without expensive (code size) code to relocate a DPT,
210;    this was necessary.  Now, this situation shouldn't happen in normal operation, for a couple of reasons:
211;       A. xtidecfg always puts configured serial ports at the end of the IDEVARS list
212;       B. the auto serial code is always executed last
213;       C. the serial server always returns floppy drives last
214;
215    adc     byte [RAMVARS.xlateVars+XLATEVARS.bFlopCreateCnt], 0
216    jnz     .AllDone
217%else
218;
219; Even without floppy support enabled, we shouldn't try to mount a floppy image as a hard disk, which
220; could lead to unpredictable results since no MBR will be present, etc.  The server doesn't know that
221; floppies are supported, so it is important to still fail here if a floppy is seen during the drive scan.
222;
223    jc      .AllDone
224%endif
225
226    inc     BYTE [RAMVARS.bDrvCnt]      ; Increment drive count to RAMVARS
227
228.AllDone:
229    clc
230    ret
231
232
233;--------------------------------------------------------------------
234; CreateDPT_StoreIdevarsOffsetAndBasePortFromCSBPtoDPTinDSDI
235;   Parameters:
236;       DX:     Autodetected port (for devices that support autodetection)
237;       DS:DI:  Ptr to Disk Parameter Table
238;       CS:BP:  Ptr to IDEVARS for the controller
239;   Returns:
240;       Nothing
241;   Corrupts registers:
242;       AX
243;--------------------------------------------------------------------
244CreateDPT_StoreIdevarsOffsetAndBasePortFromCSBPtoDPTinDSDI:
245    mov     [di+DPT.bIdevarsOffset], bp     ; IDEVARS must start in first 256 bytes of ROM
246
247%ifdef MODULE_8BIT_IDE_ADVANCED
248    call    DetectDrives_DoesIdevarsInCSBPbelongToXTCF
249    jne     SHORT .DeviceUsesPortSpecifiedInIDEVARS
250    mov     [di+DPT.wBasePort], dx
251    ret
252.DeviceUsesPortSpecifiedInIDEVARS:
253%endif ; MODULE_8BIT_IDE_ADVANCED
254
255    mov     ax, [cs:bp+IDEVARS.wBasePort]
256    mov     [di+DPT.wBasePort], ax
257    ret
258
259
260;--------------------------------------------------------------------
261; GetUserDefinedCapacityToBXAXandFlagsToCXandModeToDXfromROMVARS
262;   Parameters:
263;       DS:DI:      Ptr to Disk Parameter Table
264;   Returns:
265;       AX:         User defined P-CHS Cylinders or LBA low word
266;       BX:         User defined P-CHS Heads and Sectors or LBA high word
267;       DX:         Translate mode or TRANSLATEMODE_AUTO
268;       CX:         FLG_DRVPARAMS_USERCHS if user defined CHS in BX:AX
269;                   FLG_DRVPARAMS_USERLBA if user defined LBA in BX:AX
270;                   Zero if user has not defined capacity
271;   Corrupts registers:
272;       Nothing
273;--------------------------------------------------------------------
274GetUserDefinedCapacityToBXAXandFlagsToCXandModeToDXfromROMVARS:
275    call    AccessDPT_GetPointerToDRVPARAMStoCSBX
276
277    ; Get settings
278    mov     cx, [cs:bx+DRVPARAMS.wFlags]
279    mov     dx, cx
280    and     cx, BYTE FLG_DRVPARAMS_USERCHS | FLG_DRVPARAMS_USERLBA
281    and     dx, BYTE MASK_DRVPARAMS_TRANSLATEMODE
282    eSHR_IM dx, TRANSLATEMODE_FIELD_POSITION
283
284    ; Get capacity
285    mov     ax, [cs:bx+DRVPARAMS.wCylinders]        ; Or .dwMaximumLBA
286    mov     bx, [cs:bx+DRVPARAMS.wHeadsAndSectors]  ; Or .dwMaximumLBA+2
287    ret
288
289
290%ifdef MODULE_EBIOS
291;--------------------------------------------------------------------
292; StoreLba48AddressingFromCLandTotalSectorCountFromBXDXAX
293;   Parameters:
294;       BX:DX:AX:   Total Sector Count
295;       CL:         FLGL_DPT_LBA48 if LBA48 supported
296;       DS:DI:      Ptr to Disk Parameter Table
297;   Returns:
298;       Nothing
299;   Corrupts registers:
300;       CL
301;--------------------------------------------------------------------
302StoreLba48AddressingFromCLandTotalSectorCountFromBXDXAX:
303    or      cl, FLGL_DPT_LBA_AND_EBIOS_SUPPORTED
304    and     BYTE [di+DPT.bFlagsLow], ~FLGL_DPT_LBA48
305    or      [di+DPT.bFlagsLow], cl
306    mov     [di+DPT.twLbaSectors], ax
307    mov     [di+DPT.twLbaSectors+2], dx
308    mov     [di+DPT.twLbaSectors+4], bx
309    ret
310%endif ; MODULE_EBIOS
Note: See TracBrowser for help on using the repository browser.