Visual C++网络编程学习(2)-TCP阻塞模型
利用C++搭建了一个简单的TCP阻塞模型,只是做了客户端的发送与服务器的接收。程序我已经测试了一遍,如果大家在看的过程中有什么问题,也希望大家相互交流。代码如下:
服务器:
#include<iostream>
#include<WINSOCK2.h>
#pragma comment(lib,"Ws2_32.lib")
using namespace std;
#define SERVEPORT 10000
class CTcpConnectServe
{
public:
CTcpConnectServe()
{};
~CTcpConnectServe()
{};
//socket函数
int InitSocketConnect(); //初始化SOCKET
void CloseSocketConnect(); //关闭SOCKET
int Receive(_Out_ char *buf, _In_ int len, _In_ int flags); //接收函数
int Send(_Out_ char *buf, _In_ int len, _In_ int flags); //发送函数
sockaddr_in m_soClientAddr; //客户端地址
private:
SOCKET m_SocketServe;
sockaddr_in m_soServeAddr;
SOCKET m_SocketClient;
int m_nAddrlen;
};
//初始化SOCKET
int CTcpConnectServe::InitSocketConnect()
{
//初始化Winsock
WSADATA wsaData = { 0 };
WORD wVer = MAKEWORD(2, 2);
if (0 != WSAStartup(wVer, &wsaData))
{
cout << "初始化错误,错误代码:" << WSAStartup(wVer, &wsaData) << endl;
return 0;
}
//服务器创建套接字
if (NULL != m_SocketServe)
{
closesocket(m_SocketServe);
}
m_SocketServe = socket(AF_INET,SOCK_STREAM, IPPROTO_TCP);
if (INVALID_SOCKET == m_SocketServe)
{
cout << "创建套接字错误,错误代码:" << WSAGetLastError() << endl;
return 0;
}
cout << "套接字创建成功!" << endl;
//服务器将本地套接字地址绑定到套接字上
m_soServeAddr.sin_family = AF_INET;
m_soServeAddr.sin_port = htons(SERVEPORT);
m_soServeAddr.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
if (bind(m_SocketServe, (sockaddr*)&m_soServeAddr, sizeof(m_soServeAddr)))
{
cout << "套接字绑定错误" << WSAGetLastError() << endl;
return 0;
}
if (listen(m_SocketServe,1))
{
cout << "套接字监听错误,错误代码:" << WSAGetLastError() << endl;
return 0;
}
cout << "套接字进入监听状态!" << endl;
if (NULL != m_SocketClient)
{
closesocket(m_SocketClient);
}
m_nAddrlen = sizeof(m_soClientAddr);
m_SocketClient = accept(m_SocketServe, (sockaddr*)&m_soClientAddr,&m_nAddrlen);
if (m_SocketClient== INVALID_SOCKET)
{
cout << "服务器接收客户端错误" << WSAGetLastError() << endl;
}
else
{
cout << "服务器接收客户端成功!" << endl;
}
return 0;
}
//关闭SOCKET
void CTcpConnectServe::CloseSocketConnect()
{
closesocket(m_SocketServe);
closesocket(m_SocketClient);
WSACleanup(); //系统释放Winsock资源
}
//接收函数
int CTcpConnectServe::Receive(char * buf, int len, int flags)
{
int nRet = recv(m_SocketClient, buf, len, flags);
if (nRet<0)
{
cout << "接收数据错误" << WSAGetLastError() << endl;
}
return nRet;
}
//发送函数
int CTcpConnectServe::Send(char * buf, int len, int flags)
{
int nRet = send(m_SocketClient, buf, len, flags);
if (nRet<0)
{
cout << "发送数据错误" << WSAGetLastError() << endl;
}
return nRet;
}
//主函数
void main()
{
CTcpConnectServe TcpConnectServe;
TcpConnectServe.InitSocketConnect();
int buffsize = 10000;
char *revBuffer = (char*)malloc(sizeof(char)*buffsize);
while (1)
{
int nRet = TcpConnectServe.Receive(revBuffer, buffsize, 0);
cout << "收到" << nRet << "个字节数据" << endl;
cout << "收到数据为:";
for (int i = 0; i<nRet; i++)
{
cout << *(revBuffer + i);
}
cout << "" << endl;;
}
}
客户端:
#include<iostream>
#include <string>//引用头文件
#include<WINSOCK2.h>
#pragma comment(lib,"Ws2_32.lib")
using namespace std;
#define SERVEPORT 10000
class CTcpConnectServe
{
public:
CTcpConnectServe()
{};
~CTcpConnectServe()
{};
//socket函数
int InitSocketConnect(); //初始化SOCKET
void CloseSocketConnect(); //关闭SOCKET
int Receive(_Out_ char *buf, _In_ int len, _In_ int flags); //接收函数
int Send(_Out_ char *buf, _In_ int len, _In_ int flags); //发送函数
sockaddr_in m_soServeAddr; //服务器地址
private:
SOCKET m_SocketServe;
SOCKET m_SocketClient;
sockaddr_in m_soClientAddr;
int m_nAddrlen;
};
//初始化SOCKET
int CTcpConnectServe::InitSocketConnect()
{
//初始化Winsock
WSADATA wsaData = { 0 };
WORD wVer = MAKEWORD(2, 2);
if (0 != WSAStartup(wVer, &wsaData))
{
cout << "初始化错误,错误代码:" << WSAStartup(wVer, &wsaData) << endl;
return 0;
}
//服务器创建套接字
if (NULL != m_SocketClient)
{
closesocket(m_SocketClient);
}
m_SocketClient = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (INVALID_SOCKET == m_SocketClient)
{
cout << "创建套接字错误,错误代码:" << WSAGetLastError() << endl;
return 0;
}
cout << "套接字创建成功!" << endl;
m_nAddrlen = sizeof(m_soServeAddr);
if (connect(m_SocketClient, (sockaddr *)&m_soServeAddr,m_nAddrlen) == SOCKET_ERROR)
{
cout << "套接字连接失败,错误代码:" << WSAGetLastError() << endl;
return 0;
}
cout << "与服务器连接成功!" << endl;
return 0;
}
//关闭SOCKET
void CTcpConnectServe::CloseSocketConnect()
{
closesocket(m_SocketClient);
WSACleanup(); //系统释放Winsock资源
}
//接收函数
int CTcpConnectServe::Receive(char * buf, int len, int flags)
{
int nRet = recv(m_SocketClient, buf, len, flags);
if (nRet<0)
{
cout << "接收数据错误" << WSAGetLastError() << endl;
}
return nRet;
}
int CTcpConnectServe::Send(char * buf, int len, int flags)
{
int nRet = send(m_SocketClient, buf, len, flags);
if (nRet<0)
{
cout << "发送数据错误" << WSAGetLastError() << endl;
}
return nRet;
}
void main()
{
CTcpConnectServe TcpConnect;
//初始化服务器地址
TcpConnect.m_soServeAddr.sin_family = AF_INET;
TcpConnect.m_soServeAddr.sin_port = htons(SERVEPORT);
TcpConnect.m_soServeAddr.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
TcpConnect.InitSocketConnect();
while (1)
{
cout << "请输入要发送的字符串:";
string s1;
cin >> s1;
int buffsize = 10000;
char *revBuffer = (char*)malloc(sizeof(char)*buffsize);
int i = 0;
for (i = 0; i < s1.size(); i++)
{
*(revBuffer + i) = s1[i];
}
int nRet = TcpConnect.Send(revBuffer, i, 0);
cout << "发送了" << nRet << "个字节" << endl;
}
}