WSAEnumNetworkEvents 函式 (winsock2.h)

WSAEnumNetworkEvents 函式會探索指定套接字的網路事件、清除內部網路事件記錄,以及 (選擇性) 重設事件物件。

語法

int WSAAPI WSAEnumNetworkEvents(
  [in]  SOCKET             s,
  [in]  WSAEVENT           hEventObject,
  [out] LPWSANETWORKEVENTS lpNetworkEvents
);

參數

[in] s

識別套接字的描述項。

[in] hEventObject

選擇性句柄,識別要重設的相關聯事件物件。

[out] lpNetworkEvents

WSANETWORKEVENTS 結構的指標,該結構會填入所發生的網路事件記錄,以及任何相關聯的錯誤碼。

傳回值

如果作業成功,則傳回值為零。 否則,會傳回SOCKET_ERROR值,而且可以呼叫 WSAGetLastError 來擷取特定的錯誤號碼。

錯誤碼 意義
WSANOTINITIALISED
使用此函式之前,必須先進行成功的 WSAStartup 呼叫。
WSAENETDOWN
網路子系統失敗。
WSAEINVAL
其中一個指定的參數無效。
WSAEINPROGRESS
封鎖的 Windows Sockets 1.1 呼叫正在進行中,或者服務提供者仍在處理回呼函式。
WSAENOTSOCK
描述項不是套接字。
WSAEFAULT
lpNetworkEvents 參數不是使用者位址空間的有效部分。

備註

WSAEnumNetworkEvents 函式可用來探索自此函式最後一次叫用之後,所指示套接字發生的網路事件。 它適用於與 WSAEventSelect 搭配使用,其會將事件物件與一或多個網路事件產生關聯。 當使用非零 lNetworkEvents 參數呼叫 WSAEventSelect 時,網路事件的記錄就會開始,直到對 WSAEventSelect 進行另一個呼叫,並將 lNetworkEvents 參數設定為零,或直到呼叫 WSAAsyncSelect 為止。

WSAEnumNetworkEvents 只會報告透過 WSAEventSelect 所指定的網路活動和錯誤。 請參閱 selectWSAAsyncSelect 的描述,以了解這些函式如何報告網路活動和錯誤。

套接字的網路事件內部記錄會複製到 lpNetworkEvents 所參考的結構,之後會清除內部網路事件記錄。 如果 hEventObject 參數不是 NULL,表示的事件物件也會重設。 Windows Sockets 提供者保證複製網路事件記錄的作業、清除它並重設任何相關聯的事件物件都是不可部分完成的,因此下一次出現的指定網路事件會導致事件物件設定。 在此函式傳回SOCKET_ERROR的情況下,不會重設相關聯的事件物件,而且不會清除網路事件的記錄。

WSANETWORKEVENTS 結構的 lNetworkEvents 成員表示已發生哪些FD_XXX網路事件。 iErrorCode 陣列可用來包含任何相關聯的錯誤碼,以及對應至 lNetworkEvents 中事件位位置的陣列索引。 FD_READ_BIT和FD_WRITE_BIT等標識碼可用來編製 iErrorCode 陣列的索引。 請注意,只有 iErrorCode 陣列的元素會設定為對應 至 lNetworkEvents 參數中設定的位。 其他參數不會修改 (這對於不察覺新FD_ROUTING_INTERFACE_CHANGE和FD_ADDRESS_LIST_CHANGE事件) 的應用程式回溯相容性很重要。

下列錯誤碼可以連同對應的網路事件一起傳回。

事件:FD_CONNECT

錯誤碼 意義
WSAEAFNOSUPPORT 指定之系列中的位址無法用於此通訊端。
WSAECONNREFUSED 已強制拒絕連接嘗試。
WSAENETUNREACH 此時無法透過此主機連接網路。
WSAENOBUFS 沒有可用的緩衝區空間。 套接字無法連接。
WSAETIMEDOUT 嘗試連線逾時而不建立連線
 

事件:FD_CLOSE

錯誤碼 意義
WSAENETDOWN 網路子系統失敗。
WSAECONNRESET 線上已由遠端重設。
WSAECONNABORTED 線上因逾時或其他失敗而終止。
 

事件:FD_ACCEPT

