Condividi tramite


Codice di controllo SIO_SET_COMPATIBILITY_MODE

Descrizione

Il codice di controllo SIO_SET_COMPATIBILITY_MODE richiede il modo in cui lo stack di rete deve gestire determinati comportamenti per i quali il modo predefinito di gestire il comportamento può differire tra le versioni Windows.

Per eseguire questa operazione, chiamare la funzione WSAIoctl o WSPIoctl con i parametri seguenti.

int WSAIoctl(
  (socket) s,             // descriptor identifying a socket
  SIO_SET_COMPATIBILITY_MODE, // dwIoControlCode
  (LPVOID) lpvInBuffer,    // pointer to WSA_COMPATIBILITY_MODE struct
  (DWORD) cbInBuffer,      // length of input buffer
  NULL,         // output buffer
  0,       // size of output buffer
  (LPDWORD) lpcbBytesReturned,    // number of bytes returned
  (LPWSAOVERLAPPED) lpOverlapped,   // OVERLAPPED structure
  (LPWSAOVERLAPPED_COMPLETION_ROUTINE) lpCompletionRoutine,  // completion routine
);
int WSPIoctl(
  (socket) s,             // descriptor identifying a socket
  SIO_SET_COMPATIBILITY_MODE, // dwIoControlCode
  (LPVOID) lpvInBuffer,    // pointer to WSA_COMPATIBILITY_MODE struct
  (DWORD) cbInBuffer,      // length of input buffer
  NULL,         // output buffer
  0,       // size of output buffer
  (LPDWORD) lpcbBytesReturned,    // number of bytes returned
  (LPWSAOVERLAPPED) lpOverlapped,   // OVERLAPPED structure
  (LPWSAOVERLAPPED_COMPLETION_ROUTINE) lpCompletionRoutine,  // completion routine
  (LPWSATHREADID) lpThreadId,   // a WSATHREADID structure
  (LPINT) lpErrno   // a pointer to the error code.
);

Parametri

s

Descrittore che identifica un socket.

dwIoControlCode

Codice di controllo per l'operazione. Usare SIO_SET_COMPATIBILITY_MODE per questa operazione.

lpvInBuffer

Puntatore al buffer di input. Questo parametro deve puntare a una struttura WSA_COMPATIBILITY_MODE .

cbInBuffer

Dimensione, in byte, del buffer di input. Questo parametro deve essere uguale o maggiore della dimensione della struttura WSA_COMPATIBILITY_MODE a cui punta il parametro lpvInBuffer .

lpvOutBuffer

Puntatore al buffer di output. Questo parametro non è usato per questa operazione.

cbOutBuffer

Dimensione, in byte, del buffer di output. Questo parametro deve essere impostato su zero.

lpcbBytesReturned

Puntatore a una variabile che riceve le dimensioni, in byte, dei dati archiviati nel buffer di output. Questo parametro restituito punta a un valore DWORD pari a zero per questa operazione, poiché non è presente alcun output.

lpvOverlapped

Puntatore a una struttura WSAOVERLAPPED .

Se socket s è stato creato senza l'attributo sovrapposto, il parametro lpOverlapped viene ignorato.

Se s è stato aperto con l'attributo sovrapposto e il parametro lpOverlapped non è NULL, l'operazione viene eseguita come operazione sovrapposta (asincrona). In questo caso, il parametro lpOverlapped deve puntare a una struttura WSAOVERLAPPED valida.

Per le operazioni sovrapposte, la funzione WSAIoctl o WSPIoctl restituisce immediatamente e il metodo di completamento appropriato viene segnalato al termine dell'operazione. In caso contrario, la funzione non restituisce finché l'operazione non è stata completata o si verifica un errore.

lpCompletionRoutine

Tipo: _In_opt_ LPWSAOVERLAPPED_COMPLETION_ROUTINE

Puntatore alla routine di completamento chiamata quando l'operazione è stata completata (ignorata per socket non sovrapposti).

lpThreadId

Puntatore a una struttura WSATHREADID da usare dal provider in una chiamata successiva a WPUQueueApc. Il provider deve archiviare la struttura WSATHREADID a cui si fa riferimento (non il puntatore allo stesso) fino a quando non viene restituita la funzione WPUQueueApc .

