xref: /csrg-svn/sys/tests/netiso/tisrc.c (revision 49065)
144323Ssklower /*
248713Ssklower  * Copyright (c) 1989, 1990 Regents of the University of California.
344323Ssklower  * All rights reserved.
444323Ssklower  *
544323Ssklower  * %sccs.include.redist.c%
644323Ssklower  */
744323Ssklower #ifndef lint
8*49065Ssklower static char sccsid[] = "@(#)tisrc.c	7.4 (Berkeley) 05/04/91";
944323Ssklower #endif /* not lint */
1044323Ssklower 
1144323Ssklower /*
1248713Ssklower  * This is a test program to be a source for ISO transport.
1344323Ssklower  */
1444323Ssklower #include <sys/types.h>
1544323Ssklower #include <sys/socket.h>
1644323Ssklower #include <sys/uio.h>
1744323Ssklower #include <sys/ioctl.h>
1844323Ssklower #include <net/route.h>
1944323Ssklower #include <net/if.h>
2044323Ssklower #define  TCPT_NTIMERS 4
2144323Ssklower #include <netiso/iso.h>
2244323Ssklower #include <netiso/tp_user.h>
2344323Ssklower 
2444323Ssklower #include <stdio.h>
2544323Ssklower #include <errno.h>
2644323Ssklower #include <ctype.h>
2744323Ssklower #include <netdb.h>
2844323Ssklower 
2944323Ssklower 
3044323Ssklower #define dbprintf if(verbose)printf
3144323Ssklower #define try(a,b,c) {x = (a b);dbprintf("%s%s returns %d\n",c,"a",x);\
3244323Ssklower 		    if (x < 0) {perror("a"); exit(1);}}
3344323Ssklower 
3444323Ssklower struct	iso_addr eon = {20, 0x47, 0, 6, 3, 0, 0, 0, 25 /*EGP for Berkeley*/};
35*49065Ssklower struct	iso_addr *iso_addr();
3644323Ssklower struct  sockaddr_iso to_s = { sizeof(to_s), AF_ISO }, *to = &to_s;
3748713Ssklower struct  sockaddr_iso old_s = { sizeof(to_s), AF_ISO }, *old = &old_s;
3848843Ssklower struct	tp_conn_param tp_params;
3944323Ssklower fd_set	readfds, writefds, exceptfds;
4044323Ssklower long size, count = 10;
4144323Ssklower int verbose = 1, selectp, type = SOCK_SEQPACKET, nobuffs, errno, playtag = 0;
4248843Ssklower int verify = 0, dgramp = 0, debug = 0, tp0mode = 1;
4344323Ssklower short portnumber = 3000;
4444323Ssklower char your_it[] = "You're it!";
4548713Ssklower char *Servername, *conndata, data_msg[2048];
4648713Ssklower char Serverbuf[128];
4748713Ssklower char name[128];
4844323Ssklower struct iovec iov[1] = {data_msg};
4944323Ssklower union {
5044323Ssklower     struct {
5144323Ssklower 	    struct cmsghdr	cmhdr;
5248713Ssklower 	    char		cmdata[128 - sizeof(struct cmsghdr)];
5344323Ssklower     } cm;
5444323Ssklower     char data[128];
5544323Ssklower } cm;
5644323Ssklower struct msghdr msg = { 0, 0, iov, 1, 0, 0, 0};
5744323Ssklower 
5844323Ssklower main(argc, argv)
5944323Ssklower int argc;
6044323Ssklower char *argv[];
6144323Ssklower {
6244323Ssklower 	register char **av = argv;
6344323Ssklower 	register char *cp;
6444323Ssklower 	u_long len;
6544323Ssklower 	int handy;
6644323Ssklower 
6744323Ssklower 	while(--argc > 0) {
6844323Ssklower 		av++;
6944323Ssklower 		if(strcmp(*av,"Servername")==0) {
7044323Ssklower 			av++;
7148713Ssklower 			Servername = *av;
7244323Ssklower 			argc--;
7344323Ssklower 		} else if(strcmp(*av,"conndata")==0) {
7444323Ssklower 			av++;
7544323Ssklower 			conndata = *av;
7644323Ssklower 			argc--;
7744323Ssklower 		} else if(strcmp(*av,"host")==0) {
7844323Ssklower 			av++;
7948713Ssklower 			to_s.siso_addr = *iso_addr(*av);
8044323Ssklower 			argc--;
8144323Ssklower 		} else if(strcmp(*av,"port")==0) {
8244323Ssklower 			av++;
8344323Ssklower 			sscanf(*av,"%hd",&portnumber);
8444323Ssklower 			argc--;
8544323Ssklower 		} else if(strcmp(*av,"count")==0) {
8644323Ssklower 			av++;
8744323Ssklower 			sscanf(*av,"%ld",&count);
8844323Ssklower 			argc--;
8944323Ssklower 		} else if(strcmp(*av,"size")==0) {
9044323Ssklower 			av++;
9144323Ssklower 			sscanf(*av,"%ld",&size);
9244323Ssklower 			iov->iov_len = size;
9344323Ssklower 		} else if(strcmp(*av,"stream")==0) {
9444323Ssklower 			type = SOCK_STREAM;
9544323Ssklower 		} else if (strcmp(*av,"eon") == 0) {
9644323Ssklower 			unsigned long l, inet_addr();
9744323Ssklower 
9844323Ssklower 			l = inet_addr(*++av); argc--;
9944323Ssklower 			to_s.siso_addr = eon;
10044323Ssklower 			bcopy((char *)&l, &to_s.siso_data[15], 4);
10144323Ssklower 		}
10244323Ssklower 	}
10348713Ssklower 	maketoaddr();
10448713Ssklower 	tisrc();
10548713Ssklower }
10648713Ssklower 
10748713Ssklower maketoaddr()
10848713Ssklower {
10948713Ssklower 	if (Servername) {
11048713Ssklower 		int tlen = strlen(Servername);
11148713Ssklower 		int len =  tlen + TSEL(to) - (caddr_t) to;
11248713Ssklower 		if (len < sizeof(*to)) len = sizeof(*to);
11348713Ssklower 		if (len > to->siso_len) {
114*49065Ssklower 			old = to;
11544323Ssklower 			to = (struct sockaddr_iso *)malloc(len);
116*49065Ssklower 			*to = *old; /* We dont care if all old tsel is copied*/
117*49065Ssklower 			if (old != &to_s) free(old);
11844323Ssklower 		}
119*49065Ssklower 		bcopy(Servername, TSEL(to), tlen);
120*49065Ssklower 		to->siso_tlen = tlen;
12144323Ssklower 	} else {
122*49065Ssklower 		to->siso_tlen = sizeof(portnumber);
12344323Ssklower 		portnumber = htons(portnumber);
124*49065Ssklower 		bcopy((char *)&portnumber, TSEL(to), sizeof(portnumber));
12544323Ssklower 	}
12644323Ssklower }
12744323Ssklower 
12844323Ssklower tisrc() {
12948843Ssklower 	int x, s, pid, on = 1, flags = 8, n, proto = tp0mode ? ISOPROTO_TP0: 0;
13044323Ssklower 
13148713Ssklower 	if (dgramp) type = SOCK_DGRAM;
13248843Ssklower 	try(socket, (AF_ISO, type, proto),"");
13344323Ssklower 	s = x;
13444323Ssklower 
13548713Ssklower 	if (debug)
13648713Ssklower 		try(setsockopt, (s, SOL_SOCKET, SO_DEBUG, &on, sizeof on), "");
13748713Ssklower 	if (dgramp == 0) {
13848713Ssklower 		if (conndata)
13948713Ssklower 			doconndata(s);
14048713Ssklower 		try(connect, (s, (struct sockaddr *) to, to->siso_len), "");
14148713Ssklower 	}
14244323Ssklower 	if (selectp) {
14344323Ssklower 		FD_ZERO(&writefds); FD_SET(s, &writefds);
14444323Ssklower 		select(1, &writefds, 0, 0, 0);
14544323Ssklower 	}
14644323Ssklower 	while (count-- > 0) {
14744323Ssklower 		if (size <= 0 && get_record(&flags) == EOF)
14844323Ssklower 			exit(0);
14944323Ssklower 		n = put_record(s, flags);
15044323Ssklower 		if (n < iov->iov_len) {
15144323Ssklower 			if (n==-1 && errno == 55) {
15244323Ssklower 				nobuffs++;
15344323Ssklower 				count++;
15444323Ssklower 				continue;
15544323Ssklower 			}
15644323Ssklower 			fprintf(stderr, "wrote %d < %d, count %d,",
15744323Ssklower 						n, iov->iov_len, count);
15844323Ssklower 			perror("due to");
15944323Ssklower 		}
16044323Ssklower 	}
16144323Ssklower 	if (playtag) {
16244323Ssklower 		printf("Tag time!\n");
16344323Ssklower 		iov->iov_base = your_it;
16444323Ssklower 		iov->iov_len = sizeof your_it;
16544323Ssklower 		sendmsg(s, &msg, MSG_EOR);
16644323Ssklower 		sendmsg(s, &msg, MSG_EOR);
16744323Ssklower 		iov->iov_base = data_msg;
16844323Ssklower 		iov->iov_len = sizeof data_msg;
16944323Ssklower 		try(recvmsg, (s, &msg, flags), " playtag ");
17044323Ssklower 	}
17144323Ssklower 	if(nobuffs) {
17244323Ssklower 		printf("looped %d times waiting for bufs\n", nobuffs);
17344323Ssklower 	}
17444323Ssklower }
17544323Ssklower int localsize;
17644323Ssklower char dupbuf[4096];
17744323Ssklower 
17844323Ssklower put_record(s, flags)
17944323Ssklower int s, flags;
18044323Ssklower {
18144323Ssklower 	int fd, buflen;
18244323Ssklower 	char *buf;
18344323Ssklower 	int x, saved_x;
18444323Ssklower 
18544323Ssklower 	msg.msg_flags = flags;
18644323Ssklower 	if (verbose) {
18744323Ssklower 		if (msg.msg_controllen) {
18844323Ssklower 			printf("(CMessage Type is %x) ", cm.cm.cmhdr.cmsg_type);
18948713Ssklower 			dumpit("CMsg data:\n", &msg.msg_control, msg.msg_controllen);
19044323Ssklower 		}
19144323Ssklower 		if (iov->iov_len) {
19244323Ssklower 			printf("sending: %s %s",
19344323Ssklower 			(flags & MSG_OOB ? "(OOB Data)" : ""),
19444323Ssklower 				(flags & MSG_EOR ? "(Record Mark)" : ""));
19548713Ssklower 			dumpit("data: ", data_msg, localsize);
19644323Ssklower 		}
19744323Ssklower 	}
19844323Ssklower 	if (verify) {
19944323Ssklower 		buflen = iov->iov_len;
20044323Ssklower 		bcopy(iov->iov_base, dupbuf, buflen);
20144323Ssklower 	}
20248713Ssklower 	if (dgramp) {
20348713Ssklower 		msg.msg_name = (caddr_t)to;
20448713Ssklower 		msg.msg_namelen = to->siso_len;
20548713Ssklower 	}
20644323Ssklower 	try(sendmsg, (s, &msg, flags), " put_record ");
20744323Ssklower 	saved_x = x;
20844323Ssklower 	while (verify && buflen > 0) {
20944323Ssklower 		iov->iov_len = buflen;
21044323Ssklower 		iov->iov_base = dupbuf;
21144323Ssklower 		try(recvmsg, (s, &msg, flags), " put_record ");
21248713Ssklower 		if (dgramp) {
21348713Ssklower 			if (msg.msg_namelen)
21448713Ssklower 				dumpit("from: ", to, msg.msg_namelen);
21548713Ssklower 			msg.msg_namelen = old->siso_len;
21648713Ssklower 		}
21744323Ssklower 		printf("verify got %d\n", x);
21844323Ssklower 		buflen -= x;
21944323Ssklower 	}
22048713Ssklower 	bcopy(old, to, old->siso_len);
22144323Ssklower 	msg.msg_control = 0;
22244323Ssklower 	return (saved_x);
22344323Ssklower }
22448713Ssklower dumpit(what, where, n)
22548713Ssklower char *what; unsigned short *where; int n;
22648713Ssklower {
22748713Ssklower 	unsigned short *s = where;
22848713Ssklower 	unsigned short *z = where + (n+1)/2;
22948713Ssklower 	int count = 0;
23048713Ssklower 	if (verbose == 0)
23148713Ssklower 		return;
23248713Ssklower 	printf(what);
23348713Ssklower 	while(s < z) {
23448713Ssklower 		count++;
23548713Ssklower 		printf("%x ",*s++);
23648713Ssklower 		if ((count & 15) == 0)
23748713Ssklower 			putchar('\n');
23848713Ssklower 	}
23948713Ssklower 	if (count & 15)
24048713Ssklower 		putchar('\n');
24148713Ssklower 	fflush(stdout);
24248713Ssklower }
24344323Ssklower int *datasize = &iov->iov_len;
24444323Ssklower char *cp, *cplim;
24544323Ssklower 
24644323Ssklower get_control_data(type)
24744323Ssklower {
24844323Ssklower 
24944323Ssklower 	datasize = (int *)&msg.msg_controllen;
25044323Ssklower 	cp = cm.cm.cmdata;
25144323Ssklower 	cplim = cp + sizeof(cm.cm.cmdata);
25244323Ssklower 	cm.cm.cmhdr.cmsg_level = SOL_TRANSPORT;
25344323Ssklower 	cm.cm.cmhdr.cmsg_type = type;
25444323Ssklower 	msg.msg_control = cm.data;
25544323Ssklower }
25644323Ssklower 
25744323Ssklower doconndata(s)
25844323Ssklower {
25944323Ssklower 	get_control_data(TPOPT_CONN_DATA);
26044323Ssklower 	*datasize = strlen(conndata) + sizeof(cm.cm.cmhdr);
26144323Ssklower 	cm.cm.cmhdr.cmsg_len = *datasize;
26244323Ssklower 	bcopy(conndata, cp, *datasize);
26344323Ssklower 	put_record(s, 0);
26444323Ssklower }
26544323Ssklower 
26648713Ssklower get_altbuf(addrbuf)
26748713Ssklower char *addrbuf;
26848713Ssklower {
26948713Ssklower 	if (dgramp == 0) {
27048713Ssklower 		printf("illegal option for stream\n");
27148713Ssklower 		return 1;
27248713Ssklower 	}
27348713Ssklower 	return (scanf("%s", addrbuf) == EOF ? 1 : 0);
27448713Ssklower }
27544323Ssklower 
27644323Ssklower get_record(flags)
27744323Ssklower int *flags;
27844323Ssklower {
27948713Ssklower 	int factor = 1, x = 0, newaddr = 0;
28048713Ssklower 	static repeatcount, repeatsize;
28144323Ssklower 	char workbuf[10240];
28248713Ssklower 	char addrbuf[128];
28344323Ssklower 
28448713Ssklower 	if (repeatcount > 0) {
28548713Ssklower 		repeatcount--;
28648713Ssklower 		return;
28748713Ssklower 	}
28848713Ssklower 
28944323Ssklower 	*flags = 0;
29044323Ssklower 	*datasize = 0;
29144323Ssklower 	datasize = &iov->iov_len;
29244323Ssklower 	cp = data_msg;
29344323Ssklower 	cplim  = cp + sizeof(data_msg);
29444323Ssklower 
29544323Ssklower 	for(;;) {
29644323Ssklower 		x = scanf("%s", workbuf);
29744323Ssklower 		if (x == EOF)
29844323Ssklower 			break;
29948713Ssklower 		if (strcmp(workbuf, "host") == 0) {
30048713Ssklower 			if (get_altbuf(addrbuf))
30148713Ssklower 				break;
30248713Ssklower 			to->siso_addr = *iso_addr(addrbuf);
30348713Ssklower 			newaddr = 1;
30448713Ssklower 		} else if (strcmp(workbuf, "Servername") == 0) {
30548713Ssklower 			if (get_altbuf(Serverbuf))
30648713Ssklower 				break;
30748713Ssklower 			Servername = Serverbuf;
30848713Ssklower 			newaddr = 1;
30948713Ssklower 		} else if (strcmp(workbuf, "port") == 0) {
31048713Ssklower 			x = scanf("%hd", &portnumber);
31148713Ssklower 			if (x == EOF)
31248713Ssklower 				break;
31348713Ssklower 			Servername = 0;
31448713Ssklower 			newaddr = 1;
31548713Ssklower 		} else if (strcmp(workbuf, "repeat") == 0) {
31648713Ssklower 			x = scanf("%d", &repeatcount);
31748713Ssklower 			if (repeatcount <= 0) repeatcount = 1;
31848713Ssklower 			repeatcount--;
31948713Ssklower 			if (x == EOF)
32048713Ssklower 				break;
32148713Ssklower 		} else if (strcmp(workbuf, "disc") == 0)
32244323Ssklower 			x = get_control_data(TPOPT_DISC_DATA);
32344323Ssklower 		else if (strcmp(workbuf, "cfrm") == 0)
32444323Ssklower 			x = get_control_data(TPOPT_CFRM_DATA);
32544323Ssklower 		else if (strcmp(workbuf, "oob") == 0)
32644323Ssklower 			*flags |= MSG_OOB;
32744323Ssklower 		else if (strcmp(workbuf, "eom") == 0)
32844323Ssklower 			*flags |= MSG_EOR;
32944323Ssklower 		else if (strcmp(workbuf, "factor") == 0) {
33044323Ssklower 			x = scanf("%d", &factor);
33144323Ssklower 			if (factor <= 0) factor = 1;
33244323Ssklower 			if (x == EOF)
33344323Ssklower 				break;
33444323Ssklower 		} else {
33544323Ssklower 			int len = strlen(workbuf);
33644323Ssklower 			localsize = 0;
33744323Ssklower 			while ((factor-- > 0) &&
33844323Ssklower 			       ((cp + len) < cplim)) {
33944323Ssklower 					strcpy(cp, workbuf);
34044323Ssklower 					cp += len;
34144323Ssklower 					localsize += len;
34244323Ssklower 			}
34344323Ssklower 			*datasize = localsize;
34444323Ssklower 			if (datasize != &iov->iov_len) {
34544323Ssklower 				*datasize += sizeof(cm.cm.cmhdr);
34648713Ssklower 				repeatsize = cm.cm.cmhdr.cmsg_len = *datasize;
34744323Ssklower 			}
34844323Ssklower 			break;
34944323Ssklower 		}
35044323Ssklower 	}
35144323Ssklower 	errno = 0;
35248713Ssklower 	if (newaddr)
35348713Ssklower 		maketoaddr();
35444323Ssklower 	return (x);
35544323Ssklower }
356