Freigeben über


Fallstudie: Problembehandlung für ein unbekanntes USB-Gerät mithilfe von ETW und Netmon

Dieses Thema enthält ein Beispiel für die Verwendung von USB ETW und Netmon zur Problembehandlung für ein USB-Gerät, das Von Windows nicht erkannt wird.

In diesem Beispiel haben wir ein Gerät angeschlossen, und es wurde als unbekanntes Gerät im Geräte-Manager und in anderen Teilen der Benutzeroberfläche angezeigt. Die Hardware-ID war USB\UNBEKANNT. Um das Gerät weiter zu diagnostizieren, zogen wir den Stecker des Geräts, begannen eine ETW-Ablaufverfolgung und steckten das Gerät wieder ein. Nachdem das Gerät als ein unbekanntes Gerät angezeigt wurde, haben wir die Protokollierung gestoppt.

Informationen zum Problem mit dem unbekannten Gerät

Um ein unbekanntes USB-Geräteproblem zu debuggen, hilft es zu verstehen, was der USB-Treiberstapel tut, um ein Gerät auflisten, wenn ein Benutzer es an das System einbindet. Informationen zur USB-Aufzählung finden Sie im Blogbeitrag "Wie zählt der USB-Stack ein Gerät auf?"

Wenn der USB-Treiberstapel ein Gerät nicht aufzählt, meldet der Hubtreiber weiterhin das Eintreffen des Geräts bei Windows, und das USB-Gerät wird im Geräte-Manager als unbekanntes Gerät gekennzeichnet. Das Gerät verfügt über eine Geräte-ID von USB\VID_0000&PID_0000 und eine Hardware-ID und eine kompatible ID von USB\UNKNOWN. Die folgenden Ereignisse führen dazu, dass der USB-Hubtreiber ein USB-Gerät als unbekanntes Gerät aufzählt:

  • Die Anforderung zum Zurücksetzen des Ports hat während der Aufzählung ein Timeout.
  • Fehler bei der Set Address-Anforderung für das USB-Gerät.
  • Fehler bei der Anforderung des Gerätedeskriptors des USB-Geräts.
  • Der USB-Gerätedeskriptor war falsch formatiert und konnte nicht überprüft werden.
  • Fehler bei der Anforderung für den Konfigurationsdeskriptor.
  • Der USB-Konfigurationsdeskriptor war falsch formatiert und konnte nicht überprüft werden.

In Windows 7 werden unbekannte Geräte, bei denen die Aufzählung fehlschlägt, im Geräte-Manager mit Fehlercode 43 gekennzeichnet.

Wenn ein Gerät mit Fehlercode 28 im Geräte-Manager gekennzeichnet ist, wurde das Gerät erfolgreich aufgezählt, ist aber weiterhin ein unbekanntes Gerät. Dieser Fehlercode gibt an, dass das Gerät während der Enumeration keine Produkt-ID-Zeichenfolge bereitgestellt hat, und Windows konnte keinen übereinstimmenden INF für das Gerät finden, um einen Treiber zu installieren.

Starten der Ereignisablaufverfolgungsanalyse

Da dies ein Gerätefehler ist, empfehlen wir, Netmon mit dem USB-Parser zu verwenden, um die Protokolldatei zu analysieren.

Ereignisablaufverfolgungsprotokoll anzeigen

  1. Führen Sie Netmon aus, klicken Sie auf Datei -> Öffnen –> Erfassen, und wählen Sie dann die Datei aus.

  2. Wählen Sie das erste Ereignis im Bereich "Framezusammenfassung " aus, das die Beschreibung "SystemTrace" aufweist. Diese Abbildung zeigt, wie der Bildschirm aussieht, wenn Sie das erste Ereignis auswählen.

    Screenshot des Fensters

  3. Klicken Sie zum Anpassen der angezeigten Spalten mit der rechten Maustaste auf einen Spaltennamen, und wählen Sie „Spalten auswählen“ aus.

  4. Das erste Ereignis, das als SystemTrace-Typ identifiziert wird, enthält allgemeine Informationen zum Protokoll. Sie können die Informationsstruktur im Bereich Rahmendetails erweitern, um Informationen wie die Anzahl der verlorenen Ereignisse und die Startzeit des Tracings anzuzeigen.

Zusammenfassungsereignisse für USB-Geräte

