Consider the following course of action When enumerating new USB device:

1. UsbParseConfigDesc is called during new device enumeration process.
It allocates an array of USB_INTERFACE_DESC pointers in Config->Interfaces.
Each of those structures have an array of pointers to USB_INTERFACE_SETTING
which are currently set to NULL.

2. Then UsbParseConfigDesc calls UsbParseInterfaceDesc as long as there is
data left in buffer. Each call parses an interface setting and sets
appropriate pointer in Interface->Settings for related interface desc.

3. Later UsbSelectConfig traverses Config->Interfaces[NumIf]->Settings
to pick appropriate interface configuration.

However if during step 2 UsbParseInterfaceDesc returns NULL (i.e.
because UsbCreateDesc returned NULL, see f89f1db) then config will be
not fully initialized by the time it is returned to caller. Some pointers in
Config->Interfaces->Settings are still set to NULL and will be possibly
dereferenced in UsbSelectConfig.

This patch treats this situation as an error and returns NULL
instead if incompletely initialized config descriptor.

Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: Evgeny Yakovlev <[email protected]>
CC: Feng Tian <[email protected]>
---
 MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c   | 4 ++--
 MdeModulePkg/Bus/Usb/UsbBusDxe/UsbEnumer.c | 3 +++
 2 files changed, 5 insertions(+), 2 deletions(-)

diff --git a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c 
b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c
index fba60da..20e6ca3 100644
--- a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c
+++ b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c
@@ -368,8 +368,8 @@ UsbParseConfigDesc (
     Setting = UsbParseInterfaceDesc (DescBuf, Len, &Consumed);
 
     if (Setting == NULL) {
-      DEBUG (( EFI_D_ERROR, "UsbParseConfigDesc: warning: failed to get 
interface setting, stop parsing now.\n"));
-      break;
+      DEBUG (( EFI_D_ERROR, "UsbParseConfigDesc: failed to get interface 
setting, stop parsing now.\n"));
+      goto ON_ERROR;
 
     } else if (Setting->Desc.InterfaceNumber >= NumIf) {
       DEBUG (( EFI_D_ERROR, "UsbParseConfigDesc: mal-formated interface 
descriptor\n"));
diff --git a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbEnumer.c 
b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbEnumer.c
index 79453fe..57199a0 100644
--- a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbEnumer.c
+++ b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbEnumer.c
@@ -412,6 +412,9 @@ UsbSelectConfig (
     // the endpoint toggles to zero for its endpoints.
     //
     IfDesc = ConfigDesc->Interfaces[Index];
+    ASSERT (IfDesc != NULL);
+    ASSERT (IfDesc->Settings[0] != NULL);
+
     UsbSelectSetting (IfDesc, IfDesc->Settings[0]->Desc.AlternateSetting);
 
     //
-- 
2.7.4 (Apple Git-66)

_______________________________________________
edk2-devel mailing list
[email protected]
https://lists.01.org/mailman/listinfo/edk2-devel

Reply via email to