Bagikan melalui


Fungsi WSAEventSelect (winsock2.h)

Fungsi WSAEventSelect menentukan objek peristiwa yang akan dikaitkan dengan set peristiwa jaringan FD_XXX yang ditentukan.

Sintaks

int WSAAPI WSAEventSelect(
  [in] SOCKET   s,
  [in] WSAEVENT hEventObject,
  [in] long     lNetworkEvents
);

Parameter

[in] s

Deskriptor yang mengidentifikasi soket.

[in] hEventObject

Handel yang mengidentifikasi objek peristiwa yang akan dikaitkan dengan set peristiwa jaringan FD_XXX yang ditentukan.

[in] lNetworkEvents

Bitmask yang menentukan kombinasi FD_XXX peristiwa jaringan tempat aplikasi memiliki minat.

Mengembalikan nilai

Nilai yang dikembalikan adalah nol jika spesifikasi aplikasi dari peristiwa jaringan dan objek peristiwa terkait berhasil. Jika tidak, nilai SOCKET_ERROR dikembalikan, dan nomor kesalahan tertentu dapat diambil dengan memanggil WSAGetLastError.

Seperti dalam kasus fungsi pilih dan WSAAsyncSelect , WSAEventSelect akan sering digunakan untuk menentukan kapan operasi transfer data (kirim atau rekv) dapat dikeluarkan dengan harapan keberhasilan segera. Namun demikian, aplikasi yang kuat harus disiapkan untuk kemungkinan objek peristiwa diatur dan mengeluarkan panggilan Windows Sockets yang segera mengembalikan WSAEWOULDBLOCK . Misalnya, urutan operasi berikut dimungkinkan:

  • Data tiba di soket; Windows Sockets mengatur objek peristiwa WSAEventSelect .
  • Aplikasi ini melakukan beberapa pemrosesan lainnya.
  • Saat memproses, aplikasi mengeluarkan ioctlsocket(s, FIONREAD...) dan melihat bahwa ada data yang siap dibaca.
  • Aplikasi mengeluarkan recv,...) untuk membaca data.
  • Aplikasi akhirnya menunggu objek peristiwa yang ditentukan dalam WSAEventSelect, yang segera mengembalikan menunjukkan bahwa data siap dibaca.
  • Aplikasi mengeluarkan recv,...), yang gagal dengan kesalahan WSAEWOULDBLOCK.
Setelah berhasil merekam kemunculan peristiwa jaringan (dengan mengatur bit yang sesuai dalam rekaman peristiwa jaringan internal) dan memberi sinyal objek peristiwa terkait, tidak ada tindakan lebih lanjut yang diambil untuk peristiwa jaringan tersebut sampai aplikasi melakukan panggilan fungsi yang secara implisit mengaktifkan kembali pengaturan peristiwa jaringan tersebut dan memberi sinyal objek peristiwa terkait.
Peristiwa jaringan Mengaktifkan kembali fungsi
FD_READ
Fungsi recv, recvfrom, WSARecv, WSARecvEx, atau WSARecvFrom .
FD_WRITE
Fungsi send, sendto, WSASend, atau WSASendTo .
FD_OOB
Fungsi recv, recvfrom, WSARecv, WSARecvEx, atau WSARecvFrom .
FD_ACCEPT
Fungsi accept, AcceptEx, atau WSAAccept kecuali kode kesalahan yang dikembalikan WSATRY_AGAIN menunjukkan bahwa fungsi kondisi dikembalikan CF_DEFER.
FD_CONNECT
Tidak ada.
FD_CLOSE
Tidak ada.
FD_QOS
Fungsi WSAIoctl dengan perintah SIO_GET_QOS.
FD_GROUP_QOS
Dicadangkan.
FD_ROUTING_ INTERFACE_CHANGE
Fungsi WSAIoctl dengan perintah SIO_ROUTING_INTERFACE_CHANGE.
FD_ADDRESS_ LIST_CHANGE
Fungsi WSAIoctl dengan perintah SIO_ADDRESS_LIST_CHANGE.
 

