LPWSPEVENTSELECT 回呼函式 (ws2spi.h)

LPWSPEventSelect 函式會指定要與所提供網路事件集相關聯的事件物件。

語法

LPWSPEVENTSELECT Lpwspeventselect;

int Lpwspeventselect(
  [in]  SOCKET s,
  [in]  WSAEVENT hEventObject,
  [in]  long lNetworkEvents,
  [out] LPINT lpErrno
)
{...}

參數

[in] s

識別套接字的描述項。

[in] hEventObject

識別要與所提供之網路事件集相關聯之事件物件的句柄。

[in] lNetworkEvents

位掩碼,指定 Windows Sockets SPI 用戶端感興趣的網路事件組合。 使用位 OR 運算元搭配其中任何值來建構。

意義
FD_READ
讀取整備程度通知的問題。
FD_WRITE
發出寫入整備的通知。
FD_OOB
發出 OOB 資料的抵達通知。
FD_ACCEPT
發出連入連線的通知。
FD_CONNECT
已完成連線的通知問題。
FD_CLOSE
套接字關閉的通知問題。
FD_QOS
發出套接字 (QoS) 變更的通知。
FD_GROUP_QOS
保留的。
FD_ROUTING_INTERFACE_CHANGE
發出指定目的地 () 路由介面變更的通知。
FD_ADDRESS_LIST_CHANGE
發出套接字位址系列之本機位址清單變更的通知。

[out] lpErrno

錯誤碼的指標。 如需詳細資訊,請參閱 傳回值 一節。

傳回值

如果 Windows Sockets SPI 用戶端的網路事件規格和相關聯的事件物件成功,則傳回值為零。 否則,會傳回 值SOCKET_ERROR ,而且 lpErrno 中提供特定的錯誤號碼。

錯誤碼 意義
WSAENETDOWN
網路子系統失敗。
WSAEINVAL
表示其中一個指定的參數無效,或指定的套接字處於無效狀態。
WSAEINPROGRESS
封鎖 Windows Sockets 呼叫正在進行中,或服務提供者仍在處理回呼函式。
WSAENOTSOCK
描述項不是套接字。

備註

此函式用來指定事件物件 hEventObject,以與選取的網路事件 lNetworkEvents 相關聯。 指定事件物件的套接字是由 s 識別。 當發生任何指定的網路事件時,就會設定事件物件。

LPWSPEventSelect 的運作方式與 LPWSPAsyncSelect 非常類似,這是在發生指定網路事件時所採取的動作差異。 雖然 WSPAsyncSelect 會導致張貼 Windows Sockets SPI 用戶端指定的 Windows 訊息,LPWSPEventSelect 會設定相關聯的事件物件,並記錄內部網路事件記錄中發生此事件。 Windows Sockets SPI 用戶端可以使用 LPWSPEnumNetworkEvents 來擷取內部網路事件記錄的內容,進而判斷已發生的指定網路事件。

LPWSPEventSelect 是唯一會導致網路活動和錯誤透過 LPWSPEnumNetworkEvents 記錄和擷取的函式。 請參閱 LPWSPSelectLPWSPAsyncSelect 的描述,以了解這些函式如何報告網路活動和錯誤。

不論 lNetworkEvents 的值為何,此函式都會自動將套接字設定為非封鎖模式。

發出 套接字的 LPWSPEventSelect 會取消相同套接字的任何先前 LPWSPAsyncSelectLPWSPEventSelect ,並清除內部網路事件記錄。 例如,若要將事件對象與讀取和寫入網路事件產生關聯,Windows Sockets SPI 用戶端必須呼叫 LPWSPEventSelect 與 FD_READ 和 FD_WRITE,如下所示。

rc = WSPEventSelect(s, hEventObject, FD_READ | FD_WRITE);

無法為不同的網路事件指定不同的事件物件。 下列程式代碼無法運作;第二個呼叫會取消第一個的效果,唯一的關聯將是與 hEventObject2 相關聯的FD_WRITE網路事件。

// Incorrect example.
rc = WSPEventSelect(s, hEventObject1, FD_READ);
rc = WSPEventSelect(s, hEventObject2, FD_WRITE);

