Fix warnings generated by GCC.
[edk2.git] / DuetPkg / BootSector / Gpt.S
blobef70a80a2f99b4954a3f8f7b75dd65ed4f9d6665
1 #------------------------------------------------------------------------------\r
2 #*\r
3 #*   Copyright 2006 - 2007, Intel Corporation                                                         \r
4 #*   All rights reserved. This program and the accompanying materials                          \r
5 #*   are licensed and made available under the terms and conditions of the BSD License         \r
6 #*   which accompanies this distribution.  The full text of the license may be found at        \r
7 #*   http://opensource.org/licenses/bsd-license.php                                            \r
8 #*                                                                                             \r
9 #*   THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,                     \r
10 #*   WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.             \r
11 #*   \r
12 #*    gpt.asm\r
13 #*  \r
14 #*   Abstract:\r
15 #*\r
16 #------------------------------------------------------------------------------\r
18     #.MODEL small\r
19 #   .dosseg\r
20     .stack: \r
21     .486p: \r
22     .code: \r
24 .equ                      BLOCK_SIZE,  0x0200\r
25 .equ                      BLOCK_MASK,  0x01ff\r
26 .equ                      BLOCK_SHIFT, 9\r
28 # ****************************************************************************\r
29 # Code loaded by BIOS at 0x0000:0x7C00\r
30 # ****************************************************************************\r
32         .org 0x00\r
33 Start: \r
35 # ****************************************************************************\r
36 # Start Print\r
37 # ****************************************************************************\r
39     movw $0xb800, %ax\r
40     movw %ax, %es\r
41     movw $0x7c0, %ax\r
42     movw %ax, %ds\r
43     leaw %cs:StartString, %si\r
44     movw $10, %cx\r
45     movw $160, %di\r
46     rep\r
47     movsw\r
49 # ****************************************************************************\r
50 # Print over\r
51 # ****************************************************************************\r
53 # ****************************************************************************\r
54 # Initialize segment registers and copy code at 0x0000:0x7c00 to 0x0000:0x0600\r
55 # ****************************************************************************\r
56         xorw  %ax, %ax                  # AX = 0x0000  \r
57         movw  $0x7c00, %bx              # BX = 0x7C00\r
58         movw  $0x600, %bp               # BP = 0x0600\r
59         movw  RelocatedStart, %si       # SI = Offset(RelocatedStart)\r
60         movw  $0x200, %cx               # CX = 0x0200\r
61         subw  %si, %cx                  # CS = 0x0200 - Offset(RelocatedStart)\r
62         leaw  (%bp,%si,), %di           # DI = 0x0600 + Offset(RelocatedStart)\r
63         leaw  (%bx,%si,), %si           # BX = 0x7C00 + Offset(RelocatedStart)\r
64         movw  %ax, %ss                  # SS = 0x0000\r
65         movw  %bx, %sp                  # SP = 0x7C00\r
66         movw  %ax, %es                  # ES = 0x0000\r
67         movw  %ax, %ds                  # DS = 0x0000\r
68         pushw %ax                       # PUSH 0x0000\r
69         pushw %di                       # PUSH 0x0600 + Offset(RelocatedStart)\r
70         cld                             # Clear the direction flag\r
71         rep\r
72         movsb                           # Copy 0x0200 bytes from 0x7C00 to 0x0600\r
73         retl                            # JMP 0x0000:0x0600 + Offset(RelocatedStart)\r
75 # ****************************************************************************\r
76 # Code relocated to 0x0000:0x0600\r
77 # ****************************************************************************\r
79 RelocatedStart: \r
80 # ****************************************************************************\r
81 # Get Driver Parameters to 0x0000:0x7BFC\r
82 # ****************************************************************************\r
83         xorw  %ax, %ax      # ax = 0\r
84         movw  %ax, %ss      # ss = 0\r
85         addw  $0x1000, %ax\r
86         movw  %ax, %ds\r
88         movw  $0x7c00, %sp  # sp = 0x7c00\r
89         movw  %sp, %bp      # bp = 0x7c00\r
91         movb  $8, %ah                             # ah = 8 - Get Drive Parameters Function\r
92         movb  %dl, PhysicalDrive(%bp)             # BBS defines that BIOS would pass the booting driver number to the loader through DL\r
93         int   $0x13                               # Get Drive Parameters\r
94         xorw  %ax, %ax                # ax = 0\r
95         movb  %dh, %al                # al = dh\r
96         incb  %al                     # MaxHead = al + 1\r
97         pushw %ax                     # 0000:7bfe = MaxHead\r
98         movb  %cl, %al                # al = cl\r
99         andb  $0x3f, %al              # MaxSector = al & 0x3f\r
100         pushw %ax                     # 0000:7bfc = MaxSector\r
102 # ****************************************************************************\r
103 # Read GPT Header from hard disk to 0x0000:0x0800\r
104 # ****************************************************************************\r
105         xorw    %ax, %ax\r
106         movw    %ax, %es                          # Read to 0x0000:0x0800\r
107         movw    $0x800, %di                       # Read to 0x0000:0x0800\r
108         movl    $1, %eax                          # Read LBA #1\r
109         movl    $0, %edx                          # Read LBA #1\r
110         movw    $1, %bx                           # Read 1 Block\r
111         pushw   %es\r
112         call    ReadBlocks\r
113         popw    %es\r
115 # ****************************************************************************\r
116 # Read Target GPT Entry from hard disk to 0x0000:0x0A00\r
117 # ****************************************************************************\r
118         cmpl  $0x20494645, %es:(%di)              # Check for "EFI "\r
119         jne   BadGpt\r
120         cmpl  $0x54524150, %es:4(%di)             # Check for "PART"\r
121         jne   BadGpt\r
122         cmpl  $0x00010000, %es:8(%di)             # Check Revision - 0x10000\r
123         jne   BadGpt\r
125         movl  %es:84(%di), %eax                   # EAX = SizeOfPartitionEntry\r
126         mulb  GptPartitionIndicator(%bp)          # EAX = SizeOfPartitionEntry * GptPartitionIndicator\r
127         movl  %eax, %edx                          # EDX = SizeOfPartitionEntry * GptPartitionIndicator\r
128         shrl  $BLOCK_SHIFT, %eax                  # EAX = (SizeOfPartitionEntry * GptPartitionIndicator) / BLOCK_SIZE\r
129         andl  $BLOCK_MASK, %edx                   # EDX = Targer PartitionEntryLBA Offset\r
130                                                   #     = (SizeOfPartitionEntry * GptPartitionIndicator) % BLOCK_SIZE\r
131         pushl %edx\r
132         movl  %es:72(%di), %ecx                   # ECX = PartitionEntryLBA (Low)\r
133         movl  %es:76(%di), %ebx                   # EBX = PartitionEntryLBA (High)\r
134         addl  %ecx, %eax                          # EAX = Target PartitionEntryLBA (Low)\r
135                                                   #     = (PartitionEntryLBA + \r
136                                                   #        (SizeOfPartitionEntry * GptPartitionIndicator) / BLOCK_SIZE)\r
137         adcl  %ebx, %edx                          # EDX = Target PartitionEntryLBA (High)\r
139         movw  $0xA00, %di                         # Read to 0x0000:0x0A00\r
140         movw  $1, %bx                             # Read 1 Block\r
141         pushw %es\r
142         call  ReadBlocks\r
143         popw  %es\r
145 # ****************************************************************************\r
146 # Read Target DBR from hard disk to 0x0000:0x7C00\r
147 # ****************************************************************************\r
148         popl  %edx                                # EDX = (SizeOfPartitionEntry * GptPartitionIndicator) % BLOCK_SIZE\r
149         addw  %dx, %di                            # DI = Targer PartitionEntryLBA Offset\r
150         cmpl  $0xC12A7328, %es:(%di)              # Check for EFI System Partition "C12A7328-F81F-11d2-BA4B-00A0C93EC93B"\r
151         jne   BadGpt\r
152         cmpl  $0x11d2F81F, %es:4(%di)             # \r
153         jne   BadGpt\r
154         cmpl  $0xA0004BBA, %es:8(%di)             # \r
155         jne   BadGpt\r
156         cmpl  $0x3BC93EC9, %es:0xc(%di)           # \r
157         jne   BadGpt\r
159         movl  %es:32(%di), %eax                   # EAX = StartingLBA (Low)\r
160         movl  %es:36(%di), %edx                   # EDX = StartingLBA (High)\r
161         movw  $0x7C00, %di                        # Read to 0x0000:0x7C00\r
162         movw  $1, %bx                             # Read 1 Block\r
163         call  ReadBlocks\r
165 # ****************************************************************************\r
166 # Transfer control to BootSector - Jump to 0x0000:0x7C00\r
167 # ****************************************************************************\r
168         xorw  %ax, %ax\r
169         pushw %ax                       # PUSH 0x0000\r
170         movw  $0x7c00, %di\r
171         pushw %di                       # PUSH 0x7C00\r
172         retl                            # JMP 0x0000:0x7C00\r
174 # ****************************************************************************\r
175 # ReadBlocks - Reads a set of blocks from a block device\r
177 # EDX:EAX = Start LBA\r
178 # BX      = Number of Blocks to Read (must < 127)\r
179 # ES:DI   = Buffer to store sectors read from disk\r
180 # ****************************************************************************\r
182 # si = DiskAddressPacket\r
184 ReadBlocks: \r
185         pushal\r
186         pushw %ds\r
187         xorw  %cx, %cx\r
188         movw  %cx, %ds\r
189         movw  $0x600, %bp                       # bp = 0x600\r
190         leaw  AddressPacket(%bp), %si\r
191         movb  %bl, %ds:2(%si)                   #    02 = Number Of Block transfered\r
192         movw  %di, %ds:4(%si)                   #    04 = Transfer Buffer Offset\r
193         movw  %es, %ds:6(%si)                   #    06 = Transfer Buffer Segment\r
194         movl  %eax, %ds:8(%si)                  #    08 = Starting LBA (Low)\r
195         movl  %edx, %ds:0xc(%si)                #    0C = Starting LBA (High)\r
196         movb  $0x42, %ah                        # ah = Function 42\r
197         movb  PhysicalDrive(%bp), %dl           # dl = Drive Number\r
198         int   $0x13\r
199         jc    BadGpt\r
200         popw  %ds\r
201         popal\r
202         ret\r
204 # ****************************************************************************\r
205 # Address Packet used by ReadBlocks\r
206 # ****************************************************************************\r
207 AddressPacket: \r
208         .byte 0x10                      # Size of address packet\r
209         .byte 0x0                       # Reserved.  Must be 0\r
210         .byte 0x1                       # Read blocks at a time (To be fixed each times)\r
211         .byte 0x0                       # Reserved.  Must be 0\r
212         .word 0x000                     # Destination Address offset (To be fixed each times)\r
213         .word 0x000                     # Destination Address segment (To be fixed each times)\r
214 AddressPacketLba: \r
215         .long 0x0,0x0                   # Start LBA (To be fixed each times)\r
216 AddressPacketEnd: \r
218 # ****************************************************************************\r
219 # ERROR Condition:\r
220 # ****************************************************************************\r
222 BadGpt: \r
223     movw $0xb800, %ax\r
224     movw %ax, %es\r
225     movw $0x60, %ax\r
226     movw %ax, %ds\r
227     leaw %cs:ErrorString, %si\r
228     movw $10, %cx\r
229     movw $320, %di\r
230     rep\r
231     movsw\r
232 Halt: \r
233     jmp   Halt\r
235 StartString: \r
236     .byte 'G', 0x0c, 'P', 0x0c, 'T', 0x0c, ' ', 0x0c, 'S', 0x0c, 't', 0x0c, 'a', 0x0c, 'r', 0x0c, 't', 0x0c, '!', 0x0c\r
237 ErrorString: \r
238     .byte 'G', 0x0c, 'P', 0x0c, 'T', 0x0c, ' ', 0x0c, 'E', 0x0c, 'r', 0x0c, 'r', 0x0c, 'o', 0x0c, 'r', 0x0c, '!', 0x0c\r
240 # ****************************************************************************\r
241 # PhysicalDrive - Used to indicate which disk to be boot\r
242 #                 Can be patched by tool\r
243 # ****************************************************************************\r
244     # .org   0x01B6 # Just for passing build.\r
245 PhysicalDrive:        .byte 0x80\r
247 # ****************************************************************************\r
248 # GptPartitionIndicator - Used to indicate which GPT partition to be boot\r
249 #                         Can be patched by tool\r
250 # ****************************************************************************\r
251    # .org   0x01B7  # Just for passing build.\r
252 GptPartitionIndicator: .byte 0\r
254 # ****************************************************************************\r
255 # Unique MBR signature\r
256 # ****************************************************************************\r
257    # .org   0x01B8  # Just for passing build.\r
258     .ascii "DUET"\r
260 # ****************************************************************************\r
261 # Unknown\r
262 # ****************************************************************************\r
263     # .org   0x01BC  # Just for passing build.\r
264     .word 0\r
266 # ****************************************************************************\r
267 # PMBR Entry - Can be patched by tool\r
268 # ****************************************************************************\r
269     # .org   0x01BE  # Just for passing build.\r
270     .byte 0       # Boot Indicator\r
271     .byte 0xff    # Start Header\r
272     .byte 0xff    # Start Sector\r
273     .byte 0xff    # Start Track\r
274     .byte 0xee    # OS Type\r
275     .byte 0xff    # End Header\r
276     .byte 0xff    # End Sector\r
277     .byte 0xff    # End Track\r
278     .long 1       # Starting LBA\r
279     .long 0xFFFFFFFF # End LBA\r
281     # .org   0x01CE  # Just for passing build.\r
282     .long  0,0,0,0\r
283     # .org   0x01DE  # Just for passing build.\r
284     .long  0,0,0,0\r
285     # .org   0x01EE  # Just for passing build.\r
286     .long 0,0,0,0\r
288 # ****************************************************************************\r
289 # Sector Signature\r
290 # ****************************************************************************\r
292   # .org      0x01FE  # Just for passing build.\r
293 SectorSignature: \r
294   .word     0xaa55      # Boot Sector Signature\r