root/maint/gnulib/lib/pt_chown.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. do_pt_chown
  2. main

   1 /* pt_chown - helper program for 'grantpt'.
   2    Copyright (C) 1998-1999, 2009-2021 Free Software Foundation, Inc.
   3    Contributed by C. Scott Ananian <cananian@alumni.princeton.edu>, 1998.
   4 
   5    This file is free software: you can redistribute it and/or modify
   6    it under the terms of the GNU Lesser General Public License as
   7    published by the Free Software Foundation; either version 2.1 of the
   8    License, or (at your option) any later version.
   9 
  10    This file is distributed in the hope that it will be useful,
  11    but WITHOUT ANY WARRANTY; without even the implied warranty of
  12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13    GNU Lesser General Public License for more details.
  14 
  15    You should have received a copy of the GNU Lesser General Public License
  16    along with this program.  If not, see <https://www.gnu.org/licenses/>.  */
  17 
  18 #include <config.h>
  19 
  20 #include <errno.h>
  21 #include <grp.h>
  22 #include <stdio.h>
  23 #include <stdlib.h>
  24 #include <string.h>
  25 #include <sys/stat.h>
  26 #include <unistd.h>
  27 
  28 #include "root-uid.h"
  29 
  30 #include "pty-private.h"
  31 
  32 /* For security reasons, we try to minimize the dependencies on libraries
  33    outside libc.  This means, in particular:
  34      - No use of gettext(), since it's usually implemented in libintl.
  35      - No use of error() or argp, since they rely on gettext by default.  */
  36 
  37 
  38 static int
  39 do_pt_chown (void)
     /* [previous][next][first][last][top][bottom][index][help] */
  40 {
  41   char *pty;
  42   struct stat st;
  43   struct group *p;
  44   gid_t gid;
  45 
  46   /* Check that PTY_FILENO is a valid master pseudo terminal.  */
  47   pty = ptsname (PTY_FILENO);
  48   if (pty == NULL)
  49     return errno == EBADF ? FAIL_EBADF : FAIL_EINVAL;
  50 
  51   /* Check that the returned slave pseudo terminal is a
  52      character device.  */
  53   if (stat (pty, &st) < 0 || !S_ISCHR (st.st_mode))
  54     return FAIL_EINVAL;
  55 
  56   /* Get the group ID of the special 'tty' group.  */
  57   p = getgrnam (TTY_GROUP);
  58   gid = p ? p->gr_gid : getgid ();
  59 
  60   /* Set the owner to the real user ID, and the group to that special
  61      group ID.  */
  62   if (st.st_gid != gid && chown (pty, getuid (), gid) < 0)
  63     return FAIL_EACCES;
  64 
  65   /* Set the permission mode to readable and writable by the owner,
  66      and writable by the group.  */
  67   if ((st.st_mode & (S_IRWXU|S_IRWXG|S_IRWXO)) != (S_IRUSR|S_IWUSR|S_IWGRP)
  68       && chmod (pty, S_IRUSR|S_IWUSR|S_IWGRP) < 0)
  69     return FAIL_EACCES;
  70 
  71   return 0;
  72 }
  73 
  74 
  75 int
  76 main (int argc, char *argv[])
     /* [previous][next][first][last][top][bottom][index][help] */
  77 {
  78   uid_t euid = geteuid ();
  79 
  80   if (argc == 1 && euid == ROOT_UID)
  81     {
  82       /* Normal invocation of this program is with no arguments and
  83          with privileges.  */
  84       return do_pt_chown ();
  85     }
  86 
  87   /* It would be possible to drop setuid/setgid privileges here.  But it is not
  88      really needed, since the code below only calls strcmp and [f]printf.  */
  89 
  90   {
  91     int do_help = 0;
  92     int do_version = 0;
  93     int remaining;
  94 
  95     for (remaining = 1; remaining < argc; remaining++)
  96       {
  97         const char *arg = argv[remaining];
  98 
  99         if (arg[0] == '-')
 100           {
 101             if (strcmp (arg, "--") == 0)
 102               {
 103                 remaining++;
 104                 break;
 105               }
 106             else if (strcmp (arg, "--help") == 0)
 107               do_help = 1;
 108             else if (strcmp (arg, "--version") == 0)
 109               do_version = 1;
 110             else
 111               {
 112                 fprintf (stderr, "pt_chown: invalid option: %s\n", arg);
 113                 return EXIT_FAILURE;
 114               }
 115           }
 116         else
 117           break;
 118       }
 119 
 120     if (remaining < argc)
 121       {
 122         fprintf (stderr, "pt_chown: too many arguments\n");
 123         return EXIT_FAILURE;
 124       }
 125 
 126     if (do_help)
 127       {
 128         printf ("Usage: pt_chown [OPTION...]\n");
 129         printf ("Set the owner, group and access permission of the slave pseudo terminal\n"
 130                 "corresponding to the master pseudo terminal passed on file descriptor %d.\n"
 131                 "This is the helper program for the 'grantpt' function.  It is not intended\n"
 132                 "to be run directly from the command line.\n",
 133                 PTY_FILENO);
 134         printf ("\n");
 135         printf ("  --help                     Give this help list\n");
 136         printf ("  --version                  Print program version\n");
 137         printf ("\n");
 138         printf ("The owner is set to the current user, the group is set to '%s', and the\n"
 139                 "access permission is set to '%o'.\n",
 140                 TTY_GROUP, S_IRUSR|S_IWUSR|S_IWGRP);
 141         printf ("Please report bugs to <bug-gnulib@gnu.org>.\n");
 142         return EXIT_SUCCESS;
 143       }
 144 
 145     if (do_version)
 146       {
 147         printf ("pt_chown (GNU %s) %s\n", "libc", "2.11");
 148         printf ("Copyright (C) %s Free Software Foundation, Inc.\n"
 149                 "This is free software; see the source for copying conditions.  There is NO\n"
 150                 "warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n",
 151                 "1999");
 152         return EXIT_SUCCESS;
 153       }
 154   }
 155 
 156   /* Check if we are properly installed.  */
 157   if (euid != ROOT_UID)
 158     {
 159       fprintf (stderr, "pt_chown: needs to be installed setuid 'root'\n");
 160       return FAIL_EXEC;
 161     }
 162 
 163   return EXIT_SUCCESS;
 164 }

/* [previous][next][first][last][top][bottom][index][help] */