若要取消套接字上網路事件的關聯和選取,您應該將 lNetworkEvents 設定為零,在此情況下會忽略 hEventObject 參數。

rc = WSPEventSelect(s, hEventObject, 0);

使用 LPWSPCloseSocket 關閉套接字也會取消套接字在 LPWSPEventSelect 中指定的網路事件的關聯和選取。 不過,Windows Sockets SPI 用戶端仍然必須呼叫 WSACloseEvent 來明確關閉事件物件,並釋放任何資源。

由於 LPWSPAccept'ed 套接字的屬性與用來接受它的接聽套接字具有相同的屬性,因此針對接聽套接字所設定的任何 LPWSPEventSelect 關聯和網路事件選取範圍都會套用至接受的套接字。 例如,如果接聽套接字具有 hEventObject 與 FD_ACCEPT、FD_READ 和 FD_WRITE 的 LPWSPEventSelect 關聯,則該接聽套接字上接受的任何套接字也會有與相同 hEventObject 相關聯的FD_ACCEPT、FD_READ和FD_WRITE網路事件。 如果需要不同的 hEventObject 或網路事件,Windows Sockets SPI 用戶端應該呼叫 LPWSPEventSelect、傳遞接受的套接字,以及所需的新資訊。

成功記錄發生網路事件併發出相關事件對象的訊號之後,除非 Windows Sockets SPI 用戶端發出函式呼叫,才能對該網路事件發出進一步的動作,以隱含方式重新啟用該網路事件的設定,併發出相關聯事件對象的訊號。

網路事件 重新啟用函式
FD_READ LPWSPRecvLPWSPRecvFrom
FD_WRITE LPWSPSendLPWSPSendTo
FD_OOB LPWSPRecvLPWSPRecvFrom
FD_ACCEPT LPWSPAccept,除非傳回的錯誤碼WSATRY_AGAIN指出條件函式傳回CF_DEFER
FD_CONNECT
FD_CLOSE
FD_QOS LPWSPIoctl 與 SIO_GET_QOS
FD_GROUP_QOS 保留供未來搭配套接字群組使用: LPWSPIoctl 與 SIO_GET_GROUP_QOS
FD_ROUTING_INTERFACE_CHANGE 具有命令SIO_ROUTING_INTERFACE_CHANGE的 LPWSPIoctl
FD_ADDRESS_LIST_CHANGE 具有命令SIO_ADDRESS_LIST_CHANGE的 LPWSPIoctl

任何重新啟用例程的呼叫,即使是失敗的例程,也會分別重新啟用相關網路事件和事件對象的錄製和訊號。

對於FD_READ、FD_OOB和FD_ACCEPT網路事件,則會觸發網路事件錄製和事件物件訊 。 這表示,如果呼叫重新啟用例程,且相關的網路條件在呼叫之後仍然有效,則會記錄網路事件,併發出相關聯的事件物件的訊號。 這可讓 Windows Sockets SPI 用戶端成為事件驅動,同時也不受任何時間抵達的數據量所限制。 假設情節如下。

  1. 服務提供者 會在套接字上接收 100 個字節的數據、記錄FD_READ網路事件,併發出相關聯的事件對象的訊號。
  2. Windows Sockets SPI 用戶端會發出讀取 50 個字節的問題 WSPRecv(s, buffptr, 50, 0)
  3. 服務提供者會記錄FD_READ網路事件,並再次發出關聯的事件物件訊號,因為仍有數據可供讀取。

透過這些語意,Windows Sockets SPI 用戶端不需要讀取所有可用的數據,以回應FD_READ網路事件。 相反地,回應每個FD_READ網路事件的單一 LPWSPRecv 是適當的。

FD_QOS和FD_GROUP_QOS事件會被視為 邊緣觸發。 當發生 QOS (QOS) 變更時,只會張貼一次訊息。 除非服務提供者偵測到 QOS 中的進一步變更,或 Windows Sockets SPI 用戶端重新分類套接字的 QOS,否則不會發出進一步的指示。

