home *** CD-ROM | disk | FTP | other *** search
/ InfoMagic Source Code 1993 July / THE_SOURCE_CODE_CD_ROM.iso / X / mit / clients / xdm / xdmshell.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-07-18  |  5.4 KB  |  218 lines

  1. /*
  2.  * xdmshell - simple program for running xdm from login
  3.  *
  4.  * Copyright 1988 Massachusetts Institute of Technology
  5.  *
  6.  * Permission to use, copy, modify, and distribute this software and its
  7.  * documentation for any purpose and without fee is hereby granted, provided
  8.  * that the above copyright notice appear in all copies and that both that
  9.  * copyright notice and this permission notice appear in supporting
  10.  * documentation, and that the name of M.I.T. not be used in advertising
  11.  * or publicity pertaining to distribution of the software without specific,
  12.  * written prior permission.  M.I.T. makes no representations about the
  13.  * suitability of this software for any purpose.  It is provided "as is"
  14.  * without express or implied warranty.
  15.  *
  16.  * M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
  17.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
  18.  * BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
  19.  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
  20.  * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN 
  21.  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
  22.  *
  23.  * Author:  Jim Fulton, MIT X Consortium
  24.  *
  25.  * This program should probably be setuid to root.  On the macII, it must be
  26.  * run from the console so that getty doesn't get confused about zero-length
  27.  * reads.
  28.  *
  29.  * WARNING:  Make sure that you tailor your Xresources file to have a
  30.  * way of invoking the abort-display() action.  Otherwise, you won't be able
  31.  * bring down X when you are finished.
  32.  */
  33.  
  34. #include <stdio.h>
  35. #include "dm.h"
  36. #include <errno.h>
  37. extern int errno;
  38. extern int sys_nerr;
  39. extern char *sys_errlist[];
  40.  
  41. #ifdef macII
  42. #define ON_CONSOLE_ONLY
  43. #endif
  44.  
  45. #ifdef ON_CONSOLE_ONLY
  46. #include <sys/ioctl.h>
  47. #endif
  48.  
  49. #ifndef BINDIR
  50. #define BINDIR "/usr/bin/X11"
  51. #endif
  52.  
  53. /*
  54.  * HP-UX does have vfork, but A/UX doesn't
  55.  */
  56. #if (defined(SYSV) || defined(macII)) && !defined(hpux)
  57. #define vfork() fork()
  58. #endif
  59.  
  60. char *ProgramName;
  61.  
  62. static char *SysErrorMsg (n)
  63.     int n;
  64. {
  65.     char *s = (n > 0 && n < sys_nerr) ? sys_errlist[n] : "unknown";
  66.     return (s ? s : "null system error");
  67. }
  68.  
  69.  
  70. static int exec_args (filename, args)
  71.     char *filename;
  72.     char **args;
  73. {
  74.     int pid;
  75.     waitType status;
  76.  
  77.     if (!filename) return -1;
  78.  
  79.     if (filename[0] != '/') {
  80.     fprintf (stderr, 
  81.            "%s:  attempt to execute program with relative pathname:  %s\n",
  82.          ProgramName, filename);
  83.     return -1;
  84.     }
  85.  
  86.     if (access (filename, X_OK) != 0) return -1;
  87.  
  88.     switch (pid = vfork ()) {
  89.       case -1:                        /* error */
  90.     return -1;
  91.       case 0:                        /* child */
  92.     execv (filename, args);
  93.     _exit (1);
  94.     /* NOTREACHED */
  95.       default:                        /* parent */
  96.     while (wait (&status) != pid) ;
  97.     }
  98.     return waitCode (status);
  99. }
  100.  
  101. static int exec_one_arg (filename, arg)
  102.     char    *filename;
  103.     char    *arg;
  104. {
  105.     char    *argv[3];
  106.  
  107.     argv[0] = filename;
  108.     argv[1] = arg;
  109.     argv[2] = NULL;
  110.     return exec_args (filename, argv);
  111. }
  112.  
  113. main (argc, argv)
  114.     int argc;
  115.     char *argv[];
  116. {
  117.     int ttyfd;
  118.     char cmdbuf[256];
  119.     char *args[10];
  120. #ifdef ON_CONSOLE_ONLY
  121.     int consfd;
  122.     int ttypgrp, conspgrp;
  123.     char *ttyName;
  124.     extern char *ttyname();
  125. #endif
  126.  
  127.     ProgramName = argv[0];
  128.  
  129.     if (argc > 1) {
  130.     fprintf (stderr, "usage:  %s\r\n", ProgramName);
  131.     exit (1);
  132.     }
  133.  
  134.     ttyfd = open ("/dev/tty", O_RDWR, 0);
  135.     if (ttyfd < 3) {            /* stdin = 0, stdout = 1, stderr = 2 */
  136.     fprintf (stderr, 
  137.          "%s:  must be run directly from the console.\r\n",
  138.          ProgramName);
  139.     exit (1);
  140.     }
  141. #ifdef ON_CONSOLE_ONLY
  142.     if (ioctl (ttyfd, TIOCGPGRP, (char *)&ttypgrp) != 0) {
  143.     fprintf (stderr, "%s:  unable to get process group of /dev/tty\r\n",
  144.          ProgramName);
  145.     (void) close (ttyfd);
  146.     exit (1);
  147.     }
  148. #endif
  149.     (void) close (ttyfd);
  150.     
  151. #ifdef ON_CONSOLE_ONLY
  152.     ttyName = ttyname (0);
  153.     if (!ttyName || strcmp (ttyName, "/dev/console") != 0) {
  154.     fprintf (stderr, "%s:  must login on /dev/console instead of %s\r\n",
  155.          ProgramName, ttyName ? ttyName : "non-terminal device");
  156.     exit (1);
  157.     }
  158.  
  159.     consfd = open ("/dev/console", O_RDWR, 0);
  160.     if (consfd < 3) {            /* stdin = 0, stdout = 1, stderr = 2 */
  161.     fprintf (stderr, "%s:  unable to open /dev/console\r\n",
  162.          ProgramName);
  163.     exit (1);
  164.     }
  165.  
  166.     if (ioctl (consfd, TIOCGPGRP, (char *)&conspgrp) != 0) {
  167.     fprintf (stderr,
  168.          "%s:  unable to get process group of /dev/console\r\n",
  169.          ProgramName);
  170.     (void) close (consfd);
  171.     exit (1);
  172.     }
  173.     (void) close (consfd);
  174.  
  175.     if (ttypgrp != conspgrp) {
  176.     fprintf (stderr, "%s:  must be run from /dev/console\r\n", 
  177.          ProgramName);
  178.     exit (1);
  179.     }
  180. #endif
  181.  
  182.     /* make xdm run in a non-setuid environment */
  183.     setuid (geteuid());
  184.  
  185.     /*
  186.      * exec /usr/bin/X11/xdm -nodaemon -udpPort 0
  187.      */
  188.     strcpy (cmdbuf, BINDIR);
  189.     strcat (cmdbuf, "/xdm");
  190.     args[0] = cmdbuf;
  191.     args[1] = "-nodaemon";
  192.     args[2] = "-udpPort";
  193.     args[3] = "0";
  194.     args[4] = NULL;
  195.     if (exec_args (cmdbuf, args) == -1) {
  196.     fprintf (stderr, "%s:  unable to execute %s (error %d, %s)\r\n",
  197.          ProgramName, cmdbuf, errno, SysErrorMsg(errno));
  198.     exit (1);
  199.     }
  200.  
  201. #ifdef macII
  202.     strcpy (cmdbuf, BINDIR);
  203.     strcat (cmdbuf, "/Xrepair");
  204.     (void) exec_one_arg (cmdbuf, NULL);
  205.     (void) exec_one_arg ("/usr/bin/screenrestore", NULL);
  206. #endif
  207.  
  208. #ifdef sun
  209.     strcpy (cmdbuf, BINDIR);
  210.     strcat (cmdbuf, "/kbd_mode");
  211.     (void) exec_one_arg (cmdbuf, "-a");
  212. #endif
  213.  
  214.     exit (0);
  215.     /*NOTREACHED*/
  216. }
  217.  
  218.