SPB-E/A-Anforderungen

Das vom System bereitgestellte CTL_CODE Makro, das unter Definieren von E/A-Steuerungscodes beschrieben wird, wird verwendet, um IOCTL_SPB_*-Steuerelementcodes in Spb.h zu definieren.

IOCTL_SPB_EXECUTE_SEQUENCE-Steuerelementcode

Der IOCTL_SPB_EXECUTE_SEQUENCE E/A-Steuerungscode ermöglicht es einem Client (Peripherietreiber) des SPB-Controllertreibers, eine Sequenz von Übertragungen (Lese- und Schreibvorgänge) als einzelnen, atomaren Vorgang mit einer E/A-Anforderung durchzuführen. Das angegebene Gerät im Bus ist das Ziel für alle Übertragungen in der Sequenz.

Durch die Angabe einer Sequenz von Übertragungen fester Länge als einzelner, atomischer Vorgang ermöglicht die IOCTL_SPB_EXECUTE_SEQUENCE E/A-Steuerungsanforderung dem Controllertreiber, die E/A-Übertragungen zu optimieren und die Leistung zu verbessern.

Der Client sendet diese E/A-Steuerungsanforderung an das Dateiobjekt für das Zielgerät.

Ein SPB-Controllertreiber registriert eine EvtSpbControllerIoSequence-Rückruffunktion, um die Busübertragungen für eine E/A-Übertragungssequenz durchzuführen. Die SPB-Frameworkerweiterung (SpbCx) ruft diese Funktion auf, um eine IOCTL_SPB_EXECUTE_SEQUENCE-Anforderung zur Verarbeitung an den SPB-Controllertreiber zu übergeben.

IOCTL_SPB_EXECUTE_SEQUENCE Eingabepuffer

Der Eingabepuffer ist eine SPB_TRANSFER_LIST-Struktur, die eine Liste von Zeigern auf die Datenpuffer des Clients enthält. Diese Liste enthält einen Datenpuffer für jede Übertragung (Lese- oder Schreibzugriff) in der E/A-Übertragungssequenz.

IOCTL_SPB_EXECUTE_SEQUENCE Länge des Eingabepuffers

Die Größe einer SPB_TRANSFER_LIST-Struktur.

IOCTL_SPB_EXECUTE_SEQUENCE status Block

Wenn der Vorgang erfolgreich ist, legt der Controllertreiber den Status-Member auf STATUS_SUCCESS und den Information-Member auf die Gesamtzahl der während der Sequenz übertragenen Bytes fest.

Dieser Vorgang kann aus verschiedenen Gründen fehlschlagen, z. B. geringe Ressourcen, ungültige Clienteingaben und Gerätefehler.

Wenn der Controllertreiber beginnt, die E/A-Anforderung zu verarbeiten, aber während einer der Übertragungen in der Sequenz ein Fehler auftritt (z. B. signalisiert das Zielgerät einem NACK, um die Übertragung abzulehnen), bricht der Controllertreiber die verbleibenden Übertragungen in der Sequenz ab. Der Treiber legt dann die Vervollständigung status auf STATUS_SUCCESS fest, legt den Information-Member auf die Anzahl der Bytes fest, die vor dem Auftreten des Fehlers erfolgreich übertragen wurden, und schließt die Anforderung ab.

IOCTL_SPB_FULL_DUPLEX-Steuerelementcode

Der IOCTL_SPB_FULL_DUPLEX Steuercode wird von einem Client (Peripherietreiber) verwendet, um einen Vollduplex-E/A-Vorgang anzufordern. Vollduplex-E/A-Vorgänge werden von Controllern für Busse wie SPI unterstützt, die gleichzeitig Daten lesen und schreiben können. Das vom System bereitgestellte CTL_CODE Makro, das unter Definieren von E/A-Steuerungscodes beschrieben wird, wird verwendet, um IOCTL_SPB_FULL_DUPLEX wie folgt zu definieren.

Der Benutzermodustreiber oder Kernelmodustreiber für ein Gerät im Bus sendet diese E/A-Steuerungsanforderung an das Dateiobjekt für das Zielgerät.

