WSAIoctl 函式 (winsock2.h)
WSAIoctl函式會控制通訊端模式。
語法
int WSAAPI WSAIoctl(
[in] SOCKET s,
[in] DWORD dwIoControlCode,
[in] LPVOID lpvInBuffer,
[in] DWORD cbInBuffer,
[out] LPVOID lpvOutBuffer,
[in] DWORD cbOutBuffer,
[out] LPDWORD lpcbBytesReturned,
[in] LPWSAOVERLAPPED lpOverlapped,
[in] LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine
);
參數
[in] s
識別通訊端的描述項。
[in] dwIoControlCode
要執行的作業控制程式代碼。
[in] lpvInBuffer
輸入緩衝區的指標。
[in] cbInBuffer
輸入緩衝區的大小,以位元組為單位。
[out] lpvOutBuffer
輸出緩衝區的指標。
[in] cbOutBuffer
輸出緩衝區的大小,以位元組為單位。
[out] lpcbBytesReturned
輸出實際位元組數目的指標。
[in] lpOverlapped
非重迭通訊端) 忽略 WSAOVERLAPPED 結構的指標 (。
[in] lpCompletionRoutine
類型:_In_opt_ LPWSAOVERLAPPED_COMPLETION_ROUTINE
傳回值
成功完成時, WSAIoctl 會傳回零。 否則,會傳回SOCKET_ERROR的值,而且可以呼叫 WSAGetLastError來擷取特定的錯誤碼。
錯誤碼 | 意義 |
---|---|
已成功起始重迭的作業,稍後將會指出完成。 | |
網路子系統失敗。 | |
lpvInBuffer、lpvOutBuffer、lcbBytesReturned、lpOverlapped或lpCompletionRoutine參數並未完全包含在使用者位址空間的有效部分,或cbInBuffer 或 cbOutBuffer參數太小。 | |
dwIoControlCode參數不是有效的命令,或無法接受指定的輸入參數,或命令不適用於指定的通訊端類型。 | |
當回呼正在進行時,會叫用函式。 | |
描述項 s 不是通訊端。 | |
無法實現指定的 IOCTL 命令。 (例如,無法滿足SIO_SET_QOS或SIO_SET_GROUP_QOS中指定的FLOWSPEC結構。) | |
通訊端標示為非封鎖,而且要求的作業會封鎖。 | |
指定的通訊協定不支援通訊端選項。 例如,嘗試在 IPv6 通訊端上使用 SIO_GET_BROADCAST_ADDRESS IOCTL,或在資料包通訊端上嘗試使用 TCP SIO_KEEPALIVE_VALS IOCTL。 |
備註
WSAIoctl函式可用來設定或擷取與通訊端、傳輸通訊協定或通訊子系統相關聯的作業參數。
如果 lpOverlapped 和 lpCompletionRoutine 都是 Null,此函式中的通訊端將會被視為非重迭的通訊端。 對於非重迭的通訊端, 會忽略 lpOverlapped 和 lpCompletionRoutine 參數,這會導致函式的行為如同標準 ioctlsocket 函式,不同之處在于,如果通訊端 s 處於封鎖模式,函式可以封鎖。 如果通訊端 處於 非封鎖模式,當指定的作業無法立即完成時,此函式可以傳回 WSAEWOULDBLOCK。 在此情況下,應用程式可能會將通訊端變更為封鎖模式,並在使用WSAEventSel () ect) ) 型通知機制時,重新發出要求或等候對應的網路事件 (,例如 () SIO_ADDRESS_LIST_CHANGESIO_ROUTING_INTERFACE_CHANGE FD_ROUTING_INTERFACE_CHANGE或FD_ADDRESS_LIST_CHANGE。
對於重迭的通訊端,無法立即完成的作業將會起始,而且稍後會指出完成。 可能會忽略傳回之lmicrosoftBytesReturned參數所指向的DWORD值。 當作業完成時,可以擷取傳回的最終完成狀態和位元組。
根據服務提供者的實作而定,任何 IOCTL 可能會無限期地封鎖。 如果應用程式無法容許 在 WSAIoctl 呼叫中封鎖,建議您針對特別可能封鎖的 IOCTL 重迭 I/O,包括:
SIO_ADDRESS_LIST_CHANGE
SIO_FINDROUTE
SIO_FLUSH
SIO_GET_QOS
SIO_GET_GROUP_QOS
SIO_ROUTING_INTERFACE_CHANGE
SIO_SET_QOS
SIO_SET_GROUP_QOS
某些通訊協定特定的 IOCTL 也可能特別可能封鎖。 如需任何可用資訊,請查看相關的通訊協定特定附錄。
lpCompletionRoutine參數所指向完成常式的原型如下所示:
#ifndef UNICODE
#define UNICODE
#endif
#define WIN32_LEAN_AND_MEAN
#include <winsock2.h>
#include <Ws2tcpip.h>
#include <stdio.h>
// Link with ws2_32.lib
#pragma comment(lib, "Ws2_32.lib")
void CALLBACK CompletionRoutine (
IN DWORD dwError,
IN DWORD cbTransferred,
IN LPWSAOVERLAPPED lpOverlapped,
IN DWORD dwFlags
);
CompletionRoutine 是應用程式提供之函式名稱的預留位置。 dwError參數會指定重迭作業的完成狀態,如lpOverlapped參數所指出。 cbTransferred參數會指定收到的位元組數目。 dwFlags參數不會用於這個 IOCTL。 完成常式不會傳回值。
您可以採用一種編碼配置來保留目前定義的 ioctlsocket opcode,同時提供方便的方式來分割 dwIoControlCode 參數中的 opcode 識別碼空間,現在為 32 位實體。 dwIoControlCode參數是建置,以在新增控制程式代碼時允許通訊協定和廠商獨立,同時保留與 Windows Sockets 1.1 和 Unix 控制項代碼的回溯相容性。 dwIoControlCode參數的格式如下。
I | O | V | T | 廠商/位址系列 | 程式碼 |
---|---|---|---|---|---|
3 | 3 | 2 | 2 2 | 2 2 2 2 2 2 2 1 1 1 1 | 1 1 1 1 1 1 |
1 | 0 | 9 | 8 7 | 6 5 4 3 2 1 0 9 8 7 6 | 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 |
如果輸出緩衝區對程式碼有效,則設定 O,如同 IOC_OUT。 使用輸入和輸出緩衝區控制程式代碼會同時設定 I 和 O。
如果沒有程式碼的參數,則會設定 V,如同 IOC_VOID。
T 是定義 IOCTL 類型的 2 位數量。 定義下列值:
0 IOCTL 是標準 Unix IOCTL 程式碼,如同 FIONREAD 和 FIONBIO。
1 IOCTL 是一般 Windows Sockets 2 IOCTL 程式碼。 針對 Windows Sockets 2 定義的新 IOCTL 代碼將會有 T == 1。
2 IOCTL 僅適用于特定位址系列。
3 IOCTL 僅適用于特定廠商的提供者,如同 IOC_VENDOR。 此類型可讓公司獲指派廠商號碼,該號碼會出現在 Vendor/Address 系列 參數中。 然後,廠商可以定義該廠商特定的新 IOCTL,而不需要向清除中心註冊 IOCTL,進而提供廠商的彈性和隱私權。
廠商/位址系列 11 位數量,定義如果 T == 3) 或包含程式碼套用 (的位址系列,則為擁有程式碼 (如果 T == 2) ,則為 11 位數量。 如果這是 Unix IOCTL 程式碼 (T == 0) ,則此參數的值與 Unix 上的程式碼相同。 如果這是一般 Windows Sockets 2 IOCTL (T == 1) 則此參數可作為程式碼參數的延伸模組,以提供額外的程式碼值。
代碼 包含作業特定 IOCTL 程式碼的 16 位數量。
支援下列 Unix IOCTL 代碼 (命令) 。
支援下列 Windows Sockets 2 命令。
如果重迭的作業立即完成, WSAIoctl 會傳回零的值,且 lkbBytesReturned 參數會以輸出緩衝區中的位元組數目更新。 如果已成功起始重迭的作業,且稍後會完成,此函式會傳回SOCKET_ERROR,並指出錯誤碼 WSA_IO_PENDING。 在此案例中, lHTTPBytesReturned 不會更新。 當重迭的作業完成時,輸出緩衝區中的資料量會透過完成常式中的cbTransferred參數指示, (如果指定) ,或透過WSAGetOverlappedResult中的lTransfer參數。
使用重迭的通訊端呼叫時, lpOverlapped 參數在重迭作業期間必須有效。 lpOverlapped參數包含WSAOVERLAPPED結構的位址。
如果lpCompletionRoutine參數為Null,當重迭的作業包含有效的事件物件控制碼時,lpOverlapped的hEvent參數會發出訊號。 應用程式可以使用 WSAWaitForMultipleEvents 或 WSAGetOverlappedResult 來等候或輪詢事件物件。
完成常式的原型如下所示:
void CALLBACK CompletionRoutine(
IN DWORD dwError,
IN DWORD cbTransferred,
IN LPWSAOVERLAPPED lpOverlapped,
IN DWORD dwFlags
);
這個 CompletionRoutine 是應用程式定義或程式庫定義函式的預留位置。 只有線上程處於可警示狀態時,才會叫用完成常式。 若要讓執行緒進入可警示狀態,請使用 WSAWaitForMultipleEvents、 WaitForSingleObjectEx或 WaitForMultipleObjectsEx 函式,並將 fAlertable 或 bAlertable 參數設定為 TRUE。
CompletionRoutine的dwError參數會指定重迭作業的完成狀態,如lpOverlapped所指出。 cbTransferred參數會指定傳回的位元組數目。 目前未定義任何旗標值, 而且 dwFlags 會是零。 CompletionRoutine函式不會傳回值。
從此函式傳回允許叫用此通訊端的另一個擱置完成常式。 完成常式可以依任何順序呼叫,不一定以相同順序呼叫重迭作業完成。
相容性
具有 T == 0 的 IOCTL 代碼是 一部分的 IOCTL 程式碼,用於通訊端。 特別是沒有相當於 FIOASYNC的命令。Windows 8.1和Windows Server 2012 R2:Windows 8.1、Windows Server 2012 R2 及更新版本上的 Windows 市集應用程式支援此函式。
規格需求
最低支援的用戶端 | Windows 8.1、Windows Vista [傳統型應用程式|UWP 應用程式] |
最低支援的伺服器 | Windows Server 2003 [傳統型應用程式|UWP 應用程式] |
目標平臺 | Windows |
標頭 | winsock2.h |
程式庫 | Ws2_32.lib |
DLL | Ws2_32.dll |