diff options
Diffstat (limited to 'nc.c')
-rw-r--r-- | nc.c | 57 |
1 files changed, 15 insertions, 42 deletions
@@ -38,14 +38,10 @@ | |||
38 | #include <sys/time.h> | 38 | #include <sys/time.h> |
39 | #include <sys/ioctl.h> | 39 | #include <sys/ioctl.h> |
40 | 40 | ||
41 | #define BUFSIZE 100 | ||
42 | |||
43 | int nc_main(int argc, char **argv) | 41 | int nc_main(int argc, char **argv) |
44 | { | 42 | { |
45 | int sfd; | 43 | int sfd; |
46 | int result; | 44 | char buf[BUFSIZ]; |
47 | int len; | ||
48 | char ch[BUFSIZE]; | ||
49 | 45 | ||
50 | struct sockaddr_in address; | 46 | struct sockaddr_in address; |
51 | struct hostent *hostinfo; | 47 | struct hostent *hostinfo; |
@@ -54,34 +50,26 @@ int nc_main(int argc, char **argv) | |||
54 | 50 | ||
55 | argc--; | 51 | argc--; |
56 | argv++; | 52 | argv++; |
57 | if (argc < 2 || **(argv + 1) == '-') { | 53 | if (argc < 2 || **argv == '-') { |
58 | usage(nc_usage); | 54 | usage(nc_usage); |
59 | } | 55 | } |
60 | 56 | ||
61 | sfd = socket(AF_INET, SOCK_STREAM, 0); | 57 | if ((sfd = socket(AF_INET, SOCK_STREAM, 0)) < 0) |
62 | 58 | perror_msg_and_die("socket"); | |
63 | hostinfo = (struct hostent *) gethostbyname(*argv); | ||
64 | 59 | ||
65 | if (!hostinfo) { | 60 | if ((hostinfo = gethostbyname(*argv)) == NULL) |
66 | error_msg_and_die("cannot resolve %s\n", *argv); | 61 | error_msg_and_die("cannot resolve %s\n", *argv); |
67 | } | ||
68 | 62 | ||
69 | address.sin_family = AF_INET; | 63 | address.sin_family = AF_INET; |
70 | address.sin_addr = *(struct in_addr *) *hostinfo->h_addr_list; | 64 | address.sin_addr = *(struct in_addr *) *hostinfo->h_addr_list; |
71 | address.sin_port = htons(atoi(*(++argv))); | 65 | address.sin_port = htons(atoi(*(++argv))); |
72 | 66 | ||
73 | len = sizeof(address); | 67 | if (connect(sfd, (struct sockaddr *) &address, sizeof(address)) < 0) |
74 | 68 | perror_msg_and_die("connect"); | |
75 | result = connect(sfd, (struct sockaddr *) &address, len); | ||
76 | |||
77 | if (result < 0) { | ||
78 | perror("nc: connect"); | ||
79 | exit(2); | ||
80 | } | ||
81 | 69 | ||
82 | FD_ZERO(&readfds); | 70 | FD_ZERO(&readfds); |
83 | FD_SET(sfd, &readfds); | 71 | FD_SET(sfd, &readfds); |
84 | FD_SET(fileno(stdin), &readfds); | 72 | FD_SET(STDIN_FILENO, &readfds); |
85 | 73 | ||
86 | while (1) { | 74 | while (1) { |
87 | int fd; | 75 | int fd; |
@@ -90,41 +78,26 @@ int nc_main(int argc, char **argv) | |||
90 | 78 | ||
91 | testfds = readfds; | 79 | testfds = readfds; |
92 | 80 | ||
93 | result = | 81 | if (select(FD_SETSIZE, &testfds, NULL, NULL, NULL) < 0) |
94 | select(FD_SETSIZE, &testfds, (fd_set *) NULL, (fd_set *) NULL, | 82 | perror_msg_and_die("select"); |
95 | (struct timeval *) 0); | ||
96 | |||
97 | if (result < 1) { | ||
98 | perror("nc: select"); | ||
99 | exit(3); | ||
100 | } | ||
101 | 83 | ||
102 | for (fd = 0; fd < FD_SETSIZE; fd++) { | 84 | for (fd = 0; fd < FD_SETSIZE; fd++) { |
103 | if (FD_ISSET(fd, &testfds)) { | 85 | if (FD_ISSET(fd, &testfds)) { |
104 | int trn = 0; | 86 | if ((nread = safe_read(fd, buf, sizeof(buf))) < 0) |
105 | int rn; | 87 | perror_msg_and_die("read"); |
106 | |||
107 | ioctl(fd, FIONREAD, &nread); | ||
108 | 88 | ||
109 | if (fd == sfd) { | 89 | if (fd == sfd) { |
110 | if (nread == 0) | 90 | if (nread == 0) |
111 | exit(0); | 91 | exit(0); |
112 | ofd = fileno(stdout); | 92 | ofd = STDOUT_FILENO; |
113 | } else { | 93 | } else { |
114 | if (nread == 0) | 94 | if (nread == 0) |
115 | shutdown(sfd, 1); | 95 | shutdown(sfd, 1); |
116 | ofd = sfd; | 96 | ofd = sfd; |
117 | } | 97 | } |
118 | 98 | ||
119 | 99 | if (full_write(ofd, buf, nread) < 0) | |
120 | 100 | perror_msg_and_die("write"); | |
121 | do { | ||
122 | rn = (BUFSIZE < nread - trn) ? BUFSIZE : nread - trn; | ||
123 | trn += rn; | ||
124 | read(fd, ch, rn); | ||
125 | write(ofd, ch, rn); | ||
126 | } | ||
127 | while (trn < nread); | ||
128 | } | 101 | } |
129 | } | 102 | } |
130 | } | 103 | } |