Diese IOCTL wird nur von SPB-Controllertreibern für Busse wie SPI unterstützt, die Daten gleichzeitig lesen und schreiben können.

Die Schreib- und Lesepuffer für die Vollduplexübertragung werden durch eine SPB_TRANSFER_LIST-Struktur beschrieben. Diese Struktur muss das folgende Format verwenden:

  • Das Array der SPB_TRANSFER_LIST_ENTRY-Strukturen enthält genau zwei Elemente. Das erste Element beschreibt den Schreibpuffer (Direction = SpbTransferDirectionToDevice). Das zweite Element beschreibt den Lesepuffer (Direction = SpbTransferDirectionFromDevice).

  • Die DelayInUs-Member der beiden SPB_TRANSFER_LIST_ENTRY-Strukturen müssen null sein. Die Pufferformate für den Schreibpuffer und den Lesepuffer können wie folgt sein:

    • SpbTransferBufferFormatSimple
    • SpbTransferBufferFormatList
    • SpbTransferBufferFormatSimpleNonPaged
    • SpbTransferBufferFormatMdl

    Die letzten beiden Formate in der vorherigen Liste können nur von Kernelmodusclients verwendet werden. Die Formate für die Schreib- und Lesepuffer müssen nicht identisch sein. Weitere Informationen zu diesen Pufferformaten finden Sie unter SPB_TRANSFER_BUFFER_FORMAT.

Bei einem erfolgreichen Vorgang kann der Information-Member auf einen Wert festgelegt werden, der kleiner als die Summe der Größen des Schreib- und Lesepuffers ist. Dies kann auftreten, wenn die Anforderung abgebrochen wird, oder wenn der Vorgang den vollständigen Inhalt des Schreibpuffers nicht auf das Gerät schreiben oder den Lesepuffer nicht vollständig mit Daten füllen kann, die vom Gerät gelesen werden.

Die Schreib- und Lesepuffergrößen müssen nicht identisch sein. Wenn der Schreibpuffer größer als der Lesepuffer ist, schreibt der Vorgang weiterhin Daten aus dem Schreibpuffer, nachdem der Lesepuffer voll ist. Wenn der Lesepuffer größer als der Schreibpuffer ist, füllt der Vorgang den Lesepuffer weiter, nachdem der Schreibpuffer geleert wurde.

Wenn ein SPB-Controllertreiber eine EvtSpbControllerIoOther-Rückruffunktion registriert, ruft die SPB-Frameworkerweiterung (SpbCx) diese Funktion auf, um eine IOCTL_SPB_FULL_DUPLEX Anforderung zur Verarbeitung an den SPB-Controllertreiber zu übergeben. SpbCx führt keine Parameterüberprüfung, Übertragungslistenüberprüfung oder andere Verarbeitung für eine IOCTL_SPB_FULL_DUPLEX-Anforderung durch.

Weitere Informationen dazu, wie ein SPB-Controllertreiber die Unterstützung für diese IOCTL implementiert, finden Sie unter Handling IOCTL_SPB_FULL_DUPLEX Requests.For more information about how a SPB controller driver implements support for this IOCTL, see Handling IOCTL_SPB_FULL_DUPLEX Requests.

IOCTL_SPB_FULL_DUPLEX-Eingabepuffer

Ein Zeiger auf eine SPB_TRANSFER_LIST-Struktur, die Zeiger auf die Eingabe- und Ausgabedatenpuffer des Clients enthält. Diese Struktur enthält ein Transfers-Array aus genau zwei Elementen. Das erste Element beschreibt den Puffer, der die Daten enthält, die auf das Gerät geschrieben werden sollen. Das zweite Element beschreibt den Puffer, der verwendet wird, um die vom Gerät gelesenen Daten zu halten. Weitere Informationen dazu, wie ein SPB-Controllertreiber eine benutzerdefinierte I/O-Steuerelementanforderung (IOCTL) implementiert, die SPB_TRANSFER_LIST Strukturen verwendet, um Puffer zu beschreiben, finden Sie unter Verwenden der SPB_TRANSFER_LIST struktur für benutzerdefinierte IOCTLs.

