]> git.proxmox.com Git - mirror_edk2.git/blame - EdkModulePkg/Bus/Usb/UsbBus/Dxe/usbio.c
Add DevicePathUtilities DevicePathToText DevciePathFromText USB2HostController protocols
[mirror_edk2.git] / EdkModulePkg / Bus / Usb / UsbBus / Dxe / usbio.c
CommitLineData
878ddf1f 1/*++\r
2\r
3Copyright (c) 2006, Intel Corporation \r
4All rights reserved. This program and the accompanying materials \r
5are licensed and made available under the terms and conditions of the BSD License \r
6which accompanies this distribution. The full text of the license may be found at \r
7http://opensource.org/licenses/bsd-license.php \r
8 \r
9THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, \r
10WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. \r
11\r
12 Module Name:\r
13\r
14 UsbIo.c\r
15\r
16 Abstract:\r
17\r
18 USB I/O Abstraction Driver\r
19\r
20 Revision History\r
21\r
22--*/\r
23\r
24#include "usbbus.h"\r
25\r
26//\r
27// USB I/O Support Function Prototypes\r
28//\r
29STATIC\r
30EFI_STATUS\r
31EFIAPI\r
32UsbControlTransfer (\r
33 IN EFI_USB_IO_PROTOCOL *This,\r
34 IN EFI_USB_DEVICE_REQUEST *Request,\r
35 IN EFI_USB_DATA_DIRECTION Direction,\r
36 IN UINT32 Timeout,\r
37 IN OUT VOID *Data, OPTIONAL\r
38 IN UINTN DataLength, OPTIONAL\r
39 OUT UINT32 *Status\r
40 );\r
41\r
42STATIC\r
43EFI_STATUS\r
44EFIAPI\r
45UsbBulkTransfer (\r
46 IN EFI_USB_IO_PROTOCOL *This,\r
47 IN UINT8 DeviceEndpoint,\r
48 IN OUT VOID *Data,\r
49 IN OUT UINTN *DataLength,\r
50 IN UINTN Timeout,\r
51 OUT UINT32 *Status\r
52 );\r
53\r
54STATIC\r
55EFI_STATUS\r
56EFIAPI\r
57UsbAsyncInterruptTransfer (\r
58 IN EFI_USB_IO_PROTOCOL * This,\r
59 IN UINT8 DeviceEndpoint,\r
60 IN BOOLEAN IsNewTransfer,\r
61 IN UINTN PollingInterval, OPTIONAL\r
62 IN UINTN DataLength, OPTIONAL\r
63 IN EFI_ASYNC_USB_TRANSFER_CALLBACK InterruptCallBack, OPTIONAL\r
64 IN VOID *Context OPTIONAL\r
65 );\r
66\r
67STATIC\r
68EFI_STATUS\r
69EFIAPI\r
70UsbSyncInterruptTransfer (\r
71 IN EFI_USB_IO_PROTOCOL *This,\r
72 IN UINT8 DeviceEndpoint,\r
73 IN OUT VOID *Data,\r
74 IN OUT UINTN *DataLength,\r
75 IN UINTN Timeout,\r
76 OUT UINT32 *Status\r
77 );\r
78\r
79STATIC\r
80EFI_STATUS\r
81EFIAPI\r
82UsbIsochronousTransfer (\r
83 IN EFI_USB_IO_PROTOCOL *This,\r
84 IN UINT8 DeviceEndpoint,\r
85 IN OUT VOID *Data,\r
86 IN UINTN DataLength,\r
87 OUT UINT32 *Status\r
88 );\r
89\r
90STATIC\r
91EFI_STATUS\r
92EFIAPI\r
93UsbAsyncIsochronousTransfer (\r
94 IN EFI_USB_IO_PROTOCOL * This,\r
95 IN UINT8 DeviceEndpoint,\r
96 IN OUT VOID *Data,\r
97 IN UINTN DataLength,\r
98 IN EFI_ASYNC_USB_TRANSFER_CALLBACK IsochronousCallBack,\r
99 IN VOID *Context OPTIONAL\r
100 );\r
101\r
102extern\r
103EFI_STATUS\r
104EFIAPI\r
105UsbPortReset (\r
106 IN EFI_USB_IO_PROTOCOL *This\r
107 );\r
108\r
109STATIC\r
110EFI_STATUS\r
111EFIAPI\r
112UsbGetDeviceDescriptor (\r
113 IN EFI_USB_IO_PROTOCOL *This,\r
114 OUT EFI_USB_DEVICE_DESCRIPTOR *DeviceDescriptor\r
115 );\r
116\r
117STATIC\r
118EFI_STATUS\r
119EFIAPI\r
120UsbGetActiveConfigDescriptor (\r
121 IN EFI_USB_IO_PROTOCOL *This,\r
122 OUT EFI_USB_CONFIG_DESCRIPTOR *ConfigurationDescriptor\r
123 );\r
124\r
125STATIC\r
126EFI_STATUS\r
127EFIAPI\r
128UsbGetInterfaceDescriptor (\r
129 IN EFI_USB_IO_PROTOCOL *This,\r
130 OUT EFI_USB_INTERFACE_DESCRIPTOR *InterfaceDescriptor\r
131 );\r
132\r
133STATIC\r
134EFI_STATUS\r
135EFIAPI\r
136UsbGetEndpointDescriptor (\r
137 IN EFI_USB_IO_PROTOCOL *This,\r
138 IN UINT8 EndpointIndex,\r
139 OUT EFI_USB_ENDPOINT_DESCRIPTOR *EndpointDescriptor\r
140 );\r
141\r
142STATIC\r
143EFI_STATUS\r
144EFIAPI\r
145UsbGetStringDescriptor (\r
146 IN EFI_USB_IO_PROTOCOL *This,\r
147 IN UINT16 LangID,\r
148 IN UINT8 StringIndex,\r
149 OUT CHAR16 **String\r
150 );\r
151\r
152STATIC\r
153EFI_STATUS\r
154EFIAPI\r
155UsbGetSupportedLanguages (\r
156 IN EFI_USB_IO_PROTOCOL *This,\r
157 OUT UINT16 **LangIDTable,\r
158 OUT UINT16 *TableSize\r
159 );\r
160\r
161//\r
162// USB I/O Interface structure\r
163//\r
164STATIC EFI_USB_IO_PROTOCOL UsbIoInterface = {\r
165 UsbControlTransfer,\r
166 UsbBulkTransfer,\r
167 UsbAsyncInterruptTransfer,\r
168 UsbSyncInterruptTransfer,\r
169 UsbIsochronousTransfer,\r
170 UsbAsyncIsochronousTransfer,\r
171 UsbGetDeviceDescriptor,\r
172 UsbGetActiveConfigDescriptor,\r
173 UsbGetInterfaceDescriptor,\r
174 UsbGetEndpointDescriptor,\r
175 UsbGetStringDescriptor,\r
176 UsbGetSupportedLanguages,\r
177 UsbPortReset\r
178};\r
179\r
180VOID\r
181InitializeUsbIoInstance (\r
182 IN USB_IO_CONTROLLER_DEVICE *UsbIoController\r
183 )\r
184{\r
185 //\r
186 // Copy EFI_USB_IO protocol instance\r
187 //\r
188 CopyMem (\r
189 &UsbIoController->UsbIo,\r
190 &UsbIoInterface,\r
191 sizeof (EFI_USB_IO_PROTOCOL)\r
192 );\r
193}\r
194//\r
195// Implementation\r
196//\r
197STATIC\r
198EFI_STATUS\r
199EFIAPI\r
200UsbControlTransfer (\r
201 IN EFI_USB_IO_PROTOCOL *This,\r
202 IN EFI_USB_DEVICE_REQUEST *Request,\r
203 IN EFI_USB_DATA_DIRECTION Direction,\r
204 IN UINT32 Timeout,\r
205 IN OUT VOID *Data, OPTIONAL\r
206 IN UINTN DataLength, OPTIONAL\r
207 OUT UINT32 *Status\r
208 )\r
209/*++\r
210\r
211 Routine Description:\r
212 This function is used to manage a USB device with a control transfer pipe.\r
213\r
214 Arguments:\r
215 This - Indicates calling context.\r
216 Request - A pointer to the USB device request that will be sent to\r
217 the USB device.\r
218 Direction - Indicates the data direction.\r
219 Data - A pointer to the buffer of data that will be transmitted\r
220 to USB device or received from USB device.\r
221 Timeout - Indicates the transfer should be completed within this time\r
222 frame.\r
223 DataLength - The size, in bytes, of the data buffer specified by Data.\r
224 Status - A pointer to the result of the USB transfer.\r
225\r
226 Returns:\r
227 EFI_SUCCESS\r
228 EFI_INVALID_PARAMETER\r
229 EFI_OUT_OF_RESOURCES\r
230 EFI_TIMEOUT\r
231 EFI_DEVICE_ERROR\r
232\r
233--*/\r
234{\r
235 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
562d2849 236\r
878ddf1f 237 EFI_STATUS RetStatus;\r
562d2849 238 USB_IO_DEVICE *UsbIoDev;\r
878ddf1f 239 UINT8 MaxPacketLength;\r
240 UINT32 TransferResult;\r
241 BOOLEAN Disconnected;\r
242 //\r
243 // Parameters Checking\r
244 //\r
245 if (Status == NULL) {\r
246 return EFI_INVALID_PARAMETER;\r
247 }\r
248 \r
249 //\r
250 // leave the HostController's ControlTransfer\r
251 // to perform other parameters checking\r
252 //\r
253 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
562d2849 254 UsbIoDev = UsbIoController->UsbDevice;\r
255\r
256 MaxPacketLength = UsbIoDev->DeviceDescriptor.MaxPacketSize0;\r
878ddf1f 257\r
258 \r
259 if (Request->Request == USB_DEV_CLEAR_FEATURE && \r
260 Request->RequestType == 0x02 && \r
261 Request->Value == EfiUsbEndpointHalt) {\r
262 //\r
263 //Reduce the remove delay time for system response\r
264 //\r
265 IsDeviceDisconnected (UsbIoController, &Disconnected);\r
266 if (!EFI_ERROR (Status) && Disconnected == TRUE) {\r
267 DEBUG ((gUSBErrorLevel, "Device is disconnected when trying reset\n"));\r
268 return EFI_DEVICE_ERROR;\r
269 }\r
270 }\r
878ddf1f 271 //\r
272 // using HostController's ControlTransfer to complete the request\r
273 //\r
562d2849 274 RetStatus = UsbVirtualHcControlTransfer (\r
275 UsbIoDev->BusController,\r
276 UsbIoDev->DeviceAddress,\r
277 UsbIoDev->DeviceSpeed,\r
278 MaxPacketLength,\r
279 Request,\r
280 Direction,\r
281 Data,\r
282 &DataLength,\r
283 (UINTN) Timeout,\r
284 UsbIoDev->Translator,\r
285 &TransferResult\r
286 );\r
287\r
878ddf1f 288 *Status = TransferResult;\r
289\r
290 if (Request->Request == USB_DEV_CLEAR_FEATURE && \r
291 Request->RequestType == 0x02 && \r
292 Request->Value == EfiUsbEndpointHalt) {\r
293 //\r
294 // This is a UsbClearEndpointHalt request\r
295 // Need to clear data toggle\r
296 // Request.Index == EndpointAddress\r
297 //\r
298 if (!EFI_ERROR (RetStatus) && TransferResult == EFI_USB_NOERROR) {\r
299 SetDataToggleBit (\r
300 This,\r
301 (UINT8) Request->Index,\r
302 0\r
303 );\r
304 }\r
305 }\r
306 return RetStatus;\r
307}\r
308\r
309STATIC\r
310EFI_STATUS\r
311EFIAPI\r
312UsbBulkTransfer (\r
313 IN EFI_USB_IO_PROTOCOL *This,\r
314 IN UINT8 DeviceEndpoint,\r
315 IN OUT VOID *Data,\r
316 IN OUT UINTN *DataLength,\r
317 IN UINTN Timeout,\r
318 OUT UINT32 *Status\r
319 )\r
320/*++\r
321\r
322 Routine Description:\r
323 This function is used to manage a USB device with the bulk transfer pipe.\r
324\r
325 Arguments:\r
326 This - Indicates calling context.\r
327 DeviceEndpoint - The destination USB device endpoint to which the device\r
328 request is being sent.\r
329 Data - A pointer to the buffer of data that will be transmitted\r
330 to USB device or received from USB device.\r
331 DataLength - On input, the size, in bytes, of the data buffer\r
332 specified by Data. On output, the number of bytes that\r
333 were actually transferred.\r
334 Timeout - Indicates the transfer should be completed within this\r
335 time frame.\r
336 Status - This parameter indicates the USB transfer status.\r
337\r
338 Returns:\r
339 EFI_SUCCESS\r
340 EFI_INVALID_PARAMETER\r
341 EFI_OUT_OF_RESOURCES\r
342 EFI_TIMEOUT\r
343 EFI_DEVICE_ERROR\r
344\r
345--*/\r
346{\r
347 USB_IO_DEVICE *UsbIoDev;\r
562d2849 348 UINTN MaxPacketLength;\r
878ddf1f 349 UINT8 DataToggle;\r
350 UINT8 OldToggle;\r
351 EFI_STATUS RetStatus;\r
562d2849 352\r
878ddf1f 353 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
354 ENDPOINT_DESC_LIST_ENTRY *EndPointListEntry;\r
355 UINT32 TransferResult;\r
562d2849 356 UINT8 DataBuffersNumber;\r
357 \r
358 DataBuffersNumber = 1;\r
359 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
360 UsbIoDev = UsbIoController->UsbDevice;\r
878ddf1f 361\r
362 //\r
363 // Parameters Checking\r
364 //\r
365 if ((DeviceEndpoint & 0x7F) == 0) {\r
366 return EFI_INVALID_PARAMETER;\r
367 }\r
368\r
369 if ((DeviceEndpoint & 0x7F) > 15) {\r
370 return EFI_INVALID_PARAMETER;\r
371 }\r
372\r
373 if (Status == NULL) {\r
374 return EFI_INVALID_PARAMETER;\r
375 }\r
376\r
377 EndPointListEntry = FindEndPointListEntry (\r
378 This,\r
379 DeviceEndpoint\r
380 );\r
381\r
382 if (EndPointListEntry == NULL) {\r
383 return EFI_INVALID_PARAMETER;\r
384 }\r
385\r
386 if ((EndPointListEntry->EndpointDescriptor.Attributes & 0x03) != 0x02) {\r
387 return EFI_INVALID_PARAMETER;\r
388 }\r
389 \r
390 //\r
391 // leave the HostController's BulkTransfer\r
392 // to perform other parameters checking\r
393 //\r
394 GetDeviceEndPointMaxPacketLength (\r
395 This,\r
396 DeviceEndpoint,\r
397 &MaxPacketLength\r
398 );\r
399\r
400 GetDataToggleBit (\r
401 This,\r
402 DeviceEndpoint,\r
403 &DataToggle\r
404 );\r
405\r
406 OldToggle = DataToggle;\r
407\r
408 //\r
409 // using HostController's BulkTransfer to complete the request\r
410 //\r
562d2849 411 RetStatus = UsbVirtualHcBulkTransfer (\r
412 UsbIoDev->BusController,\r
413 UsbIoDev->DeviceAddress,\r
414 DeviceEndpoint,\r
415 UsbIoDev->DeviceSpeed,\r
416 MaxPacketLength,\r
417 DataBuffersNumber,\r
418 &Data,\r
419 DataLength,\r
420 &DataToggle,\r
421 Timeout,\r
422 UsbIoDev->Translator,\r
423 &TransferResult\r
424 );\r
878ddf1f 425\r
426 if (OldToggle != DataToggle) {\r
427 //\r
428 // Write the toggle back\r
429 //\r
430 SetDataToggleBit (\r
431 This,\r
432 DeviceEndpoint,\r
433 DataToggle\r
434 );\r
435 }\r
436\r
437 *Status = TransferResult;\r
438\r
439 return RetStatus;\r
440}\r
441\r
442STATIC\r
443EFI_STATUS\r
444EFIAPI\r
445UsbSyncInterruptTransfer (\r
446 IN EFI_USB_IO_PROTOCOL *This,\r
447 IN UINT8 DeviceEndpoint,\r
448 IN OUT VOID *Data,\r
449 IN OUT UINTN *DataLength,\r
450 IN UINTN Timeout,\r
451 OUT UINT32 *Status\r
452 )\r
453/*++\r
454\r
455 Routine Description:\r
456 Usb Sync Interrupt Transfer\r
457\r
458 Arguments:\r
459 This - Indicates calling context.\r
460 DeviceEndpoint - The destination USB device endpoint to which the device\r
461 request is being sent.\r
462 Data - A pointer to the buffer of data that will be transmitted\r
463 to USB device or received from USB device.\r
464 DataLength - On input, the size, in bytes, of the data buffer\r
465 specified by Data. On output, the number of bytes that\r
466 were actually transferred.\r
467 Timeout - Indicates the transfer should be completed within this\r
468 time frame.\r
469 Status - This parameter indicates the USB transfer status.\r
470\r
471 Returns:\r
472 EFI_SUCCESS\r
473 EFI_INVALID_PARAMETER\r
474 EFI_OUT_OF_RESOURCES\r
475 EFI_TIMEOUT\r
476 EFI_DEVICE_ERROR\r
477\r
478--*/\r
479{\r
562d2849 480 USB_IO_DEVICE *UsbIoDev;\r
481 UINTN MaxPacketLength;\r
482 UINT8 DataToggle;\r
483 UINT8 OldToggle;\r
484 EFI_STATUS RetStatus;\r
485 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
486 ENDPOINT_DESC_LIST_ENTRY *EndPointListEntry;\r
878ddf1f 487\r
488 //\r
489 // Parameters Checking\r
490 //\r
491 if ((DeviceEndpoint & 0x7F) == 0) {\r
492 return EFI_INVALID_PARAMETER;\r
493 }\r
494\r
495 if ((DeviceEndpoint & 0x7F) > 15) {\r
496 return EFI_INVALID_PARAMETER;\r
497 }\r
498\r
499 if (Status == NULL) {\r
500 return EFI_INVALID_PARAMETER;\r
501 }\r
502\r
503 EndPointListEntry = FindEndPointListEntry (\r
504 This,\r
505 DeviceEndpoint\r
506 );\r
507\r
508 if (EndPointListEntry == NULL) {\r
509 return EFI_INVALID_PARAMETER;\r
510 }\r
511\r
512 if ((EndPointListEntry->EndpointDescriptor.Attributes & 0x03) != 0x03) {\r
513 return EFI_INVALID_PARAMETER;\r
514 }\r
515 \r
516 //\r
517 // leave the HostController's SyncInterruptTransfer\r
518 // to perform other parameters checking\r
519 //\r
520 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
521 UsbIoDev = UsbIoController->UsbDevice;\r
878ddf1f 522 GetDeviceEndPointMaxPacketLength (\r
523 This,\r
524 DeviceEndpoint,\r
525 &MaxPacketLength\r
526 );\r
527\r
528 GetDataToggleBit (\r
529 This,\r
530 DeviceEndpoint,\r
531 &DataToggle\r
532 );\r
533\r
534 OldToggle = DataToggle;\r
535 //\r
536 // using HostController's SyncInterruptTransfer to complete the request\r
537 //\r
562d2849 538 RetStatus = UsbVirtualHcSyncInterruptTransfer (\r
539 UsbIoDev->BusController,\r
540 UsbIoDev->DeviceAddress,\r
541 DeviceEndpoint,\r
542 UsbIoDev->DeviceSpeed,\r
543 MaxPacketLength,\r
544 Data,\r
545 DataLength,\r
546 &DataToggle,\r
547 Timeout,\r
548 UsbIoDev->Translator,\r
549 Status\r
550 );\r
878ddf1f 551\r
552 if (OldToggle != DataToggle) {\r
553 //\r
554 // Write the toggle back\r
555 //\r
556 SetDataToggleBit (\r
557 This,\r
558 DeviceEndpoint,\r
559 DataToggle\r
560 );\r
561 }\r
562\r
563 return RetStatus;\r
564}\r
565\r
566STATIC\r
567EFI_STATUS\r
568EFIAPI\r
569UsbAsyncInterruptTransfer (\r
570 IN EFI_USB_IO_PROTOCOL *This,\r
571 IN UINT8 DeviceEndpoint,\r
572 IN BOOLEAN IsNewTransfer,\r
573 IN UINTN PollingInterval, OPTIONAL\r
574 IN UINTN DataLength, OPTIONAL\r
575 IN EFI_ASYNC_USB_TRANSFER_CALLBACK InterruptCallBack, OPTIONAL\r
576 IN VOID *Context OPTIONAL\r
577 )\r
578/*++\r
579\r
580 Routine Description:\r
581 Usb Async Interrput Transfer\r
582\r
583 Arguments:\r
584 This - Indicates calling context.\r
585 DeviceEndpoint - The destination USB device endpoint to which the\r
586 device request is being sent.\r
587 IsNewTransfer - If TRUE, a new transfer will be submitted to USB\r
588 controller. If FALSE, the interrupt transfer is\r
589 deleted from the device's interrupt transfer queue.\r
590 PollingInterval - Indicates the periodic rate, in milliseconds, that\r
591 the transfer is to be executed.\r
592 DataLength - Specifies the length, in bytes, of the data to be\r
593 received from the USB device.\r
562d2849 594 InterruptCallBack - The Callback function. This function is called if\r
878ddf1f 595 the asynchronous interrupt transfer is completed.\r
596 Context - Passed to InterruptCallback \r
597 Returns:\r
598 EFI_SUCCESS\r
599 EFI_INVALID_PARAMETER\r
600 EFI_OUT_OF_RESOURCES\r
601\r
602--*/\r
603{\r
562d2849 604 USB_IO_DEVICE *UsbIoDev;\r
605 UINTN MaxPacketLength;\r
606 UINT8 DataToggle;\r
607 EFI_STATUS RetStatus;\r
608 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
609 ENDPOINT_DESC_LIST_ENTRY *EndpointListEntry;\r
878ddf1f 610\r
611 //\r
612 // Check endpoint\r
613 //\r
614 if ((DeviceEndpoint & 0x7F) == 0) {\r
615 return EFI_INVALID_PARAMETER;\r
616 }\r
617\r
618 if ((DeviceEndpoint & 0x7F) > 15) {\r
619 return EFI_INVALID_PARAMETER;\r
620 }\r
621\r
622 EndpointListEntry = FindEndPointListEntry (\r
623 This,\r
624 DeviceEndpoint\r
625 );\r
626\r
627 if (EndpointListEntry == NULL) {\r
628 return EFI_INVALID_PARAMETER;\r
629 }\r
630\r
631 if ((EndpointListEntry->EndpointDescriptor.Attributes & 0x03) != 0x03) {\r
632 return EFI_INVALID_PARAMETER;\r
633 }\r
634\r
635 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
636 UsbIoDev = UsbIoController->UsbDevice;\r
878ddf1f 637\r
638 if (!IsNewTransfer) {\r
639 //\r
640 // Delete this transfer\r
641 //\r
562d2849 642 UsbVirtualHcAsyncInterruptTransfer (\r
643 UsbIoDev->BusController,\r
644 UsbIoDev->DeviceAddress,\r
645 DeviceEndpoint,\r
646 UsbIoDev->DeviceSpeed,\r
647 0,\r
648 FALSE,\r
649 &DataToggle,\r
650 PollingInterval,\r
651 DataLength,\r
652 UsbIoDev->Translator,\r
653 NULL,\r
654 NULL\r
655 );\r
878ddf1f 656\r
657 //\r
658 // We need to store the toggle value\r
659 //\r
660 SetDataToggleBit (\r
661 This,\r
662 DeviceEndpoint,\r
663 DataToggle\r
664 );\r
665\r
666 return EFI_SUCCESS;\r
667 }\r
668\r
669 GetDeviceEndPointMaxPacketLength (\r
670 This,\r
671 DeviceEndpoint,\r
672 &MaxPacketLength\r
673 );\r
674\r
675 GetDataToggleBit (\r
676 This,\r
677 DeviceEndpoint,\r
678 &DataToggle\r
679 );\r
680\r
562d2849 681 RetStatus = UsbVirtualHcAsyncInterruptTransfer (\r
682 UsbIoDev->BusController,\r
683 UsbIoDev->DeviceAddress,\r
684 DeviceEndpoint,\r
685 UsbIoDev->DeviceSpeed,\r
686 MaxPacketLength,\r
687 TRUE,\r
688 &DataToggle,\r
689 PollingInterval,\r
690 DataLength,\r
691 UsbIoDev->Translator,\r
692 InterruptCallBack,\r
693 Context\r
694 );\r
878ddf1f 695\r
696 return RetStatus;\r
697}\r
698\r
699STATIC\r
700EFI_STATUS\r
701EFIAPI\r
702UsbIsochronousTransfer (\r
703 IN EFI_USB_IO_PROTOCOL *This,\r
704 IN UINT8 DeviceEndpoint,\r
705 IN OUT VOID *Data,\r
706 IN UINTN DataLength,\r
707 OUT UINT32 *Status\r
708 )\r
709/*++\r
710\r
711 Routine Description:\r
712 Usb Isochronous Transfer\r
713\r
714 Arguments:\r
715 This - Indicates calling context.\r
716 DeviceEndpoint - The destination USB device endpoint to which the\r
717 device request is being sent.\r
718 Data - A pointer to the buffer of data that will be\r
719 transmitted to USB device or received from USB device.\r
720 DataLength - The size, in bytes, of the data buffer specified by\r
721 Data.\r
722 Status - This parameter indicates the USB transfer status.\r
723\r
724 Returns:\r
725 EFI_SUCCESS\r
726 EFI_INVALID_PARAMETER\r
727 EFI_OUT_OF_RESOURCES\r
728 EFI_TIMEOUT\r
729 EFI_DEVICE_ERROR\r
730 EFI_UNSUPPORTED\r
731--*/\r
732{\r
733 //\r
734 // Currently we don't support this transfer\r
735 //\r
736 return EFI_UNSUPPORTED;\r
737}\r
738\r
739STATIC\r
740EFI_STATUS\r
741EFIAPI\r
742UsbAsyncIsochronousTransfer (\r
743 IN EFI_USB_IO_PROTOCOL *This,\r
744 IN UINT8 DeviceEndpoint,\r
745 IN OUT VOID *Data,\r
746 IN UINTN DataLength,\r
747 IN EFI_ASYNC_USB_TRANSFER_CALLBACK IsochronousCallBack,\r
748 IN VOID *Context OPTIONAL\r
749 )\r
750/*++\r
751\r
752Routine Description:\r
753\r
754 Usb Async Isochronous Transfer\r
755\r
756Arguments:\r
757\r
758 This - EFI_USB_IO_PROTOCOL\r
759 DeviceEndpoint - DeviceEndpoint number\r
760 Data - Data to transfer\r
761 DataLength - DataLength\r
762 IsochronousCallBack - Isochronous CallBack function\r
763 Context - Passed to IsochronousCallBack function\r
764Returns:\r
765\r
766 EFI_UNSUPPORTED - Unsupported now\r
767\r
768--*/\r
769{\r
770 //\r
771 // Currently we don't support this transfer\r
772 //\r
773 return EFI_UNSUPPORTED;\r
774}\r
775//\r
776// Here is new definitions\r
777//\r
778STATIC\r
779EFI_STATUS\r
780EFIAPI\r
781UsbGetDeviceDescriptor (\r
782 IN EFI_USB_IO_PROTOCOL *This,\r
783 OUT EFI_USB_DEVICE_DESCRIPTOR *DeviceDescriptor\r
784 )\r
785/*++\r
786\r
787 Routine Description:\r
788 Retrieves the USB Device Descriptor.\r
789\r
790 Arguments:\r
791 This - Indicates the calling context.\r
792 DeviceDescriptor - A pointer to the caller allocated USB Device\r
793 Descriptor.\r
794\r
795 Returns:\r
796 EFI_SUCCESS\r
797 EFI_INVALID_PARAMETER\r
798 EFI_NOT_FOUND\r
799\r
800--*/\r
801{\r
802 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
803 USB_IO_DEVICE *UsbIoDev;\r
804\r
805 //\r
806 // This function just wrapps UsbGetDeviceDescriptor.\r
807 //\r
808 \r
809 if (DeviceDescriptor == NULL) {\r
810 return EFI_INVALID_PARAMETER;\r
811 }\r
812\r
813 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
814 UsbIoDev = UsbIoController->UsbDevice;\r
815\r
816 if (!UsbIoDev->IsConfigured) {\r
817 return EFI_NOT_FOUND;\r
818 }\r
819\r
820 CopyMem (\r
821 DeviceDescriptor,\r
822 &UsbIoDev->DeviceDescriptor,\r
823 sizeof (EFI_USB_DEVICE_DESCRIPTOR)\r
824 );\r
825\r
826 return EFI_SUCCESS;\r
827}\r
828\r
829STATIC\r
830EFI_STATUS\r
831EFIAPI\r
832UsbGetActiveConfigDescriptor (\r
833 IN EFI_USB_IO_PROTOCOL *This,\r
834 OUT EFI_USB_CONFIG_DESCRIPTOR *ConfigurationDescriptor\r
835 )\r
836/*++\r
837\r
838 Routine Description:\r
839 Retrieves the current USB configuration Descriptor.\r
840\r
841 Arguments:\r
842 This - Indicates the calling context.\r
843 ConfigurationDescriptor - A pointer to the caller allocated USB active\r
844 Configuration Descriptor.\r
845\r
846 Returns:\r
847 EFI_SUCCESS\r
848 EFI_INVALID_PARAMETER\r
849 EFI_NOT_FOUND\r
850\r
851--*/\r
852{\r
853 USB_IO_DEVICE *UsbIoDev;\r
854 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
855\r
856 //\r
857 // This function just wrapps UsbGetActiveConfigDescriptor.\r
858 //\r
859 if (ConfigurationDescriptor == NULL) {\r
860 return EFI_INVALID_PARAMETER;\r
861 }\r
862\r
863 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
864 UsbIoDev = UsbIoController->UsbDevice;\r
865\r
866 if (!UsbIoDev->IsConfigured) {\r
867 return EFI_NOT_FOUND;\r
868 }\r
869\r
870 CopyMem (\r
871 ConfigurationDescriptor,\r
872 &(UsbIoDev->ActiveConfig->CongfigDescriptor),\r
873 sizeof (EFI_USB_CONFIG_DESCRIPTOR)\r
874 );\r
875\r
876 return EFI_SUCCESS;\r
877}\r
878\r
879STATIC\r
880EFI_STATUS\r
881EFIAPI\r
882UsbGetInterfaceDescriptor (\r
883 IN EFI_USB_IO_PROTOCOL *This,\r
884 OUT EFI_USB_INTERFACE_DESCRIPTOR *InterfaceDescriptor\r
885 )\r
886/*++\r
887\r
888 Routine Description:\r
889 Retrieves the interface Descriptor for that controller.\r
890\r
891 Arguments:\r
892 This - Indicates the calling context.\r
893 InterfaceDescriptor - A pointer to the caller allocated USB interface\r
894 Descriptor.\r
895\r
896 Returns:\r
897 EFI_SUCCESS\r
898 EFI_INVALID_PARAMETER\r
899 EFI_NOT_FOUND\r
900\r
901--*/\r
902{\r
903 INTERFACE_DESC_LIST_ENTRY *InterfaceListEntry;\r
904\r
905 if (InterfaceDescriptor == NULL) {\r
906 return EFI_INVALID_PARAMETER;\r
907 }\r
908\r
909 InterfaceListEntry = FindInterfaceListEntry (This);\r
910\r
911 if (InterfaceListEntry == NULL) {\r
912 return EFI_NOT_FOUND;\r
913 }\r
914\r
915 CopyMem (\r
916 InterfaceDescriptor,\r
917 &(InterfaceListEntry->InterfaceDescriptor),\r
918 sizeof (EFI_USB_INTERFACE_DESCRIPTOR)\r
919 );\r
920\r
921 return EFI_SUCCESS;\r
922}\r
923\r
924STATIC\r
925EFI_STATUS\r
926EFIAPI\r
927UsbGetEndpointDescriptor (\r
928 IN EFI_USB_IO_PROTOCOL *This,\r
929 IN UINT8 EndpointIndex,\r
930 OUT EFI_USB_ENDPOINT_DESCRIPTOR *EndpointDescriptor\r
931 )\r
932/*++\r
933\r
934 Routine Description:\r
935 Retrieves the endpoint Descriptor for a given endpoint.\r
936\r
937 Arguments:\r
938 This - Indicates the calling context.\r
939 EndpointIndex - Indicates which endpoint descriptor to retrieve.\r
940 The valid range is 0..15.\r
941 EndpointDescriptor - A pointer to the caller allocated USB Endpoint\r
942 Descriptor of a USB controller.\r
943\r
944 Returns:\r
945 EFI_SUCCESS - The endpoint descriptor was retrieved successfully.\r
946 EFI_INVALID_PARAMETER - EndpointIndex is not valid.\r
947 - EndpointDescriptor is NULL.\r
948 EFI_NOT_FOUND - The endpoint descriptor cannot be found.\r
949 The device may not be correctly configured.\r
950\r
951--*/\r
952{\r
953 INTERFACE_DESC_LIST_ENTRY *InterfaceListEntry;\r
954 LIST_ENTRY *EndpointListHead;\r
955 ENDPOINT_DESC_LIST_ENTRY *EndpointListEntry;\r
956\r
957 if (EndpointDescriptor == NULL) {\r
958 return EFI_INVALID_PARAMETER;\r
959 }\r
960\r
961 if (EndpointIndex > 15) {\r
962 return EFI_INVALID_PARAMETER;\r
963 }\r
964\r
965 InterfaceListEntry = FindInterfaceListEntry (This);\r
966\r
967 if (InterfaceListEntry == NULL) {\r
968 return EFI_NOT_FOUND;\r
969 }\r
970\r
971 EndpointListHead = (LIST_ENTRY *) (&InterfaceListEntry->EndpointDescListHead);\r
972 EndpointListEntry = (ENDPOINT_DESC_LIST_ENTRY *) (EndpointListHead->ForwardLink);\r
973\r
974 if (EndpointIndex >= InterfaceListEntry->InterfaceDescriptor.NumEndpoints) {\r
975 return EFI_NOT_FOUND;\r
976 }\r
977 //\r
978 // Loop all endpoint descriptor to get match one.\r
979 //\r
980 while (EndpointIndex != 0) {\r
981 EndpointListEntry = (ENDPOINT_DESC_LIST_ENTRY *) (EndpointListEntry->Link.ForwardLink);\r
982 EndpointIndex--;\r
983 }\r
984\r
985 CopyMem (\r
986 EndpointDescriptor,\r
987 &EndpointListEntry->EndpointDescriptor,\r
988 sizeof (EFI_USB_ENDPOINT_DESCRIPTOR)\r
989 );\r
990\r
991 return EFI_SUCCESS;\r
992}\r
993\r
994STATIC\r
995EFI_STATUS\r
996EFIAPI\r
997UsbGetSupportedLanguages (\r
998 IN EFI_USB_IO_PROTOCOL *This,\r
999 OUT UINT16 **LangIDTable,\r
1000 OUT UINT16 *TableSize\r
1001 )\r
1002/*++\r
1003\r
1004 Routine Description:\r
1005 Get all the languages that the USB device supports\r
1006\r
1007 Arguments:\r
1008 This - Indicates the calling context.\r
1009 LangIDTable - Language ID for the string the caller wants to get.\r
1010 TableSize - The size, in bytes, of the table LangIDTable.\r
1011\r
1012 Returns:\r
1013 EFI_SUCCESS\r
1014 EFI_NOT_FOUND\r
1015\r
1016--*/\r
1017{\r
1018 USB_IO_DEVICE *UsbIoDev;\r
1019 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
1020 UINTN Index;\r
1021 BOOLEAN Found;\r
1022\r
1023 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
1024 UsbIoDev = UsbIoController->UsbDevice;\r
1025\r
1026 Found = FALSE;\r
1027 Index = 0;\r
1028 //\r
1029 // Loop language table\r
1030 //\r
1031 while (UsbIoDev->LangID[Index]) {\r
1032 Found = TRUE;\r
1033 Index++;\r
1034 }\r
1035\r
1036 if (!Found) {\r
1037 return EFI_NOT_FOUND;\r
1038 }\r
1039\r
1040 *LangIDTable = UsbIoDev->LangID;\r
1041 *TableSize = (UINT16) Index;\r
1042\r
1043 return EFI_SUCCESS;\r
1044}\r
1045\r
1046STATIC\r
1047EFI_STATUS\r
1048EFIAPI\r
1049UsbGetStringDescriptor (\r
1050 IN EFI_USB_IO_PROTOCOL *This,\r
1051 IN UINT16 LangID,\r
1052 IN UINT8 StringIndex,\r
1053 OUT CHAR16 **String\r
1054 )\r
1055/*++\r
1056\r
1057 Routine Description:\r
1058 Get a given string descriptor\r
1059\r
1060 Arguments:\r
1061 This - Indicates the calling context.\r
1062 LangID - The Language ID for the string being retrieved.\r
1063 StringIndex - The ID of the string being retrieved.\r
1064 String - A pointer to a buffer allocated by this function\r
1065 with AllocatePool() to store the string. If this\r
1066 function returns EFI_SUCCESS, it stores the string\r
1067 the caller wants to get. The caller should release\r
1068 the string buffer with FreePool() after the string\r
1069 is not used any more.\r
1070 Returns:\r
1071 EFI_SUCCESS\r
1072 EFI_NOT_FOUND\r
1073 EFI_OUT_OF_RESOURCES\r
562d2849 1074 EFI_UNSUPPORTED\r
878ddf1f 1075\r
1076--*/\r
1077{\r
1078 UINT32 Status;\r
1079 EFI_STATUS Result;\r
1080 EFI_USB_STRING_DESCRIPTOR *StrDescriptor;\r
1081 UINT8 *Buffer;\r
1082 CHAR16 *UsbString;\r
1083 UINT16 TempBuffer;\r
1084 USB_IO_DEVICE *UsbIoDev;\r
1085 UINT8 Index;\r
1086 BOOLEAN Found;\r
1087 USB_IO_CONTROLLER_DEVICE *UsbIoController;\r
1088\r
1089 if (StringIndex == 0) {\r
1090 return EFI_NOT_FOUND;\r
1091 }\r
1092 //\r
1093 // Search LanguageID, check if it is supported by this device\r
1094 //\r
1095 if (LangID == 0) {\r
1096 return EFI_NOT_FOUND;\r
1097 }\r
1098\r
1099 UsbIoController = USB_IO_CONTROLLER_DEVICE_FROM_USB_IO_THIS (This);\r
1100 UsbIoDev = UsbIoController->UsbDevice;\r
1101\r
1102 Found = FALSE;\r
1103 Index = 0;\r
1104 while (UsbIoDev->LangID[Index]) {\r
1105 if (UsbIoDev->LangID[Index] == LangID) {\r
1106 Found = TRUE;\r
1107 break;\r
1108 }\r
1109\r
1110 Index++;\r
1111 }\r
1112\r
1113 if (!Found) {\r
1114 return EFI_NOT_FOUND;\r
1115 }\r
1116 //\r
1117 // Get String Length\r
1118 //\r
1119 Result = UsbGetString (\r
1120 This,\r
1121 LangID,\r
1122 StringIndex,\r
1123 &TempBuffer,\r
1124 2,\r
1125 &Status\r
1126 );\r
1127 if (EFI_ERROR (Result)) {\r
1128 return EFI_NOT_FOUND;\r
1129 }\r
1130\r
1131 StrDescriptor = (EFI_USB_STRING_DESCRIPTOR *) &TempBuffer;\r
1132\r
1133 if (StrDescriptor->Length == 0) {\r
1134 return EFI_UNSUPPORTED;\r
1135 }\r
1136\r
1137 Buffer = AllocateZeroPool (StrDescriptor->Length);\r
1138 if (Buffer == NULL) {\r
1139 return EFI_OUT_OF_RESOURCES;\r
1140 }\r
1141\r
1142 Result = UsbGetString (\r
1143 This,\r
1144 LangID,\r
1145 StringIndex,\r
1146 Buffer,\r
1147 StrDescriptor->Length,\r
1148 &Status\r
1149 );\r
1150\r
1151 if (EFI_ERROR (Result)) {\r
1152 gBS->FreePool (Buffer);\r
1153 return EFI_NOT_FOUND;\r
1154 }\r
1155\r
1156 StrDescriptor = (EFI_USB_STRING_DESCRIPTOR *) Buffer;\r
1157\r
1158 //\r
1159 // UsbString is a UNICODE string\r
1160 //\r
1161 UsbString = AllocateZeroPool (StrDescriptor->Length);\r
1162 if (UsbString == NULL) {\r
1163 gBS->FreePool (Buffer);\r
1164 return EFI_OUT_OF_RESOURCES;\r
1165 }\r
1166\r
1167 CopyMem (\r
1168 (VOID *) UsbString,\r
1169 Buffer + 2,\r
1170 StrDescriptor->Length - 2\r
1171 );\r
1172\r
1173 *String = UsbString;\r
1174\r
1175 gBS->FreePool (Buffer);\r
1176\r
1177 return EFI_SUCCESS;\r
1178}\r