Nota Questo parametro si applica solo alla funzione WSPIoctl .

lpErrno

Puntatore al codice di errore.

Nota Questo parametro si applica solo alla funzione WSPIoctl .

Valore restituito

Se l'operazione viene completata correttamente, la funzione WSAIoctl o WSPIoctl restituisce zero.

Se l'operazione ha esito negativo o è in sospeso, la funzione WSAIoctl o WSPIoctl restituisce SOCKET_ERROR. Per ottenere informazioni estese sull'errore, chiamare WSAGetLastError.

Codice di errore Significato
WSA_IO_PENDING Un'operazione sovrapposta è stata avviata correttamente e il completamento verrà indicato in un secondo momento.
WSA_OPERATION_ABORTED Un'operazione sovrapposta è stata annullata a causa della chiusura del socket o dell'esecuzione del comando SIO_FLUSH IOCTL.
WSAEFAULT Il parametro lpOverlapped o lpCompletionRoutine non è totalmente contenuto in una parte valida dello spazio indirizzi utente.
WSAEINPROGRESS La funzione viene richiamata quando è in corso un callback.
WSAEINTR Un'operazione di blocco è stata interrotta.
WSAEINVAL Il parametro dwIoControlCode non è un comando valido o un parametro di input specificato non è accettabile oppure il comando non è applicabile al tipo di socket specificato. Questo errore viene restituito se il parametro cbInBuffer è minore della dimensione della struttura WSA_COMPATIBILITY_MODE .
WSAENETDOWN Il sottosistema di rete non è riuscito.
WSAENOPROTOOPT L'opzione socket non è supportata nel protocollo specificato.
WSAENOTCONN Il socket s non è connesso.
WSAENOTSOCK Il descrittore s non è un socket.
WSAEOPNOTSUPP Il comando IOCTL specificato non è supportato. Questo errore viene restituito se il SIO_SET_COMPATIBILITY_MODE IOCTL non è supportato dal provider di trasporto. Questo errore viene restituito anche quando viene eseguito un tentativo di usare il SIO_SET_COMPATIBILITY_MODE IOCTL in un socket di datagrammi.

Commenti

il SIO_SET_COMPATIBILITY_MODE IOCTL richiede il modo in cui lo stack di rete deve gestire determinati comportamenti per i quali il modo predefinito di gestire il comportamento può differire tra le versioni Windows. La struttura dell'argomento di input per SIO_SET_COMPATIBILITY_MODE viene specificata nella struttura WSA_COMPATIBILITY_MODE definita nel file di intestazione Mswsockdef.h . Un puntatore alla struttura WSA_COMPATIBILITY_MODE viene passato nel parametro cbInBuffer . Questa struttura è definita come segue:

// Need to #include <mswsock.h>

/* Argument structure for SIO_SET_COMPATIBILITY_MODE */
typedef struct _WSA_COMPATIBILITY_MODE {
    WSA_COMPATIBILITY_BEHAVIOR_ID BehaviorId;
    ULONG TargetOsVersion;
} WSA_COMPATIBILITY_MODE, *PWSA_COMPATIBILITY_MODE;

Il valore specificato nel membro BehaviorId indica il comportamento richiesto. Il valore specificato nel membro TargetOsVersion indica la versione Windows richiesta per il comportamento.

Il membro BehaviorId può essere uno dei valori del tipo di enumerazione WSA_COMPATIBILITY_BEHAVIOR_ID definito nel file di intestazione Mswsockdef.h . I valori possibili per il membro BehaviorId sono i seguenti:

