Melden von Miracast-codierten Blöcken und Statistiken unter Windows 8.1
Hinweis
Ab Windows 10 (WDDM 2.0) wird das Betriebssystem mit einem integrierten Miracast-Stapel ausgeliefert, der auf jeder GPU funktionieren kann. Informationen zum Microsoft Miracast-Stapel und den Anforderungen von Treibern und Hardware zur Unterstützung von Miracast-Displays ab Windows 10 finden Sie in der folgenden Dokumentation:
Erstellen erstklassiger Drahtloser Projektionslösungen mit Windows 10
Die entsprechende WHLK-Dokumentation unter Device.Graphics.WDDM13.DisplayRender.WirelessDisplay
Treiberentwickler sollten keinen benutzerdefinierten Miracast-Stapel mehr implementieren. Microsoft entfernt möglicherweise die Unterstützung für benutzerdefinierte Miracast-Stapel in einer zukünftigen Version von Windows.
Unter Windows 8.1 kann die Anzeigehardware jeden Videoframe verarbeiten, der über eine drahtlose Miracast-Anzeigeverbindung gesendet wird, indem er den Frame in mehrere Teile aufteilt oder Blöcke codiert. Jeder Block verfügt über eine eindeutige Block-ID, die aus der Framenummer und der Frameteilnummer (oder segment) generiert wird. Jedem Block, der mit demselben Desktopframeupdate verknüpft ist, muss dieselbe Framenummer zugewiesen werden.
Berichterstellungsabschnittsverarbeitung
Ein Treiber kann einen Frame codieren, der über eine Drahtlose Miracast-Verbindung gesendet wird, entweder in mehreren Verarbeitungsschritten , z. B. beim Trennen der Farbkonvertierung von der Codierung, oder in einem einzigen Schritt. Jedem Verarbeitungsschritt sollte eine eindeutige Frameteilnummer innerhalb des Frames zugewiesen werden.
Entweder der Miracast-Benutzermodustreiber oder der Display-Miniporttreiber muss das Betriebssystem jedes Mal benachrichtigen, wenn:
- Die Hardware hat einen Verarbeitungsschritt für einen Frame abgeschlossen.
- Unmittelbar bevor jeder Teil des Frames an das Netzwerk gesendet wird.
Die Zeit eines bestimmten gemeldeten Verarbeitungsschritts wird als Zeitpunkt angenommen, zu dem das Ereignis an das Betriebssystem gemeldet wurde, daher ist es wichtig, die Phasen so schnell wie möglich zu melden.
Das Betriebssystem führt keine andere Aktion aus, als diese Ereignisse mithilfe der Ablaufverfolgungseinrichtung auf Kernelebene für Windows (ETW) zu protokollieren. Diese Informationen sind dennoch wichtig für die Messung und Untersuchung von Leistungsproblemen.
Ein Treiber kann die Benachrichtigung mithilfe einer der folgenden möglichen Möglichkeiten bereitstellen:
- Der Miracast-Benutzermodustreiber ruft die ReportStatistic-Rückruffunktion auf, um Details mit dem MIRACAST_STATISTIC_TYPE_CHUNK_PROCESSING_COMPLETE Typ zu melden, oder mit MIRACAST_STATISTIC_TYPE_CHUNK_SENT , um anzugeben, dass der Block zur Übertragung an den Netzwerkstapel gesendet werden soll.
- Der Miniporttreiber meldet Details der Blockverarbeitung mit dem DXGK_INTERRUPT_MICACAST_CHUNK_PROCESSING_COMPLETE Interrupttyp, obwohl dieser Bericht nur zur Unterbrechungszeit erfolgen kann. Zusätzlich zur Protokollierung der Blockinformationen wird ein Blockpaket erstellt und in die Warteschlange gestellt, sodass der Miracast-Benutzermodustreiber sie abrufen kann, indem die GetNextChunkData-Rückruffunktion aufgerufen wird.
- Der Miniporttreiber der Anzeige ruft die DxgkCbReportChunkInfo-Rückruffunktion auf jeder IRQL-Ebene auf. Diese Funktion protokolliert nur die Blockinformationen und stellt keine Blockpakete in die Warteschlange.
Die gleiche Framenummer und Teilenummern sollten verwendet werden, wenn das Desktopimage nicht aktualisiert wird, aber der Treiber das Desktopimage erneut codieren muss, um die Qualität zu verbessern. Die Leistungstools lösen das zweite codierte vollständige Ereignis für denselben Frame und die gleiche Teilnummer aus, was angibt, dass eine zweite Codierung desselben Frames ausgeführt wurde.
Das letzte Segment jedes Frames muss eine Frameteilnummer null aufweisen, was das letzte Segment des Frames für Leistungstools angibt.
Um die korrekte Synchronisierung der primären Oberfläche sicherzustellen, sollte, wenn die Pixelpipeline die Codierung ausführt, alle angeforderten Flip-Vorgänge in einem VSync-Intervall nicht gemeldet werden, bevor die Codierung den Zugriff auf die primäre Oberfläche abgeschlossen hat. Dieses Verhalten verhindert, dass der Referenten auf der primären Oberfläche gerendert wird, während das codierte Modul sie liest.
Der Miracast-Benutzermodustreiber sollte das Betriebssystem in den einzelnen Phasen der Verarbeitung des Frames informieren:
Startframe, Blocktyp MIRACAST_CHUNK_TYPE_FRAME_START
Stellt den Punkt dar, an dem das Betriebssystem den Treiber auffordern, den neuen Desktopframe anzuzeigen. Obwohl technisch der Miracast-Benutzermodustreiber diese Phase melden könnte, umfasst der Beginn der Verarbeitung eines neuen Frames immer den Anzeige-Miniporttreiber und sollte daher von diesem Treiber gemeldet werden.
Farbkonvertierung abgeschlossen, Blocktyp MIRACAST_CHUNK_TYPE_COLOR_CONVERT_COMPLETE
Einige Lösungen verfügen über separate Farbkonvert- und Codierungsphasen. In solchen Lösungen sollte das vollständige Verarbeitungsereignis für die Farbkonvertung so schnell wie möglich gemeldet werden, und der Treiber sollte die DXGK_MIRACAST_CHUNK_INFO verwenden.ProcessingTime-Member , um die Zeit zu melden, die für die Ausführung des Vorgangs für die Hardware benötigt wurde. Wenn der gesamte Frame alle gleichzeitig und nicht in Segmenten konvertiert wird, sollte die Teilenummer null sein.
Codieren des vollständigen, blocktyps MIRACAST_CHUNK_TYPE_ENCODE_COMPLETE
Gibt an, dass die H.264-Codierung abgeschlossen wurde. Die Member "ProcessingTime " und "EncodeRate " der DXGK_MIRACAST_CHUNK_INFO-Struktur sollten abgeschlossen werden.
Frame send, calling ReportStatistic using MIRACAST_STATISTIC_TYPE_CHUNK_SENT
Gibt an, dass der Miracast-Benutzermodustreiber das Datenpaket für diese Frame-/Teilnummer zur Übertragung an die Netzwerk-API sendet. Wenn die Daten für diesen Frame/Teil mithilfe mehrerer Aufrufe an die Netzwerk-API gesendet werden, sollte sie nur vor dem Senden des ersten Pakets protokolliert werden. Der Aufruf sollte direkt vor dem Aufrufen der Netzwerk-API erfolgen. Diese Anzeigedauer ist wichtig, denn wenn die Netzwerk-API Aufrufe blockiert, soll diese blockierte Zeit nicht für die Verarbeitung des Frames im Grafikstapel gezählt werden.
Verworfener Rahmen, Blocktyp MIRACAST_CHUNK_TYPE_FRAME_DROPPED
Wenn der Treiber zu einem beliebigen Zeitpunkt entscheidet, dass er die Verarbeitung des Frames/Teils nicht abgeschlossen und an die Spüle sendet, sollte er den verworfenen Frame melden. In diesem Zusammenhang wird ein Frame nur als verworfen betrachtet, wenn der Treiber die Verarbeitung tatsächlich gestartet hat, indem MIRACAST_CHUNK_TYPE_FRAME_START protokolliert wird. Wenn ein Treiber berechnet, dass dieser Frame ohne Verarbeitung übersprungen wird, kann er MIRACAST_CHUNK_TYPE_FRAME_DROPPED protokollieren, ohne MIRACAST_CHUNK_TYPE_FRAME_START zu protokollieren.
Treiber definierter Blocktyp MIRACAST_CHUNK_TYPE_ENCODE_DRIVER_DEFINED_1 oder _2
Diese Blocktypen stehen zur Verfügung, um die Leistung eines Szenarios zu verstehen. Beispiele hierfür sind:
- Der Treiber verwendet diese Typen, um anzugeben, dass für diesen Frame ein I-Frame erstellt wurde.
- Der Treiber protokolliert ein weiteres Paket, nachdem das letzte Segment des Frames an Netzwerk-APIs gesendet wurde, die die Gesamtgröße des codierten Frames enthielten.
Beispiele für die Framefarbkonvertierung
Die folgenden Beispiele zeigen, wie die Framefarbe konvertiert wird und wie der Anzeigeminiporttreiber den Abschluss der Farbkonvertierung meldet.
Tabellenverweise auf die Elemente der MIRACAST_CHUNK_INFO-Struktur sind:
ChunkType ist ein MIRACAST_CHUNK_TYPE_XXX-Wert .
FrameNumber und PartNumber sind Mitglieder der ChunkId-Union.
ProcessingTime ist die Zeit in Mikrosekunden.
EncodeRate liegt in Kilobits pro Sekunde.
MIRACAST_STATISTIC_TYPE_CHUNK_SENT wird in Verarbeitungsphasen mit Aufrufen von ReportStatistic verwendet.
Melden eines einzelnen Frames ohne Verwendung von Segmenten
Verarbeitungsphase | ChunkType | FrameNumber | PartNumber | Verarbeitungszeit | EncodeRate |
---|---|---|---|---|---|
Starten des Verarbeitungsrahmens | FRAME_START | 101 | 0 | 0 | 0 |
Die Farbkonvertierung ist abgeschlossen. | COLOR_CONVERT_COMPLETE | 101 | 0 | 950 | 0 |
Codieren ist abgeschlossen | ENCODE_COMPLETE | 101 | 0 | 1042 | 15000 |
Direkt vor dem Anruf zum Senden von Daten an den ReportStatistic-Netzwerkanruf | Nicht zutreffend | 101 (Wert von ChunkSent.ChunkId.FrameNumber) | 0 (Wert von ChunkSent.ChunkId.PartNumber) | Nicht zutreffend | Nicht zutreffend |
Melden eines einzelnen Frames, verarbeitet mithilfe von Segmenten
Verarbeitungsphase | ChunkType | FrameNumber | PartNumber | Verarbeitungszeit | EncodeRate |
---|---|---|---|---|---|
Starten des Verarbeitungsrahmens | FRAME_START | 101 | 0 | 0 | 0 |
Die Farbkonvertierung ist abgeschlossen. | COLOR_CONVERT_COMPLETE | 101 | 0 | 950 | 0 |
Die Codierung von Segment 1 ist abgeschlossen. | ENCODE_COMPLETE | 101 | 1 | 1042 | 15000 |
Die Codierung von Segment 2 ist abgeschlossen. | ENCODE_COMPLETE | 101 | 0 | 400 | 15000 |
Direkt vor dem Anruf zum Senden von Daten in Segment 1 an den ReportStatistic-Netzwerkanruf | Nicht zutreffend | 101 (Wert von "ChunkSent.ChunkId.FrameNumber " für Segment 1) | 1 (Wert von ChunkSent.ChunkId.PartNumber für Segment 1) | Nicht zutreffend | Nicht zutreffend |
Direkt vor dem Anruf zum Senden von Daten in Segment 2 an den ReportStatistic-Netzwerkanruf | Nicht zutreffend | 101 (Wert von ChunkSent.ChunkId.FrameNumber für Segment 2) | 0 (Wert von "ChunkSent.ChunkId.FrameNumber " für Segment 2) | Nicht zutreffend | Nicht zutreffend |
Melden eines ursprünglichen Frames, verarbeitet und dann erneut codiert, ohne Datenschnitte zu verwenden
Verarbeitungsphase | ChunkType | FrameNumber | PartNumber | Verarbeitungszeit | EncodeRate |
---|---|---|---|---|---|
Starten des Verarbeitungsrahmens | FRAME_START | 101 | 0 | 0 | 0 |
Die Farbkonvertierung ist abgeschlossen. | COLOR_CONVERT_COMPLETE | 101 | 0 | 950 | 0 |
Codieren ist abgeschlossen | ENCODE_COMPLETE | 101 | 0 | 1042 | 15000 |
Direkt vor dem Anruf zum Senden von Daten für den ursprünglichen Frame an den ReportStatistic-Netzwerkanruf | Nicht zutreffend | 101 (Wert von ChunkSent.ChunkId.FrameNumber) | 0 (Wert von ChunkSent.ChunkId.PartNumber) | Nicht zutreffend | Nicht zutreffend |
Erneutes Codieren ist abgeschlossen | ENCODE_COMPLETE | 101 | 0 | 500 | 15000 |
Direkt vor dem Aufruf zum Senden von Daten für den recodierten Frame an das Netzwerk ReportStatistic | Nicht zutreffend | 101 (Wert von ChunkSent.ChunkId.FrameNumber) | 0 (Wert von ChunkSent.ChunkId.PartNumber) | Nicht zutreffend | Nicht zutreffend |
Melden von Protokollereignissen
Wenn der Miracast-Benutzermodustreiber Protokollereignisse meldet, indem die ReportStatistic-Funktion mit MIRACAST_STATISTIC_DATA aufgerufen wird. "StatisticType" wird auf MIRACAST_STATISTIC_TYPE_EVENT festgelegt, das Ereignis wird vom Betriebssystem protokolliert, jedoch keine andere Aktion ausgeführt. Diese Ereignisse sind jedoch für die Diagnose- und Leistungsuntersuchung wertvoll.
Die MIRACAST_PROTOCOL_EVENT-Aufzählung enthält mögliche Protokollereignistypen, die gemeldet werden können.
Melden von Protokollfehlern
Während eine verbundene Miracast-Sitzung ausgeführt wird, wenn ein Miracast-Benutzermodustreiber einen Fehler erkennt, sollte die ReportSessionStatus-Rückruffunktion mit den entsprechenden MIRACAST_STATUS Fehlerstatusinformationen im MiracastStatus-Parameter aufgerufen werden. Die Betriebssitzung zerstört immer die Sitzung, wenn ein Fehler gemeldet wird.
Obwohl das Betriebssystem lediglich den ReportSessionStatus-Statusparameter für die Diagnose protokolliert und keine Aktion basierend auf seinem Wert ergreift, sollte der Treiber diesen Parameter verwenden, um zwischen verschiedenen Ursachen des Fehlers zu unterscheiden.