平顶山建设局网站,win7 网站系统怎么做,seo怎么做新手入门,广州建设工程领域平台登录本文章介绍一种基于Linux使用C语言实现简单的局域网聊天室程序的方法#xff0c;支持消息群发#xff0c;历史数据查询#xff0c;好友列表查看#xff0c;好友上线下线提醒等功能。聊天界面如下图所示#xff1a;下面将按步骤介绍该系统的设计实现#xff0c;首先在linu…本文章介绍一种基于Linux使用C语言实现简单的局域网聊天室程序的方法支持消息群发历史数据查询好友列表查看好友上线下线提醒等功能。聊天界面如下图所示下面将按步骤介绍该系统的设计实现首先在linux下创建一个目录在目录下按顺序创建几个文件clientlist.c common.h sock.c main.c Makefile,如下图所示创建完各文件之后依次在文件里面新增相关的代码内容。1.在Makefile文件里面添加如下内容CCgcc
CPROG chat
BIN $(CPROG)
OBJS main.o sock.o clientlist.o
LDFLAGS -lpthread
CFLAGS -I.
all: $(BIN)
install:$(BIN)true
uninstall:rm -f $(OBJS) $(BIN)
clean:rm -f $(OBJS) $(BIN)
$(BIN): $(OBJS)$(CC) $(OBJS) $(CFLAGS) $(LDFLAGS) $(CFLAGS_EXTRA) -o $(BIN)2.在main.c文件里面添加如下内容#include stdio.h
#include string.h
#include common.h
void main(int argc, char *argv[])
{if(argc2) {LOG(input fmt err!\n);return ;}if(!strcmp(argv[1], s)) {svr_start(SERVER_PORT);}else if(!strcmp(argv[1], c)) {cli_start(argv);}
}
3.在common.h文件添加如下内容#include stdio.h
#include unistd.h
#include string.h
#include stdlib.h
#include errno.h
#include pthread.h
#include netinet/tcp.h
#include netinet/in.h
#include sys/socket.h
#include sys/queue.h
#include sys/ioctl.h
#include linux/if.h
#include semaphore.h
#include arpa/inet.h
#include net/if_arp.h
#include fcntl.h#define MAXCLI 10
#define SERVER_PORT 8080
#define USRNAME_LENGTH 32
#define RGST_INIT 0
#define RGST_OK 1
#define PKG_HEAD m
#define MSG_MODE_LOGIN 0
#define MSG_MODE_LOGIN_ACK 1
#define MSG_MODE_SEND 2
#define MSG_MODE_GET_LIST 3
#define MSG_MODE_GET_LIST_ACK 4
#define MSG_MODE_ONLINE 5
#define MSG_MODE_OFFLINE 6
#define HISTROY_FILE h.txtstruct client_chn_s {int skfd;char usrname[USRNAME_LENGTH];CIRCLEQ_ENTRY(client_chn_s) link;
};
typedef struct client_chn_s client_chn_t;
typedef struct svr {int listener;unsigned short port;
}svr_t;typedef struct cli {int sockfd;unsigned char stat;unsigned char history_enable;time_t login_timeout;time_t reconn_timeout;char usrname[USRNAME_LENGTH];char ip[48];unsigned short port;
}cli_t;typedef struct msg_s {unsigned char msgtyp;unsigned char *payload;int payloadlen;unsigned char *username;int username_len;
}msg_t;
4.在sock.c添加如下内容#include stdio.h
#include string.h
#include stdlib.h
#include unistd.h
#include sys/types.h
#include fcntl.h
#include errno.h
#include sys/socket.h
#include netinet/in.h
#include arpa/inet.h
#include netinet/tcp.h
#include netdb.h
#include stdarg.h
#include common.h
cli_t cli;
void LOG(const char *format,...)
{va_list argptr;char buffer[2048];va_start(argptr,format);vsprintf(buffer,format,argptr);va_end(argptr);//printf(%s, buffer);
}
/*
Hex打印
*/
void dump_buf(char *label, unsigned char *in, int len)
{int i0;LOG(%s:\n, label);for(i0;ilen;i) {LOG(%02x , in[i]0xff);if(0(i1)%16) {LOG(\n);}}LOG(\n);
}
void get_cur_time(char *timestamp)
{time_t timep;struct tm *p, pp;time(timep);localtime_r(timep, pp);p pp; sprintf(timestamp,%04d-%02d-%02d %02d:%02d:%02d,p-tm_year 1900, p-tm_mon 1, p-tm_mday, p-tm_hour, p-tm_min, p-tm_sec);
}
void sk_history_record(char *msg)
{FILE *fp fopen(HISTROY_FILE, ab);if(!fp) {LOG([%s]open %s fail, __func__, HISTROY_FILE);return 0;}fprintf(fp, %s\r\n, msg);fclose(fp);
}
int sk_tcp_svr_init(int port)
{int yes 1;struct sockaddr_in svr_addr;int listenfd -1;if((listenfd socket(AF_INET, SOCK_STREAM, 0)) -1){ LOG(create socket() fail\n); return -1;} if(setsockopt(listenfd, SOL_SOCKET, SO_REUSEADDR, yes, sizeof(int)) -1){ LOG(setsockopt() fail!\n); exit(0);return -1; }svr_addr.sin_family AF_INET; svr_addr.sin_addr.s_addr INADDR_ANY; svr_addr.sin_port htons(port);memset((svr_addr.sin_zero), \0, 8);if(bind(listenfd, (struct sockaddr *)svr_addr, sizeof(svr_addr)) -1){LOG(bind fail!\n);return -1;}if(listen(listenfd, MAXCLI) -1) { LOG(listen fail\n);return -1;}LOG(listen success!!!\n);return listenfd;
}
int sk_start_connect(int *sockfd,char *ip,unsigned short port)
{int i; int iRet;int status;int times3;struct sockaddr_in host;int err; int errlen; struct timeval timeout{3,0};fd_set mask;iRet0;status-1;*sockfd-1;if ((0port) || 0strlen(ip)){LOG(invalid param);return 0;}host.sin_familyAF_INET; host.sin_porthtons(port); LOG(connect %s:%u\n,ip,port);inet_aton(ip,host.sin_addr);if ( (*sockfdsocket(AF_INET,SOCK_STREAM,0))0 ) { LOG(create sock err); iRet0;goto err_out; }iRetconnect(*sockfd,(struct sockaddr *)host,sizeof(host));if(iRet0) {LOG(connect succ\n);if(fcntl(*sockfd,F_SETFL,O_NDELAY) 0 ){ LOG(set sock non_block error); iRet0;LOG(fcntl err);goto err_out; } return 1;}LOG(iRet:%d\n, iRet);
err_out:return (iRet);
}
int sk_tcp_connect_init(char *svr, int port)
{int iRet, sockfd -1;iRetsk_start_connect(sockfd,svr, port);if (iRet 0)return -1;return sockfd;
}
int sk_msg_pack(unsigned char *buf, msg_t *m)
{int len 0;unsigned char msgtype m-msgtyp;buf[len] PKG_HEAD;buf[len] msgtype;switch(msgtype){case MSG_MODE_LOGIN:{LOG([%s][%d]\n,__FUNCTION__,__LINE__);if(m-username_lenUSRNAME_LENGTH) {buf[len]m-username_len/256;buf[len]m-username_len;memcpy(buflen, m-username, m-username_len);lenm-username_len;}LOG([%s][%d]\n,__FUNCTION__,__LINE__);break;}case MSG_MODE_SEND:{char timestamp[48];get_cur_time(timestamp);LOG([%s][%d]\n,__FUNCTION__,__LINE__);unsigned char msgbuf[1024];int msglen sprintf(msgbuf,%s%s:%s, m-username, timestamp,m-payload);buf[len]msglen/256;buf[len]msglen;memcpy(buflen, msgbuf, msglen);lenmsglen;break;}case MSG_MODE_GET_LIST_ACK:case MSG_MODE_OFFLINE:case MSG_MODE_ONLINE:{buf[len]m-payloadlen/256;buf[len]m-payloadlen;memcpy(buflen, m-payload, m-payloadlen);lenm-payloadlen;break;}}return len;
}
void svr_msg_hander(int fd, unsigned char *in, int len)
{unsigned char msgtyp in[1];switch(msgtyp){case MSG_MODE_LOGIN:{char usr[USRNAME_LENGTH];strcpy(usr, in[4]);client_chn_add_usr(fd, usr);msg_t m;m.msgtyp MSG_MODE_LOGIN_ACK;unsigned char ackbuf[64];int acklen sk_msg_pack(ackbuf, m);LOG(Send RGST Ack!\n);send(fd, ackbuf, acklen, 0);svr_online_offline_notify(fd,1);break;}case MSG_MODE_SEND:{client_chn_msg_proc(0,in, len);break;}case MSG_MODE_GET_LIST:{char usrlist[1024];int retclient_chn_get_usr_list(usrlist);msg_t m;m.msgtyp MSG_MODE_GET_LIST_ACK;m.payload usrlist;m.payloadlen ret;unsigned char ackbuf[1450];int acklen sk_msg_pack(ackbuf, m);dump_buf(Send friend list resuest Ack, ackbuf,acklen);send(fd, ackbuf, acklen, 0);break;}}
}
void svr_online_offline_notify(int fd, int isonline)
{client_chn_t *chn client_chn_get_elm(fd);msg_t m;if(isonline1) {m.msgtyp MSG_MODE_ONLINE;}else {m.msgtyp MSG_MODE_OFFLINE;}char payload[128];char timestamp[48];get_cur_time(timestamp);if(isonline1) {sprintf(payload, %s%s Online!, timestamp, chn-usrname);}else {sprintf(payload, %s%s Quit!, timestamp, chn-usrname);}m.payload payload;m.payloadlen strlen(payload);unsigned char buf[1450];int len sk_msg_pack(buf, m);dump_buf(notify offline, buf,len);client_chn_msg_proc(fd,buf, len);
}
int svr_recv_proc(int fd)
{unsigned char recvbuf[1450];int ret recv(fd, recvbuf, sizeof(recvbuf), 0);if(ret0) {int close_flag 0;if(ret 0){/* connection closed */LOG(socket %d close\n, fd);close_flag 1;}else {if(errno!EAGAIN) {LOG(recv error!\n);close_flag 1;}}if(close_flag) {svr_online_offline_notify(fd, 0);return -1;}}else {LOG([clisk:%d]recv %d bytes\n, fd, ret);dump_buf(recv, recvbuf, ret);//client_chn_msg_proc(fd, recvbuf, ret);svr_msg_hander(fd, recvbuf, ret);return ret;}return 0;
}
void svr_accept(svr_t *svr)
{int newfd;struct sockaddr_in clientaddr;int addrlen sizeof(clientaddr);if((newfd accept(svr-listener, (struct sockaddr *)clientaddr, (socklen_t *)addrlen)) -1){LOG(accept() error !\n);}else{LOG( New connection from %s on socket %d\n, inet_ntoa(clientaddr.sin_addr), newfd);client_chn_t *elm (client_chn_t *)malloc(sizeof(client_chn_t));elm-skfd newfd;client_chn_insert(elm);}
}
int svr_add_fds(svr_t *svr, fd_set *master)
{int i;int fdmax 0;if(svr-listener0) {FD_SET(svr-listener, master);if (svr-listener fdmax) {fdmax svr-listener;}}int max client_chn_add_fds(master);if(fdmaxmax) fdmax max;return fdmax;
}
void svr_select_fd_proc(svr_t *svr, int fd)
{if(svr-listenerfd) {svr_accept(svr);return;}else {if(svr_recv_proc(fd)0) {client_chn_del(fd);close(fd);}}
}
void svr_start(int port)
{svr_t svr;svr.portport;svr.listenersk_tcp_svr_init(port);struct timeval tv, timeo;fd_set master;client_chn_init();while(1) {tv.tv_sec0;tv.tv_usec20000;FD_ZERO(master);int fdmax svr_add_fds(svr, master);if(select(fdmax1, master, NULL, NULL, tv)0){LOG(select err\n);}int i;for(i 0; i fdmax; i){if(FD_ISSET(i, master)) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);svr_select_fd_proc(svr,i);}}}
}
void *cli_input_hander(void *arg)
{while(1) {char msgbuf[1024];//scanf(%s, msgbuf);gets(msgbuf);if((cli.sockfd0)(cli.statRGST_OK)) {if((strlen(msgbuf)2)(msgbuf[0]-)) {switch(msgbuf[1]) {case h:{show_help();break;}case H:{printf(---------History----------\n);char cmd[64];sprintf(cmd, cat %s, HISTROY_FILE);system(cmd);printf(---------------------------\n);break;}case q:{printf(Bye!\n);exit(0);break;}case g:{char sendbuf[1450];char username[32];msg_t m;m.msgtyp MSG_MODE_GET_LIST;int sendlen sk_msg_pack(sendbuf, m);dump_buf(send, sendbuf, sendlen);send(cli.sockfd, sendbuf, sendlen, 0);break;}}}else {char sendbuf[1450];char username[32];msg_t m;m.payload msgbuf;m.payloadlenstrlen(msgbuf);strcpy(username, cli.usrname);m.username username;m.username_len strlen(cli.usrname);m.msgtyp MSG_MODE_SEND;int sendlen sk_msg_pack(sendbuf, m);dump_buf(send, sendbuf, sendlen);send(cli.sockfd, sendbuf, sendlen, 0);}}}
}
void cli_input_start()
{pthread_t thread_id;int ret pthread_create(thread_id, NULL, cli_input_hander, NULL);if (ret ! 0) {LOG([%s] create phread fail,%s.\n, __func__, strerror(ret));exit(1);}
}
void cli_login_send(cli_t *c)
{unsigned char logibuf[512];unsigned char usrname[32];msg_t m;m.msgtyp MSG_MODE_LOGIN;sprintf(usrname,%s,c-usrname);m.username usrname;m.username_len strlen(c-usrname);LOG([%s][%d]\n,__FUNCTION__,__LINE__);int len sk_msg_pack(logibuf, m);if(c-sockfd0) {send(c-sockfd, logibuf, len, 0);}
}
void cli_login_check(cli_t *c)
{if(c-statRGST_INIT) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);cli_login_send(c);}
}
void cli_reconnet_check(cli_t *c)
{if(c-sockfd0) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);cli.sockfd sk_tcp_connect_init(cli.ip,cli.port);if(cli.sockfd0)cli_login_send(c);}
}
void cli_recv_msg_hander(cli_t *c, unsigned char *msg, int len)
{unsigned char msgtypemsg[1];if(msgtypeMSG_MODE_LOGIN_ACK) {c-stat RGST_OK;LOG(RGST_OK!\n);}else if(msgtypeMSG_MODE_GET_LIST_ACK) {unsigned char data[1024];int datalen msg[2];datalendatalen*256msg[3];memcpy(data, msg4, datalen);printf(---------Friends list----------\n);printf(%s, data);printf(--------------------------------\n);}else if(msgtypeMSG_MODE_SEND||msgtypeMSG_MODE_ONLINE||msgtypeMSG_MODE_OFFLINE||msgtypeMSG_MODE_ONLINE) {unsigned char data[1024];int datalen msg[2];datalendatalen*256msg[3];memcpy(data, msg4, datalen);LOG(recv%s\n, data);printf(%s\n, data);if(c-history_enable) {sk_history_record(data);}}
}
int cli_recv_proc(cli_t *c)
{int fd c-sockfd;unsigned char recvbuf[1450];int ret recv(fd, recvbuf, sizeof(recvbuf), 0);if(ret0) {int close_flag 0;if(ret 0){/* connection closed */LOG(socket %d close\n, fd);close_flag 1;}else {if(errno!EAGAIN) {LOG(recv error!\n);close_flag 1;}}if(close_flag) {return -1;}}else {LOG([clisk:%d]recv %d bytes, %s\n, fd, ret, recvbuf);cli_recv_msg_hander(c, recvbuf, ret);return ret;}return 0;
}
void cli_start(char *argv[])
{strcpy(cli.ip,127.0.0.1);cli.portSERVER_PORT;cli.sockfd sk_tcp_connect_init(cli.ip,cli.port);cli.stat RGST_INIT;cli.history_enable 1;strcpy(cli.usrname, argv[2]);LOG([%s][%d]cli.usrname:%s\n,__FUNCTION__,__LINE__, cli.usrname);struct timeval tv, timeo;fd_set master;time_t timenow;client_chn_init();cli_input_start();while(1) {tv.tv_sec0;tv.tv_usec20000;FD_ZERO(master);time(timenow);int fdmax0;if(cli.sockfd0) {FD_SET(cli.sockfd, master);if (cli.sockfd fdmax) {fdmax cli.sockfd;}}if(select(fdmax1, master, NULL, NULL, tv)0){LOG(select err\n);}if(FD_ISSET(cli.sockfd, master)) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);if(cli_recv_proc(cli)0) {close(cli.sockfd);cli.sockfd -1;cli.statRGST_INIT;}}if(abs(timenow-cli.login_timeout)10) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);cli.login_timeout timenow;cli_login_check(cli);}if(abs(timenow-cli.reconn_timeout)30) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);cli.reconn_timeout timenow;cli_reconnet_check(cli);}}
}
/*
服务端程序入口
*/
void svr_start(int port)
{ svr_t svr;svr.portport;svr.listenersk_tcp_svr_init(port);struct timeval tv, timeo;fd_set master;client_chn_init();while(1) {tv.tv_sec0;tv.tv_usec20000;FD_ZERO(master);int fdmax svr_add_fds(svr, master);if(select(fdmax1, master, NULL, NULL, tv)0){LOG(select err\n);}int i;for(i 0; i fdmax; i){if(FD_ISSET(i, master)) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);svr_select_fd_proc(svr,i);}}}
}
void *cli_input_hander(void *arg)
{while(1) {char msgbuf[1024];scanf(%s, msgbuf);if((cli.sockfd0)(cli.statRGST_OK)) {char sendbuf[1450];char username[32];msg_t m;m.payload msgbuf;m.payloadlenstrlen(msgbuf);strcpy(username, cli.usrname);m.username username;m.username_len strlen(cli.usrname);m.msgtyp MSG_MODE_SEND;int sendlen sk_msg_pack(sendbuf, m);dump_buf(send, sendbuf, sendlen);send(cli.sockfd, sendbuf, sendlen, 0);}}
}
void cli_input_start()
{pthread_t thread_id;int ret pthread_create(thread_id, NULL, cli_input_hander, NULL);if (ret ! 0) {LOG([%s] create phread fail,%s.\n, __func__, strerror(ret));exit(1);}
}
void cli_login_send(cli_t *c)
{unsigned char logibuf[512];unsigned char usrname[32];msg_t m;m.msgtyp MSG_MODE_LOGIN;sprintf(usrname,%s,c-usrname);m.username usrname;m.username_len strlen(c-usrname);LOG([%s][%d]\n,__FUNCTION__,__LINE__);int len sk_msg_pack(logibuf, m);if(c-sockfd0) {send(c-sockfd, logibuf, len, 0);}
}
void cli_login_check(cli_t *c)
{if(c-statRGST_INIT) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);cli_login_send(c);}
}
void cli_reconnet_check(cli_t *c)
{if(c-sockfd0) {LOG([%s][%d]\n,__FUNCTION__,__LINE__);cli.sockfd sk_tcp_connect_init(cli.ip,cli.port);if(cli.sockfd0)cli_login_send(c);}
}
void cli_recv_msg_hander(cli_t *c, unsigned char *msg, int len)
{unsigned char msgtypemsg[1];if(msgtypeMSG_MODE_LOGIN_ACK) {c-stat RGST_OK;LOG(RGST_OK!\n);}else if(msgtypeMSG_MODE_SEND) {unsigned char data[1024];int datalen msg[2];datalendatalen*256msg[3];memcpy(data, msg4, datalen);LOG(recv%s\n, data);printf(%s\n, data);}
}
/*
客户端数据接收
*/
int cli_recv_proc(cli_t *c)
{int fd c-sockfd;unsigned char recvbuf[1450];int ret recv(fd, recvbuf, sizeof(recvbuf), 0);if(ret0) {int close_flag 0;if(ret 0){/* connection closed */LOG(socket %d close\n, fd);close_flag 1;}else {if(errno!EAGAIN) {LOG(recv error!\n);close_flag 1;}}if(close_flag) {return -1;}}else {LOG([clisk:%d]recv %d bytes, %s\n, fd, ret, recvbuf);cli_recv_msg_hander(c, recvbuf, ret);return ret;}return 0;
}
/*
客户端程序入口
*/
void cli_start(char *argv[])
{strcpy(cli.ip,127.0.0.1);cli.portSERVER_PORT;cli.sockfd sk_tcp_connect_init(cli.ip,cli.port);cli.stat RGST_INIT;strcpy(cli.usrname, argv[2]);LOG([%s][%d]cli.usrname:%s\n,__FUNCTION__,__LINE__, cli.usrname);struct timeval tv, timeo;fd_set master;time_t timenow;client_chn_init();cli_input_start();while(1) {tv.tv_sec0;tv.tv_usec20000;FD_ZERO(master);time(timenow);int fdmax0;if(cli.sockfd0) {FD_SET(cli.sockfd, master);if (cli.sockfd fdmax) {fdmax cli.sockfd;}}if(select(fdmax1, master, NULL, NULL, tv)0){LOG(select err\n);}if(FD_ISSET(cli.sockfd, master)) {if(cli_recv_proc(cli)0) {close(cli.sockfd);cli.sockfd -1;cli.statRGST_INIT;}}if(abs(timenow-cli.login_timeout)10) {//定时检查登录状态cli.login_timeout timenow;cli_login_check(cli);}if(abs(timenow-cli.reconn_timeout)30) {//定时检查连接状态cli.reconn_timeout timenow;cli_reconnet_check(cli);}}
}
5.在clientlist.c添加如下内容#include stdio.h
#include unistd.h
#include string.h
#include stdlib.h
#include errno.h
#include pthread.h
#include netinet/tcp.h
#include netinet/in.h
#include sys/socket.h
#include sys/queue.h
#include sys/ioctl.h
#include linux/if.h
#include semaphore.h
#include arpa/inet.h
#include net/if_arp.h
#include fcntl.h
#include common.h
static CIRCLEQ_HEAD(client_Head, client_chn_s) client_head;
void client_chn_init(void)
{CIRCLEQ_INIT(client_head);
}
void client_chn_insert(client_chn_t *elm)
{CIRCLEQ_INSERT_HEAD(client_head, elm, link);
}
void client_chn_del(int skfd)
{struct client_chn_s *chn;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {if (chn-skfd skfd) {CIRCLEQ_REMOVE(client_head, chn, link);free(chn);break;}}}
int client_chn_add_usr(int skfd, char *usr)
{struct client_chn_s *chn;int ret0;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {if(chn-skfdskfd) {sprintf(chn-usrname, %s\n,usr);LOG([%s](%d)add user:%s\n, __func__, __LINE__, chn-usrname);}}return ret;
}
int client_chn_add_fds(fd_set *master)
{int i;int fdmax 0;struct client_chn_s *chn;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {if(chn-skfdfdmax) fdmax chn-skfd;FD_SET(chn-skfd, master);}return fdmax;
}
void client_chn_print()
{struct client_chn_s *chn;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {LOG([%s](%d)skfd:%d\n, __func__, __LINE__, chn-skfd);}
}
client_chn_t *client_chn_get_elm(int fd)
{struct client_chn_s *chn;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {if(chn-skfdfd) {return chn;} }return NULL;
}
int client_chn_msg_proc(int fd, unsigned char *in, int len)
{struct client_chn_s *chn;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {if(fd0) {if(chn-skfd!fd) {send(chn-skfd, in, len, 0);}}else {send(chn-skfd, in, len, 0);}}
}
int client_chn_get_usr_list(char *out)
{struct client_chn_s *chn;int ret0;int cnt0;for (chn client_head.cqh_first; chn ! (void *)client_head;chn chn-link.cqe_next) {cnt;retsprintf(outret, %d:%s, cnt, chn-usrname);LOG([%s](%d)pack user:%s\n, __func__, __LINE__, chn-usrname);}return ret;
}
6.代码编译make cleanmake最后生成“chat”可执行文件用户便可以在Linux环境下启用聊天室了。7.启动聊天室步骤这里以三个用户为例子7.1启用后台服务端7.2依次启动三个客户端至此所有接入该聊天室的用户都可以开始使用聊天室的基本功能了。总结该程序使用了大家熟悉的TCP协议通过客户端/服务端的方式在Linux系统下使用C语言实现简单的局域网聊天室的功能该功能的实现过程中可以让初学者熟悉Linux下socket编程以及不同设备之间的以太网通信机制为以后做其它的项目打下基础并积累一些经验。