Fixed unexpected timeout in Usb MassStorage Driver.
[mirror_edk2.git] / MdeModulePkg / Bus / Usb / UsbMassStorageDxe / UsbMassBoot.h
1 /** @file
2
3 Copyright (c) 2007, Intel Corporation
4 All rights reserved. This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
8
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
11
12 Module Name:
13
14 UsbMassBoot.h
15
16 Abstract:
17
18 The definition of command and data of the USB mass storage for
19 bootability command set.
20
21 Revision History
22
23
24 **/
25
26 #ifndef _EFI_USB_MASS_BOOT_H_
27 #define _EFI_USB_MASS_BOOT_H_
28
29 enum {
30 //
31 // The opcodes of various usb boot commands:
32 // INQUIRY/REQUEST_SENSE are "No Timeout Commands" as specified
33 // by MMC command set. Others are "Group 1 Timeout Commands". That
34 // is they should be retried if driver is ready.
35 // We can't use the Peripheral Device Type in Inquiry data to
36 // determine the timeout used. For example, both floppy and flash
37 // are likely set their PDT to 0, or Direct Access Device.
38 //
39 USB_BOOT_INQUIRY_OPCODE = 0x12,
40 USB_BOOT_REQUEST_SENSE_OPCODE = 0x03,
41 USB_BOOT_MODE_SENSE10_OPCODE = 0x5A,
42 USB_BOOT_READ_CAPACITY_OPCODE = 0x25,
43 USB_BOOT_TEST_UNIT_READY_OPCODE = 0x00,
44 USB_BOOT_READ10_OPCODE = 0x28,
45 USB_BOOT_WRITE10_OPCODE = 0x2A,
46
47 USB_SCSI_MODE_SENSE6_OPCODE = 0x1A,
48
49 //
50 // The Sense Key part of the sense data. Sense data has three levels:
51 // Sense key, Additional Sense Code and Additional Sense Code Qualifier
52 //
53 USB_BOOT_SENSE_NO_SENSE = 0x00, // No sense key
54 USB_BOOT_SENSE_RECOVERED = 0x01, // Last command succeed with recovery actions
55 USB_BOOT_SENSE_NOT_READY = 0x02, // Device not ready
56 USB_BOOT_SNESE_MEDIUM_ERROR = 0X03, // Failed probably because flaw in the media
57 USB_BOOT_SENSE_HARDWARE_ERROR = 0X04, // Non-recoverable hardware failure
58 USB_BOOT_SENSE_ILLEGAL_REQUEST = 0X05, // Illegal parameters in the request
59 USB_BOOT_SENSE_UNIT_ATTENTION = 0X06, // Removable medium may have been changed
60 USB_BOOT_SNESE_DATA_PROTECT = 0X07, // Write protected
61 USB_BOOT_SENSE_BLANK_CHECK = 0X08, // Blank/non-blank medium while reading/writing
62 USB_BOOT_SENSE_VENDOR = 0X09, // Vendor specific sense key
63 USB_BOOT_SENSE_ABORTED = 0X0B, // Command aborted by the device
64 USB_BOOT_SENSE_VOLUME_OVERFLOW = 0x0D, // Partition overflow
65 USB_BOOT_SENSE_MISCOMPARE = 0x0E, // Source data mis-match while verfying.
66
67 USB_BOOT_ASC_NOT_READY = 0x04,
68 USB_BOOT_ASC_NO_MEDIA = 0x3A,
69 USB_BOOT_ASC_MEDIA_CHANGE = 0x28,
70
71 //
72 // Supported PDT codes, or Peripheral Device Type
73 //
74 USB_PDT_DIRECT_ACCESS = 0x00, // Direct access device
75 USB_PDT_CDROM = 0x05, // CDROM
76 USB_PDT_OPTICAL = 0x07, // Non-CD optical disks
77 USB_PDT_SIMPLE_DIRECT = 0x0E, // Simplified direct access device
78
79 //
80 // Other parameters, Max carried size is 512B * 128 = 64KB
81 //
82 USB_BOOT_IO_BLOCKS = 128,
83
84 //
85 // Retry mass command times, set by experience
86 //
87 USB_BOOT_COMMAND_RETRY = 5,
88 USB_BOOT_INIT_MEDIA_RETRY = 5,
89
90 //
91 // Wait for unit ready command, set by experience
92 //
93 USB_BOOT_RETRY_UNIT_READY_STALL = 500 * USB_MASS_1_MILLISECOND,
94
95 //
96 // Mass command timeout, refers to specification[USB20-9.2.6.1]
97 //
98 // USB2.0 Spec define the up-limit timeout 5s for all command. USB floppy,
99 // USB CD-Rom and iPod devices are much slower than USB key when reponse
100 // most of commands, So we set 5s as timeout here.
101 //
102 //
103 USB_BOOT_GENERAL_CMD_TIMEOUT = 5 * USB_MASS_1_SECOND,
104 };
105
106 //
107 // The required commands are INQUIRY, READ CAPACITY, TEST UNIT READY,
108 // READ10, WRITE10, and REQUEST SENSE. The BLOCK_IO protocol uses LBA
109 // so it isn't necessary to issue MODE SENSE / READ FORMAT CAPACITY
110 // command to retrieve the disk gemotrics.
111 //
112 #pragma pack(1)
113 typedef struct {
114 UINT8 OpCode;
115 UINT8 Lun; // Lun (high 3 bits)
116 UINT8 Reserved0[2];
117 UINT8 AllocLen;
118 UINT8 Reserved1;
119 UINT8 Pad[6];
120 } USB_BOOT_INQUIRY_CMD;
121
122 typedef struct {
123 UINT8 Pdt; // Peripheral Device Type (low 5 bits)
124 UINT8 Removable; // Removable Media (highest bit)
125 UINT8 Reserved0[2];
126 UINT8 AddLen; // Additional length
127 UINT8 Reserved1[3];
128 UINT8 VendorID[8];
129 UINT8 ProductID[16];
130 UINT8 ProductRevision[4];
131 } USB_BOOT_INQUIRY_DATA;
132
133 typedef struct {
134 UINT8 OpCode;
135 UINT8 Lun;
136 UINT8 Reserved0[8];
137 UINT8 Pad[2];
138 } USB_BOOT_READ_CAPACITY_CMD;
139
140 typedef struct {
141 UINT8 LastLba[4];
142 UINT8 BlockLen[4];
143 } USB_BOOT_READ_CAPACITY_DATA;
144
145 typedef struct {
146 UINT8 OpCode;
147 UINT8 Lun;
148 UINT8 Reserved[4];
149 UINT8 Pad[6];
150 } USB_BOOT_TEST_UNIT_READY_CMD;
151
152 typedef struct {
153 UINT8 OpCode;
154 UINT8 Lun;
155 UINT8 PageCode;
156 UINT8 Reserved0[4];
157 UINT8 ParaListLenMsb;
158 UINT8 ParaListLenLsb;
159 UINT8 Reserved1;
160 UINT8 Pad[2];
161 } USB_BOOT_MODE_SENSE10_CMD;
162
163 typedef struct {
164 UINT8 ModeDataLenMsb;
165 UINT8 ModeDataLenLsb;
166 UINT8 Reserved0[4];
167 UINT8 BlkDesLenMsb;
168 UINT8 BlkDesLenLsb;
169 } USB_BOOT_MODE_SENSE10_PARA_HEADER;
170
171 typedef struct {
172 UINT8 OpCode;
173 UINT8 Lun; // Lun (High 3 bits)
174 UINT8 Lba[4]; // Logical block address
175 UINT8 Reserved0;
176 UINT8 TransferLen[2]; // Transfer length
177 UINT8 Reserverd1;
178 UINT8 Pad[2];
179 } USB_BOOT_READ10_CMD;
180
181 typedef struct {
182 UINT8 OpCode;
183 UINT8 Lun;
184 UINT8 Lba[4];
185 UINT8 Reserved0;
186 UINT8 TransferLen[2];
187 UINT8 Reserverd1;
188 UINT8 Pad[2];
189 } USB_BOOT_WRITE10_CMD;
190
191 typedef struct {
192 UINT8 OpCode;
193 UINT8 Lun; // Lun (High 3 bits)
194 UINT8 Reserved0[2];
195 UINT8 AllocLen; // Allocation length
196 UINT8 Reserved1;
197 UINT8 Pad[6];
198 } USB_BOOT_REQUEST_SENSE_CMD;
199
200 typedef struct {
201 UINT8 ErrorCode;
202 UINT8 Reserved0;
203 UINT8 SenseKey; // Sense key (low 4 bits)
204 UINT8 Infor[4];
205 UINT8 AddLen; // Additional Sense length, 10
206 UINT8 Reserved1[4];
207 UINT8 ASC; // Additional Sense Code
208 UINT8 ASCQ; // Additional Sense Code Qualifier
209 UINT8 Reserverd2[4];
210 } USB_BOOT_REQUEST_SENSE_DATA;
211
212 typedef struct {
213 UINT8 OpCode;
214 UINT8 Lun;
215 UINT8 PageCode;
216 UINT8 Reserved0;
217 UINT8 AllocateLen;
218 UINT8 Control;
219 } USB_SCSI_MODE_SENSE6_CMD;
220
221 typedef struct {
222 UINT8 ModeDataLen;
223 UINT8 MediumType;
224 UINT8 DevicePara;
225 UINT8 BlkDesLen;
226 } USB_SCSI_MODE_SENSE6_PARA_HEADER;
227 #pragma pack()
228
229 //
230 // Convert a LUN number to that in the command
231 //
232 #define USB_BOOT_LUN(Lun) ((Lun) << 5)
233
234 //
235 // Get the removable, PDT, and sense key bits from the command data
236 //
237 #define USB_BOOT_REMOVABLE(RmbByte) (((RmbByte) & 0x80) != 0)
238 #define USB_BOOT_PDT(Pdt) ((Pdt) & 0x1f)
239 #define USB_BOOT_SENSE_KEY(Key) ((Key) & 0x0f)
240
241 //
242 // Swap the byte sequence of a UINT32. Intel CPU uses little endian
243 // in UEFI environment, but USB boot uses big endian.
244 //
245 #define USB_BOOT_SWAP32(Data32) \
246 ((((Data32) & 0x000000ff) << 24) | (((Data32) & 0xff000000) >> 24) | \
247 (((Data32) & 0x0000ff00) << 8) | (((Data32) & 0x00ff0000) >> 8))
248
249 #define USB_BOOT_SWAP16(Data16) \
250 ((((Data16) & 0x00ff) << 8) | (((Data16) & 0xff00) >> 8))
251
252 EFI_STATUS
253 UsbBootGetParams (
254 IN USB_MASS_DEVICE *UsbMass
255 );
256
257 EFI_STATUS
258 UsbBootIsUnitReady (
259 IN USB_MASS_DEVICE *UsbMass
260 );
261
262 EFI_STATUS
263 UsbBootDetectMedia (
264 IN USB_MASS_DEVICE *UsbMass
265 );
266
267 EFI_STATUS
268 UsbBootReadBlocks (
269 IN USB_MASS_DEVICE *UsbMass,
270 IN UINT32 Lba,
271 IN UINTN TotalBlock,
272 OUT UINT8 *Buffer
273 );
274
275 EFI_STATUS
276 UsbBootWriteBlocks (
277 IN USB_MASS_DEVICE *UsbMass,
278 IN UINT32 Lba,
279 IN UINTN TotalBlock,
280 OUT UINT8 *Buffer
281 );
282 #endif
283