command.c revision 28461
16059Samurai/*
26059Samurai *		PPP User command processing module
36059Samurai *
46059Samurai *	    Written by Toshiharu OHNO (tony-o@iij.ad.jp)
56059Samurai *
66059Samurai *   Copyright (C) 1993, Internet Initiative Japan, Inc. All rights reserverd.
76059Samurai *
86059Samurai * Redistribution and use in source and binary forms are permitted
96059Samurai * provided that the above copyright notice and this paragraph are
106059Samurai * duplicated in all such forms and that any documentation,
116059Samurai * advertising materials, and other materials related to such
126059Samurai * distribution and use acknowledge that the software was developed
136059Samurai * by the Internet Initiative Japan, Inc.  The name of the
146059Samurai * IIJ may not be used to endorse or promote products derived
156059Samurai * from this software without specific prior written permission.
166059Samurai * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
176059Samurai * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
186059Samurai * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
198857Srgrimes *
2028461Sbrian * $Id: command.c,v 1.70 1997/08/19 01:10:19 brian Exp $
218857Srgrimes *
226059Samurai */
2313379Sphk#include <sys/types.h>
2427089Sbrian#include <sys/stat.h>
256059Samurai#include <ctype.h>
266735Samurai#include <termios.h>
2713385Speter#include <sys/wait.h>
2813379Sphk#include <time.h>
2926031Sbrian#include <netdb.h>
3026031Sbrian#include <sys/socket.h>
3126031Sbrian#include <netinet/in.h>
3226031Sbrian#include <arpa/inet.h>
3326031Sbrian#include <net/route.h>
3426031Sbrian#include <paths.h>
3526031Sbrian#include <alias.h>
3626516Sbrian#include <fcntl.h>
3726516Sbrian#include <errno.h>
386059Samurai#include "fsm.h"
396059Samurai#include "phase.h"
406059Samurai#include "lcp.h"
416059Samurai#include "ipcp.h"
426059Samurai#include "modem.h"
4313389Sphk#include "filter.h"
446059Samurai#include "command.h"
4526031Sbrian#include "alias_cmd.h"
466059Samurai#include "hdlc.h"
4726142Sbrian#include "loadalias.h"
486059Samurai#include "vars.h"
4925630Sbrian#include "systems.h"
5025630Sbrian#include "chat.h"
516059Samurai#include "os.h"
5226516Sbrian#include "timeout.h"
5326940Sbrian#include "server.h"
546059Samurai
556059Samuraiextern void Cleanup(), TtyTermMode(), PacketMode();
566059Samuraiextern int  EnableCommand(), DisableCommand(), DisplayCommand();
576059Samuraiextern int  AcceptCommand(), DenyCommand();
5826031Sbrianstatic int  AliasCommand();
596735Samuraiextern int  LocalAuthCommand();
606059Samuraiextern int  LoadCommand(), SaveCommand();
616059Samuraiextern int  ChangeParity(char *);
626059Samuraiextern int  SelectSystem();
636059Samuraiextern int  ShowRoute();
6410528Samuraiextern void TtyOldMode(), TtyCommandMode();
656735Samuraiextern struct pppvars pppVars;
6614418Sacheextern struct cmdtab const SetCommands[];
676059Samurai
6822973Sphkextern char *IfDevName;
6922973Sphk
706059Samuraistruct in_addr ifnetmask;
7123603Sacheint randinit;
726059Samurai
736059Samuraistatic int ShowCommand(), TerminalCommand(), QuitCommand();
746059Samuraistatic int CloseCommand(), DialCommand(), DownCommand();
756059Samuraistatic int SetCommand(), AddCommand(), DeleteCommand();
7628381Sbrianstatic int BgShellCommand(struct cmdtab *, int, char **);
7728381Sbrianstatic int FgShellCommand(struct cmdtab *, int, char **);
7828381Sbrianstatic int ShellCommand(struct cmdtab *, int, char **, int);
796059Samurai
806059Samuraistatic int
816059SamuraiHelpCommand(list, argc, argv, plist)
826059Samuraistruct cmdtab *list;
836059Samuraiint argc;
846059Samuraichar **argv;
856059Samuraistruct cmdtab *plist;
866059Samurai{
876059Samurai  struct cmdtab *cmd;
886059Samurai  int n;
896059Samurai
9026516Sbrian  if (!VarTerm)
9126516Sbrian    return 0;
9226516Sbrian
936059Samurai  if (argc > 0) {
9426516Sbrian    for (cmd = plist; cmd->name; cmd++)
9525566Sbrian      if (strcasecmp(cmd->name, *argv) == 0 && (cmd->lauth & VarLocalAuth)) {
9626516Sbrian        fprintf(VarTerm, "%s\n", cmd->syntax);
9726516Sbrian        return 0;
986059Samurai      }
9926516Sbrian
10026516Sbrian    return -1;
1016059Samurai  }
10226516Sbrian
1036059Samurai  n = 0;
10426516Sbrian  for (cmd = plist; cmd->func; cmd++)
1056764Samurai    if (cmd->name && (cmd->lauth & VarLocalAuth)) {
10626587Sbrian      fprintf(VarTerm, "  %-9s: %-20s\n", cmd->name, cmd->helpmes);
1076059Samurai      n++;
1086059Samurai    }
10926516Sbrian
1106059Samurai  if (n & 1)
11126516Sbrian    fprintf(VarTerm, "\n");
11226516Sbrian
11326516Sbrian  return 0;
1146059Samurai}
1156059Samurai
1166059Samuraiint
1176059SamuraiIsInteractive()
1186059Samurai{
1196059Samurai  char *mes = NULL;
1206059Samurai
12120120Snate  if (mode & MODE_DDIAL)
12220120Snate    mes = "Working in dedicated dial mode.";
12325908Sbrian  else if (mode & MODE_BACKGROUND)
12425908Sbrian    mes = "Working in background mode.";
12520120Snate  else if (mode & MODE_AUTO)
12610528Samurai    mes = "Working in auto mode.";
1276059Samurai  else if (mode & MODE_DIRECT)
12810528Samurai    mes = "Working in direct mode.";
1296059Samurai  else if (mode & MODE_DEDICATED)
13010528Samurai    mes = "Working in dedicated mode.";
1316059Samurai  if (mes) {
13226516Sbrian    if (VarTerm)
13326516Sbrian      fprintf(VarTerm, "%s\n", mes);
13426516Sbrian    return 0;
1356059Samurai  }
13626516Sbrian  return 1;
1376059Samurai}
1386059Samurai
1396059Samuraistatic int
1406059SamuraiDialCommand(cmdlist, argc, argv)
1416059Samuraistruct cmdtab *cmdlist;
1426059Samuraiint argc;
1436059Samuraichar **argv;
1446059Samurai{
14511336Samurai  int tries;
14626858Sbrian  int res;
14711336Samurai
1486059Samurai  if (LcpFsm.state > ST_CLOSED) {
14926516Sbrian    if (VarTerm)
15026516Sbrian      fprintf(VarTerm, "LCP state is [%s]\n", StateNames[LcpFsm.state]);
15126516Sbrian    return 0;
1526059Samurai  }
15326516Sbrian
1546059Samurai  if (!IsInteractive())
1556059Samurai    return(1);
15626516Sbrian
1576735Samurai  if (argc > 0) {
1586735Samurai    if (SelectSystem(*argv, CONFFILE) < 0) {
15926516Sbrian      if (VarTerm)
16026516Sbrian        fprintf(VarTerm, "%s: not found.\n", *argv);
16126516Sbrian      return -1;
1626735Samurai    }
1636735Samurai  }
16426516Sbrian
16511336Samurai  tries = 0;
16611336Samurai  do {
16726516Sbrian    if (VarTerm)
16826516Sbrian      fprintf(VarTerm, "Dial attempt %u of %d\n", ++tries, VarDialTries);
16911336Samurai    modem = OpenModem(mode);
17011336Samurai    if (modem < 0) {
17126516Sbrian      if (VarTerm)
17226516Sbrian        fprintf(VarTerm, "Failed to open modem.\n");
17311336Samurai      break;
17411336Samurai    }
17526858Sbrian    if ((res = DialModem()) == EX_DONE) {
17611336Samurai      sleep(1);
17711336Samurai      ModemTimeout();
17811336Samurai      PacketMode();
17911336Samurai      break;
18026858Sbrian    } else if (res == EX_SIG)
18126858Sbrian      return 1;
18211336Samurai  } while (VarDialTries == 0 || tries < VarDialTries);
18326516Sbrian
18426516Sbrian  return 0;
1856059Samurai}
1866059Samurai
18710528Samuraistatic int
18828381SbrianBgShellCommand(struct cmdtab *cmdlist, int argc, char **argv)
18910528Samurai{
19028381Sbrian  if (argc == 0)
19128381Sbrian    return -1;
19228381Sbrian  return ShellCommand(cmdlist, argc, argv, 1);
19328381Sbrian}
19428381Sbrian
19528381Sbrianstatic int
19628381SbrianFgShellCommand(struct cmdtab *cmdlist, int argc, char **argv)
19728381Sbrian{
19828381Sbrian  return ShellCommand(cmdlist, argc, argv, 0);
19928381Sbrian}
20028381Sbrian
20128381Sbrianstatic int
20228381SbrianShellCommand(struct cmdtab *cmdlist, int argc, char **argv, int bg)
20328381Sbrian{
20410528Samurai  const char *shell;
20510528Samurai  pid_t shpid;
20626516Sbrian  FILE *oVarTerm;
20720813Sjkh
20818856Ssos#ifdef SHELL_ONLY_INTERACTIVELY
20926911Sbrian  /* we're only allowed to shell when we run ppp interactively */
21026516Sbrian  if (mode != MODE_INTER) {
21126516Sbrian    LogPrintf(LogWARN, "Can only start a shell in interactive mode\n");
21226516Sbrian    return 1;
21310528Samurai  }
21426911Sbrian#endif
21526911Sbrian#ifdef NO_SHELL_IN_AUTO_INTERACTIVE
21626911Sbrian  /*
21726911Sbrian   * we want to stop shell commands when we've got a telnet connection
21826911Sbrian   * to an auto mode ppp
21926911Sbrian   */
22026516Sbrian  if ((mode & (MODE_AUTO|MODE_INTER)) == (MODE_AUTO|MODE_INTER)) {
22126516Sbrian    LogPrintf(LogWARN,  "Shell is not allowed interactively in auto mode\n");
22226516Sbrian    return 1;
22326516Sbrian  }
22426516Sbrian#endif
22526516Sbrian
22628381Sbrian  if(argc == 0)
22728381Sbrian    if (!(mode & MODE_INTER)) {
22828381Sbrian      LogPrintf(LogWARN, "Can only start an interactive shell in"
22928381Sbrian	        " interactive mode\n");
23028381Sbrian      return 1;
23128381Sbrian    } else if (bg) {
23228381Sbrian      LogPrintf(LogWARN, "Can only start an interactive shell in"
23328381Sbrian	        " the foreground mode\n");
23428381Sbrian      return 1;
23528381Sbrian    }
23626516Sbrian
23726516Sbrian  if((shell = getenv("SHELL")) == 0)
23826516Sbrian    shell = _PATH_BSHELL;
23926516Sbrian
24010528Samurai  if((shpid = fork()) == 0) {
24126516Sbrian     int dtablesize, i, fd;
24218531Sbde
24326516Sbrian     if (VarTerm)
24426516Sbrian       fd = fileno(VarTerm);
24526516Sbrian     else if ((fd = open("/dev/null", O_RDWR)) == -1) {
24626516Sbrian       LogPrintf(LogALERT, "Failed to open /dev/null: %s\n", strerror(errno));
24726516Sbrian       exit(1);
24826516Sbrian     }
24926516Sbrian
25026516Sbrian     for (i = 0; i < 3; i++)
25126516Sbrian       dup2(fd, i);
25226516Sbrian
25326516Sbrian     if (fd > 2)
25426516Sbrian       if (VarTerm) {
25526516Sbrian	 oVarTerm = VarTerm;
25626516Sbrian	 VarTerm = 0;
25726516Sbrian         if (oVarTerm && oVarTerm != stdout)
25826516Sbrian           fclose(oVarTerm);
25926516Sbrian       } else
26026516Sbrian         close(fd);
26126516Sbrian
26218531Sbde     for (dtablesize = getdtablesize(), i = 3; i < dtablesize; i++)
26310528Samurai	(void)close(i);
26410528Samurai
26510528Samurai     /*
26610528Samurai      * We are running setuid, we should change to
26710528Samurai      * real user for avoiding security problems.
26810528Samurai      */
26916263Sache     if (setgid(getgid()) < 0) {
27026516Sbrian        LogPrintf(LogERROR, "setgid: %s\n", strerror(errno));
27116263Sache	exit(1);
27216263Sache     }
27316263Sache     if (setuid(getuid()) < 0) {
27426516Sbrian        LogPrintf(LogERROR, "setuid: %s\n", strerror(errno));
27516263Sache	exit(1);
27616263Sache     }
27710528Samurai     TtyOldMode();
27818790Ssos     if(argc > 0) {
27918790Ssos       /* substitute pseudo args */
28027011Sbrian       for (i=1; i<argc; i++)
28127011Sbrian         if (strcasecmp(argv[i], "HISADDR") == 0)
28218790Ssos           argv[i] = strdup(inet_ntoa(IpcpInfo.his_ipaddr));
28327011Sbrian         else if (strcasecmp(argv[i], "INTERFACE") == 0)
28422973Sphk           argv[i] = strdup(IfDevName);
28527011Sbrian         else if (strcasecmp(argv[i], "MYADDR") == 0)
28618790Ssos           argv[i] = strdup(inet_ntoa(IpcpInfo.want_ipaddr));
28728381Sbrian       if (bg) {
28828381Sbrian         pid_t p;
28928381Sbrian         p = getpid();
29028381Sbrian         if (daemon(1,1) == -1) {
29128381Sbrian           LogPrintf(LogERROR, "%d: daemon: %s", p, strerror(errno));
29228381Sbrian           exit(1);
29328381Sbrian         }
29428381Sbrian       }
29525630Sbrian       (void)execvp(argv[0], argv);
29618790Ssos     }
29710528Samurai     else
29825630Sbrian       (void)execl(shell, shell, NULL);
29920813Sjkh
30026516Sbrian     LogPrintf(LogWARN, "exec() of %s failed\n", argc > 0 ? argv[0] : shell);
30110528Samurai     exit(255);
30210528Samurai  }
30326516Sbrian
30410528Samurai  if( shpid == (pid_t)-1 ) {
30526516Sbrian    LogPrintf(LogERROR, "Fork failed: %s\n", strerror(errno));
30610528Samurai  } else {
30710528Samurai    int status;
30810528Samurai    (void)waitpid(shpid, &status, 0);
30910528Samurai  }
31020813Sjkh
31110528Samurai  TtyCommandMode(1);
31220813Sjkh
31310528Samurai  return(0);
31410528Samurai}
31510528Samurai
31613760Sphkstruct cmdtab const Commands[] = {
3176735Samurai  { "accept",  NULL,    AcceptCommand,	LOCAL_AUTH,
31826516Sbrian  	"accept option request",	"accept option .."},
3196735Samurai  { "add",     NULL,	AddCommand,	LOCAL_AUTH,
32026516Sbrian	"add route",			"add dest mask gateway"},
32128381Sbrian  { "bg",   "!bg",      BgShellCommand,   LOCAL_AUTH,
32228381Sbrian	"Run a command in the background",  "[!]bg command"},
3236735Samurai  { "close",   NULL,    CloseCommand,	LOCAL_AUTH,
32426516Sbrian	"Close connection",		"close"},
3256735Samurai  { "delete",  NULL,    DeleteCommand,	LOCAL_AUTH,
32626591Sbrian	"delete route",                 "delete ALL | dest [gateway [mask]]"},
3276735Samurai  { "deny",    NULL,    DenyCommand,	LOCAL_AUTH,
32826516Sbrian  	"Deny option request",		"deny option .."},
3296735Samurai  { "dial",    "call",  DialCommand,	LOCAL_AUTH,
33026516Sbrian  	"Dial and login",		"dial|call [remote]"},
3316735Samurai  { "disable", NULL,    DisableCommand,	LOCAL_AUTH,
33226516Sbrian  	"Disable option",		"disable option .."},
3336735Samurai  { "display", NULL,    DisplayCommand,	LOCAL_AUTH,
33426516Sbrian  	"Display option configs",	"display"},
3356735Samurai  { "enable",  NULL,    EnableCommand,	LOCAL_AUTH,
33626516Sbrian  	"Enable option",		"enable option .."},
3376764Samurai  { "passwd",  NULL,	LocalAuthCommand,LOCAL_NO_AUTH,
33826516Sbrian  	"Password for manipulation", "passwd option .."},
3396735Samurai  { "load",    NULL,    LoadCommand,	LOCAL_AUTH,
34026516Sbrian  	"Load settings",		"load [remote]"},
3416735Samurai  { "save",    NULL,    SaveCommand,	LOCAL_AUTH,
34226516Sbrian  	"Save settings", "save"},
3436735Samurai  { "set",     "setup", SetCommand,	LOCAL_AUTH,
34426516Sbrian  	"Set parameters",  "set[up] var value"},
34528381Sbrian  { "shell",   "!",     FgShellCommand,   LOCAL_AUTH,
34626516Sbrian	"Run a subshell",  "shell|! [sh command]"},
3476735Samurai  { "show",    NULL,    ShowCommand,	LOCAL_AUTH,
34826516Sbrian  	"Show status and statictics", "show var"},
3496735Samurai  { "term",    NULL,    TerminalCommand,LOCAL_AUTH,
35026516Sbrian  	"Enter to terminal mode", "term"},
35126031Sbrian  { "alias",   NULL,    AliasCommand,   LOCAL_AUTH,
35226516Sbrian        "alias control",        "alias option [yes|no]"},
3536764Samurai  { "quit",    "bye",   QuitCommand,	LOCAL_AUTH | LOCAL_NO_AUTH,
35426516Sbrian	"Quit PPP program", "quit|bye [all]"},
3556735Samurai  { "help",    "?",     HelpCommand,	LOCAL_AUTH | LOCAL_NO_AUTH,
35626516Sbrian	"Display this message", "help|? [command]", (void *)Commands },
3576735Samurai  { NULL,      "down",  DownCommand,	LOCAL_AUTH,
35826516Sbrian  	"Generate down event",		"down"},
3596059Samurai  { NULL,      NULL,    NULL },
3606059Samurai};
3616059Samurai
3626059Samuraiextern int ReportCcpStatus();
3636059Samuraiextern int ReportLcpStatus();
3646059Samuraiextern int ReportIpcpStatus();
3656059Samuraiextern int ReportProtStatus();
3666059Samuraiextern int ReportCompress();
3676059Samuraiextern int ShowModemStatus();
3686059Samuraiextern int ReportHdlcStatus();
3696059Samuraiextern int ShowMemMap();
3706059Samurai
37126516Sbrianstatic int ShowLogLevel()
3726059Samurai{
3736059Samurai  int i;
3746059Samurai
37526516Sbrian  if (!VarTerm)
37626516Sbrian    return 0;
37726516Sbrian  fprintf(VarTerm, "Log:");
37826516Sbrian  for (i = LogMIN; i < LogMAXCONF; i++) {
37926516Sbrian    if (LogIsKept(i))
38026516Sbrian      fprintf(VarTerm, " %s", LogName(i));
3816059Samurai  }
38226516Sbrian  fprintf(VarTerm, "\n");
38326516Sbrian
38426516Sbrian  return 0;
3856059Samurai}
3866059Samurai
3876059Samuraistatic int ShowEscape()
3886059Samurai{
3896059Samurai  int code, bit;
3906059Samurai
39126516Sbrian  if (!VarTerm)
39226516Sbrian    return 0;
3936059Samurai  if (EscMap[32]) {
39426516Sbrian    for (code = 0; code < 32; code++)
39526516Sbrian      if (EscMap[code])
39626516Sbrian        for (bit = 0; bit < 8; bit++)
39726516Sbrian          if (EscMap[code] & (1<<bit))
39826516Sbrian            fprintf(VarTerm, " 0x%02x", (code << 3) + bit);
39926516Sbrian    fprintf(VarTerm, "\n");
4006059Samurai  }
40126516Sbrian  return 1;
4026059Samurai}
4036059Samurai
4046059Samuraistatic int ShowTimeout()
4056059Samurai{
40626516Sbrian  if (!VarTerm)
40726516Sbrian    return 0;
40826516Sbrian  fprintf(VarTerm, " Idle Timer: %d secs   LQR Timer: %d secs"
40926516Sbrian          "   Retry Timer: %d secs\n", VarIdleTimeout, VarLqrTimeout,
41026516Sbrian          VarRetryTimeout);
41126516Sbrian  return 1;
4126059Samurai}
4136059Samurai
41428327Sbrianstatic int ShowStopped()
41528327Sbrian{
41628327Sbrian  if (!VarTerm)
41728327Sbrian    return 0;
41828461Sbrian
41928461Sbrian  fprintf(VarTerm, " Stopped Timer:  LCP: ");
42028461Sbrian  if (!LcpFsm.StoppedTimer.load)
42128461Sbrian    fprintf(VarTerm, "Disabled");
42228327Sbrian  else
42328461Sbrian    fprintf(VarTerm, "%ld secs", LcpFsm.StoppedTimer.load / SECTICKS);
42428461Sbrian
42528461Sbrian  fprintf(VarTerm, ", IPCP: ");
42628461Sbrian  if (!IpcpFsm.StoppedTimer.load)
42728461Sbrian    fprintf(VarTerm, "Disabled");
42828461Sbrian  else
42928461Sbrian    fprintf(VarTerm, "%ld secs", IpcpFsm.StoppedTimer.load / SECTICKS);
43028461Sbrian
43128461Sbrian  fprintf(VarTerm, ", CCP: ");
43228461Sbrian  if (!CcpFsm.StoppedTimer.load)
43328461Sbrian    fprintf(VarTerm, "Disabled");
43428461Sbrian  else
43528461Sbrian    fprintf(VarTerm, "%ld secs", CcpFsm.StoppedTimer.load / SECTICKS);
43628461Sbrian
43728461Sbrian  fprintf(VarTerm, "\n");
43828461Sbrian
43928327Sbrian  return 1;
44028327Sbrian}
44128327Sbrian
4426059Samuraistatic int ShowAuthKey()
4436059Samurai{
44426516Sbrian  if (!VarTerm)
44526516Sbrian    return 0;
44626516Sbrian  fprintf(VarTerm, "AuthName = %s\n", VarAuthName);
44726516Sbrian  fprintf(VarTerm, "AuthKey  = %s\n", VarAuthKey);
44826516Sbrian  return 1;
4496059Samurai}
4506059Samurai
4516059Samuraistatic int ShowVersion()
4526059Samurai{
45313389Sphk  extern char VarVersion[];
45413389Sphk  extern char VarLocalVersion[];
4556059Samurai
45626516Sbrian  if (!VarTerm)
45726516Sbrian    return 0;
45826516Sbrian  fprintf(VarTerm, "%s - %s \n", VarVersion, VarLocalVersion);
45926516Sbrian  return 1;
4606059Samurai}
4616059Samurai
46226326Sbrianstatic int ShowInitialMRU()
46326326Sbrian{
46426516Sbrian  if (!VarTerm)
46526516Sbrian    return 0;
46626516Sbrian  fprintf(VarTerm, " Initial MRU: %ld\n", VarMRU);
46726516Sbrian  return 1;
46826326Sbrian}
46926326Sbrian
47026326Sbrianstatic int ShowPreferredMTU()
47126326Sbrian{
47226516Sbrian  if (!VarTerm)
47326516Sbrian    return 0;
47426326Sbrian  if (VarPrefMTU)
47526516Sbrian    fprintf(VarTerm, " Preferred MTU: %ld\n", VarPrefMTU);
47626326Sbrian  else
47726516Sbrian    fprintf(VarTerm, " Preferred MTU: unspecified\n");
47826516Sbrian  return 1;
47926326Sbrian}
48026326Sbrian
48125067Sbrianstatic int ShowReconnect()
48225067Sbrian{
48326516Sbrian  if (!VarTerm)
48426516Sbrian    return 0;
48526516Sbrian  fprintf(VarTerm, " Reconnect Timer:  %d,  %d tries\n",
48625067Sbrian         VarReconnectTimer, VarReconnectTries);
48726516Sbrian  return 1;
48825067Sbrian}
48925067Sbrian
49011336Samuraistatic int ShowRedial()
49111336Samurai{
49226516Sbrian  if (!VarTerm)
49326516Sbrian    return 0;
49426516Sbrian  fprintf(VarTerm, " Redial Timer: ");
49511336Samurai
49611336Samurai  if (VarRedialTimeout >= 0) {
49726516Sbrian    fprintf(VarTerm, " %d seconds, ", VarRedialTimeout);
49811336Samurai  }
49911336Samurai  else {
50026516Sbrian    fprintf(VarTerm, " Random 0 - %d seconds, ", REDIAL_PERIOD);
50111336Samurai  }
50211336Samurai
50326516Sbrian  fprintf(VarTerm, " Redial Next Timer: ");
50424939Sbrian
50524939Sbrian  if (VarRedialNextTimeout >= 0) {
50626516Sbrian    fprintf(VarTerm, " %d seconds, ", VarRedialNextTimeout);
50724939Sbrian  }
50824939Sbrian  else {
50926516Sbrian    fprintf(VarTerm, " Random 0 - %d seconds, ", REDIAL_PERIOD);
51024939Sbrian  }
51124939Sbrian
51211336Samurai  if (VarDialTries)
51326516Sbrian      fprintf(VarTerm, "%d dial tries", VarDialTries);
51411336Samurai
51526516Sbrian  fprintf(VarTerm, "\n");
51611336Samurai
51726516Sbrian  return 1;
51811336Samurai}
51911336Samurai
52026516Sbrian#ifndef NOMSEXT
52118752Sjkhstatic int ShowMSExt()
52218752Sjkh{
52326516Sbrian  if (!VarTerm)
52426516Sbrian    return 0;
52526516Sbrian  fprintf(VarTerm, " MS PPP extention values \n" );
52626516Sbrian  fprintf(VarTerm, "   Primary NS     : %s\n", inet_ntoa( ns_entries[0] ));
52726516Sbrian  fprintf(VarTerm, "   Secondary NS   : %s\n", inet_ntoa( ns_entries[1] ));
52826516Sbrian  fprintf(VarTerm, "   Primary NBNS   : %s\n", inet_ntoa( nbns_entries[0] ));
52926516Sbrian  fprintf(VarTerm, "   Secondary NBNS : %s\n", inet_ntoa( nbns_entries[1] ));
53026516Sbrian  return 1;
53118752Sjkh}
53226516Sbrian#endif
53318752Sjkh
5346735Samuraiextern int ShowIfilter(), ShowOfilter(), ShowDfilter(), ShowAfilter();
5356059Samurai
53613760Sphkstruct cmdtab const ShowCommands[] = {
5376735Samurai  { "afilter",  NULL,     ShowAfilter,		LOCAL_AUTH,
53826516Sbrian	"Show keep Alive filters", "show afilter option .."},
5396735Samurai  { "auth",     NULL,     ShowAuthKey,		LOCAL_AUTH,
54026516Sbrian	"Show auth name/key", "show auth"},
5416735Samurai  { "ccp",      NULL,     ReportCcpStatus,	LOCAL_AUTH,
54226516Sbrian	"Show CCP status", "show cpp"},
5436735Samurai  { "compress", NULL,     ReportCompress,	LOCAL_AUTH,
54426516Sbrian	"Show compression statictics", "show compress"},
5456735Samurai  { "dfilter",  NULL,     ShowDfilter,		LOCAL_AUTH,
54626516Sbrian	"Show Demand filters", "show dfilteroption .."},
5476735Samurai  { "escape",   NULL,     ShowEscape,		LOCAL_AUTH,
54826516Sbrian	"Show escape characters", "show escape"},
5496735Samurai  { "hdlc",	NULL,	  ReportHdlcStatus,	LOCAL_AUTH,
55026516Sbrian	"Show HDLC error summary", "show hdlc"},
5516735Samurai  { "ifilter",  NULL,     ShowIfilter,		LOCAL_AUTH,
55226516Sbrian	"Show Input filters", "show ifilter option .."},
5536735Samurai  { "ipcp",     NULL,     ReportIpcpStatus,	LOCAL_AUTH,
55426516Sbrian	"Show IPCP status", "show ipcp"},
5556735Samurai  { "lcp",      NULL,     ReportLcpStatus,	LOCAL_AUTH,
55626516Sbrian	"Show LCP status", "show lcp"},
55726516Sbrian  { "log",	NULL,	  ShowLogLevel,	LOCAL_AUTH,
55826516Sbrian	"Show current log level", "show log"},
5596735Samurai  { "mem",      NULL,     ShowMemMap,		LOCAL_AUTH,
56026516Sbrian	"Show memory map", "show mem"},
5616735Samurai  { "modem",    NULL,     ShowModemStatus,	LOCAL_AUTH,
56226516Sbrian	"Show modem setups", "show modem"},
56326326Sbrian  { "mru",      NULL,     ShowInitialMRU,	LOCAL_AUTH,
56426516Sbrian	"Show Initial MRU", "show mru"},
56526326Sbrian  { "mtu",      NULL,     ShowPreferredMTU,	LOCAL_AUTH,
56626516Sbrian	"Show Preferred MTU", "show mtu"},
5676735Samurai  { "ofilter",  NULL,     ShowOfilter,		LOCAL_AUTH,
56826516Sbrian	"Show Output filters", "show ofilter option .."},
5696735Samurai  { "proto",    NULL,     ReportProtStatus,	LOCAL_AUTH,
57026516Sbrian	"Show protocol summary", "show proto"},
57125067Sbrian  { "reconnect",NULL,	  ShowReconnect,	LOCAL_AUTH,
57226516Sbrian	"Show Reconnect timer,tries", "show reconnect"},
57325067Sbrian  { "redial",   NULL,	  ShowRedial,		LOCAL_AUTH,
57426516Sbrian	"Show Redial timeout value", "show redial"},
5756735Samurai  { "route",    NULL,     ShowRoute,		LOCAL_AUTH,
57626516Sbrian	"Show routing table", "show route"},
5776735Samurai  { "timeout",  NULL,	  ShowTimeout,		LOCAL_AUTH,
57826516Sbrian	"Show Idle timeout value", "show timeout"},
57928327Sbrian  { "stopped",  NULL,	  ShowStopped,		LOCAL_AUTH,
58028327Sbrian	"Show STOPPED timeout value", "show stopped"},
58126516Sbrian#ifndef NOMSEXT
58218752Sjkh  { "msext", 	NULL,	  ShowMSExt,		LOCAL_AUTH,
58326516Sbrian	"Show MS PPP extentions", "show msext"},
58426516Sbrian#endif
5856735Samurai  { "version",  NULL,	  ShowVersion,		LOCAL_NO_AUTH | LOCAL_AUTH,
58626516Sbrian	"Show version string", "show version"},
5876735Samurai  { "help",     "?",      HelpCommand,		LOCAL_NO_AUTH | LOCAL_AUTH,
58826698Sbrian	"Display this message", "show help|? [command]", (void *)ShowCommands},
5896059Samurai  { NULL,       NULL,     NULL },
5906059Samurai};
5916059Samurai
5926059Samuraistruct cmdtab *
5936059SamuraiFindCommand(cmds, str, pmatch)
5946059Samuraistruct cmdtab *cmds;
5956059Samuraichar *str;
5966059Samuraiint *pmatch;
5976059Samurai{
59826516Sbrian  int nmatch;
59926516Sbrian  int len;
60026516Sbrian  struct cmdtab *found;
6016059Samurai
60226516Sbrian  found = NULL;
60326516Sbrian  len = strlen(str);
60426516Sbrian  nmatch = 0;
6056059Samurai  while (cmds->func) {
60625566Sbrian    if (cmds->name && strncasecmp(str, cmds->name, len) == 0) {
60726516Sbrian      if (cmds->name[len] == '\0') {
60826516Sbrian        *pmatch = 1;
60926516Sbrian        return cmds;
61026516Sbrian      }
6116059Samurai      nmatch++;
6126059Samurai      found = cmds;
61326516Sbrian    } else if(cmds->alias && strncasecmp(str, cmds->alias, len) == 0) {
61426516Sbrian      if (cmds->alias[len] == '\0') {
61526516Sbrian        *pmatch = 1;
61626516Sbrian        return cmds;
61726516Sbrian      }
6186059Samurai      nmatch++;
6196059Samurai      found = cmds;
6206059Samurai    }
6216059Samurai    cmds++;
6226059Samurai  }
6236059Samurai  *pmatch = nmatch;
62426516Sbrian  return found;
6256059Samurai}
6266059Samurai
6276059Samuraiint
6286059SamuraiFindExec(cmdlist, argc, argv)
6296059Samuraistruct cmdtab *cmdlist;
6306059Samuraiint argc;
6316059Samuraichar **argv;
6326059Samurai{
6336059Samurai  struct cmdtab *cmd;
6346059Samurai  int val = 1;
6356059Samurai  int nmatch;
6366059Samurai
6376059Samurai  cmd = FindCommand(cmdlist, *argv, &nmatch);
6386059Samurai  if (nmatch > 1)
63926516Sbrian    LogPrintf(LogWARN, "%s: Ambiguous command\n", *argv);
6406735Samurai  else if (cmd && ( cmd->lauth & VarLocalAuth ) )
6416059Samurai    val = (cmd->func)(cmd, --argc, ++argv, cmd->args);
6426059Samurai  else
64326516Sbrian    LogPrintf(LogWARN, "%s: Invalid command\n", *argv);
64426516Sbrian
64526516Sbrian  if (val == -1)
64626516Sbrian    LogPrintf(LogWARN, "Usage: %s\n", cmd->syntax);
64726516Sbrian  else if(val)
64826516Sbrian    LogPrintf(LogCOMMAND, "%s: Failed %d\n", *argv, val);
64926516Sbrian
65026516Sbrian  return val;
6516059Samurai}
6526059Samurai
65318885Sjkhint aft_cmd = 1;
65426516Sbrianextern int TermMode;
65518885Sjkh
6566059Samuraivoid
65718885SjkhPrompt()
6586059Samurai{
6596735Samurai  char *pconnect, *pauth;
6606735Samurai
66126516Sbrian  if (!(mode & MODE_INTER) || !VarTerm || TermMode)
6626059Samurai    return;
6636735Samurai
66418885Sjkh  if (!aft_cmd)
66526516Sbrian    fprintf(VarTerm, "\n");
66618885Sjkh  else
66718885Sjkh    aft_cmd = 0;
6686735Samurai
6696735Samurai  if ( VarLocalAuth == LOCAL_AUTH )
6706735Samurai    pauth = " ON ";
6716735Samurai  else
6726735Samurai    pauth = " on ";
6736059Samurai  if (IpcpFsm.state == ST_OPENED && phase == PHASE_NETWORK)
6746735Samurai    pconnect = "PPP";
6756059Samurai  else
6766735Samurai    pconnect = "ppp";
67726516Sbrian  fprintf(VarTerm, "%s%s%s> ", pconnect, pauth, VarShortHost);
67826516Sbrian  fflush(VarTerm);
6796059Samurai}
6806059Samurai
6816059Samuraivoid
6826059SamuraiDecodeCommand(buff, nb, prompt)
6836059Samuraichar *buff;
6846059Samuraiint nb;
6856059Samuraiint prompt;
6866059Samurai{
6876059Samurai  char *vector[20];
6886059Samurai  char **argv;
68926516Sbrian  int argc;
6906059Samurai  char *cp;
6916059Samurai
6926059Samurai  if (nb > 0) {
6936059Samurai    cp = buff + strcspn(buff, "\r\n");
6946059Samurai    if (cp)
6956059Samurai      *cp = '\0';
69626516Sbrian    argc = MakeArgs(buff, vector, VECSIZE(vector));
69726516Sbrian    argv = vector;
6986059Samurai
69926516Sbrian    if (argc > 0)
70026516Sbrian      FindExec(Commands, argc, argv);
7016059Samurai  }
70226516Sbrian  if (prompt)
70325630Sbrian    Prompt();
7046059Samurai}
7056059Samurai
7066059Samuraistatic int
7076059SamuraiShowCommand(list, argc, argv)
7086059Samuraistruct cmdtab *list;
7096059Samuraiint argc;
7106059Samuraichar **argv;
7116059Samurai{
7126059Samurai  if (argc > 0)
71326516Sbrian    FindExec(ShowCommands, argc, argv);
71426516Sbrian  else if (VarTerm)
71526516Sbrian    fprintf(VarTerm, "Use ``show ?'' to get a list.\n");
7166059Samurai  else
71726516Sbrian    LogPrintf(LogWARN, "show command must have arguments\n");
71826516Sbrian
71926516Sbrian  return 0;
7206059Samurai}
7216059Samurai
7226059Samuraistatic int
7236059SamuraiTerminalCommand()
7246059Samurai{
7256059Samurai  if (LcpFsm.state > ST_CLOSED) {
72626516Sbrian    if (VarTerm)
72726516Sbrian      fprintf(VarTerm, "LCP state is [%s]\n", StateNames[LcpFsm.state]);
72826516Sbrian    return 1;
7296059Samurai  }
7306059Samurai  if (!IsInteractive())
7316059Samurai    return(1);
7326059Samurai  modem = OpenModem(mode);
7336059Samurai  if (modem < 0) {
73426516Sbrian    if (VarTerm)
73526516Sbrian      fprintf(VarTerm, "Failed to open modem.\n");
7366059Samurai    return(1);
7376059Samurai  }
73826516Sbrian  if (VarTerm) {
73926516Sbrian    fprintf(VarTerm, "Enter to terminal mode.\n");
74026516Sbrian    fprintf(VarTerm, "Type `~?' for help.\n");
74126516Sbrian  }
7426059Samurai  TtyTermMode();
7436059Samurai  return(0);
7446059Samurai}
7456059Samurai
7466059Samuraistatic int
7476059SamuraiQuitCommand(list, argc, argv)
7486059Samuraistruct cmdtab *list;
7496059Samuraiint argc;
7506059Samuraichar **argv;
7516059Samurai{
75226516Sbrian  FILE *oVarTerm;
75326516Sbrian
7546059Samurai  if (mode & (MODE_DIRECT|MODE_DEDICATED|MODE_AUTO)) {
7556764Samurai    if (argc > 0 && (VarLocalAuth & LOCAL_AUTH)) {
7566059Samurai      Cleanup(EX_NORMAL);
75718911Ssos      mode &= ~MODE_INTER;
75826516Sbrian      oVarTerm = VarTerm;
75926516Sbrian      VarTerm = 0;
76026516Sbrian      if (oVarTerm && oVarTerm != stdout)
76126516Sbrian        fclose(oVarTerm);
7626059Samurai    } else {
76326516Sbrian      LogPrintf(LogPHASE, "Client connection closed.\n");
7646735Samurai      VarLocalAuth = LOCAL_NO_AUTH;
76526516Sbrian      mode &= ~MODE_INTER;
76626516Sbrian      oVarTerm = VarTerm;
76726516Sbrian      VarTerm = 0;
76826516Sbrian      if (oVarTerm && oVarTerm != stdout)
76926516Sbrian        fclose(oVarTerm);
7706059Samurai      close(netfd);
7716059Samurai      netfd = -1;
7726059Samurai    }
7736059Samurai  } else
7746059Samurai    Cleanup(EX_NORMAL);
77526516Sbrian
77626516Sbrian  return 0;
7776059Samurai}
7786059Samurai
7796059Samuraistatic int
7806059SamuraiCloseCommand()
7816059Samurai{
78226098Sbrian  reconnect(RECON_FALSE);
7836059Samurai  LcpClose();
78425908Sbrian  if (mode & MODE_BACKGROUND)
78525908Sbrian      Cleanup(EX_NORMAL);
78626516Sbrian  return 0;
7876059Samurai}
7886059Samurai
7896059Samuraistatic int
7906059SamuraiDownCommand()
7916059Samurai{
7926059Samurai  LcpDown();
79326516Sbrian  return 0;
7946059Samurai}
7956059Samurai
79625067Sbrianstatic int
79725067SbrianSetModemSpeed(list, argc, argv)
7986059Samuraistruct cmdtab *list;
7996059Samuraiint argc;
8006059Samuraichar **argv;
8016059Samurai{
8026059Samurai  int speed;
8036059Samurai
8046059Samurai  if (argc > 0) {
8056735Samurai    if (strcmp(*argv, "sync") == 0) {
8066735Samurai      VarSpeed = 0;
80726516Sbrian      return 0;
8086735Samurai    }
8096059Samurai    speed = atoi(*argv);
8106735Samurai    if (IntToSpeed(speed) != B0) {
8116735Samurai      VarSpeed = speed;
81226516Sbrian      return 0;
8136059Samurai    }
81426516Sbrian    LogPrintf(LogWARN, "%s: Invalid speed\n", *argv);
8156059Samurai  }
81626516Sbrian  return -1;
8176059Samurai}
8186059Samurai
81925067Sbrianstatic int
82025067SbrianSetReconnect(list, argc, argv)
82111336Samuraistruct cmdtab *list;
82211336Samuraiint argc;
82311336Samuraichar **argv;
82411336Samurai{
82525067Sbrian  if (argc == 2) {
82625067Sbrian    VarReconnectTimer = atoi(argv[0]);
82725067Sbrian    VarReconnectTries = atoi(argv[1]);
82826516Sbrian    return 0;
82926516Sbrian  }
83026516Sbrian
83126516Sbrian  return -1;
83225067Sbrian}
83325067Sbrian
83425067Sbrianstatic int
83525067SbrianSetRedialTimeout(list, argc, argv)
83625067Sbrianstruct cmdtab *list;
83725067Sbrianint argc;
83825067Sbrianchar **argv;
83925067Sbrian{
84011336Samurai  int timeout;
84111336Samurai  int tries;
84224939Sbrian  char *dot;
84311336Samurai
84411336Samurai  if (argc == 1 || argc == 2 ) {
84524939Sbrian    if (strncasecmp(argv[0], "random", 6) == 0 &&
84624939Sbrian	(argv[0][6] == '\0' || argv[0][6] == '.')) {
84711336Samurai      VarRedialTimeout = -1;
84823603Sache      if (!randinit) {
84923603Sache	randinit = 1;
85026626Sache	srandomdev();
85123603Sache      }
85226516Sbrian    } else {
85311336Samurai      timeout = atoi(argv[0]);
85411336Samurai
85526516Sbrian      if (timeout >= 0)
85611336Samurai	VarRedialTimeout = timeout;
85711336Samurai      else {
85826516Sbrian	LogPrintf(LogWARN, "Invalid redial timeout\n");
85926516Sbrian        return -1;
86011336Samurai      }
86111336Samurai    }
86224939Sbrian
86324939Sbrian    dot = index(argv[0],'.');
86424939Sbrian    if (dot) {
86524939Sbrian      if (strcasecmp(++dot, "random") == 0) {
86624939Sbrian        VarRedialNextTimeout = -1;
86724939Sbrian        if (!randinit) {
86824939Sbrian          randinit = 1;
86926626Sache	  srandomdev();
87024939Sbrian        }
87124939Sbrian      }
87224939Sbrian      else {
87324939Sbrian        timeout = atoi(dot);
87426516Sbrian        if (timeout >= 0)
87524939Sbrian          VarRedialNextTimeout = timeout;
87624939Sbrian        else {
87726516Sbrian          LogPrintf(LogWARN, "Invalid next redial timeout\n");
87826516Sbrian	  return -1;
87924939Sbrian        }
88024939Sbrian      }
88124939Sbrian    }
88224939Sbrian    else
88324939Sbrian      VarRedialNextTimeout = NEXT_REDIAL_PERIOD;   /* Default next timeout */
88424939Sbrian
88511336Samurai    if (argc == 2) {
88611336Samurai      tries = atoi(argv[1]);
88711336Samurai
88811336Samurai      if (tries >= 0) {
88926516Sbrian	VarDialTries = tries;
89026516Sbrian      } else {
89126516Sbrian	LogPrintf(LogWARN, "Invalid retry value\n");
89226516Sbrian	return 1;
89311336Samurai      }
89411336Samurai    }
89526516Sbrian    return 0;
89611336Samurai  }
89726516Sbrian
89826516Sbrian  return -1;
89911336Samurai}
90011336Samurai
90125067Sbrianstatic int
90228327SbrianSetStoppedTimeout(list, argc, argv)
90328327Sbrianstruct cmdtab *list;
90428327Sbrianint argc;
90528327Sbrianchar **argv;
90628327Sbrian{
90728461Sbrian  LcpFsm.StoppedTimer.load = 0;
90828461Sbrian  IpcpFsm.StoppedTimer.load = 0;
90928461Sbrian  CcpFsm.StoppedTimer.load = 0;
91028461Sbrian  if (argc <= 3) {
91128461Sbrian    if (argc > 0) {
91228461Sbrian      LcpFsm.StoppedTimer.load = atoi(argv[0]) * SECTICKS;
91328461Sbrian      if (argc > 1) {
91428461Sbrian        IpcpFsm.StoppedTimer.load = atoi(argv[1]) * SECTICKS;
91528461Sbrian        if (argc > 2)
91628461Sbrian          CcpFsm.StoppedTimer.load = atoi(argv[2]) * SECTICKS;
91728461Sbrian      }
91828461Sbrian    }
91928327Sbrian    return 0;
92028327Sbrian  }
92128327Sbrian  return -1;
92228327Sbrian}
92328327Sbrian
92428327Sbrianstatic int
92526940SbrianSetServer(list, argc, argv)
92626940Sbrianstruct cmdtab *list;
92726940Sbrianint argc;
92826940Sbrianchar **argv;
92926940Sbrian{
93026940Sbrian  int res = -1;
93126940Sbrian
93227089Sbrian  if (argc > 0 && argc < 3)
93326940Sbrian    if (strcasecmp(argv[0], "none") == 0) {
93426940Sbrian      ServerClose();
93526940Sbrian      LogPrintf(LogPHASE, "Disabling server port.\n");
93626940Sbrian      res = 0;
93727089Sbrian    } else if (*argv[0] == '/') {
93827089Sbrian      mode_t mask;
93927089Sbrian      umask(mask = umask(0));
94027089Sbrian      if (argc == 2) {
94127089Sbrian        unsigned m;
94227089Sbrian        if (sscanf(argv[1], "%o", &m) == 1)
94327089Sbrian          mask = m;
94427089Sbrian      }
94527089Sbrian      res = ServerLocalOpen(argv[0], mask);
94627346Sbrian    } else {
94727346Sbrian      int port;
94827346Sbrian      if (strspn(argv[0], "0123456789") != strlen(argv[0])) {
94927346Sbrian        struct servent *s;
95027346Sbrian        if ((s = getservbyname(argv[0], "tcp")) == NULL) {
95127346Sbrian          port = 0;
95227346Sbrian          LogPrintf(LogWARN, "%s: Invalid port or service\n", argv[0]);
95327346Sbrian        } else
95427346Sbrian          port = ntohs(s->s_port);
95527346Sbrian      } else
95627346Sbrian        port = atoi(argv[0]);
95727346Sbrian      if (port)
95827346Sbrian        res = ServerTcpOpen(port);
95927346Sbrian    }
96026940Sbrian
96126940Sbrian  return res;
96226940Sbrian}
96326940Sbrian
96426940Sbrianstatic int
96525067SbrianSetModemParity(list, argc, argv)
9666059Samuraistruct cmdtab *list;
9676059Samuraiint argc;
9686059Samuraichar **argv;
9696059Samurai{
97026845Sbrian  return argc > 0 ? ChangeParity(*argv) : -1;
9716059Samurai}
9726059Samurai
9736059Samuraistatic int
97426516SbrianSetLogLevel(list, argc, argv)
9756059Samuraistruct cmdtab *list;
9766059Samuraiint argc;
9776059Samuraichar **argv;
9786059Samurai{
97926516Sbrian  int i;
98026516Sbrian  int res;
98126516Sbrian  char *arg;
9826059Samurai
98326516Sbrian  res = 0;
98426516Sbrian  if (argc == 0 || (argv[0][0] != '+' && argv[0][0] != '-'))
98526516Sbrian    LogDiscardAll();
98626516Sbrian  while (argc--) {
98726516Sbrian    arg = **argv == '+' || **argv == '-' ? *argv + 1 : *argv;
98826516Sbrian    for (i = LogMIN; i <= LogMAX; i++)
98926516Sbrian      if (strcasecmp(arg, LogName(i)) == 0) {
99026516Sbrian        if (**argv == '-')
99126516Sbrian          LogDiscard(i);
99226516Sbrian        else
99326516Sbrian	  LogKeep(i);
9946059Samurai	break;
9956059Samurai      }
99626516Sbrian    if (i > LogMAX) {
99726516Sbrian      LogPrintf(LogWARN, "%s: Invalid log value\n", arg);
99826516Sbrian      res = -1;
9996059Samurai    }
100026516Sbrian    argv++;
10016059Samurai  }
100226516Sbrian  return res;
10036059Samurai}
10046059Samurai
10056059Samuraistatic int
10066059SamuraiSetEscape(list, argc, argv)
10076059Samuraistruct cmdtab *list;
10086059Samuraiint argc;
10096059Samuraichar **argv;
10106059Samurai{
10116059Samurai  int code;
10126059Samurai
10136059Samurai  for (code = 0; code < 33; code++)
10146059Samurai    EscMap[code] = 0;
10156059Samurai  while (argc-- > 0) {
10166059Samurai    sscanf(*argv++, "%x", &code);
10176059Samurai    code &= 0xff;
10186059Samurai    EscMap[code >> 3] |= (1 << (code&7));
10196059Samurai    EscMap[32] = 1;
10206059Samurai  }
102126516Sbrian  return 0;
10226059Samurai}
10236059Samurai
10246059Samuraistatic int
10256059SamuraiSetInitialMRU(list, argc, argv)
10266059Samuraistruct cmdtab *list;
10276059Samuraiint argc;
10286059Samuraichar **argv;
10296059Samurai{
103026326Sbrian  long mru;
103126516Sbrian  char *err;
10326059Samurai
10336059Samurai  if (argc > 0) {
103426326Sbrian    mru = atol(*argv);
103526326Sbrian    if (mru < MIN_MRU)
103626516Sbrian      err = "Given MRU value (%ld) is too small.\n";
10376059Samurai    else if (mru > MAX_MRU)
103826516Sbrian      err = "Given MRU value (%ld) is too big.\n";
103926516Sbrian    else {
10406059Samurai      VarMRU = mru;
104126516Sbrian      return 0;
104226516Sbrian    }
104326516Sbrian    LogPrintf(LogWARN, err, mru);
104426516Sbrian  }
104526326Sbrian
104626516Sbrian  return -1;
10476059Samurai}
10486059Samurai
10496059Samuraistatic int
105026326SbrianSetPreferredMTU(list, argc, argv)
105126326Sbrianstruct cmdtab *list;
105226326Sbrianint argc;
105326326Sbrianchar **argv;
105426326Sbrian{
105526326Sbrian  long mtu;
105626516Sbrian  char *err;
105726326Sbrian
105826326Sbrian  if (argc > 0) {
105926326Sbrian    mtu = atol(*argv);
106026516Sbrian    if (mtu == 0) {
106126326Sbrian      VarPrefMTU = 0;
106226516Sbrian      return 0;
106326516Sbrian    } else if (mtu < MIN_MTU)
106426516Sbrian      err = "Given MTU value (%ld) is too small.\n";
106526326Sbrian    else if (mtu > MAX_MTU)
106626516Sbrian      err = "Given MTU value (%ld) is too big.\n";
106726516Sbrian    else {
106826326Sbrian      VarPrefMTU = mtu;
106926516Sbrian      return 0;
107026516Sbrian    }
107126516Sbrian    LogPrintf(LogWARN, err, mtu);
107226516Sbrian  }
107326326Sbrian
107426516Sbrian  return -1;
107526326Sbrian}
107626326Sbrian
107726326Sbrianstatic int
10786059SamuraiSetIdleTimeout(list, argc, argv)
10796059Samuraistruct cmdtab *list;
10806059Samuraiint argc;
10816059Samuraichar **argv;
10826059Samurai{
10836059Samurai  if (argc-- > 0) {
10846059Samurai    VarIdleTimeout = atoi(*argv++);
108526516Sbrian    UpdateIdleTimer();  /* If we're connected, restart the idle timer */
10866735Samurai    if (argc-- > 0) {
10876735Samurai      VarLqrTimeout = atoi(*argv++);
10886735Samurai      if (VarLqrTimeout < 1)
10896735Samurai	VarLqrTimeout = 30;
10906735Samurai      if (argc > 0) {
10916735Samurai	VarRetryTimeout = atoi(*argv);
10926735Samurai	if (VarRetryTimeout < 1 || VarRetryTimeout > 10)
10936735Samurai	  VarRetryTimeout = 3;
10946735Samurai      }
10956735Samurai    }
109626516Sbrian    return 0;
10976059Samurai  }
109826516Sbrian
109926516Sbrian  return -1;
11006059Samurai}
11016059Samurai
11026059Samuraistruct in_addr
11036059SamuraiGetIpAddr(cp)
11046059Samuraichar *cp;
11056059Samurai{
11066059Samurai  struct hostent *hp;
11076059Samurai  struct in_addr ipaddr;
11086059Samurai
11096059Samurai  hp = gethostbyname(cp);
11106059Samurai  if (hp && hp->h_addrtype == AF_INET)
11116059Samurai    bcopy(hp->h_addr, &ipaddr, hp->h_length);
11126059Samurai  else if (inet_aton(cp, &ipaddr) == 0)
11136059Samurai    ipaddr.s_addr = 0;
11146059Samurai  return(ipaddr);
11156059Samurai}
11166059Samurai
11176059Samuraistatic int
11186059SamuraiSetInterfaceAddr(list, argc, argv)
11196059Samuraistruct cmdtab *list;
11206059Samuraiint argc;
11216059Samuraichar **argv;
11226059Samurai{
112328394Sbrian  DefMyAddress.ipaddr.s_addr = DefHisAddress.ipaddr.s_addr = 0L;
11246059Samurai
112526516Sbrian  if (argc > 4)
112626516Sbrian     return -1;
112726516Sbrian
112828394Sbrian  HaveTriggerAddress = 0;
112928394Sbrian  ifnetmask.s_addr = 0;
113028394Sbrian
11316059Samurai  if (argc > 0) {
113225630Sbrian    if (ParseAddr(argc, argv++,
113325630Sbrian            &DefMyAddress.ipaddr,
113425630Sbrian	    &DefMyAddress.mask,
113525630Sbrian	    &DefMyAddress.width) == 0)
113626516Sbrian       return 1;
11376059Samurai    if (--argc > 0) {
113825630Sbrian      if (ParseAddr(argc, argv++,
113925630Sbrian		    &DefHisAddress.ipaddr,
114025630Sbrian		    &DefHisAddress.mask,
114125630Sbrian		    &DefHisAddress.width) == 0)
114226516Sbrian	 return 2;
11436059Samurai      if (--argc > 0) {
11446059Samurai        ifnetmask = GetIpAddr(*argv);
11459440Samurai    	if (--argc > 0) {
114628394Sbrian           TriggerAddress = GetIpAddr(*argv);
114728394Sbrian	   HaveTriggerAddress = 1;
11489440Samurai	}
11496059Samurai      }
11506059Samurai    }
11516059Samurai  }
115228394Sbrian
11536059Samurai  /*
11546059Samurai   * For backwards compatibility, 0.0.0.0 means any address.
11556059Samurai   */
11566059Samurai  if (DefMyAddress.ipaddr.s_addr == 0) {
11576059Samurai    DefMyAddress.mask.s_addr = 0;
11586059Samurai    DefMyAddress.width = 0;
11596059Samurai  }
11606059Samurai  if (DefHisAddress.ipaddr.s_addr == 0) {
11616059Samurai    DefHisAddress.mask.s_addr = 0;
11626059Samurai    DefHisAddress.width = 0;
11636059Samurai  }
11646059Samurai
11656735Samurai  if ((mode & MODE_AUTO) ||
11666059Samurai	((mode & MODE_DEDICATED) && dstsystem)) {
116725630Sbrian    if (OsSetIpaddress(DefMyAddress.ipaddr, DefHisAddress.ipaddr, ifnetmask) < 0)
116826516Sbrian       return 4;
11696059Samurai  }
117026516Sbrian  return 0;
11716059Samurai}
11726059Samurai
117326516Sbrian#ifndef NOMSEXT
11746059Samurai
117518752Sjkhvoid
117618752SjkhSetMSEXT(pri_addr, sec_addr, argc, argv)
117718752Sjkhstruct in_addr *pri_addr;
117818752Sjkhstruct in_addr *sec_addr;
117918752Sjkhint argc;
118018752Sjkhchar **argv;
118118752Sjkh{
118218752Sjkh  int dummyint;
118318752Sjkh  struct in_addr dummyaddr;
118418752Sjkh
118518752Sjkh  pri_addr->s_addr = sec_addr->s_addr = 0L;
118618752Sjkh
118718752Sjkh  if( argc > 0 ) {
118818752Sjkh    ParseAddr(argc, argv++, pri_addr, &dummyaddr, &dummyint);
118918752Sjkh    if( --argc > 0 )
119018752Sjkh      ParseAddr(argc, argv++, sec_addr, &dummyaddr, &dummyint);
119118752Sjkh    else
119218752Sjkh      sec_addr->s_addr = pri_addr->s_addr;
119318752Sjkh  }
119418752Sjkh
119518752Sjkh /*
119618752Sjkh  * if the primary/secondary ns entries are 0.0.0.0 we should
119718752Sjkh  * set them to either the localhost's ip, or the values in
119818752Sjkh  * /etc/resolv.conf ??
119918752Sjkh  *
120018752Sjkh  * up to you if you want to implement this...
120118752Sjkh  */
120218752Sjkh
120318752Sjkh}
120418752Sjkh
120518752Sjkhstatic int
120618752SjkhSetNS(list, argc, argv)
120718752Sjkhstruct cmdtab *list;
120818752Sjkhint argc;
120918752Sjkhchar **argv;
121018752Sjkh{
121118752Sjkh  SetMSEXT(&ns_entries[0], &ns_entries[1], argc, argv);
121226516Sbrian  return 0;
121318752Sjkh}
121418752Sjkh
121518752Sjkhstatic int
121618752SjkhSetNBNS(list, argc, argv)
121718752Sjkhstruct cmdtab *list;
121818752Sjkhint argc;
121918752Sjkhchar **argv;
122018752Sjkh{
122118752Sjkh  SetMSEXT(&nbns_entries[0], &nbns_entries[1], argc, argv);
122226516Sbrian  return 0;
122318752Sjkh}
122418752Sjkh
122518752Sjkh#endif /* MS_EXT */
122618752Sjkh
12276059Samurai#define	VAR_AUTHKEY	0
12286059Samurai#define	VAR_DIAL	1
12296059Samurai#define	VAR_LOGIN	2
12306059Samurai#define	VAR_AUTHNAME	3
12316059Samurai#define	VAR_DEVICE	4
12326059Samurai#define	VAR_ACCMAP	5
12336059Samurai#define	VAR_PHONE	6
123427384Sbrian#define	VAR_HANGUP	7
12356059Samurai
12366059Samuraistatic int
12376059SamuraiSetVariable(list, argc, argv, param)
12386059Samuraistruct cmdtab *list;
12396059Samuraiint argc;
12406059Samuraichar **argv;
12416059Samuraiint param;
12426059Samurai{
12436059Samurai  u_long map;
124426551Sbrian  char *arg;
12456059Samurai
124626551Sbrian  if (argc > 0)
124726551Sbrian    arg = *argv;
124826551Sbrian  else
124926551Sbrian    arg = "";
125026551Sbrian
125126551Sbrian  switch (param) {
12526059Samurai    case VAR_AUTHKEY:
125326551Sbrian      strncpy(VarAuthKey, arg, sizeof(VarAuthKey)-1);
125421488Simp      VarAuthKey[sizeof(VarAuthKey)-1] = '\0';
12556059Samurai      break;
12566059Samurai    case VAR_AUTHNAME:
125726551Sbrian      strncpy(VarAuthName, arg, sizeof(VarAuthName)-1);
125821488Simp      VarAuthName[sizeof(VarAuthName)-1] = '\0';
12596059Samurai      break;
12606059Samurai    case VAR_DIAL:
126126551Sbrian      strncpy(VarDialScript, arg, sizeof(VarDialScript)-1);
126221488Simp      VarDialScript[sizeof(VarDialScript)-1] = '\0';
12636059Samurai      break;
12646059Samurai    case VAR_LOGIN:
126526551Sbrian      strncpy(VarLoginScript, arg, sizeof(VarLoginScript)-1);
126621488Simp      VarLoginScript[sizeof(VarLoginScript)-1] = '\0';
12676059Samurai      break;
12686059Samurai    case VAR_DEVICE:
126926516Sbrian      CloseModem();
127026551Sbrian      strncpy(VarDevice, arg, sizeof(VarDevice)-1);
127121488Simp      VarDevice[sizeof(VarDevice)-1] = '\0';
127225634Sbrian      VarBaseDevice = rindex(VarDevice, '/');
127325634Sbrian      VarBaseDevice = VarBaseDevice ? VarBaseDevice + 1 : "";
12746059Samurai      break;
12756059Samurai    case VAR_ACCMAP:
127626551Sbrian      sscanf(arg, "%lx", &map);
12776059Samurai      VarAccmap = map;
12786059Samurai      break;
12796059Samurai    case VAR_PHONE:
128026551Sbrian      strncpy(VarPhoneList, arg, sizeof(VarPhoneList)-1);
128121488Simp      VarPhoneList[sizeof(VarPhoneList)-1] = '\0';
128214423Sache      strcpy(VarPhoneCopy, VarPhoneList);
128314423Sache      VarNextPhone = VarPhoneCopy;
12846059Samurai      break;
128527384Sbrian    case VAR_HANGUP:
128627384Sbrian      strncpy(VarHangupScript, arg, sizeof(VarHangupScript)-1);
128727384Sbrian      VarHangupScript[sizeof(VarHangupScript)-1] = '\0';
128827384Sbrian      break;
12896059Samurai  }
129026516Sbrian  return 0;
12916059Samurai}
12926059Samurai
129320812Sjkhstatic int SetCtsRts(list, argc, argv)
129420812Sjkhstruct cmdtab *list;
129520812Sjkhint argc;
129620812Sjkhchar **argv;
129720812Sjkh{
129820812Sjkh  if (argc > 0) {
129920812Sjkh    if (strcmp(*argv, "on") == 0)
130020812Sjkh      VarCtsRts = TRUE;
130120812Sjkh    else if (strcmp(*argv, "off") == 0)
130220812Sjkh      VarCtsRts = FALSE;
130320812Sjkh    else
130426516Sbrian      return -1;
130526516Sbrian    return 0;
130620812Sjkh  }
130726516Sbrian  return -1;
130820812Sjkh}
130920812Sjkh
131020812Sjkh
13116059Samuraistatic int SetOpenMode(list, argc, argv)
13126059Samuraistruct cmdtab *list;
13136059Samuraiint argc;
13146059Samuraichar **argv;
13156059Samurai{
13166059Samurai  if (argc > 0) {
13176059Samurai    if (strcmp(*argv, "active") == 0)
13186059Samurai      VarOpenMode = OPEN_ACTIVE;
13196059Samurai    else if (strcmp(*argv, "passive") == 0)
13206059Samurai      VarOpenMode = OPEN_PASSIVE;
13216059Samurai    else
132226516Sbrian      return -1;
132326516Sbrian    return 0;
13246059Samurai  }
132526516Sbrian  return -1;
13266059Samurai}
13276059Samurai
13286735Samuraiextern int SetIfilter(), SetOfilter(), SetDfilter(), SetAfilter();
13296059Samurai
133013760Sphkstruct cmdtab const SetCommands[] = {
13316735Samurai  { "accmap",   NULL,	  SetVariable,		LOCAL_AUTH,
133226516Sbrian	"Set accmap value", "set accmap hex-value", (void *)VAR_ACCMAP},
13336735Samurai  { "afilter",  NULL,     SetAfilter, 		LOCAL_AUTH,
133426516Sbrian	"Set keep Alive filter", "set afilter ..."},
13356735Samurai  { "authkey",  "key",     SetVariable,		LOCAL_AUTH,
133626516Sbrian	"Set authentication key", "set authkey|key key", (void *)VAR_AUTHKEY},
13376735Samurai  { "authname", NULL,     SetVariable,		LOCAL_AUTH,
133826516Sbrian	"Set authentication name", "set authname name", (void *)VAR_AUTHNAME},
133920812Sjkh  { "ctsrts", NULL,	  SetCtsRts,		LOCAL_AUTH,
134026516Sbrian	"Use CTS/RTS modem signalling", "set ctsrts [on|off]"},
13416735Samurai  { "device",     "line", SetVariable, 		LOCAL_AUTH,
134226516Sbrian	"Set modem device name", "set device|line device-name", (void *)VAR_DEVICE},
13436735Samurai  { "dfilter",  NULL,     SetDfilter,		 LOCAL_AUTH,
134426516Sbrian	"Set demand filter", "set dfilter ..."},
13456735Samurai  { "dial",     NULL,     SetVariable, 		LOCAL_AUTH,
134626516Sbrian	"Set dialing script", "set dial chat-script", (void *)VAR_DIAL},
13476735Samurai  { "escape",   NULL,	  SetEscape, 		LOCAL_AUTH,
134826516Sbrian	"Set escape characters", "set escape hex-digit ..."},
134927384Sbrian  { "hangup",   NULL,     SetVariable,                LOCAL_AUTH,
135027384Sbrian        "Set hangup script", "set hangup chat-script", (void *)VAR_HANGUP},
13516735Samurai  { "ifaddr",   NULL,   SetInterfaceAddr,	LOCAL_AUTH,
135226516Sbrian	"Set destination address", "set ifaddr [src-addr [dst-addr [netmask [trg-addr]]]]"},
13536735Samurai  { "ifilter",  NULL,     SetIfilter, 		LOCAL_AUTH,
135426516Sbrian	"Set input filter", "set ifilter ..."},
135526516Sbrian  { "log",    NULL,	  SetLogLevel,	LOCAL_AUTH,
135626516Sbrian	"Set log level", "set log [+|-]value..."},
13576735Samurai  { "login",    NULL,     SetVariable,		LOCAL_AUTH,
135826516Sbrian	"Set login script", "set login chat-script",	(void *)VAR_LOGIN },
135926321Sbrian  { "mru",      NULL,     SetInitialMRU,	LOCAL_AUTH,
136026516Sbrian	"Set Initial MRU value", "set mru value" },
136126326Sbrian  { "mtu",      NULL,     SetPreferredMTU,	LOCAL_AUTH,
136226516Sbrian	"Set Preferred MTU value", "set mtu value" },
13636735Samurai  { "ofilter",  NULL,	  SetOfilter,		LOCAL_AUTH,
136426516Sbrian	"Set output filter", "set ofilter ..." },
13656735Samurai  { "openmode", NULL,	  SetOpenMode,		LOCAL_AUTH,
136626516Sbrian	"Set open mode", "set openmode [active|passive]"},
13676735Samurai  { "parity",   NULL,     SetModemParity,	LOCAL_AUTH,
136826516Sbrian	"Set modem parity", "set parity [odd|even|none]"},
13696735Samurai  { "phone",    NULL,     SetVariable,		LOCAL_AUTH,
137026516Sbrian	"Set telephone number(s)", "set phone phone1[:phone2[...]]", (void *)VAR_PHONE },
137125067Sbrian  { "reconnect",NULL,     SetReconnect,		LOCAL_AUTH,
137226516Sbrian	"Set Reconnect timeout", "set reconnect value ntries"},
137325067Sbrian  { "redial",   NULL,     SetRedialTimeout,	LOCAL_AUTH,
137426516Sbrian	"Set Redial timeout", "set redial value|random[.value|random] [dial_attempts]"},
137528327Sbrian  { "stopped",   NULL,     SetStoppedTimeout,	LOCAL_AUTH,
137628327Sbrian	"Set STOPPED timeout", "set stopped value"},
137726940Sbrian  { "server",    "socket",     SetServer,	LOCAL_AUTH,
137827089Sbrian	"Set server port", "set server|socket TcpPort|LocalName|none [mask]"},
13796735Samurai  { "speed",    NULL,     SetModemSpeed,	LOCAL_AUTH,
138026516Sbrian	"Set modem speed", "set speed value"},
13816735Samurai  { "timeout",  NULL,     SetIdleTimeout,	LOCAL_AUTH,
138226516Sbrian	"Set Idle timeout", "set timeout value"},
138326516Sbrian#ifndef NOMSEXT
138418752Sjkh  { "ns",	NULL,	  SetNS,		LOCAL_AUTH,
138526516Sbrian	"Set NameServer", "set ns pri-addr [sec-addr]"},
138618752Sjkh  { "nbns",	NULL,	  SetNBNS,		LOCAL_AUTH,
138726516Sbrian	"Set NetBIOS NameServer", "set nbns pri-addr [sec-addr]"},
138826516Sbrian#endif
13896735Samurai  { "help",     "?",      HelpCommand,		LOCAL_AUTH | LOCAL_NO_AUTH,
139026698Sbrian	"Display this message", "set help|? [command]", (void *)SetCommands},
13916059Samurai  { NULL,       NULL,     NULL },
13926059Samurai};
13936059Samurai
13946059Samuraistatic int
13956059SamuraiSetCommand(list, argc, argv)
13966059Samuraistruct cmdtab *list;
13976059Samuraiint argc;
13986059Samuraichar **argv;
13996059Samurai{
14006059Samurai  if (argc > 0)
140126516Sbrian    FindExec(SetCommands, argc, argv);
140226516Sbrian  else if (VarTerm)
140326516Sbrian    fprintf(VarTerm, "Use `set ?' to get a list or `set ? <var>' for"
140426516Sbrian	    " syntax help.\n");
14056059Samurai  else
140626516Sbrian    LogPrintf(LogWARN, "set command must have arguments\n");
140726516Sbrian
140826516Sbrian  return 0;
14096059Samurai}
14106059Samurai
14116059Samurai
14126059Samuraistatic int
14136059SamuraiAddCommand(list, argc, argv)
14146059Samuraistruct cmdtab *list;
14156059Samuraiint argc;
14166059Samuraichar **argv;
14176059Samurai{
14186059Samurai  struct in_addr dest, gateway, netmask;
14196059Samurai
14206059Samurai  if (argc == 3) {
142127011Sbrian    if (strcasecmp(argv[0], "MYADDR") == 0)
142227011Sbrian      dest = IpcpInfo.want_ipaddr;
142327011Sbrian    else
142427011Sbrian      dest = GetIpAddr(argv[0]);
14256059Samurai    netmask = GetIpAddr(argv[1]);
142625566Sbrian    if (strcasecmp(argv[2], "HISADDR") == 0)
14276059Samurai      gateway = IpcpInfo.his_ipaddr;
14286059Samurai    else
14296059Samurai      gateway = GetIpAddr(argv[2]);
14306059Samurai    OsSetRoute(RTM_ADD, dest, gateway, netmask);
143126516Sbrian    return 0;
14326059Samurai  }
143326516Sbrian
143426516Sbrian  return -1;
14356059Samurai}
14366059Samurai
14376059Samuraistatic int
14386059SamuraiDeleteCommand(list, argc, argv)
14396059Samuraistruct cmdtab *list;
14406059Samuraiint argc;
14416059Samuraichar **argv;
14426059Samurai{
14436059Samurai  struct in_addr dest, gateway, netmask;
14446059Samurai
144526591Sbrian  if (argc == 1 && strcasecmp(argv[0], "all") == 0)
144626591Sbrian    DeleteIfRoutes(0);
144726591Sbrian  else if (argc > 0 && argc < 4) {
144827011Sbrian    if (strcasecmp(argv[0], "MYADDR") == 0)
144927011Sbrian      dest = IpcpInfo.want_ipaddr;
145027011Sbrian    else
145127011Sbrian      dest = GetIpAddr(argv[0]);
145226591Sbrian    netmask.s_addr = INADDR_ANY;
145326591Sbrian    if (argc > 1) {
145426591Sbrian      if (strcasecmp(argv[1], "HISADDR") == 0)
145526591Sbrian        gateway = IpcpInfo.his_ipaddr;
145626591Sbrian      else
145726591Sbrian        gateway = GetIpAddr(argv[1]);
145826591Sbrian      if (argc == 3) {
145926591Sbrian        if (inet_aton(argv[2], &netmask) == 0) {
146026591Sbrian	  LogPrintf(LogWARN, "Bad netmask value.\n");
146126591Sbrian	  return -1;
146226591Sbrian        }
14636059Samurai      }
146426591Sbrian    } else
146526591Sbrian      gateway.s_addr = INADDR_ANY;
14666059Samurai    OsSetRoute(RTM_DELETE, dest, gateway, netmask);
146726516Sbrian  } else
146826516Sbrian    return -1;
146926516Sbrian
147026516Sbrian  return 0;
14716059Samurai}
14726059Samurai
147326031Sbrianstatic int AliasEnable();
147426031Sbrianstatic int AliasOption();
147526031Sbrian
147626031Sbrianstatic struct cmdtab const AliasCommands[] =
147726031Sbrian{
147826031Sbrian  { "enable",   NULL,     AliasEnable,          LOCAL_AUTH,
147926516Sbrian        "enable IP aliasing", "alias enable [yes|no]"},
148026031Sbrian  { "port",   NULL,     AliasRedirectPort,          LOCAL_AUTH,
148126516Sbrian        "port redirection", "alias port [proto addr_local:port_local  port_alias]"},
148226031Sbrian  { "addr",   NULL,     AliasRedirectAddr,          LOCAL_AUTH,
148326516Sbrian        "static address translation", "alias addr [addr_local addr_alias]"},
148426031Sbrian  { "deny_incoming",  NULL,    AliasOption,     LOCAL_AUTH,
148526516Sbrian        "stop incoming connections",   "alias deny_incoming [yes|no]",
148626031Sbrian        (void*)PKT_ALIAS_DENY_INCOMING},
148726031Sbrian  { "log",  NULL,     AliasOption,              LOCAL_AUTH,
148826516Sbrian        "log aliasing link creation",           "alias log [yes|no]",
148926031Sbrian        (void*)PKT_ALIAS_LOG},
149026031Sbrian  { "same_ports", NULL,     AliasOption,        LOCAL_AUTH,
149126516Sbrian        "try to leave port numbers unchanged", "alias same_ports [yes|no]",
149226031Sbrian        (void*)PKT_ALIAS_SAME_PORTS},
149326031Sbrian  { "use_sockets", NULL,     AliasOption,       LOCAL_AUTH,
149426516Sbrian        "allocate host sockets", "alias use_sockets [yes|no]",
149526031Sbrian        (void*)PKT_ALIAS_USE_SOCKETS },
149626031Sbrian  { "unregistered_only", NULL,     AliasOption, LOCAL_AUTH,
149726516Sbrian        "alias unregistered (private) IP address space only",
149826516Sbrian        "alias unregistered_only [yes|no]",
149926031Sbrian        (void*)PKT_ALIAS_UNREGISTERED_ONLY},
150026031Sbrian  { "help",     "?",      HelpCommand,          LOCAL_AUTH | LOCAL_NO_AUTH,
150126698Sbrian        "Display this message", "alias help|? [command]",
150226031Sbrian        (void *)AliasCommands},
150326031Sbrian  { NULL,       NULL,     NULL },
150426031Sbrian};
150526031Sbrian
150626031Sbrian
150726031Sbrianstatic int
150826031SbrianAliasCommand(list, argc, argv)
150926031Sbrianstruct cmdtab *list;
151026031Sbrianint argc;
151126031Sbrianchar **argv;
151226031Sbrian{
151326031Sbrian  if (argc > 0)
151426516Sbrian    FindExec(AliasCommands, argc, argv);
151526516Sbrian  else if (VarTerm)
151626516Sbrian    fprintf(VarTerm, "Use `alias help' to get a list or `alias help <option>'"
151726516Sbrian	    " for syntax help.\n");
151826031Sbrian  else
151926516Sbrian    LogPrintf(LogWARN, "alias command must have arguments\n");
152026516Sbrian
152126516Sbrian  return 0;
152226031Sbrian}
152326031Sbrian
152426031Sbrianstatic int
152526031SbrianAliasEnable(list, argc, argv)
152626031Sbrianstruct cmdtab *list;
152726031Sbrianint argc;
152826031Sbrianchar **argv;
152926031Sbrian{
153026516Sbrian  if (argc == 1)
153126516Sbrian    if (strcasecmp(argv[0], "yes") == 0) {
153226516Sbrian      if (!(mode & MODE_ALIAS)) {
153326516Sbrian        if (loadAliasHandlers(&VarAliasHandlers) == 0) {
153426516Sbrian          mode |= MODE_ALIAS;
153526516Sbrian          return 0;
153626142Sbrian        }
153726516Sbrian        LogPrintf(LogWARN, "Cannot load alias library\n");
153826516Sbrian        return 1;
153926516Sbrian      }
154026516Sbrian      return 0;
154126516Sbrian    } else if (strcasecmp(argv[0], "no") == 0) {
154226516Sbrian      if (mode & MODE_ALIAS) {
154326516Sbrian        unloadAliasHandlers();
154426516Sbrian        mode &= ~MODE_ALIAS;
154526516Sbrian      }
154626516Sbrian      return 0;
154726142Sbrian    }
154826516Sbrian
154926516Sbrian  return -1;
155026031Sbrian}
155126031Sbrian
155226031Sbrian
155326031Sbrianstatic int
155426031SbrianAliasOption(list, argc, argv, param)
155526031Sbrianstruct cmdtab *list;
155626031Sbrianint argc;
155726031Sbrianchar **argv;
155826031Sbrianvoid* param;
155926031Sbrian{
156026516Sbrian   if (argc == 1)
156126516Sbrian     if (strcasecmp(argv[0], "yes") == 0) {
156226516Sbrian       if (mode & MODE_ALIAS) {
156326142Sbrian         VarSetPacketAliasMode((unsigned)param, (unsigned)param);
156426516Sbrian         return 0;
156526516Sbrian       }
156626516Sbrian       LogPrintf(LogWARN, "alias not enabled\n");
156726516Sbrian     } else if (strcmp(argv[0], "no") == 0) {
156826516Sbrian       if (mode & MODE_ALIAS) {
156926142Sbrian         VarSetPacketAliasMode(0, (unsigned)param);
157026516Sbrian         return 0;
157126516Sbrian       }
157226516Sbrian       LogPrintf(LogWARN, "alias not enabled\n");
157326516Sbrian     }
157426516Sbrian
157526516Sbrian   return -1;
157626031Sbrian}
1577