Ereignis 2 ist das erste USB-Ereignis im Protokoll. Dies und mehrere nachfolgende Ereignisse beschreiben die USB-Hostcontroller, Hubs und Geräte, die mit dem System verbunden waren, als wir mit der Verfolgung begannen. Wir können diese Ereignisgruppe als Gerätezusammenfassungsereignisse oder einfach Zusammenfassungsereignisse nennen. Wie beim ersten Ereignis beschreiben die Zusammenfassungsereignisse keine Treiberaktivität. Zusammenfassungsereignisse zeichnen den Zustand der Geräte zu Beginn einer Protokollierungssitzung auf. Andere Ereignisse stellen etwas dar, das im Bus passiert, wie Interaktionen mit Clientfahrern oder dem System oder Änderungen des internen Zustands.

Die Treiber für den USB-Hub und die USB-Ports protokollieren beide Zusammenfassungsereignisse. Der Treiber, der ein Ereignis protokolliert hat, wird in der Spalte "Protokollname" identifiziert. Beispielsweise weist ein Ereignis, das vom USB-Porttreiber protokolliert wird, den USBPort_MicrosoftWindowsUSBPORT Protokollnamen auf. Eine USB-Ereignisablaufverfolgung enthält in der Regel eine Abfolge von Portzusammenfassungsereignissen, gefolgt von einer Sequenz von Hubzusammenfassungsereignissen. Viele der USB-Port- und USB-Hub-Zusammenfassungsereignisse enthalten die Wörter "Information" oder "Attributes" in ihrer Beschreibung.

Wie können Sie das Ende der Zusammenfassungsereignisse identifizieren? Wenn es zu Beginn des Protokolls zu einer erheblichen Unterbrechung des Zeitstempelmusters zwischen den USB-Hubereignissen kommt, ist diese Unterbrechung wahrscheinlich das Ende der Zusammenfassung des Geräts. Andernfalls ist das erste USB-Portereignis nach allen USB-Hubereignissen wahrscheinlich das erste nicht zusammenfassende Ereignis. Abbildung 3 auf der folgenden Seite zeigt das erste nicht zusammenfassende Ereignis in dieser Beispielablaufverfolgung.

In diesem Beispiel war das interessante Gerät nicht mit dem System verbunden, als wir die Ablaufverfolgung gestartet haben, sodass Sie die Gerätezusammenfassungsereignisse vorerst überspringen können.

Screenshot, der ein in der

Ereignisbeschreibung und Datennutzlast

Im Beispielprotokoll ist das erste Ereignis nach den Gerätezusammenfassungsereignissen ein USB Hub Wait Wake IRP Completed-Ereignis. Wir haben ein Gerät angeschlossen, und ein Hostcontroller oder ein Hub wacht als Reaktion auf. Um zu ermitteln, welche Komponente aufwacht, schauen Sie sich die Daten des Ereignisses an. Die Daten befinden sich im Bereich "Frame-Details", der in einer Baumstruktur in ungefähr der folgenden Form angezeigt wird:

Frame information
ETW event header information
    ETW event descriptor (Constant information about the event ID such
    as error level)
Event payload (Data logged at the time of the event)
    Name of a USB-specific structure
        Structure members and their values (Types: numbers, strings,
        or arrays)
    ...

Erweitern Sie die Nutzlastdaten für das USB Hub Wait Wake IRP Completed-Ereignis, und es wird eine ETW-Struktur mit dem Namen fid_USBHUB_Hub angezeigt. Der Name der Struktur weist die folgenden Komponenten auf:

Begriff BESCHREIBUNG
Fid_ Ein typisches Präfix für eine USB ETW-Struktur.
USBHUB_ Ein Hinweis darauf, dass der USB-Hubtreiber das Ereignis protokolliert hat.
Der Rest der Zeichenfolge Der Name des Objekts, das die Daten der Struktur beschreibt. Bei diesem Ereignis handelt es sich um ein Hub-Objekt.

Der USB-Hubtreiber verwendet die fid_USBHUB_Hub Struktur, um einen USB-Hub zu beschreiben. Ereignisse, die diese Hubstruktur in ihrer Datennutzlast enthalten, beziehen sich auf einen Hub, und wir können den spezifischen Hub mithilfe der Inhalte der Struktur identifizieren. Abbildung 4 zeigt den Bereich "Framedetails", wobei die fid_USBHUB_Hub Struktur erweitert wurde, um deren Felder anzuzeigen.

Microsoft-Netzwerkmonitor – Framedetails.

Die Hubstruktur ähnelt sehr zwei anderen Strukturen, die häufig in USB ETW-Ereignissen:fid_USBHUB_Device und fid_USBPORT_Device auftreten. Die folgenden wichtigen Felder sind für alle drei Strukturen gemeinsam:

