home *** CD-ROM | disk | FTP | other *** search
/ PC-Online 1996 May / PCOnline_05_1996.bin / linux / source / n / tcpip / netkit-a.06 / netkit-a / NetKit-A-0.06 / dip337d-uri / command.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-07-01  |  20.7 KB  |  1,047 lines

  1. /*
  2.  * dip        A program for handling dialup IP connecions.
  3.  *        Script language processor.
  4.  *
  5.  * Version:    @(#)command.c    3.3.5    12/13/93
  6.  *
  7.  * Author:      Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG>
  8.  *        Copyright 1988-1993 MicroWalt Corporation
  9.  *
  10.  *        This program is free software; you can redistribute it
  11.  *        and/or  modify it under  the terms of  the GNU General
  12.  *        Public  License as  published  by  the  Free  Software
  13.  *        Foundation;  either  version 2 of the License, or  (at
  14.  *        your option) any later version.
  15.  */
  16. #include "dip.h"
  17.  
  18.  
  19. struct commands {
  20.   char    *name;
  21.   int    (*func)(int, char **);
  22. };
  23.  
  24.  
  25. static int    timeout;        /* script "wait" timed out    */
  26. static int    errlevel;        /* script command return code    */
  27. static FILE    *scriptfp = (FILE *)NULL;    /* input script pointer    */
  28. static char    *var_modem = NULL;    /* name of modem we are using    */
  29. static char    *var_port = NULL;    /* terminal line used        */
  30. static char    *var_speed = NULL;    /* terminal line speed        */
  31. static int    var_echo = 0;        /* enable line data echoing    */
  32.  
  33.  
  34. static void
  35. TimeOut(int sig)
  36. {
  37.   (void) sig;
  38.   timeout = 1;
  39. }
  40.  
  41.  
  42. /* Convert a C-style backslash sequence to ASCII. */
  43. static char
  44. cvt_char(char c)
  45. {
  46.   if (c == '\0') return(c);
  47.   switch(c) {
  48.     case 'a':
  49.         return('\a');
  50.  
  51.     case 'b':
  52.  
  53.         return('\b');
  54.  
  55.     case 'f':
  56.         return('\f');
  57.  
  58.     case 'n':
  59.         return('\n');
  60.  
  61.     case 'r':
  62.         return('\r');
  63.  
  64.     case 's':
  65.         return(' ');
  66.  
  67.     case 't':
  68.         return('\t');
  69.  
  70.     case 'v':
  71.         return('\v');
  72.  
  73.     case '\\':
  74.         return('\\');
  75.  
  76.     case '\'':
  77.         return('\'');
  78.  
  79.     case '"':
  80.         return('\"');
  81.  
  82.     case '?':
  83.         return('\?');
  84.  
  85.     default:
  86.         return('?');
  87.   }
  88.   /* NOTREACHED */
  89.   return('?');
  90. }
  91.  
  92.  
  93. /* Split the input string into multiple fields. */
  94. static int
  95. getargs(char *string, char *arguments[])
  96. {
  97.   char *sp;
  98.   int argc;
  99.   int i;
  100.  
  101.   sp = string; i = 0;
  102.   arguments[i] = sp;
  103.   while (*sp && i < 32) {
  104.         while (*sp && (*sp == ' ' || *sp == '\t')) sp++;
  105.         arguments[i++] = sp;
  106.         while (*sp && *sp != ' ' && *sp != '\t') sp++;
  107.         if (*sp != '\0') *sp++ = '\0';
  108.   }
  109.   argc = i;
  110.   while (i < 32) arguments[i++] = (char *)NULL;
  111.   return(argc);
  112. }
  113.  
  114.  
  115. /************************************************************************
  116.  *                                    *
  117.  *        Internal Scripting Commands                *
  118.  *                                    *
  119.  ************************************************************************/
  120.  
  121. /* Enable/Disable echoing of data from terminal line. */
  122. static int
  123. do_echo(int argc, char *argv[])
  124. {
  125.   if (argc != 2) {
  126.     fprintf(stderr, "Usage: echo on|off\n");
  127.     return(-1);
  128.   }
  129.   
  130.   if (strcmp(argv[1], "on") == 0) var_echo = 1;
  131.     else if (strcmp(argv[1], "off") == 0) var_echo = 0;
  132.     else {
  133.     fprintf(stderr, "Usage: echo on|off\n");
  134.     return(-1);
  135.   }
  136.     
  137.   if (opt_v == 1) printf("Display modem output: %sabled\n",
  138.                 (var_echo == 0) ? "dis" : "en");
  139.   return(0);
  140. }
  141.  
  142.  
  143. /* Go to some label in the script. */
  144. static int
  145. do_goto(int argc, char *argv[])
  146. {
  147.   char buff[1024];
  148.   off_t oldpos;
  149.   char *label, *xp;
  150.   char *sp;
  151.  
  152.   if (argc != 2) {
  153.     fprintf(stderr, "Usage: goto label\n");
  154.     return(-1);
  155.   }
  156.   if (scriptfp == stdin) {
  157.     fprintf(stderr, "dip: GOTO not possible in TEST mode!\n");
  158.     return(-1);
  159.   }
  160.  
  161.   label = argv[1];
  162.   oldpos = ftell(scriptfp);
  163.   rewind(scriptfp);
  164.   (void) fflush(scriptfp);
  165.  
  166.   do {
  167.         if (fgets(buff, 1024, scriptfp) == (char *)NULL) break;
  168.     if ((sp = strchr(buff, '\n')) != (char *)NULL) *sp = '\0';
  169.     sp = buff;
  170.     while (*sp == ' ' || *sp == '\t') sp++;
  171.     if (*sp == '#' || *sp == '\0') continue;
  172.     if ((xp = strchr(sp, ':')) == (char *)NULL) continue;
  173.     *xp = '\0';
  174.     if (! strcmp(label, sp)) {
  175.         oldpos = ftell(scriptfp);
  176.         (void) fseek(scriptfp, oldpos, SEEK_SET);
  177.         return(0);
  178.     }
  179.   } while(1);
  180.   (void) fseek(scriptfp, oldpos, SEEK_SET);
  181.   (void) fflush(scriptfp);
  182.   return(-1);
  183. }
  184.  
  185.  
  186. /* Check some error (result) code. */
  187. static int
  188. do_if(int argc, char *argv[])
  189. {
  190.   char *cmd[3];
  191.   char opcode;
  192.   long val, var;
  193.   int ret;
  194.  
  195.   if (argc != 6) {
  196.     fprintf(stderr, "Usage: if expr goto label\n");
  197.     return(-1);
  198.   };
  199.   if (! strcmp(argv[2], "==")) opcode = '=';
  200.     else if (! strcmp(argv[2], "!=")) opcode = '@';
  201.     else if (! strcmp(argv[2], "<")) opcode = '<';
  202.     else if (! strcmp(argv[2], ">")) opcode = '>';
  203.     else if (! strcmp(argv[2], "<=")) opcode = 'L';
  204.     else if (! strcmp(argv[2], ">=")) opcode = 'G';
  205.     else {
  206.     fprintf(stderr, "Syntax error: \"%s\" is not an opcode!\n", argv[2]);
  207.     return(-1);
  208.   }
  209.   val = (long) atol(argv[3]);
  210.  
  211.   if (! strcmp(argv[1], "$errlvl")) var = (long) errlevel;
  212.     else if (! strcmp(argv[1], "$locip")) var = (long) mydip.loc_ip.s_addr;
  213.     else if (! strcmp(argv[1], "$rmtip")) var = (long) mydip.rmt_ip.s_addr;
  214.     else {
  215.     fprintf(stderr, "Invalid variable \"%s\" !\n", argv[1]);
  216.     return(-1);
  217.   }
  218.  
  219.   ret = -1;
  220.   switch(opcode) {
  221.     case '=':    /* EQUAL */
  222.         ret = (var == val);
  223.         break;
  224.  
  225.     case '@':    /* NOT EQUAL */
  226.         ret = (var != val);
  227.         break;
  228.  
  229.     case '<':    /* LESS */
  230.         ret = (var < val);
  231.         break;
  232.  
  233.     case 'L':    /* LESS-EQ */
  234.         ret = (var <= val);
  235.         break;
  236.  
  237.     case '>':    /* GREATER */
  238.         ret = (var > val);
  239.         break;
  240.  
  241.     case 'G':    /* GREATER-EQ */
  242.         ret = (var >= val);
  243.         break;
  244.   }
  245.  
  246.   if (strcmp(argv[4], "goto")) {
  247.     fprintf(stderr, "Warning: keyword not \"goto\" !\n");
  248.     argv[4] = "goto";
  249.   }
  250.  
  251.   if (ret != 0) {
  252.     cmd[1] = argv[4];
  253.     cmd[1] = argv[5];
  254.     cmd[2] = (char *)NULL;
  255.     return(do_goto(2, cmd));
  256.   }
  257.   return(-1);
  258. }
  259.  
  260.  
  261. /* Print the contents of some variable. */
  262. static int
  263. do_print(int argc, char *argv[])
  264. {
  265.   char *sp;
  266.   int i;
  267.  
  268.   if (argc == 1) {
  269.     printf("\n");
  270.     return(0);
  271.   }
  272.   i = 0;
  273.   while (argv[++i] != (char *)NULL) {
  274.     sp = argv[i];
  275.     if (i != 1) printf(" ");
  276.     if (*sp == '$') {
  277.         if (! strcmp(++sp, "errlvl")) printf("%d", errlevel);
  278.           else if (! strcmp(sp, "locip")) printf("%s",
  279.                     inet_ntoa(mydip.loc_ip));
  280.           else if (! strcmp(sp, "rmtip")) printf("%s",
  281.                     inet_ntoa(mydip.rmt_ip));
  282.           else if (! strcmp(sp, "local")) printf("%s", mydip.local);
  283.           else if (! strcmp(sp, "remote")) printf("%s", mydip.remote);
  284.           else if (! strcmp(sp, "modem")) printf("%s", var_modem);
  285.           else if (! strcmp(sp, "port")) printf("%s", var_port);
  286.           else if (! strcmp(sp, "speed")) printf("%s", var_speed);
  287.           else fprintf(stderr, "Unknown variable %s\n", sp);
  288.     } else printf("%s", sp);
  289.   }
  290.   printf("\n");
  291.   return(0);
  292. }
  293.  
  294.  
  295. /* Send a string to the serial driver. */
  296. static int
  297. do_send(int argc, char *argv[])
  298. {
  299.   char *sp;
  300.   char c;
  301.   int i;
  302.   
  303.   if (argc < 2) {
  304.     fprintf(stderr, "Usage: send text...\n");
  305.     return(-1);
  306.   }
  307.  
  308.   for (i = 1; i < argc; i++) {
  309.       sp = argv[i];
  310.       while(*sp != '\0') {
  311.         switch(*sp) {
  312.             case '~':
  313.                 tty_putc('\r');
  314.                 tty_putc('\n');
  315.                 break;
  316.  
  317.             case '\\':
  318.                 sp++;
  319.                 c = cvt_char(*sp);
  320.                 tty_putc((int) c);
  321.                 break;
  322.  
  323.             default:
  324.                 c = *sp;
  325.                 tty_putc((int) c);
  326.         }
  327.         sp++;
  328.       }
  329.         if (i < (argc - 1)) tty_putc(' ');
  330.   }
  331.   tty_putc(-1);        /* flush the connection */
  332.   return(0);
  333. }
  334.  
  335.  
  336. /* Wait some time. */
  337. static int
  338. do_sleep(int argc, char *argv[])
  339. {
  340.   int secs;
  341.  
  342.   if (argc != 2) {
  343.     fprintf(stderr, "Usage: sleep time_in_secs\n");
  344.     return(-1);
  345.   }
  346.  
  347.   secs = atoi(argv[1]);
  348.   (void) sleep(secs);
  349.   return(0);
  350. }
  351.  
  352.  
  353. /* Flush tty input */
  354. static int
  355. do_flush(int argc, char *argv[])
  356. {
  357.   if (argc != 1) {
  358.     fprintf(stderr, "Usage: flush\n");
  359.     return(-1);
  360.   }
  361.  
  362.   tty_flush();
  363.   return(0);
  364. }
  365.  
  366.  
  367. /* Wait for some string to arrive. */
  368. static int
  369. do_wait(int argc, char *argv[])
  370. {
  371.   char c, c2, *p;
  372.   int howlong;
  373.   void (*oldsig)(int);
  374.  
  375.   if (argc == 1 || argc > 3) {
  376.     fprintf(stderr, "Usage: wait text [timeout_value]\n");
  377.     return(-1);
  378.   }
  379.  
  380.   if (argc == 3) howlong = atoi(argv[2]);
  381.     else howlong = 0;
  382.   oldsig = signal(SIGALRM, TimeOut);
  383.   (void) alarm(howlong);
  384.  
  385.   p = argv[1];
  386.   timeout = 0;
  387.   while(!timeout && *p != '\0') {
  388.     c = (char) tty_getc();
  389.     c &= 0177;
  390.     if (var_echo == 1) {
  391.         fputc(c, stdout);
  392.         fflush(stdout);
  393.     }
  394.     if (timeout == 1) break;
  395.     if (*p == '\\') c2 = cvt_char(*++p);
  396.       else c2 = *p;
  397.     if (c2 != c) p = argv[1];
  398.       else p++;
  399.   }
  400.   (void) alarm(0);
  401.   (void) signal(SIGALRM, oldsig);
  402.   return((timeout == 1) ? -1 : 0);
  403. }
  404.  
  405.  
  406. /* Show some help. */
  407. static int
  408. do_help(int argc, char *argv[])
  409. {
  410.   extern struct commands commands[];
  411.   int i, j;
  412.  
  413.   i = 0; j = 0;
  414.   printf("DIP knows about the following commands:\n\n");
  415.   while (commands[i].name != (char *)NULL) {
  416.     if (j++ == 0) printf("\t");
  417.     printf("%-8.8s ", commands[i].name);
  418.     if (j == 5) {
  419.         printf("\n");
  420.         j = 0;
  421.     }
  422.     i++;
  423.   }
  424.   if (j != 0) printf("\n\n");
  425.     else printf("\n");
  426.   return(0);
  427. }
  428.  
  429.  
  430. /************************************************************************
  431.  *                                    *
  432.  *        Modem Handling and Dialing Commands            *
  433.  *                                    *
  434.  ************************************************************************/
  435.  
  436.  
  437. /* Set the name of the terminal port to use. */
  438. static int
  439. do_port(int argc, char *argv[])
  440. {
  441.   if (argc != 2) {
  442.     fprintf(stderr, "Usage: port tty_name\n");
  443.     return(-1);
  444.   }
  445.   if (var_port != NULL) {
  446.     fprintf(stderr, "PORT: terminal port already set to \"%s\".\n",
  447.                                 var_port);
  448.     return(-1);
  449.   }
  450.   var_port = argv[1];
  451.   if (opt_v == 1) printf("PORT: terminal port set to \"%s\".\n", var_port);
  452.  
  453.   /* Initialize the terminal line. */
  454.   if (tty_open(var_port) < 0) {
  455.     var_port = NULL;
  456.     return(-1);
  457.   }
  458.  
  459.   return(0);
  460. }
  461.  
  462.  
  463. /* Set the correct DATABITS to use. */
  464. static int
  465. do_databits(int argc, char *argv[])
  466. {
  467.   if (argc != 2) {
  468.         fprintf(stderr, "Usage: databits bits\n");
  469.         return(-1);
  470.   }
  471.   if (var_port == NULL) { 
  472.         fprintf(stderr, "Please set PORT first.\n");
  473.         return(-1);
  474.   }  
  475.   return(tty_databits(argv[1]));
  476. }
  477.  
  478.  
  479. /* Define a modem "INIT" string. */
  480. static int
  481. do_init(int argc, char *argv[])
  482. {
  483.   if (argc != 2) {
  484.     fprintf(stderr, "Usage: init <init string>\n");
  485.     return(-1);
  486.   }
  487.   return(mdm_init(argv[1]));
  488. }
  489.  
  490.  
  491. static int
  492. do_dial(int argc, char *argv[])
  493. {
  494.   if (argc != 2) {
  495.     fprintf(stderr, "Usage: dial telno\n");
  496.     return(-1);
  497.   }
  498.  
  499.   if (var_modem == NULL) {
  500.     fprintf(stderr, "Please set MODEM first.\n");
  501.     return(-1);
  502.   }
  503.   return(mdm_dial(argv[1]));
  504. }
  505.  
  506.  
  507. /* Set the name of the modem we want to use. */
  508. static int
  509. do_modem(int argc, char *argv[])
  510. {
  511.   if (argc != 2) {
  512.     fprintf(stderr, "Usage: modem modem_name\n");
  513.     return(-1);
  514.   }
  515.   if (var_modem != NULL) {
  516.     fprintf(stderr, "MODEM: modem already set to \"%s\".\n", var_modem);
  517.     return(-1);
  518.   }
  519.   var_modem = argv[1];
  520.   if (opt_v == 1) printf("MODEM: modem set to \"%s\".\n", var_modem);
  521.  
  522.   /* Initialize this modem. */
  523.   if (mdm_modem(var_modem) < 0) {
  524.     var_modem = NULL;
  525.     return(-1);
  526.   }
  527.  
  528.   return(0);
  529. }
  530.  
  531.  
  532. static int
  533. do_parity(int argc, char *argv[])
  534. {
  535.   if (argc != 2) {
  536.         fprintf(stderr, "Usage: parity E/O/N\n");
  537.         return(-1);
  538.   }
  539.  
  540.   if (var_port == NULL) {
  541.         fprintf(stderr, "Please set PORT first.\n");
  542.         return(-1);
  543.   }
  544.   return(tty_parity(argv[1]));
  545. }
  546.  
  547.  
  548. /* Reset the modem. */
  549. static int
  550. do_reset(int argc, char *argv[])
  551. {
  552.   if (argc != 1) {
  553.     fprintf(stderr, "Usage: reset\n");
  554.     return(-1);
  555.   }
  556.  
  557.   /* Did we get a modem to work with? */
  558.   if (var_modem == NULL) {
  559.     fprintf(stderr, "Please set MODEM first.\n");
  560.     return(-1);
  561.   }
  562.  
  563.   /* Reset the modem. */
  564.   (void) mdm_reset();
  565.   return(0);
  566. }
  567.  
  568.  
  569. /* Set the correct SPEED to use. */
  570. static int
  571. do_speed(int argc, char *argv[])
  572. {
  573.   if (argc != 2) {
  574.     fprintf(stderr, "Usage: speed baudrate\n");
  575.     return(-1);
  576.   }
  577.   if (var_port == NULL) {
  578.     fprintf(stderr, "Please set PORT first.\n");
  579.     return(-1);
  580.   }
  581.   return(tty_speed(argv[1]));
  582. }
  583.  
  584.  
  585. /* Set the correct STOPBITS to use. */
  586. static int
  587. do_stopbits(int argc, char *argv[])
  588. {
  589.   if (argc != 2) {
  590.         fprintf(stderr, "Usage: stopbits bits\n");
  591.         return(-1);
  592.   }
  593.   if (var_port == NULL) {
  594.         fprintf(stderr, "Please set PORT first.\n");
  595.         return(-1);
  596.   }
  597.   return(tty_stopbits(argv[1]));
  598.  
  599.  
  600. /* Enter a TERMINAL mode. */
  601. static int
  602. do_term(int argc, char *argv[])
  603. {
  604.   if (argc != 1) {
  605.     fprintf(stderr, "Usage: term\n");
  606.     return(-1);
  607.   }
  608.   if (var_port == NULL) {
  609.     fprintf(stderr, "Please set PORT first.\n");
  610.     return(-1);
  611.   }
  612.   do_terminal();
  613.   return(0);
  614. }
  615.  
  616.  
  617. /************************************************************************
  618.  *                                    *
  619.  *        Connection Setup Commands                *
  620.  *                                    *
  621.  ************************************************************************/
  622.  
  623. /*
  624.  * Get or ask for the value of a variable.
  625.  * Get local IP#, Remote IP# and MTU
  626.  */
  627.  
  628. #define VAR_IP        1
  629. #define VAR_NUM        2
  630. #define VAR_STR        3
  631.  
  632. static int
  633. do_get(int argc, char *argv[])
  634. {
  635.   char str[128] = "";
  636.   int var = 0;
  637.   void *v1 = NULL, *v2 = NULL;
  638.   void (*oldsig)(int);
  639.    
  640.   if (argc <= 2 || argc > 4 || argv[1][0] != '$') {
  641.      fprintf(stderr,
  642.         "Usage: get $variable [value|ask|remote [timeout_value]]\n");
  643.      return(-1);
  644.   }
  645.    
  646.   if (! strcmp(argv[1], "$locip") || !strcmp(argv[1], "$local")) {
  647.     v1 = (void *) mydip.local;
  648.     v2 = (void *) &mydip.loc_ip;
  649.     var = VAR_IP;
  650.   } else if (! strcmp(argv[1], "$rmtip") || !strcmp(argv[1], "$remote")) {
  651.     v1 = (void *) mydip.remote;
  652.     v2 = (void *) &mydip.rmt_ip;
  653.     var = VAR_IP;
  654.   } else if (! strcmp(argv[1], "$mtu")) {
  655.     v1 = (void *) &mydip.mtu;
  656.     var = VAR_NUM;
  657.   } else {
  658.      fprintf(stderr, "Variables must be :$locip|$rmtip|$local|$remote|$mtu\n");
  659.      return (-1);
  660.   }
  661.  
  662.   if (argc > 2) {
  663.     if (! strcmp(argv[2], "ask")) {
  664.         /* Ask the stdinput for the value of the variable. */
  665.         register char *sp;
  666.  
  667.         fprintf(stderr, "Enter the value for %s: ", argv[1]);
  668.         if (fgets(str, 128, stdin) == (char *)NULL) return(1);
  669.         if ((sp = strchr(str, '\n')) != (char *)NULL) *sp = '\0';
  670.     } else if (! strcmp(argv[2],"remote")) {
  671.         /* Get the variable string from the "remote" line */
  672.         register char c, *p;
  673.         int howlong = 0, state = 0;
  674.  
  675.         if (argc == 4) howlong = atoi(argv[3]);
  676.         oldsig = signal(SIGALRM, TimeOut);
  677.         (void) alarm(howlong);
  678.  
  679.         p = str;
  680.         timeout = 0;
  681.         state = 0;
  682.         if (var == VAR_IP || var == VAR_NUM) state = 1;
  683.         while(!timeout && (state >= 0)) {
  684.             c = (char) tty_getc();
  685.             c &= 0177;
  686.             if (timeout == 1) break;
  687.             switch (state) {
  688.                 case 0: /* throw away "white space" */
  689.                     if (! strchr(" \n\t", c)) break;
  690.                     if (var == VAR_STR) {
  691.                         *(p++) = c;
  692.                         state = 10;
  693.                         break;
  694.                     }
  695.                     state = 1;
  696.  
  697.                 case 1:
  698.                     if ( c >= '0' && c <= '9' ) {
  699.                         *(p++) = c;
  700.                         if (var == VAR_IP) {
  701.                             state = 2;
  702.                             break;
  703.                         } else state = 5;
  704.                         break;
  705.                     }
  706.                     break; 
  707.  
  708.                 case 2:
  709.                 case 3:
  710.                 case 4:
  711.                     if ((c >= '0' && c <= '9') || c == '.') {
  712.                         *(p++) = c;
  713.                         if (c == '.') state++;
  714.                         break;
  715.                     } 
  716.                     p = str;
  717.                     state = 0;
  718.                     break;
  719.                     case 5:
  720.                     if (c >= '0' && c <= '9') {
  721.                         *(p++) = c;
  722.                         break;
  723.                     } 
  724.                     state = -1;
  725.                     break;
  726.  
  727.                 case 10:
  728.                     if (strchr(" \n\t", c)) state = -1;
  729.                     else *(p++) = c;
  730.                     break;
  731.  
  732.                 default:
  733.                     break;
  734.             }
  735.         }
  736.         *p = '\0';
  737.         (void) alarm(0);
  738.         (void) signal(SIGALRM, oldsig);
  739.         if (timeout == 1) return (1);
  740.     } else {
  741.         /* The third argv is the value for the variable. */
  742.         strncpy(str, argv[2], 128);
  743.     }
  744.   }
  745.  
  746.   if (opt_v == 1) printf("About to set variable %s to %s\n", argv[1], str);
  747.  
  748.   if (*str) {
  749.     switch (var) {
  750.         case VAR_IP:
  751.             {
  752.                 struct hostent *hp;
  753.                 hp = gethostbyname(str);
  754.                 if (hp == (struct hostent *)NULL) {
  755.                     herror(str);
  756.                     return(-1);
  757.                 }
  758.                 strncpy((char *) v1, hp->h_name, 128);
  759.                 memcpy((char *) v2, (char *) hp->h_addr_list[0],
  760.                        hp->h_length);
  761.             }
  762.             break;
  763.  
  764.         case VAR_NUM:
  765.             *(int *) v1 = atoi(str);
  766.             break;
  767.  
  768.         case VAR_STR:
  769.             strcpy((char *) v1, str);
  770.             break;
  771.  
  772.         default:
  773.             break;
  774.     }
  775.   }
  776.  
  777.   return(0);
  778. }
  779.  
  780.  
  781. /* Enter a specific protocol. */
  782. static int
  783. do_mode(int argc, char *argv[])
  784. {
  785.   register int i;
  786.  
  787.   if ((argc != 2) ||
  788.       ((i = get_prot(argv[1])) == 0)) {
  789.     fprintf(stderr, "Usage: mode protocol_name\n");
  790.     return(-1);
  791.   }
  792.  
  793.   if (mydip.rmt_ip.s_addr == INADDR_ANY) {
  794.     fprintf(stderr, "Please set REMOTE first.\n");
  795.     return(-1);
  796.   }
  797.   mydip.protonr = i;
  798.  
  799.   /* Enter BACKGROUND mode here! */
  800.   (void) dip_daemon(&mydip);
  801.  
  802.   /*NOTREACHED*/
  803.   return(i);
  804. }
  805.  
  806. /* Quit upon error - reset the tty to the proper ldisc */
  807. static int
  808. do_quit(int argc, char *argv[])
  809. {
  810.   (void) tty_close();
  811.   exit(1);
  812. }
  813.  
  814. /* Store the netmask in "mydip" structure */
  815. static int
  816. do_netmask(int argc, char *argv[])
  817. {
  818.    if (argc != 2) {
  819.       fprintf(stderr, 
  820.               "Usage of this command: netmask xxx.xxx.xxx.xxx\n");
  821.       return(-1);
  822.    }
  823.    strcpy(mydip.netmask, argv[1]);
  824.    return(0);
  825. }
  826.  
  827. /* Set routing as default */
  828. static int
  829. do_default(int argc, char *argv[])
  830. {
  831.   if (argc != 1) {
  832.     fprintf(stderr, "Usage: default\n");
  833.     return(-1);
  834.   }
  835.   if (opt_v == 1) printf("Destination net/address set to 'default'\n");
  836.  
  837.   mydip.rtdefault = 1;
  838.   return(0);
  839. }
  840.  
  841.  
  842. /************************************************************************
  843.  *                                    *
  844.  *                Password Handling                    *
  845.  *                                    *
  846.  ************************************************************************/
  847.  
  848.  
  849. /* Prompt for a password to be sent */
  850. static int
  851.     do_password(int argc, char *argv[])
  852. {
  853.     char    *prompt = "Password:";
  854.     char    *pass[3];
  855.     
  856.     pass[0] = "send";        /* in case anyone cares */
  857.     pass[2] = NULL;        /* ditto */
  858.     
  859.     if (argc > 1)
  860.     prompt = argv[1];
  861.  
  862.     pass[1] = getpass(prompt);
  863.     do_send(2, &pass[0]);
  864.  
  865.     return(0);
  866. }
  867.  
  868. #ifdef SKEY
  869. /* scan the input stream for an S/Key challenge, prompt
  870.    the user for their secret password, generate the response
  871.    and send it to the remote host - simple....
  872.  
  873.    Parts of this code are based on skey.c in the S/Key package */
  874.  
  875. static int
  876.     do_skey(int    argc, char *argv[])
  877. {
  878.     char    buf[256];
  879.     char    *p = buf;
  880.     char    *sp;
  881.     char    c;
  882.     void    (*oldsig)(int);
  883.     int        howlong = 0;
  884.     int        challenge;
  885.     char    *seed, passwd[256], key[8];
  886.     char    response[33];
  887.     char    *param[4];
  888.  
  889.     if (argc > 2) {
  890.     fprintf(stderr, "Usage: skey [timeout]\n");
  891.     return(-1);
  892.     }
  893.  
  894.     if (argc == 2) howlong = atoi(argv[1]);
  895.     oldsig = signal(SIGALRM, TimeOut);
  896.     (void) alarm(howlong);
  897.     timeout = 0;
  898.  
  899.     while (!timeout) {
  900.     c = (char) tty_getc();
  901.     c &= 0177;
  902.     if (timeout) break;
  903.  
  904.     if (c == '\r') {
  905.         *p = '\0';
  906.         if (strncmp(buf, SKEY_CHALLENGE, strlen(SKEY_CHALLENGE)) == 0)
  907.         break;
  908.         else
  909.         p = buf;
  910.     }
  911.     else if (c != '\n') { /* just add the char to the buffer */
  912.         *p++ = c;
  913.     }
  914.     }
  915.  
  916.     (void) alarm(0);
  917.     (void) signal(SIGALRM, oldsig);
  918.     if (timeout == 1) return (1);
  919.  
  920.     if (opt_v == 1) printf("Challenge string <%s>\n", buf);
  921.  
  922.     p = buf + strlen(SKEY_CHALLENGE);
  923.     while (*p && (!isdigit((int) *p))) p++;
  924.     sp = p;
  925.     while (*p && isdigit((int) *p)) p++;
  926.     *p++ = '\0';
  927.     challenge = atoi(sp);
  928.  
  929.     while (*p && isspace((int) *p)) p++;
  930.     seed = p;
  931.     while (*p && (!isspace((int) *p)) && (*p != ']')) p++;
  932.     *p = '\0';
  933.  
  934.     printf ("Enter secret password: ");
  935.     readpass (passwd, sizeof (passwd));
  936.  
  937.     /* Crunch seed and password into starting key */
  938.     if (keycrunch (key, seed, passwd) != 0) {
  939.     fprintf (stderr, "%s: key crunch failed\n", argv[0]);
  940.     return(1);
  941.     }
  942.  
  943.     while (challenge-- != 0)
  944.     f (key);
  945.  
  946.     (void) btoe (response, key);
  947.  
  948.     /* build up our command for do_send */
  949.     param[0] = "send";
  950.     param[1] = response;
  951.     param[2] = "\r";
  952.     param[3] = NULL;
  953.  
  954.     return(do_send(3, ¶m[0]));
  955. }
  956. #endif /* SKEY */
  957.     
  958.  
  959. struct commands commands[] = {
  960.   { "databits",         do_databits     },
  961.   { "default",        do_default    },
  962.   { "dial",        do_dial        },
  963.   { "echo",        do_echo        },
  964.   { "flush",        do_flush    },
  965.   { "get",        do_get       },
  966.   { "goto",        do_goto        },
  967.   { "help",        do_help        },
  968.   { "if",        do_if        },
  969.   { "init",        do_init        },
  970.   { "mode",        do_mode        },
  971.   { "modem",        do_modem    },
  972.   { "netmask",          do_netmask      },
  973.   { "parity",           do_parity       },
  974.   { "password",        do_password    },
  975.   { "print",        do_print    },
  976.   { "port",        do_port        },
  977.   { "quit",             do_quit         },
  978.   { "reset",        do_reset    },
  979.   { "send",        do_send        },
  980. #ifdef SKEY
  981.   { "skey",        do_skey        },
  982. #endif
  983.   { "sleep",        do_sleep    },
  984.   { "speed",        do_speed    },
  985.   { "stopbits",         do_stopbits     },
  986.   { "term",        do_term        },
  987.   { "wait",        do_wait        },
  988.   { (char *)NULL,    NULL        }
  989. };
  990.  
  991.  
  992. void do_command(fp)
  993. FILE *fp;
  994. {
  995.   char cline[1024];
  996.   char *argv[32];
  997.   int argc, i;
  998.   int running;
  999.   register char *sp;
  1000.  
  1001.   /* Initialize the command level module. */
  1002.   var_modem = DEF_MODEM;
  1003.   var_speed = DEF_SPEED;
  1004.   scriptfp  = fp;
  1005.   running   = 1;
  1006.   timeout   = 0;
  1007.   errlevel  = 0;
  1008.  
  1009.   /* Tell the MODEM module about the current modem. */
  1010.   mdm_modem(var_modem);
  1011.  
  1012.   do {
  1013.     if (scriptfp == stdin) {
  1014.         if (opt_v == 1) printf("DIP [%-4d]> ", errlevel);
  1015.           else printf("DIP> ");
  1016.         fflush(stdout);
  1017.     }
  1018.         if (fgets(cline, 1024, scriptfp) == (char *)NULL) break;
  1019.     if ((sp = strchr(cline, '\n')) != (char *)NULL) *sp = '\0';
  1020.     sp = cline;
  1021.     while (*sp == ' ' || *sp == '\t') sp++;
  1022.     if (*sp == '#' || *sp == '\0') continue;
  1023.     if (opt_v) fprintf(stderr, ">> %s\n", sp);
  1024.     if ((argc = getargs(sp, argv)) == 0) continue;
  1025.  
  1026.     /* If this is a label, skip it. */
  1027.     if (strchr(argv[0], ':') != (char *)NULL) continue;
  1028.  
  1029.     /* Now, check which command it is. */
  1030.     if (strcmp(argv[0], "exit") != 0) {
  1031.         i = 0;
  1032.         while (commands[i].name != (char *)NULL) {
  1033.             if (!strcmp(commands[i].name, argv[0])) break;
  1034.             i++;
  1035.         }
  1036.         if (commands[i].name != (char *)NULL) {
  1037.             errlevel = (*commands[i].func)(argc, argv);
  1038.         } else printf("? Unknown command (%s).\n", argv[0]);
  1039.     } else running = 0;
  1040.   } while(running);
  1041.   tty_close();
  1042.  
  1043.   /*NOTREACHED*/
  1044.   exit(0);
  1045. }
  1046.