Wsasend () Description: send data on a connected set of interfaces.
# Include <winsock2.h>
Int wsaapi wsasend (
Socket s,
Lpwsabuf lpbuffers,
DWORD dwbuffercount,
Lpdword lpnumberofbytessent,
Int iflags,
Lpwsaoverlapped lpoverlapped,
Lpwsaoverlapped_completion_routine lpcompletionroutine
);
S: The description of a connected interface.
Lpbuffers: a pointer to the wsabuf structure array. Each wsabuf structure contains the pointer of the buffer and the size of the buffer.
Dwbuffercount: Number of wsabuf structures in the lpbuffers array.
Lpnumberofbytessent: if the sending operation is completed immediately, it is a pointer to the number of bytes sent.
Iflags: flag.
Lpoverlapped: pointer to the wsaoverlapped structure (this is ignored for non-overlapping APIs ).
Lpcompletionroutine: a pointer to the completion routine called after the sending operation is complete. (Ignore non-overlapping sets of interfaces ).
Return Value:
If no error occurs and the sending operation is completed immediately, the wsasend () function returns 0. At this time, the completion routine (Completion routine) should have been scheduled. Once the calling thread is in the alertable state, it will be called. Otherwise, socket_error is returned. Pass
WsagetlasterrorObtain detailed error code. The error code wsa_io_pending (in fact, it indicates that there is no error) indicates that the overlap operation has been submitted successfully (that is, the meaning of asynchronous Io), and a prompt will be sent later (this completion may not necessarily be successful, maybe there is a problem ). Other error codes indicate that the overlap operation does not start correctly and there is no mark of completion.
Error Code |
Meaning |
Wsaeacces |
The requested address is a broadcast address, but the appropriate flag was not set. |
Wsaeconnaborted |
The virtual circuit was terminated due to a time-out or other failure. |
Wsaeconnreset |
For a stream socket, the virtual circuit was reset by the remote side. the application shoshould close the socket as it is no longer useable. for a UDP datatesocket, this error wowould indicate that a previous send operation resulted in an ICMP "port unreachable" message. |
Wsaefault |
TheLpbuffers,Lpnumberofbytessent,Lpoverlapped,LpcompletionroutineParameter is not totally contained in a valid part of the user address space. |
Wsaeintr |
A blocking Windows Socket 1.1 call was canceled through wsacancelblockingcall. |
Wsaeinss SS |
A blocking Windows Sockets 1.1 call is in progress, or the service provider is still processing a callback function. |
Wsaeinval |
The socket has not been boundBindOr the socket is not created with the overlapped flag. |
Wsaemsgsize |
The socket is message oriented, and the message is larger than the maximum supported by the underlying transport. |
Wsaenetdown |
The network subsystem has failed. |
Wsaenetreset |
For a stream socket, the connection has been broken due to keep-alive activity detecting a failure while the operation was in progress. for a datatesocket, this error indicates that the time to live has expired. |
Wsaenobufs |
The Windows Sockets provider reports a buffer deadlock. |
Wsaenotconn |
The socket is not connected. |
Wsaenotsock |
The descriptor is not a socket. |
Wsaeopnotsupp |
MSG_OOB was specified, but the socket is not stream-style such as type sock_stream, OOB data is not supported in the communication domain associated with this socket, msg_partial is not supported, or the socket is unidirectional and supports only receive operations. |
Wsaeshudown |
The socket has been shut down; it is not possibleWsasendOn a socket afterShutdownHas been invoked with how set to sd_send or sd_both. |
Wsaewouldblock |
Windows NT:Overlapped sockets: there are too outstanding overlapped I/O requests. nonoverlapped sockets: the socket is marked as nonblocking AND THE send operation cannot be completed immediately. |
Wsanotinitialised |
A successfulWsastartupCall must occur before using this function. |
Wsa_io_pending |
An Overlapped operation was successfully initiated and completion will be indicated at a later time. |
Wsa_operation_aborted |
The overlapped operation has been canceled due to the closure of the socket, the execution of the "sio_flush" command inWsaioctl, Or the thread that initiated the overlapped request exited before the operation completed. For more information, see the remarks section. |
Remarks
WsasendCovering StandardSendFunction and is enhanced in the following two aspects:
> It can be used for overlapped socket (overlapping socket) to perform overlapping sending operations (simply known as Asynchronous sending)
> It can send data in multiple buffers at a time for centralized writing. It should be equivalent to writev on Unix. The advantage is to avoid Nagle algorithm.
WsasendData sent from a connection-oriented socket (the first parameter S. It can also be used, however, on connectionless sockets that have a stipulated default peer address established throughConnectOrWsaconnectFunction.
For overlapped Sockets (created using the wsa_flag_overlapped flag through the wsasocket function), overlapping io (overlapped I/O) is used for message sending, unless lpoverlapped and lpcompletionroutine are both null. this socket is considered as a non-overlapping socket. when all the buffers are sent, an action is executed to indicate that the operation is completed. This action may be a call completion routine or an event object. If the operation is not completed immediately, the final completion status is obtained through the completion routine or wsagetoverlappedresult.
For non-overlapping sockets, the last two parameters (lpoverlapped and lpcompletionroutine) are ignored. wsasend and send have the same semantics. Data is copied from the user buffer to the sending buffer (it should be the socket stack of the system ). If the socket is neither congested nor stream-oriented (simply understood as TCP), and the sending buffer does not have enough size, wsasend will only send part of the data in the user buffer. If the cache size is the same, and socke is the blocked socket, wsasend will block until all user data is sent successfully.
Note socket configuration items so_rcvtimeo and so_sndtimeo can only be used to block sockets.
The lpbuffers parameter is a pointer pointing to an array of wsabuf structures. This array can be transient (transient ). The meaning of the so-called transient state is as follows: if this operation overlaps, the service provider has the responsibility to save the wsabuf array before this call returns. This allows your applications to use a stack-based wsabuf array. That is to say, you can define a local variable. When wsasend returns an overlapping Io, your function's local variable has been destroyed (for example, your function has returned ). The system hasn't actually sent the data yet. Don't worry, the system will save the copy of this array.
For message-oriented socket (UDP ?), Do not exceed the maximum Message Size of the lower-layer protocol. This value can be obtained through the socket configuration item so_max_msg_size. If the data is too long to be sent atomically, wsaemsgsize is returned. No data is sent successfully.
Windows ME/98/95:TheWsasendFunction does not support more than 16 buffers.
NoteSuccessful completion of wsasend does not indicate that the data has been successfully sent.
Using dwflags
TheDwflagsParameter can be used to influence the behavior of the function invocation beyond the options specified for the associated socket. That is, the semantics of this function are determined by the socket options andDwflagsParameter. The latter is constructed by using the bitwise OR operator with any of the values listed in the following table.
Value |
Meaning |
Msg_dontroute |
Specifies that the data shocould not be subject to routing. A Windows Sockets service provider can choose to ignore this flag. |
MSG_OOB |
Send OOB data on a stream-style socket such as sock_stream only. |
Msg_partial |
Specifies thatLpbuffersOnly contains a partial message. Be aware that the error code wsaeopnotsupp will be returned by transports that do not support partial message transmissions. |
Overlapped socket I/O
If the overlap operation is completed immediately,WsasendReturn 0 and set at the same timeLpnumberofbytessentThe variable is the number of bytes sent. If the overlap operation is successful, initialization will be completed later,WsasendWhen socket_error is returned and the error code is set to wsa_io_pending,LpnumberofbytessentThe variable to be pointed to will not be updated. After overlapping Io is completed, the number of sent messages can be obtained in two ways: If the completion routine (I .e. lpcompletionroutine) is specifiedCbtransferredObtain the parameters. You can also callWsagetoverlappedresult,PassLpcbtransfer.
NoteIf a thread exits, all Io operations it sends will be canceled. For overlapping sockets, if the thread is closed before the operation is completed, pending asynchronous operations may fail. For more information, seeExitthread.
WsasendYou can call the following function completion routines:Wsarecv,Wsarecvfrom,Wsasend, OrWsasendto. This gives time-sensitive data transmission a higher priority (it seems that if you want to make data faster, it will give you a better chance ).
During overlapping operations,LpoverlappedThe data to be pointed to must always be valid (do not put some local variables in :-)). If there are multiple pending Io operations at the same time, each operation must have a separateWsaoverlappedStructure.
IfLpcompletionroutineNull. when the operation is complete, ifLpoverlappedThe hevent is a valid event object. The system sets this event as signaled ). User applications can useWsawaitformultipleeventsOrWsagetoverlappedresultTo wait for this event.
IfLpcompletionroutineNot empty,HeventIgnored, which can be used to transmit context information to the completion routine. If the caller sets a non-emptyLpcompletionroutineThen, it is called on the same overlapping Io.WsagetoverlappedresultThe parameter wsagetoverlappedresult is not set to true.HeventIs undefined while waitingHeventUnexpected results will also be generated. (That is, you should not use both the completion routine andWsagetoverlappedresult or hevnet).
The completion routine here is the same as the completion routine of Windows file IO. The completion routine is called until a thread is in the alertable wait state. For exampleWsawaitformultipleeventsAnd setFalertableTrue.
The transport providers layer allows users to send and receive calls in the completion routine of overlapping sockets, while ensuring that Io completion routines are not nested for a given socket. This gives time-sensitive data transmission a higher priority.
The following code is a prototype of the completion routine:
The following C ++ code example is a prototype of the completion routine.
Void callback completionroutine (
In DWORD dwerror,
In DWORD cbtransferred,
In lpwsaoverlapped lpoverlapped,
In DWORD dwflags
);
The completion routine is just a placeholder for a user-defined function. (That is, it is a callback function) dwerror indicates the status of overlapping Io completion.Lpoverlapped.CbtransferredIs the number of bytes sent. Dwflags is not used currently. It is always set to 0. This function does not return values.
Returning from this function allows invocation of another pending completion routine for this socket. all waiting completion routines are called before the alertable thread's wait is satisfied with a return code of wsa_io_completion. completion routines may be called in any order, and do not need to overlap Io completion. However, the multiple buffers submitted for sending are sent in the specified order.
If you use the complete port, pay attention to the callWsasendThe order is the order in which the buffer is filled. Do not call the wsasend function on the same socket from different threads at the same time, because the data in the buffer may be in an unpredictable order.
Example code
The following code demonstrates how to use overlapping IoWsasendFunction.
# Include <winsock2.h>
# Include <ws2tcpip. h>
# Include <stdio. h>
# Include <stdlib. h>
# Define data_bufsize 4096
# Define send_count 10
Void _ cdecl main ()
{
Wsadata WSD;
Struct addrinfo * result = NULL,
Hints =;
Wsaoverlapped sendoverlapped =;
Socket listensocket = invalid_socket,
Acceptsocket = invalid_socket;
Wsabuf databuf;
DWORD sendbytes, flags;
Char buffer [data_bufsize];
Int err, RC, I;
// Load Winsock
Rc = wsastartup (makeword (2, 2), & WSD );
If (RC! = 0 ){
Fprintf (stderr, "unable to load Winsock: % d/N", RC );
Return;
}
// Initialize the hints to obtain
// Wildcard Bind Address for IPv4
Hints. ai_family = af_inet;
Hints. ai_socktype = sock_stream;
Hints. ai_protocol = ipproto_tcp;
Hints. ai_flags = ai_passive;
Rc = fig (null, "27015", & hints, & result );
If (RC! = 0 ){
Fprintf (stderr, "getaddrinfo failed: % d/N", RC );
Return;
}
Listensocket = socket (result-> ai_family,
Result-> ai_socktype, result-> ai_protocol );
If (listensocket = invalid_socket ){
Fprintf (stderr, "socket failed: % d/N ",
Wsagetlasterror ());
Freeaddrinfo (result );
Return;
}
Rc = BIND (listensocket, result-> ai_addr,
(INT) result-> ai_addrlen );
If (rc = socket_error ){
Fprintf (stderr, "bind failed: % d/N ",
Wsagetlasterror ());
Freeaddrinfo (result );
Closesocket (listensocket );
Return;
}
Rc = listen (listensocket, 1 );
If (rc = socket_error ){
Fprintf (stderr, "Listen failed: % d/N ",
Wsagetlasterror ());
Freeaddrinfo (result );
Closesocket (listensocket );
Return;
}
// Accept an incoming connection request
Acceptsocket = accept (listensocket, null, null );
If (acceptsocket = invalid_socket ){
Fprintf (stderr, "Accept failed: % d/N ",
Wsagetlasterror ());
Freeaddrinfo (result );
Closesocket (listensocket );
Return;
}
Printf ("client accepted.../N ");
// Create an event handle and setup an overlapped structure.
Sendoverlapped. hevent = wsacreateevent ();
If (sendoverlapped. hevent = NULL ){
Fprintf (stderr, "wsacreateevent failed: % d/N ",
Wsagetlasterror ());
Freeaddrinfo (result );
Closesocket (listensocket );
Closesocket (acceptsocket );
Return;
}
Databuf. Len = data_bufsize;
Databuf. Buf = buffer;
For (I = 0; I <send_count; I ++ ){
Rc = wsasend (acceptsocket, & databuf, 1,
& Sendbytes, 0, & sendoverlapped, null );
If (rc = socket_error )&&
(Wsa_io_pending! = (ERR = wsagetlasterror ()))){
Fprintf (stderr, "wsasend failed: % d/N", err );
Break;
}
Rc = wsawaitformultipleevents (1, & sendoverlapped. hevent, true, infinite, true );
If (rc = wsa_wait_failed ){
Fprintf (stderr, "wsawaitformultipleevents failed: % d/N", wsagetlasterror ());
Break;
}
Rc = wsagetoverlappedresult (acceptsocket, & sendoverlapped, & sendbytes, false, & flags );
If (rc = false ){
Fprintf (stderr, "wsasend operation failed: % d/N", wsagetlasterror ());
Break;
}
Printf ("wrote % d Bytes/N", sendbytes );
Wsaresetevent (sendoverlapped. hevent );
}
Wsacloseevent (sendoverlapped. hevent );
Closesocket (acceptsocket );
Closesocket (listensocket );
Freeaddrinfo (result );
Wsacleanup ();
Return;
}
Requirements
Client |
Requires Windows Vista, Windows XP, Windows 2000 Professional, Windows NT Workstation 3.51 and later, Windows ME, Windows 98, or Windows 95. |
Server |
Requires Windows Server "Longhorn", Windows Server 2003, Windows 2000 server, or Windows NT Server 3.51 and later. |
Header |
Declared in winsock2.h. |
Library |
Use ws2_32.lib. |
DLL |
Requires ws2_32.dll. |
See alsowinsock reference
Winsock Functions
Wsacloseevent
Wsacreateevent
Wsagetoverlappedresult
Wsasocket
Wsawaitformultipleevents