4 Created: Feb 2001 by Philip Homburg <philip@f-mnx.phicoh.com>
18 #include <sys/ioctl.h>
22 #include <net/netlib.h>
23 #include <net/gen/in.h>
24 #include <net/gen/inet.h>
26 #include <net/gen/socket.h>
27 #include <net/gen/tcp.h>
28 #include <net/gen/tcp_io.h>
29 #include <arpa/inet.h>
31 #define BUF_SIZE 10240
38 static int stdout_issocket
= 0;
41 static void do_conn(char *hostname
, char *portname
);
42 static void alrm_conn(int sig
);
43 static void alrm_io(int sig
);
44 static void fullduplex(void);
45 static void fatal(char *msg
, ...);
46 static void usage(void);
48 int main(int argc
, char *argv
[])
54 int B_flag
, P_flag
, s_flag
;
57 (progname
=strrchr(argv
[0],'/')) ? progname
++ : (progname
=argv
[0]);
63 while (c
= getopt(argc
, argv
, "BPst:?"), c
!= -1)
67 case 'B': B_flag
= 1; break;
68 case 'P': P_flag
= 1; break;
69 case 's': s_flag
= 1; break;
70 case 't': t_arg
= optarg
; break;
73 fatal("getopt failed: '%c'", c
);
78 timeout
= strtol(t_arg
, &check
, 0);
80 fatal("unable to parse timeout '%s'\n", t_arg
);
82 fatal("bad timeout '%d'\n", timeout
);
89 hostname
= argv
[optind
++];
90 portname
= argv
[optind
++];
94 stdout_issocket
= s_flag
;
96 do_conn(hostname
, portname
);
101 signal(SIGALRM
, alrm_io
);
109 static void do_conn(char *hostname
, char *portname
)
115 char *tcp_device
, *check
;
116 nwio_tcpconf_t tcpconf
;
118 nwio_tcpopt_t tcpopt
;
120 if (!inet_aton(hostname
, (struct in_addr
*)&addr
))
122 he
= gethostbyname(hostname
);
124 fatal("unknown hostname '%s'", hostname
);
125 if (he
->h_addrtype
!= AF_INET
|| he
->h_length
!= sizeof(addr
))
126 fatal("bad address for '%s'", hostname
);
127 memcpy(&addr
, he
->h_addr
, sizeof(addr
));
130 port
= strtol(portname
, &check
, 0);
133 se
= getservbyname(portname
, "tcp");
135 fatal("unkown port '%s'", portname
);
136 port
= ntohs(se
->s_port
);
139 tcp_device
= getenv("TCP_DEVICE");
140 if (tcp_device
== NULL
) tcp_device
= TCP_DEVICE
;
142 tcpfd
= open(tcp_device
, O_RDWR
);
144 fatal("unable to open '%s': %s", tcp_device
, strerror(errno
));
145 tcpconf
.nwtc_flags
= NWTC_EXCL
| NWTC_LP_SEL
| NWTC_SET_RA
|
147 tcpconf
.nwtc_remaddr
= addr
;
148 tcpconf
.nwtc_remport
= htons(port
);;
149 if (ioctl(tcpfd
, NWIOSTCPCONF
, &tcpconf
) == -1)
150 fatal("NWIOSTCPCONF failed: %s", strerror(errno
));
154 signal(SIGALRM
, alrm_conn
);
158 tcpcl
.nwtcl_flags
= 0;
159 if (ioctl(tcpfd
, NWIOTCPCONN
, &tcpcl
) == -1)
161 fatal("unable to connect to %s:%u: %s",
162 inet_ntoa(*(struct in_addr
*)&addr
),
163 ntohs(tcpconf
.nwtc_remport
), strerror(errno
));
170 tcpopt
.nwto_flags
= NWTO_BULK
;
171 if (ioctl(tcpfd
, NWIOSTCPOPT
, &tcpopt
) == -1)
172 fatal("NWIOSTCPOPT failed: %s", strerror(errno
));
176 static void alrm_conn(int sig
)
178 fatal("timeout during connect");
181 static void alrm_io(int sig
)
183 fatal("timeout during io");
186 static void fullduplex(void)
189 int o
, r
, s
, s_errno
, loc
;
194 case -1: fatal("fork failed: %s", strerror(errno
));
196 /* Read from TCP, write to stdout. */
199 r
= read(tcpfd
, buf
, BUF_SIZE
);
206 ioctl(1, NWIOTCPSHUTDOWN
, NULL
);
207 fatal("error reading from TCP conn.: %s",
211 for (o
= 0; o
<s
; o
+= r
)
213 r
= write(1, buf
+o
, s
-o
);
216 fatal("error writing to stdout: %s",
224 r
= ioctl(1, NWIOTCPSHUTDOWN
, NULL
);
227 fatal("NWIOTCPSHUTDOWN failed on stdout: %s",
236 /* Read from stdin, write to TCP. */
239 r
= read(0, buf
, BUF_SIZE
);
246 fatal("error reading from stdin: %s",
250 for (o
= 0; o
<s
; o
+= r
)
252 r
= write(tcpfd
, buf
+o
, s
-o
);
257 fatal("error writing to TCP conn.: %s",
263 ioctl(tcpfd
, NWIOTCPPUSH
, NULL
);
265 if (ioctl(tcpfd
, NWIOTCPSHUTDOWN
, NULL
) == -1)
269 fatal("unable to shut down TCP conn.: %s", strerror(s_errno
));
272 r
= waitpid(cpid
, &loc
, 0);
277 fatal("waitpid failed: %s", strerror(s_errno
));
280 exit(WEXITSTATUS(loc
));
281 kill(getpid(), WTERMSIG(loc
));
285 static void fatal(char *fmt
, ...)
290 fprintf(stderr
, "%s: ", progname
);
291 vfprintf(stderr
, fmt
, ap
);
292 fprintf(stderr
, "\n");
297 static void usage(void)
299 fprintf(stderr
, "Usage: %s [-BPs] [-t timeout] hostname portname\n",
305 * $PchId: socket.c,v 1.3 2005/01/31 22:33:20 philip Exp $