Invio di pacchetti di richiesta di I/O asincroni nel bus IEEE 1394
I driver usano REQUEST_ASYNC_READ, REQUEST_ASYNC_WRITE e REQUEST_ASYNC_LOCK per inviare operazioni di lettura, scrittura e blocco asincrone a un dispositivo nel bus IEEE 1394. Per REQUEST_ASYNC_READ e REQUEST_ASYNC_WRITE, i parametri specifici dell'operazione dell'IRB vengono archiviati in u.AsyncRead o u.AsyncWrite membri dell'IRB.
Tipi di indirizzamento
I driver che effettuano richieste di I/O asincrone devono specificare un indirizzo di destinazione di tipo IO_ADDRESS nel membro DestinationAddress dell'IRB. L'indirizzo di destinazione è costituito da due valori: l'indirizzo del nodo e l'offset dell'indirizzo. L'interpretazione che il driver del bus dà a questi due valori dipende dalla modalità di indirizzamento usato dal driver che avvia la richiesta.
Sono disponibili tre modalità di indirizzamento per inviare pacchetti asincroni 1394: normali, non elaborati e virtuali.
In modalità normale che indirizza il driver che avvia la richiesta fornisce un offset di indirizzi, ma non specifica l'indirizzo del nodo del dispositivo di destinazione. Il driver del bus riempie l'indirizzo del nodo usando informazioni archiviate nel PDO del dispositivo quando enumera il dispositivo.
Nell'indirizzamento in modalità non elaborata, il driver che avvia la richiesta deve fornire sia l'indirizzo del nodo che l'offset dell'indirizzo. Inoltre, anziché inviare la richiesta all'oggetto PDO del dispositivo di destinazione, il driver deve inviare la richiesta all'oggetto PDO del controller host. In questo modo il driver del bus informa che non deve sovrascrivere le informazioni sull'indirizzo del nodo nel pacchetto.
Nell'indirizzamento in modalità virtuale, il driver che avvia la richiesta deve in modo esplicito indicare l'indirizzo del nodo del dispositivo di destinazione nel pacchetto, proprio come nell'indirizzamento in modalità non elaborata. Tuttavia, i dispositivi virtuali non dispongono di indirizzi di nodo reali nel bus 1394. L'indirizzo del nodo di un dispositivo virtuale è solo un valore stabilito dalla convenzione che consente al driver del dispositivo virtuale di identificare i pacchetti. Quando funziona correttamente, un driver di dispositivo virtuale deve ricevere tutti i pacchetti che vengono trasmessi sul bus e sift attraverso di essi cercando pacchetti che contengono il valore preestabliato per il relativo "indirizzo nodo".
Un driver che avvia una richiesta per un dispositivo virtuale non deve eseguire alcuna procedura speciale per impedire al driver del bus di sovrascrivere l'indirizzo del nodo registrato nel pacchetto. Quando il driver del bus enumera prima un dispositivo virtuale, imposta un flag nell'estensione del dispositivo dell'oggetto PDO del dispositivo che indica che il dispositivo è virtuale. Durante la ricezione di una richiesta per questo dispositivo, il driver del bus è in grado di verificare che sia un dispositivo virtuale e non sovrascrive l'indirizzo del nodo nel pacchetto.
Buffering delle richieste di I/O
Un driver che avvia una richiesta di I/O asincrona deve fornire un puntatore a un MDL che specifica il buffer di I/O. Inserisce questo puntatore nel membro Mdl di IRB. Il driver del bus usa questo buffer per copiare i dati letti dal dispositivo o come origine dei dati scritti nel dispositivo.
I driver specificano le dimensioni del buffer di dati nel membro nNumberOfBytesToRead o nNumberOfBytesToWrite di u.AsyncXXX e le dimensioni del blocco nel membro nBlockSize . Quando la transazione viene effettivamente eseguita, il driver del bus suddivide i dati in pacchetti delle dimensioni specificate in nBlockSize. Per impostazione predefinita, il driver del bus legge o scrive i dati in modo contiguo: ogni blocco viene letto da o scritto in posizioni successive nello spazio indirizzi del dispositivo.
Il diagramma seguente illustra blocchi di dati contigui.
Facoltativamente, il driver può specificare il flag di ASYNC_FLAGS_NONINCREMENTING per la richiesta; quindi il driver del bus userà lo stesso set di indirizzi per ogni blocco.
Il diagramma seguente illustra blocchi di dati asincroni che non aumentano.
Avviso Il driver del bus applica le dimensioni massime dei pacchetti asincroni per la velocità di connessione corrente tra il dispositivo e il computer e la velocità massima segnalata dal dispositivo nel campo MAX_REC della relativa ROM di configurazione. Se nBlockSize è maggiore di uno di questi valori, il driver del bus usa il valore applicato per le dimensioni del blocco. Se il driver imposta il flag di ASYNC_FLAGS_NONINCREMENTING, è improbabile che venga dato il comportamento desiderato. Se i driver impostano questo flag, devono verificare che le dimensioni del blocco siano inferiori alle limitazioni applicate prima di inviare la richiesta.
Invio di richieste di blocco
Il protocollo del bus IEEE 1394 fornisce richieste di blocco asincrone, che consentono operazioni atomica, test e set-type. Oltre a specificare l'indirizzo di destinazione (in u.AsyncLock.DestinationAddress), il driver specifica il tipo di transazione (in u.AsyncLock.fulTransactionType). Il valore dei dati e il valore dell'argomento dell'operazione (vedere la specifica IEEE 1394 per informazioni dettagliate) vengono passati in u.AsyncLock.DataValues e u.AsyncLock.Arguments.
Generazione di reimpostazione del bus
Un driver di dispositivo che usa I/O asincrono tiene traccia della generazione di reimpostazione del bus. In ogni richiesta asincrona, il driver di dispositivo segnala il valore nel membro u.AsyncXxx.ulGeneration della richiesta. Il driver del bus confronta tale valore con il conteggio della generazione effettiva e, se non riesce a corrispondere, la richiesta ha esito negativo con un valore di stato di STATUS_INVALID_GENERATION. Se una richiesta ha esito negativo in questo modo, il driver deve eseguire una query per la generazione corretta usando la richiesta del bus di REQUEST_GET_GENERATION_COUNT. Tuttavia, il driver non deve riemettere alcuna richiesta che non è riuscita con questo stato fino a quando non recupera nuova generazione nel callback di notifica reimpostazione del bus. Ciò garantisce che il dispositivo sia ancora presente sul bus. Si noti che i driver client non devono dipendere da IRP_MN_BUS_RESET per ricevere una notifica di reimpostazione del bus. IRP_MN_BUS_RESET è obsoleto in Windows XP e nei sistemi operativi successivi.