Termine Descrizione
WsaBehaviorAll Equivale a richiedere tutti i possibili comportamenti compatibili definiti per WSA_COMPATIBILITY_BEHAVIOR_ID.
WsaBehaviorReceiveBuffering Quando il membro TargetOsVersion è impostato su un valore per Windows Vista o versioni successive, le riduzioni delle dimensioni del buffer di ricezione TCP in questo socket tramite l'opzione socket SO_RCVBUF sono consentite anche dopo l'istituzione di una connessione TCP. Quando il membro TargetOsVersion è impostato su un valore precedente a Windows Vista, le riduzioni delle dimensioni del buffer di ricezione TCP in questo socket tramite l'opzione socket SO_RCVBUF non sono consentite dopo la creazione della connessione.
WsaBehaviorAutoTuning Quando il membro TargetOsVersion è impostato su un valore per Windows Vista o versione successiva, l'ottimizzazione automatica della finestra di ricezione è abilitata e il fattore di scala della finestra TCP viene ridotto a 2 dal valore predefinito 8. Quando TargetOsVersion è impostato su un valore precedente a Windows Vista, l'ottimizzazione automatica della finestra di ricezione è disabilitata. L'opzione tcp window scaling è disabilitata e la dimensione massima della finestra di ricezione è limitata a 65.535 byte. L'opzione di ridimensionamento delle finestre TCP non può essere negoziata sulla connessione anche se l'opzione socket SO_RCVBUF è stata chiamata su questo socket specificando un valore maggiore di 65.535 byte prima che la connessione sia stata stabilita.

Il membro TargetOsVersion può essere una delle costanti di versione NTDDI definite nel file di intestazione Sdkddkver.h . Di seguito sono riportati alcuni dei possibili valori per il membro TargetOsVersion :

Termine Descrizione
NTDDI_LONGHORN Il comportamento di destinazione è l'impostazione predefinita per Windows Vista.
NTDDI_WS03 Il comportamento di destinazione è l'impostazione predefinita per Windows Server 2003.
NTDDI_WINXP Il comportamento di destinazione è l'impostazione predefinita per Windows XP.
NTDDI_WIN2K Il comportamento di destinazione è l'impostazione predefinita per Windows 2000.

L'impatto principale del membro TargetOsVersion è se questo membro è impostato su un valore uguale o maggiore di NTDDI_LONGHORN.

Le prestazioni TCP dipendono non solo dalla velocità di trasferimento stessa, ma piuttosto dal prodotto della velocità di trasferimento e dal tempo di ritardo del round trip. Questo prodotto con ritardo della larghezza di banda misura la quantità di dati che "riempirebbero la pipe". Questo prodotto con ritardo della larghezza di banda è lo spazio del buffer necessario al mittente e al destinatario per ottenere la velocità effettiva massima sulla connessione TCP sul percorso. Questo spazio buffer rappresenta la quantità di dati non riconosciuti che TCP deve gestire per mantenere la pipeline piena. I problemi di prestazioni TCP si verificano quando il prodotto con ritardo della larghezza di banda è elevato. Un percorso di rete che opera in queste condizioni viene spesso chiamato "long, fat pipe". Gli esempi includono collegamenti satellitari a alta capacità, collegamenti wireless ad alta velocità e collegamenti ottici in fibra ottica terrestre su lunghe distanze.

L'intestazione TCP usa un campo dati a 16 bit (il campo Finestra nell'intestazione del pacchetto TCP) per segnalare le dimensioni della finestra di ricezione al mittente. Pertanto, la finestra più grande che può essere usata è di 65.535 byte. Per aggirare questa limitazione, è stata aggiunta un'opzione di estensione TCP per la scalabilità delle finestre TCP per consentire a windows più grandi di 65.535 byte. L'opzione Tcp Window Scale (WSopt) è definita in RFC 1323 disponibile nel sito Web IETF. L'estensione WSopt espande la definizione della finestra TCP a 32 bit usando un fattore di scala logaritmico a un byte per estendere il campo Finestra a 16 bit nell'intestazione TCP. L'estensione WSopt definisce un fattore di scala implicito (da 2 a una potenza), che viene usato per moltiplicare il valore delle dimensioni della finestra trovato in un'intestazione TCP per ottenere le dimensioni effettive della finestra. Pertanto, un fattore di scala della finestra pari a 8 comporterebbe una dimensione di finestra vera uguale al valore nel campo Finestra nell'intestazione TCP moltiplicato per 2^8 o 256. Pertanto, se il campo Finestra nell'intestazione TCP è stato impostato sul valore massimo di 65.535 byte e il fattore di scala WSopt è stato negoziato con un valore pari a 8, la dimensione della finestra reale sarà di 16.776.960 byte.