FD_ROUTING_INTERFACE_CHANGE和FD_ADDRESS_LIST_CHANGE事件也會被視為 邊緣觸發 。 當 Windows Sockets SPI 用戶端發出 WSAIoctl 並對應發出SIO_ROUTING_INTERFACE_CHANGE或SIO_ADDRESS_LIST_CHANGE來要求通知,只會張貼一次訊息。 直到 Windows Sockets SPI 用戶端重新發出 IOCTL ,而且 自發出 IOCTL 之後偵測到另一個變更,才會進行進一步的訊息。

如果 Windows Sockets SPI 用戶端呼叫 LPWSPEventSelect 或呼叫重新啟用函式時發生網路事件,則會視需要記錄網路事件併發出相關聯的事件物件訊號。 例如,請考慮下列順序。

  1. Windows Sockets SPI 用戶端會呼叫 LPWSPListen
  2. 已收到連線要求,但尚未接受。
  3. Windows Sockets SPI 用戶端會呼叫 LPWSPEventSelect ,指定它對於套接字FD_ACCEPT網路事件感興趣。 服務提供者會記錄FD_ACCEPT網路事件,並立即發出相關事件對象的訊號。

FD_WRITE網路事件處理方式稍有不同。 當套接字第一次與 LPWSPConnect 連線或接受 LPWSPAccept,然後在 LPWSPSend 或 LPWSPSendTo 失敗且 WSAEWOULDBLOCK 和緩衝區空間變成可用之後,就會記錄FD_WRITE網路事件。 因此,Windows Sockets SPI 用戶端可以假設從第一個FD_WRITE網路事件設定開始傳送,直到傳送傳回 WSAEWOULDBLOCK 為止。 這類失敗之後,Windows Sockets SPI 用戶端會發現當記錄FD_WRITE網路事件併發出關聯的事件物件訊號時,可能會再次傳送。

只有在套接字設定為個別接收頻外數據時,才會使用FD_OOB網路事件。 如果套接字設定為接收頻外數據內嵌,則會將頻外 (加速) 數據視為一般數據,而 Windows Sockets SPI 用戶端應該註冊感興趣的數據,而且會取得、FD_READ網路事件,而不是FD_OOB網路事件。 Windows Sockets SPI 用戶端可以使用 LPWSPSetSockOptLPWSPGetSockOpt 處理頻外數據的方式,設定或檢查SO_OOBINLINE選項。

FD_CLOSE網路事件中的錯誤碼會指出套接字關閉是否正常或中止。 如果錯誤碼為 0,則關閉正常;如果錯誤碼為 WSAECONNRESET,則套接字的虛擬線路已重設。 這隻適用於連線導向套接字,例如 SOCK_STREAM。

當收到對應至套接字之虛擬線路的關閉指示時,就會記錄FD_CLOSE網路事件。 在 TCP 詞彙中,這表示當連線進入 FIN WAIT 或 CLOSE WAIT 狀態時,會記錄FD_CLOSE。 這會導致遠端端在傳送端或 LPWSPCloseSocket 上執行 LPWSPShutdown

服務提供者 應該只 記錄FD_CLOSE網路事件,以指出虛擬線路關閉;它 不應該 記錄FD_READ網路事件,以指出該條件。

FD_QOS或FD_GROUP_QOS網路事件會記錄在流量規格中與套接字 s 相關聯的任何欄位變更,或分別屬於 套接字群組時。 此變更必須透過具有 SIO_GET_QOS 和/或 SIO_GET_GROUP_QOS 的 LPWSPIoctl 函式提供給 Windows Sockets SPI 用戶端,以分別擷取套接字 目前 QOS,或 分別屬於套接字 群組的 QOS。

FD_ROUTING_INTERFACE_CHANGE網路事件會在發出這類 IOCTL 之後,用來連線到 WSAIoctl 中指定的目的地時,會記錄 SIO_ROUTING_INTERFACE_CHANGE FD_ROUTING_INTERFACE_CHANGE網路事件。

當發出 WSAIoctl 與 SIO_ADDRESS_LIST_CHANGE 之後,Windows Sockets SPI 用戶端可繫結變更的套接字通訊協定系列清單,就會記錄FD_ADDRESS_LIST_CHANGE網路事件。

規格需求

需求
最低支援的用戶端 Windows 10 組建 20348
最低支援的伺服器 Windows 10 組建 20348
標頭 ws2spi.h

另請參閱

LPWSPEnumNetworkEvents