IOCTL_SPB_FULL_DUPLEX Länge des Eingabepuffers

Die Größe einer SPB_TRANSFER_LIST-Struktur.

IOCTL_SPB_FULL_DUPLEX status Block

Wenn der Vorgang erfolgreich ist, legt der Controllertreiber den Status-Member auf STATUS_SUCCESS und das Information-Element auf die Gesamtanzahl der übertragenen Bytes (gelesene Bytes plus geschriebene Bytes) während des Vollduplexvorgangs fest.

Dieser Vorgang kann aus verschiedenen Gründen fehlschlagen, z. B. geringe Ressourcen, ungültige Clienteingaben und Gerätefehler.

IOCTL_SPB_LOCK_CONNECTION Steuerungscode

Der IOCTL_SPB_LOCK_CONNECTION Steuercode wird von einem Client (Peripherietreiber) verwendet, um die Verbindungssperre auf einem SPB-verbundenen Zielgerät abzurufen, das für einen anderen Client freigegeben ist. Während ein Client die Verbindungssperre besitzt, hat dieser Client exklusiven Zugriff auf das Gerät. Das vom System bereitgestellte CTL_CODE Makro, das unter Definieren von E/A-Steuerungscodes beschrieben wird, wird verwendet, um IOCTL_SPB_LOCK_CONNECTION wie folgt zu definieren.

Die IOCTL_SPB_LOCK_CONNECTION und IOCTL_SPB_UNLOCK_CONNECTION anforderungen die Verbindungssperre auf einem Zielgerät, das an einen einfachen Peripheriebus angeschlossen ist, abzurufen und freizugeben. Die meisten Clients verwenden diese E/A-Steuerungsanforderungen nicht. Diese Anforderungen werden nur verwendet, wenn zwei Clients den Zugriff auf dasselbe Zielgerät gemeinsam nutzen. Weitere Informationen finden Sie unter SPB-Verbindungssperren.

Zwei Clients können separate logische Verbindungen mit demselben Zielgerät öffnen und die Verbindungssperre verwenden, wenn ein Client exklusiven Zugriff auf das Gerät benötigt. Wenn ein Client die Sperre hält, werden E/A-Anforderungen an das Gerät vom zweiten Client automatisch zurückgestellt, bis der erste Client die Sperre freigibt.

Ein Client kann gleichzeitig eine Verbindungssperre auf dem Zielgerät und eine Controllersperre auf dem SPB-Controller halten. Die IOCTL_SPB_LOCK_CONTROLLER- und IOCTL_SPB_UNLOCK_CONTROLLER-Anforderungen rufen die Controllersperre ab und geben sie frei. Der Client muss die Verbindungssperre vor dem Abrufen der Controllersperre erwerben und die Controllersperre vor dem Freigeben der Verbindungssperre freigeben. Ein Client verwendet eine Controllersperre, um eine geordnete Gruppe von Busübertragungen (Lese- und Schreibvorgänge) als einzelnen Atombusvorgang auszuführen. Weitere Informationen finden Sie unter E/A-Übertragungssequenzen.

Eine Verbindungssperre wird automatisch beendet, wenn eine IRP_MJ_CLEANUP Anforderung an ein Zielgerät gesendet wird, während die Verbindung auf dem Gerät gesperrt ist. Eine Bereinigungsanforderung wird an ein Zielgerät gesendet, wenn ein Client sein Dateihandle auf dem Gerät schließt.

IOCTL_SPB_LOCK_CONNECTION status Block

Wenn der Vorgang erfolgreich ist, wird der Status-Member auf STATUS_SUCCESS festgelegt.

Wenn der Vorgang fehlschlägt, wird der Status-Member auf einen entsprechenden Fehler status Code festgelegt.

Wenn der Client bereits die Verbindungssperre auf dem Zielgerät oder die Controllersperre auf dem SPB-Controller besitzt, schlägt dieser Vorgang mit Status = STATUS_INVALID_DEVICE_REQUEST fehl. Dieser Vorgang kann aus anderen Gründen fehlschlagen, z. B. geringe Ressourcen, ungültige Clienteingaben und Gerätefehler.

