diff options
Diffstat (limited to 'pgm4/inet_streams.d')
-rw-r--r-- | pgm4/inet_streams.d/Makefile | 13 | ||||
-rw-r--r-- | pgm4/inet_streams.d/README | 3 | ||||
-rw-r--r-- | pgm4/inet_streams.d/inet_rstream.c | 110 | ||||
-rw-r--r-- | pgm4/inet_streams.d/inet_wstream.c | 91 |
4 files changed, 217 insertions, 0 deletions
diff --git a/pgm4/inet_streams.d/Makefile b/pgm4/inet_streams.d/Makefile new file mode 100644 index 0000000..72c101d --- /dev/null +++ b/pgm4/inet_streams.d/Makefile @@ -0,0 +1,13 @@ +CC=gcc +CFLAGS=-g -Wall + +all: inet_rstream inet_wstream + +inet_rstream: inet_rstream.o + $(CC) -o inet_rstream inet_rstream.o + +inet_wstream: inet_wstream.o + $(CC) -o inet_wstream inet_wstream.o + +clean: + rm -f *.o inet_rstream inet_wstream diff --git a/pgm4/inet_streams.d/README b/pgm4/inet_streams.d/README new file mode 100644 index 0000000..ecbe3dc --- /dev/null +++ b/pgm4/inet_streams.d/README @@ -0,0 +1,3 @@ +A pair of simple programs which interact via a virtual circuit on +the Internet. + diff --git a/pgm4/inet_streams.d/inet_rstream.c b/pgm4/inet_streams.d/inet_rstream.c new file mode 100644 index 0000000..3dafee6 --- /dev/null +++ b/pgm4/inet_streams.d/inet_rstream.c @@ -0,0 +1,110 @@ +/************************************************************************\ +* INET_RSTREAM.C * +* Test of TCP/IP. Set up a socket for establishing a connection at * +* some free port on the local host. After accepting a connection, speak * +* briefly to peer, and then read char at a time from the stream. Write * +* to stdout. At EOF, shut down. * +* * +* Phil Kearns * +* April 11, 1987 * +* * +* Modified February 2009 to use getaddrinfo() * +\************************************************************************/ + +#include <stdio.h> +#include <unistd.h> +#include <stdlib.h> +#include <string.h> +#include <sys/types.h> +#include <sys/socket.h> +#include <netinet/in.h> +#include <arpa/inet.h> +#include <netdb.h> + +void printsin(struct sockaddr_in*, char*, char*); + +int main() +{ + int listener; /* fd for socket on which we get connection requests */ + int conn; /* fd for socket thru which we pass data */ + struct sockaddr_in *localaddr, peer; + int ecode; + socklen_t length; + char ch; + struct addrinfo hints, *addrlist; + + +/* + Want to specify local server address of: + addressing family: AF_INET + ip address: any interface on this system + port: 0 => system will pick free port +*/ + + memset(&hints, 0, sizeof(hints)); + hints.ai_family = AF_INET; hints.ai_socktype = SOCK_STREAM; + hints.ai_flags = AI_NUMERICSERV | AI_PASSIVE; hints.ai_protocol = 0; + hints.ai_canonname = NULL; hints.ai_addr = NULL; + hints.ai_next = NULL; + + ecode = getaddrinfo(NULL, "0", &hints, &addrlist); + if (ecode != 0) { + fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(ecode)); + exit(1); + } + + localaddr = (struct sockaddr_in *) addrlist->ai_addr; + +/* + Create socket on which we will accept connections. This is NOT the + same as the socket on which we pass data. +*/ + if ( (listener = socket( addrlist->ai_family, addrlist->ai_socktype, 0 )) < 0 ) { + perror("inet_rstream:socket"); + exit(1); + } + + + if (bind(listener, (struct sockaddr *)localaddr, sizeof(struct sockaddr_in)) < 0) { + perror("inet_rstream:bind"); + exit(1); + } + +/* + Print out the port number assigned to this process by bind(). +*/ + length = sizeof(struct sockaddr_in); + if (getsockname(listener, (struct sockaddr *)localaddr, &length) < 0) { + perror("inet_rstream:getsockname"); + exit(1); + } + printf("RSTREAM:: assigned port number %d\n", ntohs(localaddr->sin_port)); + +/* + Now accept a single connection. Upon connection, data will be + passed through the socket on descriptor conn. +*/ + listen(listener,1); + length = sizeof(peer); + if ((conn=accept(listener, (struct sockaddr *)&peer, &length)) < 0) { + perror("inet_rstream:accept"); + exit(1); + } + printsin(&peer,"RSTREAM::", "accepted connection from"); + + printf("\n\nRSTREAM:: data from stream:\n"); + while ( read(conn, &ch, 1) == 1) + putchar(ch); + putchar('\n'); + exit(0); +} + +void printsin(struct sockaddr_in *sin, char *m1, char *m2 ) +{ + char fromip[INET_ADDRSTRLEN]; + + printf ("%s %s:\n", m1, m2); + printf (" family %d, addr %s, port %d\n", sin -> sin_family, + inet_ntop(AF_INET, &(sin->sin_addr.s_addr), fromip, sizeof(fromip)), + ntohs((unsigned short)(sin -> sin_port))); +} diff --git a/pgm4/inet_streams.d/inet_wstream.c b/pgm4/inet_streams.d/inet_wstream.c new file mode 100644 index 0000000..8dcd284 --- /dev/null +++ b/pgm4/inet_streams.d/inet_wstream.c @@ -0,0 +1,91 @@ +/************************************************************************\ +* INET_WSTREAM.C * +* Test of TCP/IP. Invoke as * +* inet_wstream hostname portnumber * +* in order to send a fragment of an obnoxious Dijkstra quote to a * +* process assumed to be reading from a stream at the specified * +* address. * +* * +* Phil Kearns * +* April 11, 1987 * +* * +* Modified February 2009 to use getaddrinfo() * +\************************************************************************/ + +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <string.h> +#include <sys/types.h> +#include <sys/socket.h> +#include <netinet/in.h> +#include <netdb.h> + +char msg[] = { "false pearls before real swine" }; + +int main(argc, argv) +int argc; +char **argv; +{ + int sock, left, num, put, ecode; + struct sockaddr_in *server; + struct addrinfo hints, *addrlist; + + if (argc != 3) { + fprintf(stderr,"inet_wstream:usage is inet_wstream host port\n"); + exit(1); + } + + + +/* + Want a sockaddr_in containing the ip address for the system + specified in argv[1] and the port specified in argv[2]. +*/ + + memset( &hints, 0, sizeof(hints)); + hints.ai_family = AF_INET; hints.ai_socktype = SOCK_STREAM; + hints.ai_flags = AI_NUMERICSERV; hints.ai_protocol = 0; + hints.ai_canonname = NULL; hints.ai_addr = NULL; + hints.ai_next = NULL; + + ecode = getaddrinfo(argv[1], argv[2], &hints, &addrlist); + if (ecode != 0) { + fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(ecode)); + exit(1); + } + + server = (struct sockaddr_in *) addrlist->ai_addr; + +/* + Create the socket. +*/ + if ( (sock = socket( addrlist->ai_family, addrlist->ai_socktype, 0 )) < 0 ) { + perror("inet_wstream:socket"); + exit(1); + } + +/* + Connect to data socket on the peer at the specified Internet + address. +*/ + if ( connect(sock, (struct sockaddr *)server, sizeof(struct sockaddr_in)) < 0) { + perror("inet_wstream:connect"); + exit(1); + } + +/* + Write the quote and terminate. This will close the connection on + this end, so eventually an "EOF" will be detected remotely. +*/ + left = sizeof(msg); put=0; + while (left > 0){ + if((num = write(sock, msg+put, left)) < 0) { + perror("inet_wstream:write"); + exit(1); + } + else left -= num; + put += num; + } + exit(0); +} |