Setiap panggilan ke mengaktifkan kembali rutinitas, bahkan panggilan yang gagal, menghasilkan pengaktifan kembali perekaman dan sinyal untuk peristiwa jaringan dan objek peristiwa yang relevan.

Untuk peristiwa jaringan FD_READ, FD_OOB, dan FD_ACCEPT, perekaman peristiwa jaringan dan sinyal objek peristiwa dipicu tingkat. Ini berarti bahwa jika rutinitas pengaktifan kembali dipanggil dan kondisi jaringan yang relevan masih valid setelah panggilan, peristiwa jaringan direkam dan objek peristiwa terkait diatur. Ini memungkinkan aplikasi untuk digerakkan oleh peristiwa dan tidak peduli dengan jumlah data yang tiba pada satu waktu. Pertimbangkan urutan berikut ini:

  1. Penyedia transportasi menerima 100 byte data pada soket dan menyebabkan WS2_32.DLL merekam peristiwa jaringan FD_READ dan mengatur objek peristiwa terkait.
  2. Aplikasi mengeluarkan recv(s, buffptr, 50, 0) untuk membaca 50 byte.
  3. Penyedia transportasi menyebabkan WS2_32.DLL merekam peristiwa jaringan FD_READ dan mengatur objek peristiwa terkait lagi karena masih ada data yang akan dibaca.
Dengan semantik ini, aplikasi tidak perlu membaca semua data yang tersedia sebagai respons terhadap peristiwa jaringan FD_READ—satu respon terhadap setiap peristiwa jaringan FD_READ sesuai.

Peristiwa FD_QOS dianggap tepi dipicu. Pesan akan diposting tepat sekali ketika kualitas perubahan layanan terjadi. Pesan lebih lanjut tidak akan datang sampai penyedia mendeteksi perubahan lebih lanjut dalam kualitas layanan atau aplikasi menegosiasikan ulang kualitas layanan untuk soket.

Peristiwa FD_ROUTING_INTERFACE_CHANGE dan FD_ADDRESS_LIST_CHANGE juga dianggap sebagai tepi yang dipicu. Pesan akan diposting tepat sekali ketika perubahan terjadi setelah aplikasi meminta pemberitahuan dengan mengeluarkan WSAIoctl dengan SIO_ROUTING_INTERFACE_CHANGE atau SIO_ADDRESS_LIST_CHANGE yang sesuai. Pesan lain tidak akan masuk sampai aplikasi menerbitkan kembali IOCTL dan perubahan lain terdeteksi karena IOCTL telah diterbitkan.

Jika peristiwa jaringan telah terjadi ketika aplikasi memanggil WSAEventSelect atau ketika fungsi pengaktifan kembali dipanggil, maka peristiwa jaringan direkam dan objek peristiwa terkait diatur sebagaimana mewajibkan. Misalnya, pertimbangkan urutan berikut:

  1. Aplikasi memanggil mendengarkan.
  2. Permintaan koneksi diterima tetapi belum diterima.
  3. Aplikasi memanggil WSAEventSelect yang menentukan bahwa aplikasi tertarik pada peristiwa jaringan FD_ACCEPT untuk soket. Karena persistensi peristiwa jaringan, Windows Sockets merekam peristiwa jaringan FD_ACCEPT dan segera mengatur objek peristiwa terkait.
Peristiwa jaringan FD_WRITE ditangani sedikit berbeda. Peristiwa jaringan FD_WRITE direkam ketika soket pertama kali terhubung dengan panggilan ke fungsi connect, ConnectEx, WSAConnect, WSAConnectByList, atau WSAConnectByName atau ketika soket diterima dengan fungsi accept, AcceptEx, atau WSAAccept dan kemudian setelah pengiriman gagal dengan WSAEWOULDBLOCK dan ruang buffer menjadi tersedia. Oleh karena itu, aplikasi dapat mengasumsikan bahwa pengiriman dimungkinkan mulai dari pengaturan peristiwa jaringan FD_WRITE pertama dan berlangsung hingga pengiriman mengembalikan WSAEWOULDBLOCK. Setelah kegagalan seperti itu, aplikasi akan mengetahui bahwa pengiriman kembali dimungkinkan ketika peristiwa jaringan FD_WRITE direkam dan objek peristiwa terkait diatur.