IOCTL_SPB_LOCK_CONTROLLER-Steuerungscode

Der IOCTL_SPB_LOCK_CONTROLLER Steuercode wird von einem Client (Peripherietreiber) verwendet, um den SPB-Controller zu sperren. Während der Controller gesperrt ist, nutzt der Client den Bus exklusiv, um auf das angegebene Zielgerät für die Sperre zuzugreifen. Das vom System bereitgestellte CTL_CODE Makro, das unter Definieren von E/A-Steuerungscodes beschrieben wird, wird verwendet, um IOCTL_SPB_LOCK_CONTROLLER wie folgt zu definieren.

Um die exklusive Verwendung des Busses für den Zugriff auf ein Zielgerät zu erhalten, sendet ein Client (Peripherietreiber) diese IOCTL an das Dateiobjekt für das Ziel. Nach Abschluss dieser IOCTL ist der Controller gesperrt, und alle E/A-Übertragungen (Lese- oder Schreibzugriff) auf dem Bus greifen auf das angegebene Ziel zu. Zwischen den Übertragungen behält der Controller die Auswahl des Zielgeräts bei, hält aber die Uhr an.

Der Controller bleibt gesperrt, bis der Client eine IOCTL_SPB_UNLOCK_CONTROLLER Anforderung zum Entsperren des Controllers sendet. Wenn die Abfolge der Übertragungen des Clients zum oder vom Zielgerät abgeschlossen ist, muss der Client den Controller entsperren, damit der Controller E/A-Anforderungen für andere Ziele im Bus verarbeiten kann.

Eine Sperre wird automatisch beendet, wenn eine IRP_MJ_CLEANUP Anforderung an ein Zielgerät gesendet wird, während der Controller auf dem Ziel gesperrt ist. Eine Bereinigungsanforderung wird an ein Ziel gesendet, wenn ein Client sein Handle für das Ziel schließt.

SPB-Controller müssen IOCTL_SPB_LOCK_CONTROLLER- und IOCTL_SPB_UNLOCK_CONTROLLER-Anforderungen nicht unterstützen, und Treiber für Peripheriegeräte sollten nicht davon ausgehen, dass sie unterstützt werden.

Wenn ein SPB-Controllertreiber eine EvtSpbControllerLock-Rückruffunktion registriert, ruft die SPB-Frameworkerweiterung (SpbCx) diese Funktion auf, um eine IOCTL_SPB_LOCK_CONTROLLER Anforderung zur Verarbeitung an den SPB-Controllertreiber zu übergeben.

IOCTL_SPB_LOCK_CONTROLLER status Block

Wenn der Vorgang erfolgreich ist, wird der Status-Member auf STATUS_SUCCESS festgelegt. Diese IOCTL kann einen Fehler status aus verschiedenen Gründen zurückgeben, z. B. aus einem Fehler beim Konfigurieren des Controllers für den Betrieb im Modus für exklusiven Zugriff. In diesem Modus behält der Controller die Auswahl des Zielgeräts bei, sodass es das exklusive Ziel für alle E/A-Übertragungen im Bus ist. Der Controller verbleibt in diesem Modus, bis er entsperrt wird.

IOCTL_SPB_UNLOCK_CONNECTION-Steuerelementcode

Der IOCTL_SPB_UNLOCK_CONNECTION E/A-Steuerungscode wird von einem Client (Peripherietreiber) verwendet, um die Verbindungssperre auf einem mit SPB verbundenen Zielgerät, das für einen anderen Client freigegeben wird, freizugeben. Der Client hat zuvor eine IOCTL_SPB_LOCK_CONNECTION-Anforderung gesendet, um exklusiven Zugriff auf das Gerät zu erhalten.