Feld BESCHREIBUNG
fid_idVendor Die USB-Anbieter-ID (VID) des Geräts
fid_idProduct Die USB-Produkt-ID (PID) des Geräts
fid_PortPath Die Liste der 1-basierten Hubanschlussnummern, über die ein USB-Gerät angeschlossen ist. Die Anzahl der Portnummern in der Liste ist im Feld "PortPathDepth " enthalten. Für die Stammhubgeräte besteht diese Liste aus ausschließlich Nullen. Bei einem USB-Gerät, das direkt an einen Stammhubport angeschlossen ist, ist der Wert in PortPath[0] die Nummer des Stammhubports des Ports, an den das Gerät angeschlossen ist.

Bei einem USB-Gerät, das über einen oder mehrere zusätzliche USB-Hubs verbunden ist, beginnt die Liste der Hubportnummern mit dem Stammhubport und setzt mit den zusätzlichen Hubs fort (in der Reihenfolge des Abstands vom Stammhub). Ignorieren Sie alle Nullen. Beispiel:

Beispielwert BESCHREIBUNG
[0, 0, 0, 0, 0, 0] Das Ereignis bezieht sich auf einen Stammhub (ein Port auf dem PC, der direkt von einem USB-Hostcontroller gesteuert wird).
[3, 0, 0, 0, 0, 0] Das Ereignis bezieht sich auf einen Hub oder ein Gerät, das an die Portnummer 3 eines Stammhubs angeschlossen ist.
[3, 1, 0, 0, 0, 0] Ein Hub ist an den Port 3 eines Stammhubs angeschlossen. Das Ereignis bezieht sich auf einen Hub oder ein Gerät, das an den Port 1 des externen Hubs angeschlossen ist.

Sie sollten die Portpfade aller geräte von Interesse überwachen. Wenn ein Gerät aufgezählt wird, sind VID und PID unbekannt und als 0 protokolliert. Die VID- und PID-Nummern werden während einiger Geräteanforderungen auf niedriger Ebene, wie zum Beispiel bei einem Neustart und Anhalten, nicht angezeigt. Diese Anforderungen werden an den Hub gesendet, an den das Gerät angeschlossen ist.

In unserem Beispielprotokoll verfügt das Wait Wake-Abschlussereignis über einen Portpfad mit sechs Nullen. Das Ereignis zeigt eine Wait Wake-Aktion auf einem Root Hub an. Das ist aufgrund unserer Aktionen logisch: Wir haben das Gerät an einen Stammhubport angeschlossen, sodass der Stammhub aufwacht.

USB-Netmon-Filter

Sie können jedes Ereignis in einem Protokoll in chronologischer Reihenfolge untersuchen, wenn Sie die Zeit haben. Selbst mit Erfahrung ist es schwierig, die wichtigen Ereignisse schnell zu identifizieren, indem die Liste der Ereignisbeschreibungen durchsucht wird. Um die Ursache des unbekannten Geräts schneller zu finden, können Sie die Netmon-Filterfunktion verwenden.

Der USB-Fehlerfilter

Um den USB-Fehlerfilter in Netmon zu aktivieren, klicken Sie auf Filter -> Anzeigefilter -> Ladefilter -> Standardfilter -> USB -> USB-Hubfehler, und klicken Sie dann im Bereich "Anzeigefilterübernehmen".

Der USB-Fehlerfilter beschränkt die Liste der Ereignisse auf diejenigen, die den in der folgenden Tabelle gezeigten Kriterien entsprechen.

Filtern von Text BESCHREIBUNG
(USBPort_MicrosoftWindowsUSBUSBPORT AND NetEvent.Header.Descriptor.Opcode == 34) USB-Portereignisse mit Opcode 34 sind Portfehler.
(USBHub_MicrosoftWindowsUSBUSBHUB AND NetEvent.Header.Descriptor.Opcode == 11) USB-Hubereignisse mit Opcode 11 sind Hubfehler.
(NetEvent.Header.Descriptor.Level == 0x2) Ereignisse mit Level 0x2 sind in der Regel Fehler.
(USBHub_MicrosoftWindowsUSBUSBHUB UND NetEvent.Header.Descriptor.Id == 210) USB-Hubereignisse mit der ID 210 sind Ereignisse, bei denen eine "USB-Hub-Ausnahme protokolliert" wird. Weitere Informationen finden Sie unter Grundlegendes zu Fehlerereignissen und Statuscodes.

Diese Abbildung zeigt den kleineren Satz von Ereignissen, die im Bereich "Framezusammenfassung " angezeigt werden, nachdem wir den USB-Fehlerfilter auf unser Beispielablaufverfolgungsprotokoll angewendet haben.

