日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

socket 编程 基于 select 实现的回射客户端/服务程序

發布時間:2023/12/1 编程问答 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 socket 编程 基于 select 实现的回射客户端/服务程序 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

github 代碼 地址

  • unp.h
#include <stdio.h> #include <unistd.h> #include <arpa/inet.h> #include <string.h> #include <sys/socket.h> #include <stdlib.h> #include <errno.h> #include <sys/wait.h> #include <sys/select.h>#define MAXLINE 4096 #define SERV_PORT 9877 #define LISTENQ 1024void str_echo(int sockfd); void err_sys(const char *, ...);// client interface void str_cli(FILE *fp, int sockfd);
  • echo_client.c
#include "unp.h" #include <stdio.h> #include <unistd.h> #include <arpa/inet.h>int main(int argc, char **argv) {int sockfd[5];struct sockaddr_in servaddr;int i=0;for (i=0; i<5; i++) {sockfd[i] = socket(AF_INET, SOCK_STREAM, 0);bzero(&servaddr, sizeof(servaddr));servaddr.sin_family = AF_INET;servaddr.sin_port = htons(SERV_PORT);inet_pton(AF_INET, "127.0.0.1", &servaddr.sin_addr);connect(sockfd[i], (struct sockaddr*)&servaddr, sizeof(servaddr));}str_cli(stdin, sockfd[0]);exit(0); }
  • str_cli.c
#include "unp.h"// maxline 4096int max(int a, int b) {return a>b? a : b; }void str_cli(FILE *fp, int sockfd) {int maxfdp1, stdineof;fd_set rset;char sendline[MAXLINE], receline[MAXLINE];int n;stdineof = 0;FD_ZERO(&rset);for (; ;) {// fileno 將標準 I/O 文件指針轉換為對應的描述符if (stdineof == 0) {FD_SET(fileno(fp), &rset);}FD_SET(sockfd, &rset);maxfdp1 = max(fileno(fp), sockfd) + 1;select(maxfdp1, &rset, NULL, NULL, NULL);// 如果服務掛掉,客戶端可以接受到消息,并退出if (FD_ISSET(sockfd, &rset)) { // socket is readableif ((n = read(sockfd, receline, MAXLINE)) == 0) {if (stdineof == 1) {return;} else {printf("str_cli: server terminated prematurely");return;}}write(fileno(stdout), receline, strlen(receline));bzero(receline, strlen(receline));}if (FD_ISSET(fileno(fp), &rset)) {if ( (n = read(fileno(stdin), sendline, MAXLINE) == 0) ){stdineof = 1;shutdown(sockfd, SHUT_WR);FD_CLR(fileno(fp), &rset);continue;}write(sockfd, sendline, strlen(sendline));bzero(sendline, strlen(sendline));}} }
  • echo_service.c
#include "unp.h"int main(int argc, char **argv) {int i, maxi, maxfd, listenfd, connfd, sockfd;int nready, client[FD_SETSIZE];size_t n;fd_set rset, allset;char buf[MAXLINE];socklen_t clilen;struct sockaddr_in cliaddr, servaddr;listenfd = socket(AF_INET, SOCK_STREAM, 0);bzero(&servaddr, sizeof(servaddr));servaddr.sin_family = AF_INET;servaddr.sin_addr.s_addr = htonl(INADDR_ANY);servaddr.sin_port = htons(SERV_PORT);bind(listenfd, (struct sockaddr*)&servaddr, sizeof(servaddr));listen(listenfd, LISTENQ);maxfd = listenfd;maxi = -1; // client 數組當前使用項的最大下標for(i=0; i<FD_SETSIZE; i++) {client[i] = -1;}FD_ZERO(&allset);FD_SET(listenfd, &allset);for(;;) {rset = allset;nready = select(maxfd+1, &rset, NULL, NULL, NULL);if(FD_ISSET(listenfd, &rset)) {clilen = sizeof(cliaddr);connfd = accept(listenfd, (struct sockaddr*)&cliaddr, &clilen);for (i=0; i<FD_SETSIZE; i++) {if (client[i] < 0 ) {client[i] = connfd;break;}}if (i == FD_SETSIZE) {exit(0);}FD_SET(connfd, &allset);if (connfd > maxfd) {maxfd = connfd;}if (i > maxi) {maxi = i;}if (--nready <= 0) {continue;}}for (i = 0; i <= maxi; i++) {if ((sockfd = client[i]) < 0) {continue;}if (FD_ISSET(sockfd, &rset)) {if ( ( n = read(sockfd, buf, MAXLINE)) == 0) {close(sockfd);FD_CLR(sockfd, &allset);client[i] = -1;} else {write(sockfd, buf, n);}if (--nready <= 0) {break;}}}} }
  • CMakeList.txt
project(echo_srv) set(CMAKE_CXX_STANDARD 11) add_executable(echo_srv echo_service.c error.c)# client add_executable(echo_cli echo_client.c str_cli.c)

總結

以上是生活随笔為你收集整理的socket 编程 基于 select 实现的回射客户端/服务程序的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。