生活需要一颗感恩的心来创造, 一颗感恩的心需要生活来滋养。——王符
感谢《精通windows socket网络编程》的作者等工作人员,这文章说是原创太牵强,是我学习这本书的学习笔记。
这个服务器的基本流程(主线程的流程):
初始化服务器 --> 启动服务 --> 停止服务 --> 服务器退出
一。初始化服务器
初始化服务器的流程:初始化全局变量-->初始化SOCKET
BOOL InitSever(void)
{
InitMember();//初始化全局变量
//初始化SOCKET
if (!InitSocket())
return FALSE;
return TRUE;
}
A.初始化全局变量
//全局变量
HANDLE hThreadAccept; //接收客户端请求线程句柄
HANDLE hThreadHelp; //清理资源线程句柄
SOCKET sServer; //监听客户端连接套接字
BOOL bServerRunning; //服务器的当前工作状态变量
HANDLE hServerEvent; //服务器退出事件句柄
CLIENTLIST clientlist; //管理客户端连接的链表
CRITICAL_ SECTION csClientList; //保护链表的临界区对象。使用该临界区对象确保各线程对该链表的互斥访问
void InitMember(void)
{
InitializeCriticalSection(&csClientList); //初始化临界区
hServerEvent = CreateEvent(NULL, TRUE, FALSE, NULL); //手动设置事件,初始化为无信息号状态
hThreadAccept = NULL; //设置为NULL
hThreadHelp = NULL; //设置为NULL
sServer = INVALID_SOCKET; //设置为无效的套接字
bServerRunning = FALSE; //服务器为没有运行状态
clientlist.clear(); //清空链表
}
注意hServerEvent变量的应用。
B.初始化SOCKET
主要完成 1·创建套接字,2·绑定套接字,3·监听套接字
BOOL InitSocket(void)
{
//返回值
int reVal;
//初始化Windows Sockets DLL
WSADATA wsData;
reVal = WSAStartup(MAKEWORD(2,2),&wsData);
//创建套接字
sServer = socket(AF_INET, SOCK_STREAM, 0);
if(INVALID_SOCKET== sServer)
return FALSE;
//设置套接字非阻塞模式
unsigned long ul = 1;
reVal = ioctlsocket(sServer, FIONBIO, (unsigned long*)&ul);
if (SOCKET_ERROR == reVal)
return FALSE;
//绑定套接字
sockaddr_in serAddr;
serAddr.sin_family = AF_INET;
serAddr.sin_port = htons(SERVERPORT);
serAddr.sin_addr.S_un.S_addr = INADDR_ANY;
reVal = bind(sServer, (struct sockaddr*)&serAddr, sizeof(serAddr));
if(SOCKET_ERROR == reVal )
return FALSE;
//监听
reVal = listen(sServer, SOMAXCONN);
if(SOCKET_ERROR == reVal)
return FALSE;
return TRUE;
}
下面还有(⊙o⊙)哦。。。。