Peristiwa jaringan FD_OOB hanya digunakan ketika soket dikonfigurasi untuk menerima data OOB secara terpisah. Jika soket dikonfigurasi untuk menerima data OOB sebaris, data OOB (dipercepat) diperlakukan sebagai data normal dan aplikasi harus mendaftarkan minat, dan akan mendapatkan peristiwa jaringan FD_READ, bukan peristiwa jaringan FD_OOB. Aplikasi dapat mengatur atau memeriksa cara data OOB ditangani dengan menggunakan setsockopt atau getsockopt untuk opsi SO_OOBINLINE.

Kode kesalahan dalam peristiwa jaringan FD_CLOSE menunjukkan apakah penutupan soket anggun atau abortif. Jika kode kesalahan adalah nol, maka penutupannya anggun; jika kode kesalahan adalah WSAECONNRESET, maka sirkuit virtual soket diatur ulang. Ini hanya berlaku untuk soket berorientasi koneksi seperti SOCK_STREAM.

Peristiwa jaringan FD_CLOSE direkam ketika indikasi dekat diterima untuk sirkuit virtual yang sesuai dengan soket. Dalam istilah TCP, ini berarti bahwa FD_CLOSE direkam ketika koneksi masuk ke status TIME WAIT atau CLOSE WAIT. Ini hasil dari akhir jarak jauh yang melakukan pematian pada sisi kirim atau closesocket. FD_CLOSE diposting setelah semua data dibaca dari soket. Aplikasi harus memeriksa data yang tersisa setelah menerima FD_CLOSE untuk menghindari kemungkinan kehilangan data. Untuk informasi selengkapnya, lihat bagian tentang Graceful Shutdown, Linger Options, dan Socket Closure dan fungsi shutdown .

Perhatikan bahwa Windows Sockets hanya akan merekam peristiwa jaringan FD_CLOSE untuk menunjukkan penutupan sirkuit virtual. Ini tidak akan merekam peristiwa jaringan FD_READ untuk menunjukkan kondisi ini.

Peristiwa jaringan FD_QOS atau FD_GROUP_QOS direkam ketika parameter apa pun dalam spesifikasi alur yang terkait dengan soket. Aplikasi harus menggunakan WSAIoctl dengan perintah SIO_GET_QOS untuk mendapatkan kualitas layanan saat ini untuk soket.

Peristiwa jaringan FD_ROUTING_INTERFACE_CHANGE direkam ketika antarmuka lokal yang harus digunakan untuk mencapai tujuan yang ditentukan di WSAIoctl dengan perubahan SIO_ROUTING_INTERFACE_CHANGE setelah IOCTL tersebut diterbitkan.

Peristiwa jaringan FD_ADDRESS_LIST_CHANGE direkam ketika daftar alamat keluarga protokol untuk soket tempat aplikasi dapat mengikat perubahan setelah WSAIoctl dengan SIO_ADDRESS_LIST_CHANGE diterbitkan.

Kode kesalahan Makna
WSANOTINITIALISED Panggilan WSAStartup yang berhasil harus terjadi sebelum menggunakan fungsi ini.
WSAENETDOWN Subsistem jaringan gagal.
WSAEINVAL Salah satu parameter yang ditentukan tidak valid, atau soket yang ditentukan dalam status tidak valid.
WSAEINPROGRESS Pemblokiran panggilan Windows Sockets 1.1 sedang berlangsung, atau penyedia layanan masih memproses fungsi panggilan balik.
WSAENOTSOCK Deskriptor bukan soket.

Keterangan

Fungsi WSAEventSelect digunakan untuk menentukan objek peristiwa, hEventObject, yang akan dikaitkan dengan peristiwa jaringan FD_XXX yang dipilih, lNetworkEvents. Soket tempat objek peristiwa ditentukan diidentifikasi oleh parameter s . Objek peristiwa diatur ketika salah satu peristiwa jaringan yang dicalonkan terjadi.

