10 FILE_LICENCE ( GPL2_OR_LATER
);
13 #include <gpxe/list.h>
19 * @defgroup int13ops INT 13 operation codes
23 /** Reset disk system */
24 #define INT13_RESET 0x00
25 /** Get status of last operation */
26 #define INT13_GET_LAST_STATUS 0x01
28 #define INT13_READ_SECTORS 0x02
30 #define INT13_WRITE_SECTORS 0x03
31 /** Get drive parameters */
32 #define INT13_GET_PARAMETERS 0x08
34 #define INT13_GET_DISK_TYPE 0x15
35 /** Extensions installation check */
36 #define INT13_EXTENSION_CHECK 0x41
38 #define INT13_EXTENDED_READ 0x42
40 #define INT13_EXTENDED_WRITE 0x43
41 /** Get extended drive parameters */
42 #define INT13_GET_EXTENDED_PARAMETERS 0x48
43 /** Get CD-ROM status / terminate emulation */
44 #define INT13_CDROM_STATUS_TERMINATE 0x4b
49 * @defgroup int13status INT 13 status codes
53 /** Operation completed successfully */
54 #define INT13_STATUS_SUCCESS 0x00
55 /** Invalid function or parameter */
56 #define INT13_STATUS_INVALID 0x01
58 #define INT13_STATUS_READ_ERROR 0x04
60 #define INT13_STATUS_WRITE_ERROR 0xcc
64 /** Block size for non-extended INT 13 calls */
65 #define INT13_BLKSIZE 512
67 /** An INT 13 emulated drive */
69 /** List of all registered drives */
70 struct list_head list
;
72 /** Underlying block device */
73 struct block_device
*blockdev
;
75 /** BIOS in-use drive number (0x80-0xff) */
77 /** BIOS natural drive number (0x80-0xff)
79 * This is the drive number that would have been assigned by
80 * 'naturally' appending the drive to the end of the BIOS
83 * If the emulated drive replaces a preexisting drive, this is
84 * the drive number that the preexisting drive gets remapped
87 unsigned int natural_drive
;
89 /** Number of cylinders
91 * The cylinder number field in an INT 13 call is ten bits
92 * wide, giving a maximum of 1024 cylinders. Conventionally,
93 * when the 7.8GB limit of a CHS address is exceeded, it is
94 * the number of cylinders that is increased beyond the
97 unsigned int cylinders
;
100 * The head number field in an INT 13 call is eight bits wide,
101 * giving a maximum of 256 heads. However, apparently all
102 * versions of MS-DOS up to and including Win95 fail with 256
103 * heads, so the maximum encountered in practice is 255.
106 /** Number of sectors per track
108 * The sector number field in an INT 13 call is six bits wide,
109 * giving a maximum of 63 sectors, since sector numbering
110 * (unlike head and cylinder numbering) starts at 1, not 0.
112 unsigned int sectors_per_track
;
114 /** Status of last operation */
118 /** An INT 13 disk address packet */
119 struct int13_disk_address
{
120 /** Size of the packet, in bytes */
122 /** Reserved, must be zero */
127 struct segoff buffer
;
128 /** Starting block number */
130 /** Data buffer (EDD-3.0 only) */
131 uint64_t buffer_phys
;
132 } __attribute__ (( packed
));
134 /** INT 13 disk parameters */
135 struct int13_disk_parameters
{
136 /** Size of this structure */
140 /** Number of cylinders */
142 /** Number of heads */
144 /** Number of sectors per track */
145 uint32_t sectors_per_track
;
146 /** Total number of sectors on drive */
148 /** Bytes per sector */
149 uint16_t sector_size
;
151 } __attribute__ (( packed
));
154 * @defgroup int13types INT 13 disk types
159 #define INT13_DISK_TYPE_NONE 0x00
160 /** Floppy without change-line support */
161 #define INT13_DISK_TYPE_FDD 0x01
162 /** Floppy with change-line support */
163 #define INT13_DISK_TYPE_FDD_CL 0x02
165 #define INT13_DISK_TYPE_HDD 0x03
170 * @defgroup int13flags INT 13 disk parameter flags
174 /** DMA boundary errors handled transparently */
175 #define INT13_FL_DMA_TRANSPARENT 0x01
176 /** CHS information is valid */
177 #define INT13_FL_CHS_VALID 0x02
178 /** Removable drive */
179 #define INT13_FL_REMOVABLE 0x04
180 /** Write with verify supported */
181 #define INT13_FL_VERIFIABLE 0x08
182 /** Has change-line supported (valid only for removable drives) */
183 #define INT13_FL_CHANGE_LINE 0x10
184 /** Drive can be locked (valid only for removable drives) */
185 #define INT13_FL_LOCKABLE 0x20
186 /** CHS is max possible, not current media (valid only for removable drives) */
187 #define INT13_FL_CHS_MAX 0x40
192 * @defgroup int13exts INT 13 extension flags
196 /** Extended disk access functions supported */
197 #define INT13_EXTENSION_LINEAR 0x01
198 /** Removable drive functions supported */
199 #define INT13_EXTENSION_REMOVABLE 0x02
200 /** EDD functions supported */
201 #define INT13_EXTENSION_EDD 0x04
206 * @defgroup int13vers INT 13 extension versions
210 /** INT13 extensions version 1.x */
211 #define INT13_EXTENSION_VER_1_X 0x01
212 /** INT13 extensions version 2.0 (EDD-1.0) */
213 #define INT13_EXTENSION_VER_2_0 0x20
214 /** INT13 extensions version 2.1 (EDD-1.1) */
215 #define INT13_EXTENSION_VER_2_1 0x21
216 /** INT13 extensions version 3.0 (EDD-3.0) */
217 #define INT13_EXTENSION_VER_3_0 0x30
221 /** Bootable CD-ROM specification packet */
222 struct int13_cdrom_specification
{
223 /** Size of packet in bytes */
225 /** Boot media type */
229 /** CD-ROM controller number */
231 /** LBA of disk image to emulate */
233 /** Device specification */
235 /** Segment of 3K buffer for caching CD-ROM reads */
236 uint16_t cache_segment
;
237 /** Load segment for initial boot image */
238 uint16_t load_segment
;
239 /** Number of 512-byte sectors to load */
240 uint16_t load_sectors
;
241 /** Low 8 bits of cylinder number */
243 /** Sector number, plus high 2 bits of cylinder number */
247 } __attribute__ (( packed
));
249 /** A C/H/S address within a partition table entry */
250 struct partition_chs
{
253 /** Sector number, plus high 2 bits of cylinder number */
255 /** Low 8 bits of cylinder number */
257 } __attribute__ (( packed
));
259 #define PART_HEAD(chs) ( (chs).head )
260 #define PART_SECTOR(chs) ( (chs).cyl_sector & 0x3f )
261 #define PART_CYLINDER(chs) ( (chs).cyl | ( ( (chs).cyl_sector & 0xc0 ) << 2 ) )
263 /** A partition table entry within the MBR */
264 struct partition_table_entry
{
267 /** C/H/S start address */
268 struct partition_chs chs_start
;
269 /** System indicator (partition type) */
271 /** C/H/S end address */
272 struct partition_chs chs_end
;
273 /** Linear start address */
277 } __attribute__ (( packed
));
279 /** A Master Boot Record */
280 struct master_boot_record
{
282 /** Partition table */
283 struct partition_table_entry partitions
[4];
284 /** 0x55aa MBR signature */
286 } __attribute__ (( packed
));
288 extern void register_int13_drive ( struct int13_drive
*drive
);
289 extern void unregister_int13_drive ( struct int13_drive
*drive
);
290 extern int int13_boot ( unsigned int drive
);