source: xtideuniversalbios/trunk/XTIDE_Universal_BIOS/Src/Handlers/Int13h/Tools/Address.asm@ 389

Last change on this file since 389 was 376, checked in by gregli@…, 12 years ago

WIDE checkin... Added copyright and license information to sorce files, as per the GPL instructions for usage.

File size: 6.4 KB
Line 
1; Project name : XTIDE Universal BIOS
2; Description : Functions for address translations.
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; Address_ExtractLCHSparametersFromOldInt13hAddress
25; Parameters:
26; CH: Cylinder number, bits 7...0
27; CL: Bits 7...6: Cylinder number bits 9 and 8
28; Bits 5...0: Sector number
29; DH: Head number
30; Returns:
31; BL: Sector number (1...63)
32; BH: Head number (0...255)
33; CX: Cylinder number (0...1023)
34; Corrupts registers:
35; Nothing
36;--------------------------------------------------------------------
37ALIGN JUMP_ALIGN
38Address_ExtractLCHSparametersFromOldInt13hAddress:
39 mov bl, cl ; Copy sector number...
40 and bl, 3Fh ; ...and limit to 1...63
41 sub cl, bl ; Remove from cylinder number high
42 eROL_IM cl, 2 ; High bits to beginning
43 mov bh, dh ; Copy Head number
44 xchg cl, ch ; Cylinder number now in CX
45 ret
46
47
48;---------------------------------------------------------------------
49; Converts LCHS parameters to IDE P-CHS parameters.
50; PCylinder = (LCylinder << n) + (LHead / PHeadCount)
51; PHead = LHead % PHeadCount
52; PSector = LSector
53;
54; Address_ConvertLCHStoPCHS:
55; Parameters:
56; BL: Sector number (1...63)
57; BH: Head number (0...255)
58; CX: Cylinder number (0...1023)
59; DS:DI: Ptr to Disk Parameter Table
60; Returns:
61; BL: Sector number (1...63)
62; BH: Head number (0...15)
63; CX: Cylinder number (0...16382)
64; Corrupts registers:
65; AX, DX
66;--------------------------------------------------------------------
67ALIGN JUMP_ALIGN
68ConvertLCHStoPCHS:
69 ; LHead / PHeadCount and LHead % PHeadCount
70 eMOVZX ax, bh ; Copy L-CHS Head number to AX
71 div BYTE [di+DPT.bPchsHeads]; AL = LHead / PHeadCount, AH = LHead % PHeadCount
72 mov bh, ah ; Copy P-CHS Head number to BH
73 xor ah, ah ; AX = LHead / PHeadCount
74
75 ; (LCylinder << n) + (LHead / PHeadCount)
76 mov dx, cx ; Copy L-CHS Cylinder number to DX
77 mov cl, [di+DPT.bFlagsLow] ; Load shift count
78 and cl, MASKL_DPT_CHS_SHIFT_COUNT
79 shl dx, cl ; DX = LCylinder << n
80 add ax, dx ; AX = P-CHS Cylinder number
81 xchg cx, ax ; Move P-CHS Cylinder number to CX
82DoNotConvertLCHS:
83 ret
84
85;--------------------------------------------------------------------
86; Address_OldInt13hAddressToIdeAddress
87; Parameters:
88; CH: Cylinder number, bits 7...0
89; CL: Bits 7...6: Cylinder number bits 9 and 8
90; Bits 5...0: Starting sector number (1...63)
91; DH: Starting head number (0...255)
92; DS:DI: Ptr to DPT
93; Returns:
94; BL: LBA Low Register / Sector Number Register (LBA 7...0)
95; CL: LBA Mid Register / Low Cylinder Register (LBA 15...8)
96; CH: LBA High Register / High Cylinder Register (LBA 23...16)
97; BH: Drive and Head Register (LBA 27...24)
98; Corrupts registers:
99; AX, DX
100;--------------------------------------------------------------------
101ALIGN JUMP_ALIGN
102Address_OldInt13hAddressToIdeAddress:
103 call Address_ExtractLCHSparametersFromOldInt13hAddress
104
105 AccessDPT_GetUnshiftedAddressModeToALZF
106
107;;; 0: ADDR_DPT_LCHS
108 jz DoNotConvertLCHS
109
110;;; 1: ADDR_DPT_PCHS
111 ;
112 ; Since we are only checking for zero, we can do our math in the high order bits,
113 ; in this case effectively subtracting 1 from the address mode.
114 ;
115 sub al,(1<<ADDRESSING_MODE_FIELD_POSITION)
116 jz ConvertLCHStoPCHS
117
118;;; 2: ADDR_DPT_LBA28 and 3: ADDR_DPT_LBA48
119 ; Fall through to ConvertLCHStoLBARegisterValues
120
121;---------------------------------------------------------------------
122; Converts LCHS parameters to 28-bit LBA address.
123; Only 24-bits are used since LHCS to LBA28 conversion has 8.4GB limit.
124; LBA = ((cylToSeek*headsPerCyl+headToSeek)*sectPerTrack)+sectToSeek-1
125;
126; Returned address is in same registers that
127; Address_DoNotConvertLCHS and Address_ConvertLCHStoPCHS returns.
128;
129; ConvertLCHStoLBARegisterValues:
130; Parameters:
131; BL: Sector number (1...63)
132; BH: Head number (0...255)
133; CX: Cylinder number (0...1023)
134; DS:DI: Ptr to Disk Parameter Table
135; Returns:
136; BL: LBA Low Register / Sector Number Register (LBA 7...0)
137; CL: LBA Mid Register / Low Cylinder Register (LBA 15...8)
138; CH: LBA High Register / High Cylinder Register (LBA 23...16)
139; BH: Drive and Head Register (LBA 27...24)
140; Corrupts registers:
141; AX, DX
142;--------------------------------------------------------------------
143ALIGN JUMP_ALIGN
144ConvertLCHStoLBARegisterValues:
145 ; cylToSeek*headsPerCyl (18-bit result)
146 mov ax, LBA_ASSIST_SPT ; Load Sectors per Track
147 xchg cx, ax ; Cylinder number to AX, Sectors per Track to CX
148
149%ifdef USE_386
150 movzx dx, [di+DPT.bLbaHeads]
151%else
152 cwd
153 mov dl, [di+DPT.bLbaHeads]
154%endif
155 mul dx ; DX:AX = cylToSeek*headsPerCyl
156
157 ; +=headToSeek (18-bit result)
158 add al, bh ; Add Head number to DX:AX
159 adc ah, dh ; DH = Zero after previous multiplication
160 adc dl, dh
161
162 ; *=sectPerTrack (18-bit by 6-bit multiplication with 24-bit result)
163 xchg ax, dx ; Hiword to AX, loword to DX
164 mul cl ; AX = hiword * Sectors per Track
165 mov bh, al ; Backup hiword * Sectors per Track
166 xchg ax, dx ; Loword back to AX
167 mul cx ; DX:AX = loword * Sectors per Track
168 add dl, bh ; DX:AX = (cylToSeek*headsPerCyl+headToSeek)*sectPerTrack
169
170 ; +=sectToSeek-1 (24-bit result)
171 xor bh, bh ; Sector number now in BX
172 dec bx ; sectToSeek-=1
173 add ax, bx ; Add to loword
174 adc dl, bh ; Add possible carry to byte2, BH=zero
175
176 ; Copy DX:AX to proper return registers
177 xchg bx, ax ; BL = Sector Number Register (LBA 7...0)
178 mov cl, bh ; Low Cylinder Register (LBA 15...8)
179 mov ch, dl ; High Cylinder Register (LBA 23...16)
180 mov bh, dh ; Drive and Head Register (LBA 27...24)
181 ret
Note: See TracBrowser for help on using the repository browser.