Fungsi WSAEventSelect beroperasi sangat mirip dengan WSAAsyncSelect, perbedaannya adalah tindakan yang diambil ketika peristiwa jaringan yang ditunjuk terjadi. Fungsi WSAAsyncSelect menyebabkan pesan Windows yang ditentukan aplikasi diposting. WSAEventSelect mengatur objek peristiwa terkait dan merekam kemunculan peristiwa ini dalam rekaman peristiwa jaringan internal. Aplikasi dapat menggunakan WSAWaitForMultipleEvents untuk menunggu atau melakukan polling pada objek peristiwa, dan menggunakan WSAEnumNetworkEvents untuk mengambil konten rekaman peristiwa jaringan internal dan dengan demikian menentukan peristiwa jaringan mana yang dicalonkan telah terjadi.

Cara yang tepat untuk mengatur ulang status objek peristiwa yang digunakan dengan fungsi WSAEventSelect adalah dengan meneruskan handel objek peristiwa ke fungsi WSAEnumNetworkEvents dalam parameter hEventObject . Ini akan mengatur ulang objek peristiwa dan menyesuaikan status peristiwa FD aktif pada soket dengan cara atomik.

WSAEventSelect adalah satu-satunya fungsi yang menyebabkan aktivitas dan kesalahan jaringan direkam dan diambil melalui WSAEnumNetworkEvents. Lihat deskripsi pilih dan WSAAsyncSelect untuk mengetahui bagaimana fungsi tersebut melaporkan aktivitas dan kesalahan jaringan.

Fungsi WSAEventSelect secara otomatis mengatur soket ke mode nonblocking, terlepas dari nilai lNetworkEvents. Untuk mengatur soket kembali ke mode pemblokiran, pertama-tama perlu untuk menghapus catatan peristiwa yang terkait dengan soket melalui panggilan ke WSAEventSelect dengan lNetworkEvents diatur ke nol dan parameter hEventObject diatur ke NULL. Anda kemudian dapat memanggil ioctlsocket atau WSAIoctl untuk mengatur soket kembali ke mode pemblokiran.

Parameter lNetworkEvents dibangun dengan menggunakan operator BITWISE OR dengan salah satu nilai yang ditentukan dalam daftar berikut.

