#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>
#include <semaphore.h>
#include <wait.h>
#include <signal.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <sys/ipc.h>
#include <sys/sem.h>
#include <semaphore.h>
#include <sys/msg.h>
#include <sys/shm.h>
#include <sys/un.h>
#include <sys/time.h>
#include <sys/select.h>
#include “doublyList.h”
#include “array.h”
myListOP * fdList;
struct info{
struct sockaddr_in client_addr;
int fd;
};
void printInt( int*a){
printf(“%d”,a);
}
struct info creatInfo(struct sockaddr_in client_addr,int fd){
struct info ret = malloc(sizeof(struct info));
if (client_addr)
{
ret->client_addr=*client_addr;
}
else{
memset(&ret->client_addr,0,sizeof(struct sockaddr_in));
}
ret->fd = fd;
return ret;
}
void printInfo(struct info* info){
static char ip_human[16] = {0};
if (info ==0 || (&(info->client_addr)==0))
{
return;
}
int port_human=ntohs(info->client_addr.sin_port);
inet_ntop(AF_INET,&info->client_addr.sin_addr,ip_human,16);
printf("ip:%s,port:%d,fd:%d::",ip_human,port_human,info->fd);
}
int serverfun(struct info* info){
int client = info->fd;
char ip_human[16]={0};
int port_human=0;
struct sockaddr_in client_addr = {0};
client_addr = info->client_addr;
inet_ntop(AF_INET,&client_addr.sin_addr,ip_human,16);
port_human=ntohs(client_addr.sin_port);
char buf[64] = “”;
int res = read(client,buf,64);
if (res == 0)
{
printf(“客户端已断开连接:\nIP:%s\nport:%d\n”,ip_human,port_human);
close(client);
fdList->del(fdList,fdList->find(fdList,info,0));
return 0;
}
printf(“客户端IP:%s\nport:%d\n发来消息:%s\n”,ip_human,port_human,buf);
return 1;
}
int main(int argc, char const *argv[])
{
if (argc<2)
{
printf(“请输入端口号\n”);
return 1;
}
int server = socket(AF_INET,SOCK_STREAM,0);
struct sockaddr_in addr={0};
addr.sin_family=AF_INET;
addr.sin_port=htons(atoi(argv[1]));
addr.sin_addr.s_addr=inet_addr("0.0.0.0");
if(bind(server,(struct sockaddr * )&addr,sizeof(addr))==-1){
perror("bind:");
return 1;
}
struct sockaddr_in client_addr = {0};
int client_len = sizeof(client_addr);
int ret;
int max = 10;
listen(server,max);
char ip_human[16]="";
int port_human = 0;
//创建监视列表
fd_set fd_listen;
FD_ZERO(&fd_listen);
int client;
fdList = myListDInit((void(*)(void*))printInt);
struct info * currentinfo=0;
int* currentfd =0;
unsigned int i=0;
fdList->append(fdList,creatInfo(0,server));
printf("服务器正在运行:\n");
for (;;)
{
i=0;
while (currentinfo = (struct info*)fdList->slice(fdList,i++))
{
currentfd = ¤tinfo->fd;
FD_SET(*currentfd,&fd_listen);//重置fd表
}
select(max,&fd_listen,0,0,0);//让服务器阻塞,等待
//似乎有问题,select不一定有东西可以操作
//解除阻塞时一定有东西可以操作
i=0;
while (currentinfo = fdList->slice(fdList,i++))
{
currentfd = ¤tinfo->fd;
if (*currentfd == server&&FD_ISSET(*currentfd,&fd_listen))//有新的客户端连接
{
client = accept(server,(struct sockaddr * )&client_addr,&client_len);
fdList->append(fdList,creatInfo(&client_addr,client));
inet_ntop(AF_INET,&client_addr.sin_addr,ip_human,16);
port_human=ntohs(client_addr.sin_port);
printf("客户端已连接:\nIP:%s\nport:%d\n",ip_human,port_human);
continue;
}
//客户端操作
else{
serverfun(currentinfo);
}
}
}
return 0;
}