Annotation of previous/src/slirp/misc.c, revision 1.1

1.1     ! root        1: /*
        !             2:  * Copyright (c) 1995 Danny Gasparovski.
        !             3:  * 
        !             4:  * Please read the file COPYRIGHT for the
        !             5:  * terms and conditions of the copyright.
        !             6:  */
        !             7: 
        !             8: #define WANT_SYS_IOCTL_H
        !             9: #include <stdlib.h>
        !            10: #include <slirp.h>
        !            11: 
        !            12: u_int curtime, time_fasttimo, last_slowtimo, detach_time;
        !            13: u_int detach_wait = 600000;    /* 10 minutes */
        !            14: 
        !            15: #if 0
        !            16: int x_port = -1;
        !            17: int x_display = 0;
        !            18: int x_screen = 0;
        !            19: 
        !            20: int
        !            21: show_x(buff, inso)
        !            22:        char *buff;
        !            23:        struct socket *inso;
        !            24: {
        !            25:        if (x_port < 0) {
        !            26:                lprint("X Redir: X not being redirected.\r\n");
        !            27:        } else {
        !            28:                lprint("X Redir: In sh/bash/zsh/etc. type: DISPLAY=%s:%d.%d; export DISPLAY\r\n",
        !            29:                      inet_ntoa(our_addr), x_port, x_screen);
        !            30:                lprint("X Redir: In csh/tcsh/etc. type:    setenv DISPLAY %s:%d.%d\r\n",
        !            31:                      inet_ntoa(our_addr), x_port, x_screen);
        !            32:                if (x_display)
        !            33:                   lprint("X Redir: Redirecting to display %d\r\n", x_display);
        !            34:        }
        !            35:        
        !            36:        return CFG_OK;
        !            37: }
        !            38: 
        !            39: 
        !            40: /*
        !            41:  * XXX Allow more than one X redirection?
        !            42:  */
        !            43: void
        !            44: redir_x(inaddr, start_port, display, screen)
        !            45:        u_int32_t inaddr;
        !            46:        int start_port;
        !            47:        int display;
        !            48:        int screen;
        !            49: {
        !            50:        int i;
        !            51:        
        !            52:        if (x_port >= 0) {
        !            53:                lprint("X Redir: X already being redirected.\r\n");
        !            54:                show_x(0, 0);
        !            55:        } else {
        !            56:                for (i = 6001 + (start_port-1); i <= 6100; i++) {
        !            57:                        if (solisten(htons(i), inaddr, htons(6000 + display), 0)) {
        !            58:                                /* Success */
        !            59:                                x_port = i - 6000;
        !            60:                                x_display = display;
        !            61:                                x_screen = screen;
        !            62:                                show_x(0, 0);
        !            63:                                return;
        !            64:                        }
        !            65:                }
        !            66:                lprint("X Redir: Error: Couldn't redirect a port for X. Weird.\r\n");
        !            67:        }
        !            68: }
        !            69: #endif
        !            70: 
        !            71: #ifndef HAVE_INET_ATON
        !            72: int
        !            73: inet_aton(cp, ia)
        !            74:        const char *cp;
        !            75:        struct in_addr *ia;
        !            76: {
        !            77:        u_int32_t addr = inet_addr(cp);
        !            78:        if (addr == 0xffffffff)
        !            79:                return 0;
        !            80:        ia->s_addr = addr;
        !            81:        return 1;
        !            82: }
        !            83: #endif
        !            84: 
        !            85: /*
        !            86:  * Get our IP address and put it in our_addr
        !            87:  */
        !            88: void
        !            89: getouraddr()
        !            90: {
        !            91:        char buff[256];
        !            92:        struct hostent *he = NULL;
        !            93:        
        !            94:        if (gethostname(buff,256) == 0)
        !            95:             he = gethostbyname(buff);
        !            96:         if (he)
        !            97:             our_addr = *(struct in_addr *)he->h_addr;
        !            98:         if (our_addr.s_addr == 0)
        !            99:             our_addr.s_addr = loopback_addr.s_addr;
        !           100: }
        !           101: 
        !           102: struct quehead {
        !           103:        struct quehead *qh_link;
        !           104:        struct quehead *qh_rlink;
        !           105: };
        !           106: 
        !           107: void
        !           108: insque(a, b)
        !           109:        void *a, *b;
        !           110: {
        !           111:        register struct quehead *element = (struct quehead *) a;
        !           112:        register struct quehead *head = (struct quehead *) b;
        !           113:        element->qh_link = head->qh_link;
        !           114:        head->qh_link = (struct quehead *)element;
        !           115:        element->qh_rlink = (struct quehead *)head;
        !           116:        ((struct quehead *)(element->qh_link))->qh_rlink
        !           117:        = (struct quehead *)element;
        !           118: }
        !           119: 
        !           120: void
        !           121: remque(a)
        !           122:      void *a;
        !           123: {
        !           124:   register struct quehead *element = (struct quehead *) a;
        !           125:   ((struct quehead *)(element->qh_link))->qh_rlink = element->qh_rlink;
        !           126:   ((struct quehead *)(element->qh_rlink))->qh_link = element->qh_link;
        !           127:   element->qh_rlink = NULL;
        !           128:   /*  element->qh_link = NULL;  TCP FIN1 crashes if you do this.  Why ? */
        !           129: }
        !           130: 
        !           131: /* #endif */
        !           132: 
        !           133: 
        !           134: int
        !           135: add_exec(ex_ptr, do_pty, exec, addr, port)
        !           136:        struct ex_list **ex_ptr;
        !           137:        int do_pty;
        !           138:        char *exec;
        !           139:        int addr;
        !           140:        int port;
        !           141: {
        !           142:        struct ex_list *tmp_ptr;
        !           143:        
        !           144:        /* First, check if the port is "bound" */
        !           145:        for (tmp_ptr = *ex_ptr; tmp_ptr; tmp_ptr = tmp_ptr->ex_next) {
        !           146:                if (port == tmp_ptr->ex_fport && addr == tmp_ptr->ex_addr)
        !           147:                   return -1;
        !           148:        }
        !           149:        
        !           150:        tmp_ptr = *ex_ptr;
        !           151:        *ex_ptr = (struct ex_list *)malloc(sizeof(struct ex_list));
        !           152:        (*ex_ptr)->ex_fport = port;
        !           153:        (*ex_ptr)->ex_addr = addr;
        !           154:        (*ex_ptr)->ex_pty = do_pty;
        !           155:        (*ex_ptr)->ex_exec = strdup(exec);
        !           156:        (*ex_ptr)->ex_next = tmp_ptr;
        !           157:        return 0;
        !           158: }
        !           159: 
        !           160: #ifndef HAVE_STRERROR
        !           161: 
        !           162: /*
        !           163:  * For systems with no strerror
        !           164:  */
        !           165: 
        !           166: extern int sys_nerr;
        !           167: extern char *sys_errlist[];
        !           168: 
        !           169: char *
        !           170: strerror(error)
        !           171:        int error;
        !           172: {
        !           173:        if (error < sys_nerr)
        !           174:           return sys_errlist[error];
        !           175:        else
        !           176:           return "Unknown error.";
        !           177: }
        !           178: 
        !           179: #endif
        !           180: 
        !           181: 
        !           182: #ifdef _WIN32
        !           183: 
        !           184: int
        !           185: fork_exec(so, ex, do_pty)
        !           186:        struct socket *so;
        !           187:        char *ex;
        !           188:        int do_pty;
        !           189: {
        !           190:     /* not implemented */
        !           191:     return 0;
        !           192: }
        !           193: 
        !           194: #else
        !           195: 
        !           196: int
        !           197: slirp_openpty(amaster, aslave)
        !           198:      int *amaster, *aslave;
        !           199: {
        !           200:        register int master, slave;
        !           201: 
        !           202: #ifdef HAVE_GRANTPT
        !           203:        char *ptr;
        !           204:        
        !           205:        if ((master = open("/dev/ptmx", O_RDWR)) < 0 ||
        !           206:            grantpt(master) < 0 ||
        !           207:            unlockpt(master) < 0 ||
        !           208:            (ptr = ptsname(master)) == NULL)  {
        !           209:                close(master);
        !           210:                return -1;
        !           211:        }
        !           212:        
        !           213:        if ((slave = open(ptr, O_RDWR)) < 0 ||
        !           214:            ioctl(slave, I_PUSH, "ptem") < 0 ||
        !           215:            ioctl(slave, I_PUSH, "ldterm") < 0 ||
        !           216:            ioctl(slave, I_PUSH, "ttcompat") < 0) {
        !           217:                close(master);
        !           218:                close(slave);
        !           219:                return -1;
        !           220:        }
        !           221:        
        !           222:        *amaster = master;
        !           223:        *aslave = slave;
        !           224:        return 0;
        !           225:        
        !           226: #else
        !           227:        
        !           228:        static char line[] = "/dev/ptyXX";
        !           229:        register const char *cp1, *cp2;
        !           230:        
        !           231:        for (cp1 = "pqrsPQRS"; *cp1; cp1++) {
        !           232:                line[8] = *cp1;
        !           233:                for (cp2 = "0123456789abcdefghijklmnopqrstuv"; *cp2; cp2++) {
        !           234:                        line[9] = *cp2;
        !           235:                        if ((master = open(line, O_RDWR, 0)) == -1) {
        !           236:                                if (errno == ENOENT)
        !           237:                                   return (-1);    /* out of ptys */
        !           238:                        } else {
        !           239:                                line[5] = 't';
        !           240:                                /* These will fail */
        !           241:                                (void) chown(line, getuid(), 0);
        !           242:                                (void) chmod(line, S_IRUSR|S_IWUSR|S_IWGRP);
        !           243: #ifdef HAVE_REVOKE
        !           244:                                (void) revoke(line);
        !           245: #endif
        !           246:                                if ((slave = open(line, O_RDWR, 0)) != -1) {
        !           247:                                        *amaster = master;
        !           248:                                        *aslave = slave;
        !           249:                                        return 0;
        !           250:                                }
        !           251:                                (void) close(master);
        !           252:                                line[5] = 'p';
        !           253:                        }
        !           254:                }
        !           255:        }
        !           256:        errno = ENOENT; /* out of ptys */
        !           257:        return (-1);
        !           258: #endif
        !           259: }
        !           260: 
        !           261: /*
        !           262:  * XXX This is ugly
        !           263:  * We create and bind a socket, then fork off to another
        !           264:  * process, which connects to this socket, after which we
        !           265:  * exec the wanted program.  If something (strange) happens,
        !           266:  * the accept() call could block us forever.
        !           267:  * 
        !           268:  * do_pty = 0   Fork/exec inetd style
        !           269:  * do_pty = 1   Fork/exec using slirp.telnetd
        !           270:  * do_ptr = 2   Fork/exec using pty
        !           271:  */
        !           272: int
        !           273: fork_exec(so, ex, do_pty)
        !           274:        struct socket *so;
        !           275:        char *ex;
        !           276:        int do_pty;
        !           277: {
        !           278:        int s;
        !           279:        struct sockaddr_in addr;
        !           280:        socklen_t addrlen = sizeof(addr);
        !           281:        int opt;
        !           282:         int master;
        !           283:        char *argv[256];
        !           284: #if 0
        !           285:        char buff[256];
        !           286: #endif
        !           287:        /* don't want to clobber the original */
        !           288:        char *bptr;
        !           289:        char *curarg;
        !           290:        int c, i, ret;
        !           291:        
        !           292:        DEBUG_CALL("fork_exec");
        !           293:        DEBUG_ARG("so = %lx", (long)so);
        !           294:        DEBUG_ARG("ex = %lx", (long)ex);
        !           295:        DEBUG_ARG("do_pty = %lx", (long)do_pty);
        !           296:        
        !           297:        if (do_pty == 2) {
        !           298:                if (slirp_openpty(&master, &s) == -1) {
        !           299:                        lprint("Error: openpty failed: %s\n", strerror(errno));
        !           300:                        return 0;
        !           301:                }
        !           302:        } else {
        !           303:                memset(&addr, 0, sizeof(struct sockaddr_in));
        !           304:                addr.sin_family = AF_INET;
        !           305:                addr.sin_port = 0;
        !           306:                addr.sin_addr.s_addr = INADDR_ANY;
        !           307:                
        !           308:                if ((s = socket(AF_INET, SOCK_STREAM, 0)) < 0 ||
        !           309:                    bind(s, (struct sockaddr *)&addr, addrlen) < 0 ||
        !           310:                    listen(s, 1) < 0) {
        !           311:                        lprint("Error: inet socket: %s\n", strerror(errno));
        !           312:                        closesocket(s);
        !           313:                        
        !           314:                        return 0;
        !           315:                }
        !           316:        }
        !           317:        
        !           318:        switch(fork()) {
        !           319:         case -1:
        !           320:                lprint("Error: fork failed: %s\n", strerror(errno));
        !           321:                close(s);
        !           322:                if (do_pty == 2)
        !           323:                   close(master);
        !           324:                return 0;
        !           325:                
        !           326:         case 0:
        !           327:                /* Set the DISPLAY */
        !           328:                if (do_pty == 2) {
        !           329:                        (void) close(master);
        !           330: #ifdef TIOCSCTTY /* XXXXX */
        !           331:                        (void) setsid();
        !           332:                        ioctl(s, TIOCSCTTY, (char *)NULL);
        !           333: #endif
        !           334:                } else {
        !           335:                        getsockname(s, (struct sockaddr *)&addr, &addrlen);
        !           336:                        close(s);
        !           337:                        /*
        !           338:                         * Connect to the socket
        !           339:                         * XXX If any of these fail, we're in trouble!
        !           340:                         */
        !           341:                        s = socket(AF_INET, SOCK_STREAM, 0);
        !           342:                        addr.sin_addr = loopback_addr;
        !           343:                         do {
        !           344:                             ret = connect(s, (struct sockaddr *)&addr, addrlen);
        !           345:                         } while (ret < 0 && errno == EINTR);
        !           346:                }
        !           347:                
        !           348: #if 0
        !           349:                if (x_port >= 0) {
        !           350: #ifdef HAVE_SETENV
        !           351:                        sprintf(buff, "%s:%d.%d", inet_ntoa(our_addr), x_port, x_screen);
        !           352:                        setenv("DISPLAY", buff, 1);
        !           353: #else
        !           354:                        sprintf(buff, "DISPLAY=%s:%d.%d", inet_ntoa(our_addr), x_port, x_screen);
        !           355:                        putenv(buff);
        !           356: #endif
        !           357:                }
        !           358: #endif 
        !           359:                dup2(s, 0);
        !           360:                dup2(s, 1);
        !           361:                dup2(s, 2);
        !           362:                for (s = 3; s <= 255; s++)
        !           363:                   close(s);
        !           364:                
        !           365:                i = 0;
        !           366:                bptr = strdup(ex); /* No need to free() this */
        !           367:                if (do_pty == 1) {
        !           368:                        /* Setup "slirp.telnetd -x" */
        !           369:                        argv[i++] = "slirp.telnetd";
        !           370:                        argv[i++] = "-x";
        !           371:                        argv[i++] = bptr;
        !           372:                } else
        !           373:                   do {
        !           374:                        /* Change the string into argv[] */
        !           375:                        curarg = bptr;
        !           376:                        while (*bptr != ' ' && *bptr != (char)0)
        !           377:                           bptr++;
        !           378:                        c = *bptr;
        !           379:                        *bptr++ = (char)0;
        !           380:                        argv[i++] = strdup(curarg);
        !           381:                   } while (c);
        !           382:                
        !           383:                argv[i] = 0;
        !           384:                execvp(argv[0], argv);
        !           385:                
        !           386:                /* Ooops, failed, let's tell the user why */
        !           387:                  {
        !           388:                          char buff[256];
        !           389:                          
        !           390:                          sprintf(buff, "Error: execvp of %s failed: %s\n", 
        !           391:                                  argv[0], strerror(errno));
        !           392:                          write(2, buff, strlen(buff)+1);
        !           393:                  }
        !           394:                close(0); close(1); close(2); /* XXX */
        !           395:                exit(1);
        !           396:                
        !           397:         default:
        !           398:                if (do_pty == 2) {
        !           399:                        close(s);
        !           400:                        so->s = master;
        !           401:                } else {
        !           402:                        /*
        !           403:                         * XXX this could block us...
        !           404:                         * XXX Should set a timer here, and if accept() doesn't
        !           405:                         * return after X seconds, declare it a failure
        !           406:                         * The only reason this will block forever is if socket()
        !           407:                         * of connect() fail in the child process
        !           408:                         */
        !           409:                         do {
        !           410:                             so->s = accept(s, (struct sockaddr *)&addr, &addrlen);
        !           411:                         } while (so->s < 0 && errno == EINTR);
        !           412:                         closesocket(s);
        !           413:                        opt = 1;
        !           414:                        setsockopt(so->s,SOL_SOCKET,SO_REUSEADDR,(char *)&opt,sizeof(int));
        !           415:                        opt = 1;
        !           416:                        setsockopt(so->s,SOL_SOCKET,SO_OOBINLINE,(char *)&opt,sizeof(int));
        !           417:                }
        !           418:                fd_nonblock(so->s);
        !           419:                
        !           420:                /* Append the telnet options now */
        !           421:                if (so->so_m != 0 && do_pty == 1)  {
        !           422:                        sbappend(so, so->so_m);
        !           423:                        so->so_m = 0;
        !           424:                }
        !           425:                
        !           426:                return 1;
        !           427:        }
        !           428: }
        !           429: #endif
        !           430: 
        !           431: #if !(defined HAVE_STRDUP || defined __GNUC__)
        !           432: char *
        !           433: strdup(str)
        !           434:        const char *str;
        !           435: {
        !           436:        char *bptr;
        !           437:        
        !           438:        bptr = (char *)malloc(strlen(str)+1);
        !           439:        strcpy(bptr, str);
        !           440:        
        !           441:        return bptr;
        !           442: }
        !           443: #endif
        !           444: 
        !           445: #if 0
        !           446: void
        !           447: snooze_hup(num)
        !           448:        int num;
        !           449: {
        !           450:        int s, ret;
        !           451: #ifndef NO_UNIX_SOCKETS
        !           452:        struct sockaddr_un sock_un;
        !           453: #endif
        !           454:        struct sockaddr_in sock_in;
        !           455:        char buff[256];
        !           456:        
        !           457:        ret = -1;
        !           458:        if (slirp_socket_passwd) {
        !           459:                s = socket(AF_INET, SOCK_STREAM, 0);
        !           460:                if (s < 0)
        !           461:                   slirp_exit(1);
        !           462:                sock_in.sin_family = AF_INET;
        !           463:                sock_in.sin_addr.s_addr = slirp_socket_addr;
        !           464:                sock_in.sin_port = htons(slirp_socket_port);
        !           465:                if (connect(s, (struct sockaddr *)&sock_in, sizeof(sock_in)) != 0)
        !           466:                   slirp_exit(1); /* just exit...*/
        !           467:                sprintf(buff, "kill %s:%d", slirp_socket_passwd, slirp_socket_unit);
        !           468:                write(s, buff, strlen(buff)+1);
        !           469:        }
        !           470: #ifndef NO_UNIX_SOCKETS
        !           471:          else {
        !           472:                s = socket(AF_UNIX, SOCK_STREAM, 0);
        !           473:                if (s < 0)
        !           474:                   slirp_exit(1);
        !           475:                sock_un.sun_family = AF_UNIX;
        !           476:                strcpy(sock_un.sun_path, socket_path);
        !           477:                if (connect(s, (struct sockaddr *)&sock_un,
        !           478:                              sizeof(sock_un.sun_family) + sizeof(sock_un.sun_path)) != 0)
        !           479:                   slirp_exit(1);
        !           480:                sprintf(buff, "kill none:%d", slirp_socket_unit);
        !           481:                write(s, buff, strlen(buff)+1);
        !           482:        }
        !           483: #endif
        !           484:        slirp_exit(0);
        !           485: }
        !           486:        
        !           487:        
        !           488: void
        !           489: snooze()
        !           490: {
        !           491:        sigset_t s;
        !           492:        int i;
        !           493:        
        !           494:        /* Don't need our data anymore */
        !           495:        /* XXX This makes SunOS barf */
        !           496: /*     brk(0); */
        !           497:        
        !           498:        /* Close all fd's */
        !           499:        for (i = 255; i >= 0; i--)
        !           500:           close(i);
        !           501:        
        !           502:        signal(SIGQUIT, slirp_exit);
        !           503:        signal(SIGHUP, snooze_hup);
        !           504:        sigemptyset(&s);
        !           505:        
        !           506:        /* Wait for any signal */
        !           507:        sigsuspend(&s);
        !           508:        
        !           509:        /* Just in case ... */
        !           510:        exit(255);
        !           511: }
        !           512: 
        !           513: void
        !           514: relay(s)
        !           515:        int s;
        !           516: {
        !           517:        char buf[8192];
        !           518:        int n;
        !           519:        fd_set readfds;
        !           520:        struct ttys *ttyp;
        !           521:        
        !           522:        /* Don't need our data anymore */
        !           523:        /* XXX This makes SunOS barf */
        !           524: /*     brk(0); */
        !           525:        
        !           526:        signal(SIGQUIT, slirp_exit);
        !           527:        signal(SIGHUP, slirp_exit);
        !           528:         signal(SIGINT, slirp_exit);
        !           529:        signal(SIGTERM, slirp_exit);
        !           530:        
        !           531:        /* Fudge to get term_raw and term_restore to work */
        !           532:        if (NULL == (ttyp = tty_attach (0, slirp_tty))) {
        !           533:          lprint ("Error: tty_attach failed in misc.c:relay()\r\n");
        !           534:          slirp_exit (1);
        !           535:     }
        !           536:        ttyp->fd = 0;
        !           537:        ttyp->flags |= TTY_CTTY;
        !           538:        term_raw(ttyp);
        !           539:        
        !           540:        while (1) {
        !           541:                FD_ZERO(&readfds);
        !           542:                
        !           543:                FD_SET(0, &readfds);
        !           544:                FD_SET(s, &readfds);
        !           545:                
        !           546:                n = select(s+1, &readfds, (fd_set *)0, (fd_set *)0, (struct timeval *)0);
        !           547:                
        !           548:                if (n <= 0)
        !           549:                   slirp_exit(0);
        !           550:                
        !           551:                if (FD_ISSET(0, &readfds)) {
        !           552:                        n = read(0, buf, 8192);
        !           553:                        if (n <= 0)
        !           554:                           slirp_exit(0);
        !           555:                        n = writen(s, buf, n);
        !           556:                        if (n <= 0)
        !           557:                           slirp_exit(0);
        !           558:                }
        !           559:                
        !           560:                if (FD_ISSET(s, &readfds)) {
        !           561:                        n = read(s, buf, 8192);
        !           562:                        if (n <= 0)
        !           563:                           slirp_exit(0);
        !           564:                        n = writen(0, buf, n);
        !           565:                        if (n <= 0)
        !           566:                           slirp_exit(0);
        !           567:                }
        !           568:        }
        !           569:        
        !           570:        /* Just in case.... */
        !           571:        exit(1);
        !           572: }
        !           573: #endif
        !           574: 
        !           575: int (*lprint_print) _P((void *, const char *, va_list));
        !           576: char *lprint_ptr, *lprint_ptr2, **lprint_arg;
        !           577: 
        !           578: void
        !           579: #ifdef __STDC__
        !           580: lprint(const char *format, ...)
        !           581: #else
        !           582: lprint(va_alist) va_dcl
        !           583: #endif
        !           584: {
        !           585:        va_list args;
        !           586:         
        !           587: #ifdef __STDC__
        !           588:         va_start(args, format);
        !           589: #else
        !           590:         char *format;
        !           591:         va_start(args);
        !           592:         format = va_arg(args, char *);
        !           593: #endif
        !           594: #if 0
        !           595:        /* If we're printing to an sbuf, make sure there's enough room */
        !           596:        /* XXX +100? */
        !           597:        if (lprint_sb) {
        !           598:                if ((lprint_ptr - lprint_sb->sb_wptr) >=
        !           599:                    (lprint_sb->sb_datalen - (strlen(format) + 100))) {
        !           600:                        int deltaw = lprint_sb->sb_wptr - lprint_sb->sb_data;
        !           601:                        int deltar = lprint_sb->sb_rptr - lprint_sb->sb_data;
        !           602:                        int deltap = lprint_ptr -         lprint_sb->sb_data;
        !           603:                                                
        !           604:                        lprint_sb->sb_data = (char *)realloc(lprint_sb->sb_data,
        !           605:                                                             lprint_sb->sb_datalen + TCP_SNDSPACE);
        !           606:                        
        !           607:                        /* Adjust all values */
        !           608:                        lprint_sb->sb_wptr = lprint_sb->sb_data + deltaw;
        !           609:                        lprint_sb->sb_rptr = lprint_sb->sb_data + deltar;
        !           610:                        lprint_ptr =         lprint_sb->sb_data + deltap;
        !           611:                        
        !           612:                        lprint_sb->sb_datalen += TCP_SNDSPACE;
        !           613:                }
        !           614:        }
        !           615: #endif 
        !           616:        if (lprint_print)
        !           617:           lprint_ptr += (*lprint_print)(*lprint_arg, format, args);
        !           618:        
        !           619:        /* Check if they want output to be logged to file as well */
        !           620:        if (lfd) {
        !           621:                /* 
        !           622:                 * Remove \r's
        !           623:                 * otherwise you'll get ^M all over the file
        !           624:                 */
        !           625:                int len = strlen(format);
        !           626:                char *bptr1, *bptr2;
        !           627:                
        !           628:                bptr1 = bptr2 = strdup(format);
        !           629:                
        !           630:                while (len--) {
        !           631:                        if (*bptr1 == '\r')
        !           632:                           memcpy(bptr1, bptr1+1, len+1);
        !           633:                        else
        !           634:                           bptr1++;
        !           635:                }
        !           636:                vfprintf(lfd, bptr2, args);
        !           637:                free(bptr2);
        !           638:        }
        !           639:        va_end(args);
        !           640: }
        !           641: 
        !           642: void
        !           643: add_emu(buff)
        !           644:        char *buff;
        !           645: {
        !           646:        u_int lport, fport;
        !           647:        u_int8_t tos = 0, emu = 0;
        !           648:        char buff1[256], buff2[256], buff4[128];
        !           649:        char *buff3 = buff4;
        !           650:        struct emu_t *emup;
        !           651:        struct socket *so;
        !           652:        
        !           653:        if (sscanf(buff, "%256s %256s", buff2, buff1) != 2) {
        !           654:                lprint("Error: Bad arguments\r\n");
        !           655:                return;
        !           656:        }
        !           657:        
        !           658:        if (sscanf(buff1, "%d:%d", &lport, &fport) != 2) {
        !           659:                lport = 0;
        !           660:                if (sscanf(buff1, "%d", &fport) != 1) {
        !           661:                        lprint("Error: Bad first argument\r\n");
        !           662:                        return;
        !           663:                }
        !           664:        }
        !           665:        
        !           666:        if (sscanf(buff2, "%128[^:]:%128s", buff1, buff3) != 2) {
        !           667:                buff3 = 0;
        !           668:                if (sscanf(buff2, "%256s", buff1) != 1) {
        !           669:                        lprint("Error: Bad second argument\r\n");
        !           670:                        return;
        !           671:                }
        !           672:        }
        !           673:        
        !           674:        if (buff3) {
        !           675:                if (strcmp(buff3, "lowdelay") == 0)
        !           676:                   tos = IPTOS_LOWDELAY;
        !           677:                else if (strcmp(buff3, "throughput") == 0)
        !           678:                   tos = IPTOS_THROUGHPUT;
        !           679:                else {
        !           680:                        lprint("Error: Expecting \"lowdelay\"/\"throughput\"\r\n");
        !           681:                        return;
        !           682:                }
        !           683:        }
        !           684:        
        !           685:        if (strcmp(buff1, "ftp") == 0)
        !           686:           emu = EMU_FTP;
        !           687:        else if (strcmp(buff1, "irc") == 0)
        !           688:           emu = EMU_IRC;
        !           689:        else if (strcmp(buff1, "none") == 0)
        !           690:           emu = EMU_NONE; /* ie: no emulation */
        !           691:        else {
        !           692:                lprint("Error: Unknown service\r\n");
        !           693:                return;
        !           694:        }
        !           695:        
        !           696:        /* First, check that it isn't already emulated */
        !           697:        for (emup = tcpemu; emup; emup = emup->next) {
        !           698:                if (emup->lport == lport && emup->fport == fport) {
        !           699:                        lprint("Error: port already emulated\r\n");
        !           700:                        return;
        !           701:                }
        !           702:        }
        !           703:        
        !           704:        /* link it */
        !           705:        emup = (struct emu_t *)malloc(sizeof (struct emu_t));
        !           706:        emup->lport = (u_int16_t)lport;
        !           707:        emup->fport = (u_int16_t)fport;
        !           708:        emup->tos = tos;
        !           709:        emup->emu = emu;
        !           710:        emup->next = tcpemu;
        !           711:        tcpemu = emup;
        !           712:        
        !           713:        /* And finally, mark all current sessions, if any, as being emulated */
        !           714:        for (so = tcb.so_next; so != &tcb; so = so->so_next) {
        !           715:                if ((lport && lport == ntohs(so->so_lport)) ||
        !           716:                    (fport && fport == ntohs(so->so_fport))) {
        !           717:                        if (emu)
        !           718:                           so->so_emu = emu;
        !           719:                        if (tos)
        !           720:                           so->so_iptos = tos;
        !           721:                }
        !           722:        }
        !           723:        
        !           724:        lprint("Adding emulation for %s to port %d/%d\r\n", buff1, emup->lport, emup->fport);
        !           725: }
        !           726: 
        !           727: #ifdef BAD_SPRINTF
        !           728: 
        !           729: #undef vsprintf
        !           730: #undef sprintf
        !           731: 
        !           732: /*
        !           733:  * Some BSD-derived systems have a sprintf which returns char *
        !           734:  */
        !           735: 
        !           736: int
        !           737: vsprintf_len(string, format, args)
        !           738:        char *string;
        !           739:        const char *format;
        !           740:        va_list args;
        !           741: {
        !           742:        vsprintf(string, format, args);
        !           743:        return strlen(string);
        !           744: }
        !           745: 
        !           746: int
        !           747: #ifdef __STDC__
        !           748: sprintf_len(char *string, const char *format, ...)
        !           749: #else
        !           750: sprintf_len(va_alist) va_dcl
        !           751: #endif
        !           752: {
        !           753:        va_list args;
        !           754: #ifdef __STDC__
        !           755:        va_start(args, format);
        !           756: #else
        !           757:        char *string;
        !           758:        char *format;
        !           759:        va_start(args);
        !           760:        string = va_arg(args, char *);
        !           761:        format = va_arg(args, char *);
        !           762: #endif
        !           763:        vsprintf(string, format, args);
        !           764:        return strlen(string);
        !           765: }
        !           766: 
        !           767: #endif
        !           768: 
        !           769: void
        !           770: u_sleep(usec)
        !           771:        int usec;
        !           772: {
        !           773:        struct timeval t;
        !           774:        fd_set fdset;
        !           775:        
        !           776:        FD_ZERO(&fdset);
        !           777:        
        !           778:        t.tv_sec = 0;
        !           779:        t.tv_usec = usec * 1000;
        !           780:        
        !           781:        select(0, &fdset, &fdset, &fdset, &t);
        !           782: }
        !           783: 
        !           784: /*
        !           785:  * Set fd blocking and non-blocking
        !           786:  */
        !           787: 
        !           788: void
        !           789: fd_nonblock(fd)
        !           790:        int fd;
        !           791: {
        !           792: #if defined USE_FIONBIO && defined FIONBIO
        !           793:        ioctlsockopt_t opt = 1;
        !           794:        
        !           795:        ioctlsocket(fd, FIONBIO, &opt);
        !           796: #else
        !           797:        int opt;
        !           798:        
        !           799:        opt = fcntl(fd, F_GETFL, 0);
        !           800:        opt |= O_NONBLOCK;
        !           801:        fcntl(fd, F_SETFL, opt);
        !           802: #endif
        !           803: }
        !           804: 
        !           805: void
        !           806: fd_block(fd)
        !           807:        int fd;
        !           808: {
        !           809: #if defined USE_FIONBIO && defined FIONBIO
        !           810:        ioctlsockopt_t opt = 0;
        !           811:        
        !           812:        ioctlsocket(fd, FIONBIO, &opt);
        !           813: #else
        !           814:        int opt;
        !           815:        
        !           816:        opt = fcntl(fd, F_GETFL, 0);
        !           817:        opt &= ~O_NONBLOCK;
        !           818:        fcntl(fd, F_SETFL, opt);
        !           819: #endif
        !           820: }
        !           821: 
        !           822: 
        !           823: #if 0
        !           824: /*
        !           825:  * invoke RSH
        !           826:  */
        !           827: int
        !           828: rsh_exec(so,ns, user, host, args)
        !           829:        struct socket *so;
        !           830:        struct socket *ns;
        !           831:        char *user;
        !           832:        char *host;
        !           833:        char *args;
        !           834: {
        !           835:        int fd[2];
        !           836:        int fd0[2];
        !           837:        int s;
        !           838:        char buff[256];
        !           839:        
        !           840:        DEBUG_CALL("rsh_exec");
        !           841:        DEBUG_ARG("so = %lx", (long)so);
        !           842:        
        !           843:        if (pipe(fd)<0) {
        !           844:           lprint("Error: pipe failed: %s\n", strerror(errno));
        !           845:           return 0;
        !           846:        }
        !           847: /* #ifdef HAVE_SOCKETPAIR */
        !           848: #if 1
        !           849:         if (socketpair(PF_UNIX,SOCK_STREAM,0, fd0) == -1) {
        !           850:           close(fd[0]);
        !           851:           close(fd[1]);
        !           852:           lprint("Error: openpty failed: %s\n", strerror(errno));
        !           853:           return 0;
        !           854:         }
        !           855: #else
        !           856:         if (slirp_openpty(&fd0[0], &fd0[1]) == -1) {
        !           857:           close(fd[0]);
        !           858:           close(fd[1]);
        !           859:           lprint("Error: openpty failed: %s\n", strerror(errno));
        !           860:           return 0;
        !           861:         }
        !           862: #endif
        !           863:        
        !           864:        switch(fork()) {
        !           865:         case -1:
        !           866:            lprint("Error: fork failed: %s\n", strerror(errno));
        !           867:            close(fd[0]);
        !           868:            close(fd[1]);
        !           869:            close(fd0[0]);
        !           870:            close(fd0[1]);
        !           871:            return 0;
        !           872:            
        !           873:         case 0:
        !           874:            close(fd[0]);
        !           875:            close(fd0[0]);
        !           876:            
        !           877:                /* Set the DISPLAY */
        !           878:            if (x_port >= 0) {
        !           879: #ifdef HAVE_SETENV
        !           880:              sprintf(buff, "%s:%d.%d", inet_ntoa(our_addr), x_port, x_screen);
        !           881:              setenv("DISPLAY", buff, 1);
        !           882: #else
        !           883:              sprintf(buff, "DISPLAY=%s:%d.%d", inet_ntoa(our_addr), x_port, x_screen);
        !           884:              putenv(buff);
        !           885: #endif
        !           886:            }
        !           887:            
        !           888:            dup2(fd0[1], 0);
        !           889:            dup2(fd0[1], 1);
        !           890:            dup2(fd[1], 2);
        !           891:            for (s = 3; s <= 255; s++)
        !           892:              close(s);
        !           893:            
        !           894:            execlp("rsh","rsh","-l", user, host, args, NULL);
        !           895:            
        !           896:            /* Ooops, failed, let's tell the user why */
        !           897:            
        !           898:            sprintf(buff, "Error: execlp of %s failed: %s\n", 
        !           899:                    "rsh", strerror(errno));
        !           900:            write(2, buff, strlen(buff)+1);
        !           901:            close(0); close(1); close(2); /* XXX */
        !           902:            exit(1);
        !           903:            
        !           904:         default:
        !           905:           close(fd[1]);
        !           906:           close(fd0[1]);
        !           907:           ns->s=fd[0];
        !           908:           so->s=fd0[0];
        !           909:           
        !           910:           return 1;
        !           911:        }
        !           912: }
        !           913: #endif

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.