Screenshot einer Reihe von Ereignissen im Bereich

Um eine Übersicht über die Abfolge von Fehlern anzuzeigen, können Sie die einzelnen Fehlerereignisse kurz anzeigen. Wichtige Zu beobachtende Felder umfassen fid_NtStatus, fid_UsbdStatus und fid_DebugText. Weitere Informationen finden Sie unter Grundlegendes zu Fehlerereignissen und Statuscodes. Um einen Filter zu deaktivieren, klicken Sie im Bereich "Filter anzeigen" auf die Schaltfläche "Entfernen".

Benutzerdefinierte Netmon-Filter

Sie können benutzerdefinierte Filter in Netmon erstellen. Die einfachste Methode besteht darin, einen Filter aus Daten auf dem Bildschirm auf eine der folgenden Arten zu erstellen:

  • Klicken Sie im Bereich " Framedetails " mit der rechten Maustaste auf ein Feld, und wählen Sie "Ausgewählten Wert hinzufügen" aus, um den Filter anzuzeigen.
  • Klicken Sie mit der rechten Maustaste auf ein Feld im Bereich " Rahmenzusammenfassung ", und wählen Sie "[Feldname] hinzufügen" aus, um "Filter anzeigen" anzuzeigen.

Sie können die Operatoren (z. B. OR, AND und ==) und die Filterwerte ändern, um die entsprechenden Filterausdrücke zu erstellen.

Grundlegendes zu Fehlerereignissen und Statuscodes

In unserem unbekannten Gerätebeispiel haben die meisten USB-Hub-Ausnahmen fid_DebugText-Daten von CreateDeviceFailure. Es ist nicht klar, wie schwerwiegend die Ausnahme ist, aber der Debugtext gibt einen Hinweis auf die Ursache: Ein Vorgang im Zusammenhang mit dem neuen Gerät ist fehlgeschlagen. Gehen Sie vorerst davon aus, dass die angrenzenden Ereignisse "Create Device Failed" redundant sind. Die beiden letzten Ausnahmen sind CreateDeviceFailure_Popup und GenErr_UserIoctlFailed. Die Popup-Ausnahme klingt wie ein Fehler, der für den Benutzer verfügbar gemacht wurde, aber alle diese Fehler können mit dem unbekannten Geräteproblem zusammenhängen.

USB-Fehlerereignisse und andere Ereignisse enthalten Statuswerte in ihren Daten, die wertvolle Informationen zum Problem liefern. Mithilfe der Ressourcen in der folgenden Tabelle finden Sie Informationen zu Statuswerten.

Statustyp Ressource
fid_NtStatus Siehe NTSTATUS-Werte.
Das Statusfeld eines USB-Anforderungsblocks (URB) oder fid_UsbdStatus Suchen Sie den Wert als USBD_STATUS in der Datei inc\api\usb.h im Windows Driver Kit (WDK) nach. Sie können auch die USBD_STATUS verwenden. In diesem Thema werden die symbolischen Namen und die Bedeutungen der USBD_STATUS Werte aufgeführt.

Rückwärtslesen von Problemereignissen

Die Ereignisse, die vor den Fehlerereignissen protokolliert werden, können wichtige Hinweise zur Ursache des Fehlers liefern. Sie sollten sich die Ereignisse ansehen, die vor den Fehlern protokolliert werden, um zu versuchen, die Ursache des unbekannten Geräts zu ermitteln. Beginnen Sie in diesem Beispiel rückblickend beim CreateDeviceFailure_Popup-Ereignis, der vorletzten Ausnahme. Wählen Sie dieses Ereignis aus, während der USB-Fehlerfilter aktiviert ist, und klicken Sie dann im Bereich "Anzeigefilterentfernen". Der USB-Fehlerfilter wird weiterhin im Bereich "Anzeigefilter " angezeigt, und Sie können ihn später erneut anwenden. Jetzt ist der Filter deaktiviert, und im Bereich "Framezusammenfassung " werden alle Ereignisse angezeigt, wie in dieser Abbildung dargestellt.

Microsoft-Netzwerkmonitor.

Die beiden Ereignisse, die unmittelbar vor dem CreateDeviceFailure_Popup-Ereignis protokolliert werden, sind eine Weiterleitung und ein Abschluss eines USB-Steuertransfers. Das Feld "fid_USBPORT_Device Portpfad" ist für beide Ereignisse null, was angibt, dass das Ziel der Übertragung der Stammhub ist. In der fid_USBPORT_URB_CONTROL_TRANSFER Struktur des Abschlussereignisses ist der Status null (USBD_STATUS_SUCCESS), was angibt, dass die Übertragung erfolgreich war. Fahren Sie mit der Untersuchung der vorherigen Ereignisse fort.