Die IOCTL_SPB_LOCK_CONNECTION- und IOCTL_SPB_UNLOCK_CONNECTION-Anforderungen rufen die Verbindungssperre auf einem Zielgerät, das an einen einfachen Peripheriebus angeschlossen ist, ab und geben sie frei. Die meisten Clients verwenden diese E/A-Steuerungsanforderungen nicht. Diese Anforderungen werden nur verwendet, wenn zwei Clients den Zugriff auf dasselbe Zielgerät gemeinsam nutzen. Weitere Informationen finden Sie unter SPB-Verbindungssperren.

Nachdem ein Client (Peripherietreiber) eine IOCTL_SPB_LOCK_CONNECTION-Anforderung an ein Zielgerät auf dem Bus sendet und die Anforderung erfolgreich abgeschlossen wurde, bleibt die Verbindung gesperrt, bis der Client eine IOCTL_SPB_UNLOCK_CONNECTION Anforderung zum Entsperren der Verbindung sendet.

Der Client sendet eine IOCTL_SPB_UNLOCK_CONNECTION Anforderung zum Freigeben der Verbindungssperre an das Zielgerät, wenn der Client keinen exklusiven Zugriff mehr auf das Gerät benötigt. Die Verbindung muss entsperrt werden, damit der andere Client auf das Gerät zugreifen kann.

IOCTL_SPB_UNLOCK_CONNECTION status Block

Wenn der Vorgang erfolgreich ist, wird das Statuselement auf STATUS_SUCCESS festgelegt.

Wenn der Vorgang fehlschlägt, wird der Statusmember auf einen entsprechenden Fehler status Code festgelegt. Wenn der Client die Verbindungssperre auf dem Zielgerät nicht hält oder wenn der Client weiterhin die Verbindungssperre auf dem SPB-Controller hält, schlägt dieser Vorgang mit Status = STATUS_INVALID_DEVICE_REQUEST fehl. Dieser Vorgang kann aus anderen Gründen fehlschlagen, z. B. niedrige Ressourcen, ungültige Clienteingaben und Gerätefehler.

IOCTL_SPB_UNLOCK_CONTROLLER Steuerungscode

Der IOCTL_SPB_UNLOCK_CONTROLLER E/A-Steuerungscode wird von einem Client (Peripherietreiber) verwendet, um den SPB-Controller zu entsperren. Der Client hat den Controller zuvor gesperrt, um den Bus exklusiv für den Zugriff auf ein Zielgerät auf dem Bus zu nutzen.

Nachdem ein Client (Peripherietreiber) eine IOCTL_SPB_LOCK_CONTROLLER E/A-Steuerungsanforderung an ein Zielgerät auf dem Bus sendet, bleibt der Controller gesperrt, bis der Client eine IOCTL_SPB_UNLOCK_CONTROLLER E/A-Steuerungsanforderung sendet, um den Controller zu entsperren. Der Client sendet diese E/A-Steuerelementanforderungen an das Dateiobjekt für das Zielgerät.

Der Client sendet eine IOCTL_SPB_UNLOCK_CONTROLLER Anforderung, wenn er eine Sequenz von Übertragungen auf dem Bus abgeschlossen hat und das Zielgerät freigeben möchte. Der Controller muss entsperrt werden, damit er E/A-Anforderungen für andere Ziele auf dem Bus verarbeiten kann.

SPB-Controller sind nicht erforderlich, um IOCTL_SPB_LOCK_CONTROLLER- und IOCTL_SPB_UNLOCK_CONTROLLER-Anforderungen zu unterstützen, und Treiber von Peripheriegeräten sollten nicht davon ausgehen, dass sie unterstützt werden.

Die SPB-Frameworkerweiterung (SpbCx) ruft die optionale EvtSpbControllerUnlock-Rückruffunktion eines SPB-Controllertreibers auf, um eine IOCTL_SPB_LOCK_CONTROLLER Anforderung an den SPB-Controllertreiber zur Verarbeitung zu übergeben.

IOCTL_SPB_UNLOCK_CONTROLLER status Block

Wenn der Vorgang erfolgreich ist, wird das Statuselement auf STATUS_SUCCESS festgelegt.

Diese IOCTL kann nur dann fehlschlagen, wenn sie von einem Client gesendet wird, für den der Controller nicht für den exklusiven Zugriff auf das angegebene Ziel gesperrt ist.