Nilai Makna
FD_READ Ingin menerima pemberitahuan kesiapan untuk membaca.
FD_WRITE Ingin menerima pemberitahuan kesiapan untuk menulis.
FD_OOB Ingin menerima pemberitahuan tentang kedatangan data OOB.
FD_ACCEPT Ingin menerima pemberitahuan tentang koneksi masuk.
FD_CONNECT Ingin menerima pemberitahuan tentang koneksi yang diselesaikan atau operasi gabungan multi-titik.
FD_CLOSE Ingin menerima pemberitahuan penutupan soket.
FD_QOS Ingin menerima pemberitahuan soket (perubahan QoS.
FD_GROUP_QOS Dicadangkan untuk digunakan di masa mendatang dengan grup soket. Ingin menerima pemberitahuan perubahan QoS grup soket.
FD_ROUTING_ INTERFACE_CHANGE Ingin menerima pemberitahuan perubahan antarmuka perutean untuk tujuan yang ditentukan.
FD_ADDRESS_ LIST_CHANGE Ingin menerima pemberitahuan perubahan daftar alamat lokal untuk keluarga alamat soket.
 

Mengeluarkan WSAEventSelect untuk soket membatalkan WSAAsyncSelect atau WSAEventSelect sebelumnya untuk soket yang sama dan menghapus rekaman peristiwa jaringan internal. Misalnya, untuk mengaitkan objek peristiwa dengan membaca dan menulis peristiwa jaringan, aplikasi harus memanggil WSAEventSelect dengan FD_READ dan FD_WRITE, sebagai berikut:

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

Tidak dimungkinkan untuk menentukan objek peristiwa yang berbeda untuk peristiwa jaringan yang berbeda. Kode berikut tidak akan berfungsi; panggilan kedua akan membatalkan efek yang pertama, dan hanya peristiwa jaringan FD_WRITE yang akan dikaitkan dengan hEventObject2:

rc = WSAEventSelect(s, hEventObject1, FD_READ);
rc = WSAEventSelect(s, hEventObject2, FD_WRITE); //bad

Untuk membatalkan asosiasi dan pemilihan peristiwa jaringan pada soket, lNetworkEvents harus diatur ke nol, dalam hal ini parameter hEventObject akan diabaikan.

rc = WSAEventSelect(s, hEventObject, 0);

Menutup soket dengan closesocket juga membatalkan asosiasi dan pemilihan peristiwa jaringan yang ditentukan dalam WSAEventSelect untuk soket. Namun, aplikasi harus memanggil WSACloseEvent untuk secara eksplisit menutup objek peristiwa dan membebaskan sumber daya apa pun.

Soket yang dibuat ketika fungsi terima disebut memiliki properti yang sama dengan soket mendengarkan yang digunakan untuk menerimanya. Setiap pemilihan asosiasi WSAEventSelect dan peristiwa jaringan yang ditetapkan untuk soket mendengarkan berlaku untuk soket yang diterima. Misalnya, jika soket mendengarkan memiliki asosiasi WSAEventSelecthEventObject dengan FD_ACCEPT, FD_READ, dan FD_WRITE, soket apa pun yang diterima pada soket mendengarkan tersebut juga akan memiliki peristiwa jaringan FD_ACCEPT, FD_READ, dan FD_WRITE yang terkait dengan hEventObject yang sama. Jika hEventObject atau peristiwa jaringan yang berbeda diinginkan, aplikasi harus memanggil WSAEventSelect, melewati soket yang diterima dan informasi baru yang diinginkan.

Contoh Kode

Contoh berikut menunjukkan penggunaan fungsi WSAEventSelect .
//-------------------------
// Declare and initialize variables
SOCKET ListenSocket;
WSAEVENT NewEvent;
sockaddr_in InetAddr;

//-------------------------
// Initialize listening socket
ListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);

//-------------------------
// Bind listening socket
InetAddr.sin_family = AF_INET;
InetAddr.sin_addr.s_addr = htonl(INADDR_ANY);
InetAddr.sin_port = htons(27015);

bind (ListenSocket, (SOCKADDR *) &InetAddr, sizeof(InetAddr));

//-------------------------
// Create new event
NewEvent = WSACreateEvent();

//-------------------------
// Associate event types FD_ACCEPT and FD_CLOSE
// with the listening socket and NewEvent
WSAEventSelect( ListenSocket, NewEvent, FD_ACCEPT | FD_CLOSE);

//----------------------
// Listen for incoming connection requests 
// on the created socket
if (listen( ListenSocket, SOMAXCONN ) == SOCKET_ERROR)
    printf("Error listening on socket.\n");

printf("Listening on socket...\n");

// Need an event handler added to handle connection requests



Windows Phone 8: Fungsi ini didukung untuk aplikasi Windows Phone Store di Windows Phone 8 dan yang lebih baru.

Windows 8.1 dan Windows Server 2012 R2: Fungsi ini didukung untuk aplikasi Windows Store di Windows 8.1, Windows Server 2012 R2, dan yang lebih baru.

Persyaratan

Persyaratan Nilai
Klien minimum yang didukung Windows 8.1, Windows Vista [aplikasi desktop | Aplikasi UWP]
Server minimum yang didukung Windows Server 2003 [aplikasi desktop | Aplikasi UWP]
Target Platform Windows
Header winsock2.h
Pustaka Ws2_32.lib
DLL Ws2_32.dll

Lihat juga

WSAAsyncSelect

WSACloseEvent

WSACreateEvent

WSAEnumNetworkEvents

WSAWaitForMultipleEvents

Fungsi Winsock

Referensi Winsock

Shutdown