/* ** get data from the client and return it ** run in a child process that was forked off from the main process. */ void process(int sock) { char buf[XIA_MAXBUF + 1]; int n; pid_t pid = getpid(); fd_set fds; FD_ZERO(&fds); FD_SET(sock, &fds); #ifdef USE_SELECT struct timeval tv; tv.tv_sec = WAIT_FOR_DATA; tv.tv_usec = 0; #endif while (1) { memset(buf, 0, sizeof(buf)); #ifdef USE_SELECT tv.tv_sec = WAIT_FOR_DATA; tv.tv_usec = 0; if ((n = Xselect(sock + 1, &fds, NULL, NULL, &tv)) < 0) { warn("%5d Select failed, closing...\n", pid); break; } else if (n == 0) { // we timed out, close the socket say("%5d timed out on recv\n", pid); break; } else if (!FD_ISSET(sock, &fds)) { // this shouldn't happen! die(-4, "something is really wrong, exiting\n"); } #endif if ((n = Xrecv(sock, buf, sizeof(buf), 0)) < 0) { warn("Recv error on socket %d, closing connection\n", pid); break; } else if (n == 0) { warn("%d client closed the connection\n", pid); break; } say("%5d received %d bytes\n", pid, n); if ((n = Xsend(sock, buf, n, 0)) < 0) { warn("%5d send error\n", pid); break; } say("%5d sent %d bytes\n", pid, n); } say("%5d closing\n", pid); Xclose(sock); }
int main(int argc, char **argv) { struct addrinfo *ai; sockaddr_x *sa; int seq = 0; // FIXME: put signal handlers back into code once Xselect is working // signal(SIGINT, handler); // signal(SIGTERM, handler); getConfig(argc, argv); if (Xgetaddrinfo(NAME, NULL, NULL, &ai) < 0) die("Unable to lookup address for %s\n", NAME); sa = (sockaddr_x*)ai->ai_addr; if ((sock = Xsocket(AF_XIA, SOCK_STREAM, 0)) < 0) die("Unable to create a socket\n"); say("Opening firehose: %s\n", NAME); if (Xconnect(sock, (struct sockaddr*)sa, sizeof(sockaddr_x)) < 0) { Xclose(sock); die("Unable to connect to %s\n", NAME); } // tell firehose how many packets we expect if (Xsend(sock, &fhc, sizeof(fhc), 0) < 0) { Xclose(sock); die("Unable to send config information to the firehose\n"); } int count = 0; char *buf = (char *)malloc(pktSize); while (!timetodie) { int n; fd_set fds; FD_ZERO(&fds); FD_SET(sock, &fds); struct timeval tv; tv.tv_sec = 2; tv.tv_usec = 0; if ((n = Xselect(sock + 1, &fds, NULL, NULL, &tv)) < 0) { printf("select failed\n"); break; } else if (n == 0) { printf("recv timeout\n"); break; } else if (!FD_ISSET(sock, &fds)) { // this shouldn't happen! printf("something is really wrong, exiting\n"); break; } int rc = Xrecv(sock, buf, sizeof(buf), 0); if (rc < 0) die("Receive failure\n"); memcpy(&seq, buf, sizeof(int)); say("expecting %d, got %d", count, seq); if (count == seq) say("\n"); else say(" lost %d\n", seq - count); count++; if (count == numPkts) break; if (delay) usleep(delay); } seq++; if (count != seq) printf("lost %d packets, received %d, expected %d\n", seq - count, count, seq); else printf("success!\n"); Xclose(sock); }
/* ** get data from the client and return it ** run in a child process that was forked off from the main process. */ void process(int sock, XSSL_CTX *ctx) { char buf[XIA_MAXBUF + 1]; int n; pid_t pid = getpid(); fd_set fds; FD_ZERO(&fds); FD_SET(sock, &fds); struct timeval tv; tv.tv_sec = WAIT_FOR_DATA; tv.tv_usec = 0; /* set up XSSL connection */ XSSL *xssl = XSSL_new(ctx); if (xssl == NULL) { die(-6, "Error creating new XSSL object\n"); } if (XSSL_set_fd(xssl, sock) != 1) { die(-7, "Error setting XSSL sockfd\n"); } if (XSSL_accept(xssl) != 1) { die(-8, "Error accepting XSSL connection\n"); } while (1) { memset(buf, 0, sizeof(buf)); tv.tv_sec = WAIT_FOR_DATA; tv.tv_usec = 0; if ((n = Xselect(xssl->sockfd + 1, &fds, NULL, NULL, &tv)) < 0) { warn("%5d Select failed, closing...\n", pid); break; } else if (n == 0) { // we timed out, close the socket say("%5d timed out on recv\n", pid); break; } else if (!FD_ISSET(xssl->sockfd, &fds)) { // this shouldn't happen! die(-4, "something is really wrong, exiting\n"); } if ((n = XSSL_read(xssl, buf, sizeof(buf))) < 0) { warn("Recv error on socket %d, closing connection\n", pid); break; } say("%5d received %d bytes\n", pid, n); if ((n = XSSL_write(xssl, buf, n)) < 0) { warn("%5d send error\n", pid); break; } say("%5d sent %d bytes\n", pid, n); } say("%5d closing\n", pid); XSSL_shutdown(xssl); Xclose(sock); XSSL_free(xssl); }
void process(int peer) { fhConfig fhc; char *buf = NULL; uint32_t count = 0; int n; signal(SIGINT, handler); fd_set fds; FD_ZERO(&fds); FD_SET(peer, &fds); struct timeval tv; tv.tv_sec = 5; tv.tv_usec = 0; n = Xselect(peer + 1, &fds, NULL, NULL, &tv); if (n < 0) { printf("select failed\n"); goto done; } else if (n == 0) { printf("recv timeout\n"); goto done; } else if (!FD_ISSET(peer, &fds)) { // this shouldn't happen! printf("something is really wrong, exiting\n"); goto done; } if (Xrecv(peer, &fhc, sizeof(fhc), 0) < 0) { printf("Unable to get configuration block\n"); goto done; } fhc.numPkts = ntohl(fhc.numPkts); fhc.delay = ntohl(fhc.delay); fhc.pktSize = ntohl(fhc.pktSize); // need to have at least enough room for the sequence # fhc.pktSize = MAX(fhc.pktSize, sizeof(unsigned)); if (fhc.numPkts == 0) say("packet count = non-stop\n"); else say("packet count = %d\n", fhc.numPkts); say("packet size = %d\n", fhc.pktSize); say("inter-packet delay = %d\n", fhc.delay); if (!(buf = (char *)malloc(fhc.pktSize))) { printf("Memory error\n"); goto done; } while (!timetodie) { if (fhc.numPkts > 0 && count == fhc.numPkts) break; printf("sending packet %d\n", count); data(count, buf, sizeof(buf)); Xsend(peer, buf, sizeof(buf), 0); count++; if (fhc.delay != 0) usleep(fhc.delay); } done: say("done\n"); if (buf) free(buf); Xclose(peer); }
int main(int argc, char **argv) { int sock = -1; int peer = -1; struct addrinfo hints, *ai; // FIXME: put signal handlers back into code once Xselect is working // signal(SIGINT, handler); // signal(SIGTERM, handler); configure(argc, argv); say("XIA firehose listening on %s\n", name); // get our local AD/HID and append the SID to the resultant dag memset(&hints, 0, sizeof(hints)); hints.ai_flags = XAI_XIDSERV; int rc = Xgetaddrinfo(NULL, SID, &hints, &ai); if (rc != 0) die("%s\n", Xgai_strerror(rc)); sockaddr_x *sa = (sockaddr_x*)ai->ai_addr; if ( XregisterName(NAME, sa) < 0) die("Unable to register name %s\n", name); if ((sock = Xsocket(AF_XIA, SOCK_STREAM, 0)) < 0) die("Unable to create socket\n"); if (Xbind(sock, (struct sockaddr*)sa, sizeof(sockaddr_x)) < 0) { Xclose(sock); die("Unable to bind to DAG\n"); } while (!timetodie) { fd_set fds; FD_ZERO(&fds); FD_SET(sock, &fds); struct timeval tv; tv.tv_sec = 2; tv.tv_usec = 0; if ((rc = Xselect(sock + 1, &fds, NULL, NULL, &tv)) < 0) { printf("select failed\n"); break; } else if (rc == 0) { // timed out, try again continue; } else if (!FD_ISSET(sock, &fds)) { // this shouldn't happen! printf("something is really wrong, exiting\n"); break; } peer = Xaccept(sock, NULL, NULL); if (peer < 0) { printf("Xaccept failed\n"); break; } say("peer connected...\n"); pid_t pid = fork(); if (pid == -1) { printf("fork failed\n"); break; } else if (pid == 0) { process(peer); exit(0); } else { // use regular close so we don't rip out the Xsocket state from under the child close(peer); } } say("firehose exiting\n"); Xclose(sock); return 0; }