直接上代码,简单粗暴:
服务器端:
int clifd[10]; /* 存放客户端套接字的数组 */
sem_t sem; /* 信号量 */
pthread_mutex_t mutex; /* 互斥锁 */
void initCli() /* 初始化 */
{
int i = 0;
for(; i < 10; ++i)
{
clifd[i] = -1;
}
}
int getCli()
{
pthread_mutex_lock(&mutex); /* 保证线程安全 */
int c = clifd[0]; /* 获取先到客户端的套接字,先来先服务 */
int i = 0;
for(; (i < 9 && clifd[i] != -1); ++i)
{
clifd[i] = clifd[i+1]; /* 整理数组 */
}
clifd[i] = -1;
pthread_mutex_unlock(&mutex);
return c;
}
int insertCli(int c) /* 插入接受到的客户端套接字 */
{
int i = 0;
for(; i < 10; ++i)
{
if(-1 == clifd[i])
{
clifd[i] = c;
return 1;
}
}
return -1;
}
void *pthread_fun(void *arg) /* 函数线程, 即处理单元 */
{
while(1)
{
sem_wait(&sem); /* 对信号量进行P操作,如果目前没有可处理客户端连接则阻塞 */
int c = getCli(); /* 获取客户端套接字 */
while(1)
{
char buff[128] = {0};
if(0 >= recv(c, buff, 127, 0))
{
printf("one client has exit!\n");
break; /* 切换到其他等待的客户端 */
}
printf("%d %s\n",c,buff);
send(c, "ok", 2, 0);
}
}
}
int main()
{
int s = sem_init(&sem, 0, 0); /* 初始化信号量 */
assert(s == 0);
initCli();
int sockfd = socket(AF_INET, SOCK_STREAM, 0);
assert(sockfd != -1);
struct sockaddr_in ser,cli;
ser.sin_family = AF_INET;
ser.sin_port = htons(6000); /* 使用6000端口 */
ser.sin_addr.s_addr = inet_addr("127.0.0.1"); /* 回环地址 */
int res = bind(sockfd, (struct sockaddr *)&ser, sizeof(ser)); /* 命名套接字 */
assert(res != -1);
res = listen(sockfd, 10); /* 监听套接字 */
assert(res != -1);
int i = 0;
for(; i < 3; ++i) /* 预先创建好的线程池 */
{
pthread_t id;
res = pthread_create(&id, NULL, pthread_fun, NULL);
}
while(1)
{
int len = sizeof(cli);
int c = accept(sockfd, (struct sockaddr *)&cli, &len); /* 获取客户端套接字 */
if(-1 == insertCli(c))
{
close(c); /* 插入失败说明超过可处理客户端数量,直接退出 */
continue;
}
sem_post(&sem); /* 获取客户端套接字后就对信号箱V操作以使函数线程开始工作 */
}
}
客户端:
int main()
{
int sockfd = socket(PF_INET, SOCK_STREAM, 0);
assert(sockfd != -1);
struct sockaddr_in ser,cli;
memset(&ser, 0, sizeof(ser));
ser.sin_family = PF_INET;
ser.sin_port = htons(6000); //主机的地址格式转化到网络的地址格式(大小锻)
ser.sin_addr.s_addr = inet_addr("127.0.0.1");
int c = connect(sockfd, (struct sockaddr *)&ser, sizeof(ser));
assert(c != -1);
while(1)
{
char buff[128] = {0};
fgets(buff,128,stdin);
buff[strlen(buff) - 1] = 0;
send(sockfd, buff, strlen(buff), 0);
char recvbuf[128] = {0};
recv(sockfd, recvbuf, 127, 0);
printf("%s\n",recvbuf);
if(strcmp(buff, "end") == 0)
break;
}
close(c);
exit(0);
}