事件:FD_ADDRESS_LIST_CHANGE

事件:FD_GROUP_QOS

事件:FD_QOS

事件:FD_OOB

事件:FD_READ

事件:FD_WRITE

錯誤碼 意義
WSAENETDOWN 網路子系統失敗。
 

事件:FD_ROUTING_INTERFACE_CHANGE

錯誤碼 意義
WSAENETUNREACH 指定的目的地已無法再連線。
WSAENETDOWN 網路子系統失敗。
 

範例程序代碼

下列範例示範如何使用 WSAEnumNetworkEvents 函式。
#ifndef UNICODE
#define UNICODE
#endif

#define WIN32_LEAN_AND_MEAN

#include <windows.h>

#include <winsock2.h>
#include <Ws2tcpip.h>
#include <stdio.h>

// Link with ws2_32.lib
#pragma comment(lib, "Ws2_32.lib")

int main()
{
//-------------------------
// Declare and initialize variables
    WSADATA wsaData;
    int iResult;

    SOCKET SocketArray[WSA_MAXIMUM_WAIT_EVENTS], ListenSocket;
    WSAEVENT EventArray[WSA_MAXIMUM_WAIT_EVENTS];
    WSANETWORKEVENTS NetworkEvents;
    sockaddr_in InetAddr;
    DWORD EventTotal = 0;
    DWORD Index;
    DWORD i;
    
    HANDLE NewEvent = NULL; 

    // Initialize Winsock
    iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);
    if (iResult != 0) {
        wprintf(L"WSAStartup failed with error: %d\n", iResult);
        return 1;
    }

//-------------------------
// Create a listening socket
    ListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
    if (ListenSocket == INVALID_SOCKET) {
        wprintf(L"socket function failed with error: %d\n", WSAGetLastError() );
        return 1;
    }
    
    InetAddr.sin_family = AF_INET;
    InetAddr.sin_addr.s_addr = htonl(INADDR_ANY);
    InetAddr.sin_port = htons(27015);

//-------------------------
// Bind the listening socket
    iResult = bind(ListenSocket, (SOCKADDR *) & InetAddr, sizeof (InetAddr));
    if (iResult != 0) {
        wprintf(L"bind failed with error: %d\n", WSAGetLastError() );
        return 1;
    }

//-------------------------
// Create a new event
    NewEvent = WSACreateEvent();
    if (NewEvent == NULL) {
        wprintf(L"WSACreateEvent failed with error: %d\n", GetLastError() );
        return 1;
    }    

//-------------------------
// Associate event types FD_ACCEPT and FD_CLOSE
// with the listening socket and NewEvent
    iResult = WSAEventSelect(ListenSocket, NewEvent, FD_ACCEPT | FD_CLOSE);
    if (iResult != 0) {
        wprintf(L"WSAEventSelect failed with error: %d\n", WSAGetLastError() );
        return 1;
    }

//-------------------------
// Start listening on the socket
    iResult = listen(ListenSocket, 10);
    if (iResult != 0) {
        wprintf(L"listen failed with error: %d\n", WSAGetLastError() );
        return 1;
    }

//-------------------------
// Add the socket and event to the arrays, increment number of events
    SocketArray[EventTotal] = ListenSocket;
    EventArray[EventTotal] = NewEvent;
    EventTotal++;

//-------------------------
// Wait for network events on all sockets
    Index = WSAWaitForMultipleEvents(EventTotal, EventArray, FALSE, WSA_INFINITE, FALSE);
    Index = Index - WSA_WAIT_EVENT_0;

//-------------------------
// Iterate through all events and enumerate
// if the wait does not fail.
    for (i = Index; i < EventTotal; i++) {
        Index = WSAWaitForMultipleEvents(1, &EventArray[i], TRUE, 1000, FALSE);
        if ((Index != WSA_WAIT_FAILED) && (Index != WSA_WAIT_TIMEOUT)) {
            WSAEnumNetworkEvents(SocketArray[i], EventArray[i], &NetworkEvents);
        }
    }

//...
    return 0;


Windows Phone 8:Windows Phone 8 和更新版本 Windows Phone 市集應用程式支援此函式。

Windows 8.1Windows 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

另請參閱

WSAEventSelect

Winsock 函式

Winsock 參考