2 数据的接收
与通过已连接的套接字发送数据的函数类似,通过已连接的套接字接收数据的函数也有两个,一个是recv()函数,另一个是WSARecv()函数,其中WSARecv()函数是Winsock2版本的函数。
2.1 recv()函数
recv()函数的作用是通过套接字接收数据。
2.1.1 函数格式
recv()函数的格式为
int recv(
SOCKET s
, char *buf
, int len
, int flags
);
其中,参数s表示已连接的套接字;buf指向了缓冲区,用于保存接收到的数据;len是buf的长度;flags指定了接收数据时的方法。如果成功接收了对端发送过来的数据,recv()函数返回实际接收数据的字节,如果失败,则返回SOCKET_ERRRO。
2.1.2 相关代码
服务端通过以下代码接收来自客户端的数据:
#define DEFAULT_BUFLEN 512
char recvbuf[DEFAULT_BUFLEN];
int recvbuflen = DEFAULT_BUFLEN;
do {
iResult = recv(ClientSocket, recvbuf, recvbuflen, 0);
if ( iResult > 0 )
printf("Bytes received: %d\n", iResult);
else if ( iResult == 0 )
printf("Connection closed\n");
else
printf("recv failed: %d\n", WSAGetLastError());
} while( iResult > 0 );
其中,recv()函数的ClientSocket参数是服务端accept()函数的返回值,也就是用于与客户端数据传输的参数。如果成功接收了来自客户端的数据,则将数据保存再recvbuf中。
2.2 WSARecv()函数
WSARecv()函数的作用是通过已连接的套接字接收对端的数据。
2.2.1 函数格式
该函数的格式为
int WSAAPI WSARecv(
SOCKET s
, LPWSABUF lpBuffers
, DWORD dwBufferCount
, LPDWORD lpNumberOfBytesRecvd
, LPDWORD lpFlags
, LPWSAOVERLAPPED lpOverlapped
, LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine
);
其参数含义与WSASend()函数类似。而WSARecv()函数与recv()函数的区别可参见“1.2.3WSASend()函数与send()函数的区别”。
2.2.2 相关代码
服务端通过以下代码接收来自客户端的数据:
while (1) {
rc = WSARecv(ClientSocket, &DataBuf, 1, &RecvBytes, 0, NULL, NULL);
if (rc == SOCKET_ERROR)
{
wprintf(L"WSARecv failed with error: %d\n", err);
}
其中,WSARecv()函数的参数ClientSocket是用于与客户端通信的套接字;DataBuf是WSABUF结构的对象,用于保存接收到的数据;RecvBytes变量保存了从对端实际接收到的字节数。