Add `TZ' to the list of variables to be preserved.
[become] / src / become.c
index 2154e4b..2b8eedd 100644 (file)
@@ -1,10 +1,10 @@
 /* -*-c-*-
  *
- * $Id: become.c,v 1.9 1997/09/10 10:28:05 mdw Exp $
+ * $Id: become.c,v 1.15 1998/01/13 11:10:44 mdw Exp $
  *
  * Main code for `become'
  *
- * (c) 1997 EBI
+ * (c) 1998 EBI
  */
 
 /*----- Licensing notice --------------------------------------------------*
 /*----- Revision history --------------------------------------------------*
  *
  * $Log: become.c,v $
+ * Revision 1.15  1998/01/13 11:10:44  mdw
+ * Add `TZ' to the list of variables to be preserved.
+ *
+ * Revision 1.14  1998/01/12 16:45:39  mdw
+ * Fix copyright date.
+ *
+ * Revision 1.13  1997/09/26 09:14:57  mdw
+ * Merged blowfish branch into trunk.
+ *
+ * Revision 1.12  1997/09/25 16:04:48  mdw
+ * Change directory after becoming someone else, instead of before.  This
+ * avoids problems with root-squashed NFS mounts.
+ *
+ * Revision 1.11.2.1  1997/09/26 09:07:58  mdw
+ * Use the Blowfish encryption algorithm instead of IDEA.  This is partly
+ * because I prefer Blowfish (without any particularly strong evidence) but
+ * mainly because IDEA is patented and Blowfish isn't.
+ *
+ * Revision 1.11  1997/09/24  09:48:45  mdw
+ * Fix (scary) overrun bug in group allocation stuff.
+ *
+ * Revision 1.10  1997/09/17  10:14:10  mdw
+ * Fix a typo.  Support service names in `--port' option.
+ *
  * Revision 1.9  1997/09/10 10:28:05  mdw
  * Allow default port to be given as a service name or port number.  Handle
  * groups properly (lots of options here).
@@ -301,8 +325,8 @@ static int bc__addGroups(gid_t *g, int *png, const gid_t *a, int na)
 
     /* --- See if there's room for more --- */
 
-    if (ng > NGROUPS_MAX) {
-      moan("too many groups (system limit exceeded -- some have been lost");
+    if (ng >= NGROUPS_MAX) {
+      moan("too many groups (system limit exceeded) -- some have been lost");
       *png = ng;
       return (-1);
     }
@@ -437,7 +461,7 @@ int main(int argc, char *argv[])
   /* --- Become server setup parameters --- */
 
   char *conffile = file_RULES;         /* Default config file for daemon */
-  int port = -1;                       /* Default port for daemon */
+  int port = 0;                                /* Default port for daemon */
 
   /* --- Miscellanous shared variables --- */
 
@@ -465,7 +489,7 @@ int main(int argc, char *argv[])
   enum {
     f_daemon = 1,                      /* Start up in daemon mode */
     f_duff = 2,                                /* Fault in arguments */
-    f_login = 4,                       /* Execute as a login shell */
+    f_shell = 4,                       /* Run a default shell */
     f_dummy = 8,                       /* Don't actually do anything */
     f_setuid = 16,                     /* We're running setuid */
     f_havegroup = 32                   /* Set a default group */
@@ -752,7 +776,7 @@ int main(int argc, char *argv[])
          }
          bc__write(stdout,
 "\n"
-"Also, `+' and `-' options are recognised to turn on and off vavrious\n"
+"Also, `+' and `-' options are recognised to turn on and off various\n"
 "tracing options.  For example, `A-r' enables everything except ruleset\n"
 "tracing, and `A-D+c' is everything except the defaults, but with request\n"
 "check tracing.\n"
@@ -805,9 +829,10 @@ int main(int argc, char *argv[])
        /* --- None of the above --- */
 
        if (optarg[sz] == 0 || (optarg[sz] != '=' && optarg[sz + 1] != 0)) {
-         if (who == 0)
+         if (!who) {
            who = optarg;
-         else {
+           break;
+         } else {
            optind--;
            goto done_options;
          }
@@ -1039,45 +1064,48 @@ done_options:
     binary = todo[0];
   }
 
-  else switch (style) {
+  else {
+    flags |= f_shell;
 
-    /* --- An unadorned becoming requires little work --- */
+    switch (style) {
 
-    case l_preserve:
-      shell[0] = getenv("SHELL");
-      if (!shell[0])
-       shell[0] = from_pw->pw_shell;
-      shell[1] = 0;
-      todo = shell;
-      binary = todo[0];
-      break;
+      /* --- An unadorned becoming requires little work --- */
 
-    /* --- An su-like login needs slightly less effort --- */
+      case l_preserve:
+       shell[0] = getenv("SHELL");
+       if (!shell[0])
+         shell[0] = from_pw->pw_shell;
+       shell[1] = 0;
+       todo = shell;
+       binary = todo[0];
+       break;
 
-    case l_setuser:
-      shell[0] = to_pw->pw_shell;
-      shell[1] = 0;
-      todo = shell;
-      binary = todo[0];
-      break;
+      /* --- An su-like login needs slightly less effort --- */
 
-    /* --- A login request needs a little bit of work --- */
-
-    case l_login: {
-      const char *p = strrchr(to_pw->pw_shell, '/');
-
-      if (p)
-       p++;
-      else
-       p = to_pw->pw_shell;
-      shell[0] = xmalloc(strlen(p) + 2);
-      shell[0][0] = '-';
-      strcpy(shell[0] + 1, p);
-      shell[1] = 0;
-      todo = shell;
-      binary = to_pw->pw_shell;
-      chdir(to_pw->pw_dir);
-    } break;
+      case l_setuser:
+       shell[0] = to_pw->pw_shell;
+       shell[1] = 0;
+       todo = shell;
+       binary = todo[0];
+       break;
+
+      /* --- A login request needs a little bit of work --- */
+
+      case l_login: {
+       const char *p = strrchr(to_pw->pw_shell, '/');
+
+       if (p)
+         p++;
+       else
+         p = to_pw->pw_shell;
+       shell[0] = xmalloc(strlen(p) + 2);
+       shell[0][0] = '-';
+       strcpy(shell[0] + 1, p);
+       shell[1] = 0;
+       todo = shell;
+       binary = to_pw->pw_shell;
+      } break;
+    }
   }
 
   /* --- Mangle the environment --- *
@@ -1114,7 +1142,7 @@ done_options:
      */
 
     static char *preserve[] = {
-      "TERM", "DISPLAY", 0
+      "TERM", "DISPLAY", "TZ", 0
     };
 
     /* --- Variables to be expunged --- *
@@ -1416,7 +1444,7 @@ done_options:
 
   if (rq.from == rq.to) {
     moan("you already are `%s'!", to_pw->pw_name);
-    if (!cmd && todo == shell) {
+    if (flags & f_shell) {
       moan("(to prevent confusion, I'm not spawning a shell)");
       exit(0);
     }
@@ -1451,6 +1479,13 @@ done_options:
   if (setuid(rq.to) < 0)
     die("couldn't set uid: %s", strerror(errno));
 
+  /* --- If this was a login, change current directory --- */
+
+  if (flags & f_shell && style == l_login && chdir(to_pw->pw_dir) < 0) {
+    moan("couldn't change directory to `%s': %s",
+        to_pw->pw_dir, strerror(errno));
+  }
+
   /* --- Finally, call the program --- */
 
   fflush(0);