




下载本文档
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、LinuxLinux 下 C C 语言多线程,网络通信简单聊天程序功能描述:程序应用多线程技术,可是实现 1 1 对 N N 进行网络通信聊天。但至今没想出合适的退出机制,除了用 Ctr+CCtr+C。出于演示目的,这里采用 UNIXUNIX 域协议(文件系统套接字):程序分为客户端和服务端。应用 selectselect 函数来实现异步的读写操作。先说一下服务端:首先先创建套接字,然后绑定,接下进入一个无限循环,用acceptaccept 函数,接受连接”请求,然后调用创建线程函数,创造新的线程,进入下一个循环。这样每当有一个新的连接”被接受都会创建一个新的线程,实现 1 1 对 N N 的
2、网络通信。在服务端程序中线程中用一个 bufferbuffer 读写,为了避免错误,这时就要给关键代码加上互斥锁work_mutexwork_mutex,具体见代码。国 E E 服务端代码1#include2#include3#include4#include5#include6#include7#include8#include/这里没有用二进制信号量可以删掉910 charbuffer1024;/读写用的区域11 sem_tbin_sem;/没用到的二进制信号量,可以删掉12 void*pthread_function(void*arg);/线程入口函数声明13 pthread_mutex
3、_twork_mutex;/声明互斥锁1415 intmain()16 intresult;/整数变量用来储存调用函数的返回值17 structsockaddr_unserver_address,client_address;/UNIX 域的套接字,server_address 用于服务端的监听,client_address 用于客户端连接后的套接字18 intclient_len;/连接后,accept 函数会把客户端的地址的长度储存在这19 intserver_socketfd,client_socketfd;/服务端和客户端的套接字文件描述符20pthread_ta_thread;/线程
4、 ID 标志21pthread_attr_tthread_attr;被我注释掉了,没用到,可以删掉。2223result=sem_init(&bin_sem,0,1);/初始化二进制信号量,因为用了互斥锁,所以没用到,可以删掉24if(result!=0)25perror(sem_init);26exit(EXIT_FAILURE);272829result=pthread_mutex_init(&work_mutex,NULL);初始化互斥锁30if(result!=0)31perror(pthread_mutex_init);32exit(EXIT_FAILURE);333435serve
5、r_socketfd=socket(AF_UNIX,SOCK_STREAM,0);/创建套接字,用 TCP 连接方式,出于演示目的只用 UNIX 域套接字。3637server_address.sun_family=AF_UNIX;38strcpy(server_address.sun_path,server_socket);3940unlink(server_socket);/在绑定之前,把以前存在当前目录下的套接字删除4142result=bind(server_socketfd,(structsockaddr*)&server_address,sizeof(server_address)
6、;/绑定43if(result!=0)44perror(bind);45exit(EXIT_FAILURE);4647个连接请求/线程的属性,后面可以看的,48result=listen(server_socketfd,5);/监听,最多允许 549if(result!=0)50perror(listen);51exit(EXIT_FAILURE);525354client_len=sizeof(client_address);55while(1)/开始进入无限循环56/*printf(Ifyouwanttoquit,pleaseenterquitn);57printf(Doyouwantto
7、acceptaconnectiongn);58memset(buffer,0,sizeof(buffer);59fgets(buffer,sizeof(buffer),stdin);60if(strncmp(quit,buffer,4)=0)break;*/6162client_socketfd=accept(server_socketfd,(structsockaddr*)&client_address,&client_len);/接受一个连接请求6364/*result=pthread_attr_init(&thread_attr);65if(result!=0)66perror(pthr
8、ead_attr_init);67exit(EXIT_FAILURE);6869result=pthread_attr_setdetachstate(&thread_attr,PTHREAD_CREATE_DETACHED);70if(result!=0)71perror(pthread_attr_setdetachstate);72exit(EXIT_FAILURE);73*/74result=pthread_create(&a_thread,NULL,pthread_function,(void*)client_socketfd);/成功接受一个请求后,就会创建一个线程,然后主线程又进入
9、accept 函数,如果此时没有连接请求,那么主线程会阻塞75if(result!=0)76perror(pthread_create);77exit(EXIT_FAILURE);787980818283void*pthread_function(void*arg)/线程入口函数,每调用一次 pthread_create,都会创建一个新的线程84intfd=(int)arg;/把函数参数,即连接成功后的套接字,赋给 fd.85intresult;86fd_setread_fds;/文件描述符集合,用于 select 函数87intmax_fds;/文件描述符集合的最大数8889printf(%
10、didhasconnected!n,fd);90while(1)9192FD_ZERO(&read_fds);/清空集合93FD_SET(0,&read_fds);/将标准输入放入监听的文件描述符集合,这个用于读取标准输入,即键盘的输入94FD_SET(fd,&read_fds);/将连接后的客户文件描述符放入监听的文件描述符集合,这个用于向客户端读取数据95max_fds=fd+1;9697/sem_wait(&bin_sem);98pthread_mutex_lock(&work_mutex);/对关键区域上锁99printf(%dhasgetthelockn,fd);100result=
11、select(max_fds,&read_fds,(fd_set*)NULL,(fd_set*)NULL,(structtimeval*)NULL);/开始监听那些文件描述符出于可读状态101if(result1)102printf(select);103104if(FD_ISSET(0,&read_fds)/如果标准输入处于可读状态,说明键盘有所输入,将输入的数据存放在 buffer 中,然后向客户端写回,如果输入“quit”将会退出一个聊天线程读,那么读取存放在 buffer 中,然后显示出来,如果对方中断聊天,那么rememset(buffer,0,sizeof(buffer);resu
12、lt=read(fd,buffer,sizeof(buffer);if(result=-1)perror(read);exit(EXIT_FAILURE);elseif(result=0)printf(Theothersidehasterminalthec/sem_post(&bin_sem);pthread_mutex_unlock(&work_mutex);break;elseprintf(receivemessage:%s,buffer);138pthread_mutex_unlock(&work_mutex);/解锁sleep(1);/如果没有这一行,当前线程会一直占据 buffer.
13、105memset(buffer,0,sizeof(buffer);/保险起见,清零106107108109110111112113114115116117118119120fgets(buffer,if(strncmp(printf(sizeof(buffer),quit,buffer,stdin);4)=0)Youhaveterminaledthechatn);121/sem_post(&bin_sem);pthread_mutex_unlock(&work_mutex);break;elseresult=write(fd,buffer,if(result=-1)perror(write)
14、;exit(EXIT_FAILURE);if(FD_ISSET(fd,&read_fds)sizeof(buffer);/如果客户套接字符可sult=0122123124125126127128129hatn);130131132133134135136137139让当前线程暂停一秒可以实现 1 对 N 的功能140/sem_post(&bin_sem);141/sleep(1);142)143/printf(Iamheren);144close(fd);145pthread_exit(NULL);146147)148读者可以对比一下http:/ N N 个人进行聊天, 尽管有些 bug(bu
15、g(如果客户端对方回复太快太频繁, 服务端的锁就会切换来切换去,无法回复到正确的客户端)。客户端跟服务端很像,但比较简单。这里面就不注释了。这两个程序我都运行过。没什么基本大的问题。但是功能很不完善。还需改进。国 E E 客户端代码1 #include2 #include3 #include4 #include5 #include6 #include7 #include89 intmain()10 intresult;11 intsocketfd;12 intlen;13 structsockaddr_unaddress;14 fd_setread_fds,test_fds;15 intfd;
16、16 intmax_fds;17 charbuffer1024;1819 socketfd=socket(AF_UNIX,SOCK_STREAM,0);2021 address.sun_family=AF_UNIX;22 strcpy(address.sun_path,server_socket);23len=sizeof(address);2425result=connect(socketfd,(structsockaddr*)&address,len);26if(result=-1)27perror(connect);28exit(EXIT_FAILURE);293031FD_ZERO(&
17、read_fds);32FD_SET(0,&read_fds);33FD_SET(socketfd,&read_fds);34max_fds=socketfd+1;3536printf(Chatnow!n);3738while(1)39test_fds=read_fds;40result=select(max_fds,&test_fds,(fd_set*)NULif(result1)perror(select);exit(EXIT_FAILURE);if(FD_ISSET(0,&test_fds)memset(buffer,0,sizeof(buffer);/printf(send:);fgets(buffer,sizeof(buffer),stdin);if(strncmp(quit,buffer,4)=0)printf(nYouaregoingtoquitn);break;result=write(socketfd,buffer,sizeof(buffeif(result=-1)perror(write);exit(EXIT_FAILURE);if(FD_ISSET(socketfd,&test_fds)memset(buffer,0,sizeof(buffer);result=read(socketfd,buffer,s
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 面瘫的评估与护理
- 预防学生心理健康主题班会
- 电厂机务培训课件
- 预防医学:食物中毒及其防治
- 2022山西省对口升学语文真题(含答案)
- 广西中医药大学《英语语言素质拓展》2023-2024学年第一学期期末试卷
- 2025年江苏省横林高级中学高考生物试题命题揭秘与专题练析含解析
- 邵阳工业职业技术学院《生物信息学导论上机实验》2023-2024学年第二学期期末试卷
- 遂宁职业学院《市场实践项目创作》2023-2024学年第二学期期末试卷
- 昆明文理学院《半导体材料与器件》2023-2024学年第二学期期末试卷
- 2023年一二级建造师解聘证明
- GB 15763.4-2009建筑用安全玻璃第4部分:均质钢化玻璃
- 设备润滑管理基础知识培训教材
- 哈克贝利·费恩历险记(课堂)课件
- 小班 社会语言 懂礼貌的好宝宝 课件(互动版)
- 四川省生育登记表(样表)
- 医疗护理品管圈QCC成果汇报之提高住院病人健康宣教的知晓率(问题解决型)
- DB34-T 4243-2022 智慧医院医用耗材SPD验收规范
- 5.4直线式感应同步器解析课件
- 煤矿“双回路”供电保障专项整治实施方案
- 航空航天概论(课堂PPT)
评论
0/150
提交评论