/* sender for internet datagram demo */ /* with select and time-out */ #include #include #include #include #include #include #define ENDPACKET "end" #define toGuiSocketName "/tmp/cs522_2Gui" #define fromGuiSocketName "/tmp/cs522_4Gui" printmsg(msg, cc) char *msg; int cc; { int i; printf("Got Message:%s\n", msg); for (i= 0; i%s\n", toGuiSocketName); return sock; } int initSockFromGui() { int sock; struct sockaddr_un name; /* create a unix domain socket from which to read */ sock = socket(AF_UNIX, SOCK_DGRAM, 0); if (sock < 0) { perror("opening datagram socket"); exit(1); } /* create name structure for the UNIX domain socket */ name.sun_family = AF_UNIX; strcpy(name.sun_path, fromGuiSocketName); printf("socket from gui-->%s\n", fromGuiSocketName); return sock; } help_msg() { printf("format: ua -[d] <#timeout.sec> <#timeout.usec> hostname portno\n"); printf(" option: d set debug mode\n"); } main(argc, argv) int argc; char *argv[]; { int sockTo; int sockFrom; int sockToGui; int sockFromGui; struct sockaddr_in to; struct sockaddr_in from; struct hostent *hp, *gethostbyname(); int maxfdpl; struct timeval timeout; fd_set fdvar; long atol(); int n; int i; int pcount = 0; /* count of packets sent */ int quitFlag = 1; char toBuf[1024]; char fromBuf[1024]; char hostname[64]; extern char *optarg; extern int optind; int option_exist = 0; int c; int debug = 0; char *rcv_name; /* receiver's socket name */ int toPort_no; int length; int flag; /* process command line args */ while ((c=getopt(argc,argv,"d")) != EOF) { option_exist = 1; switch(c) { case 'd': debug = 1; if (debug) printf("turn on debug mode.\n"); break; case '?': help_msg(); exit (1); default: fprintf (stderr, "unrecognized arg >%s<\n", optarg); help_msg(); exit (1); } } if (argc < 5) { help_msg(); exit (1); } sockFromGui = initSockFromGui(); sockToGui = initSockToGui(); timeout.tv_sec = atol(argv[optind++]); timeout.tv_usec = atol(argv[optind++]); printf("timeout is set to %ld sec., %ld microsec.\n", timeout.tv_sec, timeout.tv_usec); rcv_name = argv[optind++]; if ((toPort_no = atoi(argv[optind])) < 1025) toPort_no = 1025; if (debug) printf("The receiver's host name is %s, port_no=%d\n", rcv_name, toPort_no); /* create socket from which to read */ sockFrom = socket(AF_INET, SOCK_DGRAM, 0); if (sockFrom < 0) { perror("opening datagram socket"); exit(1); } /* create name structure with wildcard using INADDR_ANY */ from.sin_family = AF_INET; from.sin_addr.s_addr = INADDR_ANY; from.sin_port = 0; /* port no. < 1024 IPPORT_RESERVED is for privillege process */ /* here just initialized it, it will be assigned value after call */ /* getsockname() */ if (bind(sockFrom, &from, sizeof(struct sockaddr_in))) { perror("binding name to datagram socket"); exit(1); } length = sizeof(from); if (getsockname(sockFrom, &from, &length)) { perror("getting socket name"); exit(1); } /* Find assigned port value and print out. */ printf("socket has port #%d\n", ntohs(from.sin_port)); /* create socket on which to sent */ sockTo = socket(AF_INET, SOCK_DGRAM, 0); if (sockTo < 0) { perror("opening datagram socket"); exit(1); } to.sin_family = AF_INET; to.sin_addr.s_addr = INADDR_ANY; to.sin_port = 0; if (bind(sockTo, &to, sizeof(to))) { perror("binding datagram socket"); exit(1); } /* construct name of the socket to send to * gethostbyname() returns a structure including the network address * of the specified host from /etc/hosts. The port number is taken from * the cmd line * create name structure for the UNIX domain socket * use the name from cmd argument */ hp = gethostbyname(rcv_name); if (hp == 0) { fprintf(stderr, "%s: unknown host",rcv_name); exit(2); } bcopy(hp->h_addr, &to.sin_addr, hp->h_length); to.sin_family = AF_INET; to.sin_port = htons(toPort_no); /*send message */ gethostname(hostname, 64); printf("hostname=%s\n", hostname); printf("sending message: %s %d This is packet %d!\n", hostname, ntohs(from.sin_port), pcount++); sprintf(toBuf, "%s %d This is packet %d!\n", hostname, ntohs(from.sin_port), pcount); if (sendto(sockTo, toBuf, strlen(toBuf), 0, &to, sizeof(to)) < 0) perror("sending datagram message"); FD_ZERO(&fdvar); /* initialize the set -- all bits off */ FD_SET(sockFrom, &fdvar); /* turn on bit for fd sockFrom */ FD_SET(sockFromGui, &fdvar); /* turn on bit for fd sockFromGui */ maxfdpl = (sockFrom > sockFromGui) ? sockFrom+1 : sockFromGui+1; while (quitFlag) { if (debug) printf("The number of file descriptors to be tested is %d\n", sockFrom+1); if ((i=select(maxfdpl, &fdvar, (fd_set *) 0, (fd_set *) 0, &timeout)) < 0) perror("select error"); if (i == 0) { printf("Time out! The receiver does not respond.\n"); exit(1); } if (FD_ISSET(sockFromGui, &fdvar)) { n = recv(sockFrom, fromBuf, 1024, flag); if (n < 0) perror("receiving datagram message"); printmsg(fromBuf, n); /* relay the gui data messge to the receiver */ if (sendto(sockTo, fromBuf, n, 0, &to, sizeof(to)) < 0) perror("sending datagram message"); if (fromBuf[0] == 1) quitFlag= 0; } if (FD_ISSET(sockFrom, &fdvar)) { n = recv(sockFrom, fromBuf, 1024, flag); if (n < 0) perror("receiving datagram message"); fromBuf[n] = 0; /* null terminate */ /* printf("received ack msg=%s\n", fromBuf); sprintf(toBuf, "%s %d This is packet %d!\n", hostname, ntohs(from.sin_port), pcount++); if (sendto(sockTo, toBuf, strlen(toBuf), 0, &to, sizeof(to)) < 0) perror("sending datagram message"); */ } } close(sockToGui); unlink(toGuiSocketName); close(sockFromGui); unlink(fromGuiSocketName); close(sockFrom); close(sockTo); }