Die nächsten beiden vorherigen Ereignisse sind das vierte (endgültige) Create Device Failed-Ereignis und vierte (endgültige) CreateDeviceFailure-Ausnahme, die wir zuvor untersucht haben.

Das nächste vorherige Ereignis ist Endpoint Close. Dieses Ereignis bedeutet, dass ein Endpunkt nicht mehr verwendet werden kann. Die Ereignisdaten beschreiben sowohl das Gerät als auch den Endpunkt auf diesem Gerät. Der Geräteportpfad lautet [1, 0, 0, 0, 0, 0, 0]. Das System, auf dem wir die Ablaufverfolgung ausgeführt haben, verfügt nur über Hostcontroller (Root Hubs) und das Gerät, das wir verbinden, sodass dieser Portpfad keinen Hub beschreibt. Der geschlossene Endpunkt muss sich auf dem einzelnen Gerät befinden, das wir angeschlossen haben, und jetzt wissen wir, dass der Pfad des Geräts 1 ist. Es ist wahrscheinlich, dass die Treiber aufgrund eines zuvor aufgetretenen Problems auf den Endpunkt des Geräts nicht zugreifen konnten. Fahren Sie mit der Untersuchung der vorherigen Ereignisse fort.

Das nächste vorherige Ereignis ist eine abgeschlossene USB-Steuerübertragung. Die Ereignisdaten zeigen, dass das Ziel der Übertragung das Gerät ist (der Portpfad ist 1). Die fid_USBPORT_Endpoint_Descriptor Struktur gibt an, dass die Adresse des Endpunkts 0 ist. Dies ist also der USB-definierte Standardsteuerungsendpunkt. Der URB-Status ist 0xC0000004. Da der Status nicht null ist, war die Übertragung wahrscheinlich nicht erfolgreich. Weitere Informationen zu diesem USBD_STATUS Wert finden Sie unter usb.h und Grundlegendes zu Fehlerereignissen und Statuscodes.

#define USBD_STATUS_STALL_PID ((USBD_STATUS)0xC0000004L)

Bedeutung: Das Gerät hat einen Stillstand-Paketbezeichner zurückgegeben. Welche Anforderung wurde vom Endpunkt angehalten? Die anderen Daten, die für das Ereignis protokolliert wurden, deuten darauf hin, dass die Anforderung eine standardmäßige Gerätesteuerungsanforderung war. Dies ist die analysierte Anforderung:

  Frame: Number = 184, Captured Frame Length = 252, MediaType = NetEvent
+ NetEvent:
- MicrosoftWindowsUSBUSBPORT: Complete Internal URB_FUNCTION_CONTROL_TRANSFER
  - USBPORT_ETW_EVENT_COMPLETE_INTERNAL_URB_FUNCTION_CONTROL_TRANSFER: Complete Internal URB_FUNCTION_CONTROL_TRANSFER
   + fid_USBPORT_HC:
   + fid_USBPORT_Device:
   + fid_USBPORT_Endpoint:
   + fid_USBPORT_Endpoint_Descriptor:
   + fid_URB_Ptr: 0x84539008
   - ControlTransfer:
    + Urb: Status = 0xc0000004, Flags 0x3, Length = 0
    - SetupPacket: GET_DESCRIPTOR
     + bmRequestType: (Standard request) 0x80
       bRequest: (6) GET_DESCRIPTOR
       Value_DescriptorIndex: 0 (0x0)
       Value_DescriptorType: (1) DEVICE
       _wIndex: 0 (0x0)
       wLength: 64 (0x40)

Kombinieren Sie die bRequest (GET_DESCRIPTOR) mit dem Value_DescriptorType (DEVICE), und Sie können feststellen, dass die Anforderung get-device descriptor war.

Damit die USB-Aufzählung fortgesetzt wird, sollte das Gerät mit seinem Gerätedeskriptor auf diese Anforderung geantwortet haben. Stattdessen hat das Gerät die Anforderung angehalten, was dazu führte, dass die Enumeration fehlschlug. Daher wurden alle vier Geräteerstellungsfehler durch blockierte Anfragen für den Gerätedeskriptor verursacht. Sie haben festgestellt, dass das Gerät unbekannt ist, da die Aufzählung fehlgeschlagen ist und die Aufzählung fehlgeschlagen ist, weil das Gerät die Anforderung für seine Gerätebeschreibung nicht abgeschlossen hat.