La dimensione della finestra di ricezione vera e quindi il fattore di scala è determinato dallo spazio massimo del buffer di ricezione. Questo spazio massimo del buffer è la quantità di dati che un ricevitore TCP consente a un mittente TCP di inviare prima di dover attendere un acknowledgement. Dopo aver stabilito la connessione, le dimensioni della finestra di ricezione vengono annunciate in ogni segmento TCP (il campo Finestra nell'intestazione TCP). La pubblicità della quantità massima di dati che il mittente può inviare è un meccanismo di controllo del flusso sul lato ricevitore che impedisce al mittente di inviare dati che il destinatario non può archiviare. Un host di invio può inviare solo la quantità massima di dati annunciati dal ricevitore prima di attendere un riconoscimento e un aggiornamento delle dimensioni della finestra di ricezione.

In Windows Server 2003 e Windows XP, lo spazio di buffer di ricezione massimo che rappresenta le dimensioni della finestra di ricezione per lo stack TCP/IP ha un valore predefinito in base alla velocità di collegamento dell'interfaccia di invio. Il valore effettivo viene modificato automaticamente in incrementi pari delle dimensioni massime del segmento negoziate durante la creazione della connessione TCP. Pertanto, per un collegamento a 10 Mbit/sec, le dimensioni predefinite della finestra di ricezione vengono normalmente impostate su 16 KB, mentre in un collegamento da 100 MBit/sec la dimensione predefinita della finestra di ricezione viene impostata su 65.535 byte.

In Windows Server 2003 e Windows XP, le dimensioni massime massime della finestra di ricezione per lo stack TCP/IP possono essere configurate manualmente usando i valori del Registro di sistema seguenti in un'interfaccia specifica o per l'intero sistema:

HKEY_LOCAL_MACHINE\SYSTEM\Current Control Set\Services\Tcpip\Parameters\TCPWindowSize

HKEY_LOCAL_MACHINE\SYSTEM\Current Control Set\Services\Tcpip\Parameters\Interface\TCPWindowSize

Il valore del Registro di sistema per TCPWindowSize può essere impostato su un massimo di 65.535 byte quando non si usa l'estensione WSopt o un massimo di 1.073.741.823 byte quando viene usata l'estensione WSopt (è supportato un fattore di scala massimo pari a 4). Senza ridimensionamento delle finestre, un'applicazione può raggiungere solo una velocità effettiva di circa 5 megabit al secondo (Mbps) in un percorso con un tempo di round trip di 100 millisecondi (RTT), indipendentemente dalla larghezza di banda del percorso. Questa velocità effettiva può essere ridimensionata su un gigabit al secondo (Gbps) con ridimensionamento delle finestre, che consente a TCP di negoziare il fattore di ridimensionamento per le dimensioni della finestra durante la creazione della connessione.

In Windows Server 2003 e Windows XP, l'estensione WSopt può essere abilitata impostando il valore del Registro di sistema seguente.

HKEY_LOCAL_MACHINE\SYSTEM\Current Control Set\Services\Tcpip\Parameters\Tcp1323Opts

Il valore del Registro di sistema Tcp1323Opts è un DWORD codificato in modo che quando è impostato bit 0, l'estensione TCP WSopt è abilitata. Quando viene impostato il bit 1, l'opzione TSopt (TCP Timestamp) definita in RFC 1323 è abilitata. Pertanto, il valore 1 o 3 abiliterà l'estensione WSopt.

In Windows Server 2003 e Windows XP, l'impostazione predefinita è che i valori del Registro di sistema TCPWindowSize e Tcp1323Opts non vengono creati. Il valore predefinito è che l'estensione WSopt è disabilitata e la dimensione della finestra di ricezione TCP viene impostata dal sistema sul valore massimo di un massimo di 65.535 byte in base alla velocità del collegamento. Quando il ridimensionamento delle finestre è abilitato in Windows Server 2003 e Windows XP impostando il valore del Registro di sistema Tcp1323Opts, il ridimensionamento delle finestre su una connessione TCP viene ancora usato solo quando sia il mittente che il ricevitore includono un'opzione di ridimensionamento delle finestre TCP nel segmento di sincronizzazione (SYN) inviato l'uno all'altro per negoziare un fattore di scala della finestra. Quando si usa il ridimensionamento delle finestre in una connessione, il campo Finestra nell'intestazione TCP è impostato su 65.535 byte e il fattore di scala della finestra viene utilizzato per regolare le dimensioni della finestra di ricezione effettive verso l'alto dal fattore di scala della finestra negoziato quando viene stabilita la connessione.

Un'applicazione può specificare le dimensioni della finestra di ricezione TCP per una connessione usando l'opzione socket SO_RCVBUF . Le dimensioni della finestra di ricezione TCP per un socket possono essere aumentate in qualsiasi momento usando SO_RCVBUF, ma possono essere ridotte solo prima di stabilire una connessione. Per usare il ridimensionamento delle finestre, un'applicazione deve specificare una dimensione della finestra superiore a 65.535 byte quando si usa l'opzione socket SO_RCVBUF prima di stabilire la connessione.

Il valore ideale per le dimensioni della finestra di ricezione TCP è spesso difficile da determinare. Per riempire la capacità della rete tra il mittente e il ricevitore, le dimensioni della finestra di ricezione devono essere impostate sul prodotto con ritardo della larghezza di banda per la connessione, ovvero la larghezza di banda moltiplicata per il tempo di round trip. Anche se un'applicazione può determinare correttamente il prodotto con ritardo della larghezza di banda, non è ancora noto quanto rapidamente l'applicazione ricevente recupererà i dati dal buffer dei dati in ingresso (frequenza di recupero dell'applicazione). Nonostante il supporto per il ridimensionamento delle finestre TCP, le dimensioni massime della finestra di ricezione in Windows Server 2003 e Windows XP possono comunque limitare la velocità effettiva perché si tratta di una dimensione massima fissa per tutte le connessioni TCP (a meno che non venga specificato per ogni applicazione che usa SO_RCVBUF), che può migliorare la velocità effettiva per alcune connessioni e ridurre la velocità effettiva per altre. Inoltre, le dimensioni massime fisse della finestra di ricezione per una connessione TCP non variano con le condizioni di rete variabili.

Per risolvere il problema di determinare correttamente il valore della dimensione massima della finestra di ricezione per una connessione TCP in base alle condizioni correnti della rete, lo stack TCP/IP in Windows Vista supporta una funzionalità di ottimizzazione automatica della finestra di ricezione. Quando questa funzionalità è abilitata, l'ottimizzazione automatica della finestra di ricezione determina continuamente le dimensioni ottimali della finestra di ricezione misurando il prodotto con ritardo della larghezza di banda e la frequenza di recupero dell'applicazione e regola la dimensione massima massima della finestra di ricezione in base alle condizioni di rete variabili. L'ottimizzazione automatica della finestra di ricezione abilita l'estensione TCP WSopt per impostazione predefinita, consentendo fino a 16.776.960 byte per le dimensioni effettive della finestra. Man mano che i dati passano attraverso la connessione, lo stack TCP/IP monitora la connessione, misura il prodotto di ritardo della larghezza di banda corrente per la connessione e la frequenza di ricezione dell'applicazione e modifica le dimensioni effettive della finestra di ricezione per ottimizzare la velocità effettiva. Lo stack TCP/IP modifica il valore del campo Finestra nell'intestazione TCP in base alle condizioni di rete, poiché il fattore di scala WSopt viene risolto quando viene stabilita la connessione per la prima volta.

Lo stack TCP/IP in Windows Vista non usa più i valori del Registro di sistema TCPWindowSize. Con una migliore velocità effettiva tra peer TCP, l'utilizzo della larghezza di banda di rete aumenta durante il trasferimento dei dati. Se tutte le applicazioni sono ottimizzate per la ricezione di dati TCP, l'utilizzo complessivo della rete può aumentare notevolmente, rendendo più importante l'uso di Qualità del servizio (QoS) nelle reti che operano a o vicino alla capacità.

Il comportamento predefinito in Windows Vista per la ricezione del buffer quando SIO_SET_COMPATIBILITY_MODE non viene specificato tramite WsaBehaviorReceiveBuffering è che non è consentita alcuna riduzione delle dimensioni della finestra di ricezione utilizzando SO_RCVBUF'opzione socket dopo che è stata stabilita una connessione.

Il comportamento predefinito in Windows Vista per l'ottimizzazione automatica quando SIO_SET_COMPATIBILITY_MODE non viene specificato usando WsaBehaviorAutoTuning è che lo stack riceverà l'ottimizzazione automatica della finestra usando un fattore di scala della finestra pari a 8. Si noti che se un'applicazione imposta una dimensione valida della finestra di ricezione con l'opzione socket SO_RCVBUF , lo stack userà le dimensioni specificate e la finestra riceverà l'ottimizzazione automatica disabilitata. Windows la sincronizzazione automatica può anche essere disabilitata completamente usando il comando seguente, netsh interface tcp set global autotuninglevel=disabled, nel qual caso specificando WsaBehaviorAutoTuning non avrà alcun effetto. La sincronizzazione automatica della ricezione della finestra può essere disabilitata anche in base ai criteri di gruppo impostati in Windows Server 2008.

L'opzione WsaBehaviorAutoTuning è necessaria in Windows Vista per alcuni dispositivi gateway Internet e firewall che non supportano correttamente i flussi di dati per le connessioni TCP che usano l'estensione WSopt e un fattore di scala di Windows. In Windows Vista, un ricevitore negozia per impostazione predefinita un fattore di scala di finestra pari a 8 per una dimensione massima di finestra vera di 16.776.960 byte. Quando i dati iniziano a fluire su un collegamento rapido, Windows inizialmente inizia con una dimensione di finestra true di 64 Kilobyte impostando il campo Finestra dell'intestazione TCP su 256 e impostando il fattore di scala della finestra su 8 nelle opzioni TCP (256*2^8=64 KB). Alcuni dispositivi gateway Internet e firewall ignorano il fattore di scala della finestra e esaminano solo il campo Finestra annunciata nell'intestazione TCP specificata come 256 e eliminano i pacchetti in ingresso per la connessione che contengono più di 256 byte di dati TCP. Per supportare il ridimensionamento delle finestre di ricezione TCP, un dispositivo gateway o un firewall deve monitorare l'handshake TCP e tenere traccia del fattore di scala della finestra negoziata come parte dei dati di connessione TCP. Alcune applicazioni e implementazioni dello stack TCP in altre piattaforme ignorano anche l'estensione TCP WSopt e il fattore di ridimensionamento delle finestre. L'host remoto che invia i dati può quindi inviare dati alla frequenza pubblicizzata nel campo Finestra dell'intestazione TCP (256 byte). Ciò può comportare la ricezione dei dati molto lentamente dal ricevitore.

L'impostazione del membro BehaviorId su WsaBehaviorAutoTuning e TargetOsVersion su Windows Vista riduce il fattore di scala della finestra su 2, quindi il campo Finestra nell'intestazione TCP viene inizialmente impostato su 16.384 byte e il fattore di scala della finestra è impostato su 2 per una dimensione di ricezione della finestra reale iniziale di 64 KB. La funzionalità di ottimizzazione automatica della finestra può quindi aumentare le dimensioni della ricezione della finestra reale fino a 262.140 byte impostando il campo Finestra nell'intestazione TCP su 65.535 byte. Un'applicazione deve impostare il SIO_SET_COMPATIBILITY_MODE IOCTL non appena viene creato un socket, poiché questa opzione non ha senso o si applica dopo l'invio di un SYN. L'impostazione di questa opzione ha lo stesso impatto del comando seguente: netsh interface tcp set global autotuninglevel=highlyrestricted

Si noti che il file di intestazione Mswsockdef.h viene incluso automaticamente in Mswsock.h o Netiodef.h e non deve essere usato direttamente.

Vedi anche

Socket

WSAGetLastError

WSAGetOverlappedResult

Wsaioctl

WSAOVERLAPPED

WSASocketA

WSASocketW