#include #include #include #include #include #include #include #include #include #include #include #include #include using namespace std; void sig_chld(int signo) { pid_t pid; int stat; while ((pid = waitpid(-1, &stat, WNOHANG)) > 0) printf("child %d terminated.\n", pid); return ; } int main(int argc, char * argv[]) { int sockfd, rec_sock; socklen_t len; vector sock_vector; // vector::iterator itr; struct sockaddr_in addr, recaddr; struct sigaction abc; char buf[100]; fd_set allset, rset; int maxfd; abc.sa_handler = sig_chld; sigemptyset(&abc.sa_mask); abc.sa_flags = 0; sigaction(SIGCHLD, &abc, NULL); if (argc < 2) { printf("Usage: a.out port.\n"); exit(0); } if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0) { perror(": Can't get socket"); exit(1); } addr.sin_addr.s_addr = INADDR_ANY; addr.sin_family = AF_INET; addr.sin_port = htons((short)atoi(argv[1])); if (bind(sockfd, (struct sockaddr *)&addr, sizeof(addr)) < 0) { perror(": bind"); exit(1); } len = sizeof(addr); if (getsockname(sockfd, (struct sockaddr *)&addr, &len) < 0) { perror(": can't get name"); _exit(1); } printf("ip = %s, port = %d\n", inet_ntoa(addr.sin_addr), htons(addr.sin_port)); if (listen(sockfd, 5) < 0) { perror(": bind"); exit(1); } FD_ZERO(&allset); FD_SET(sockfd, &allset); maxfd = sockfd; sock_vector.clear(); while (1) { rset = allset; select(maxfd+1, &rset, NULL, NULL, NULL); if (FD_ISSET(sockfd, &rset)) { /* somebody tries to connect */ if ((rec_sock = accept(sockfd, (struct sockaddr *)(&recaddr), &len)) < 0) { if (errno == EINTR) continue; else { perror(":accept error"); exit(1); } } /* if (rec_sock < 0) { perror(": accept"); exit(1); } */ /* print the remote socket information */ printf("remote machine = %s, port = %d.\n", inet_ntoa(recaddr.sin_addr), ntohs(recaddr.sin_port)); sock_vector.push_back(rec_sock); FD_SET(rec_sock, &allset); if (rec_sock > maxfd) maxfd = rec_sock; } // vector::iterator itr = sock_vector.begin(); auto itr = sock_vector.begin(); while (itr != sock_vector.end()) { int num, fd; fd = *itr; if (FD_ISSET(fd, &rset)) { num = read(fd, buf, 100); if (num == 0) { /* client exits */ close(fd); FD_CLR(fd, &allset); itr = sock_vector.erase(itr); continue; } else { write(fd, buf, num); } } ++itr; } maxfd = sockfd; if (!sock_vector.empty()) { maxfd = max(maxfd, *max_element(sock_vector.begin(), sock_vector.end())); } } }