home *** CD-ROM | disk | FTP | other *** search
/ Geek Gadgets 1 / ADE-1.bin / ade-dist / sh-utils-1.12-src.tgz / tar.out / fsf / sh-utils / src / id.c < prev    next >
C/C++ Source or Header  |  1996-09-28  |  8KB  |  377 lines

  1. /* id -- print real and effective UIDs and GIDs
  2.    Copyright (C) 89, 90, 91, 92, 93, 1994 Free Software Foundation, Inc.
  3.  
  4.    This program is free software; you can redistribute it and/or modify
  5.    it under the terms of the GNU General Public License as published by
  6.    the Free Software Foundation; either version 2, or (at your option)
  7.    any later version.
  8.  
  9.    This program is distributed in the hope that it will be useful,
  10.    but WITHOUT ANY WARRANTY; without even the implied warranty of
  11.    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12.    GNU General Public License for more details.
  13.  
  14.    You should have received a copy of the GNU General Public License
  15.    along with this program; if not, write to the Free Software
  16.    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
  17.  
  18. /* Written by Arnold Robbins, arnold@audiofax.com.
  19.    Major rewrite by David MacKenzie, djm@gnu.ai.mit.edu. */
  20.  
  21. #include <config.h>
  22. #include <stdio.h>
  23. #include <getopt.h>
  24. #include <sys/types.h>
  25. #include <pwd.h>
  26. #include <grp.h>
  27. #include <getopt.h>
  28.  
  29. #include "version.h"
  30. #include "system.h"
  31.  
  32. #ifdef _POSIX_VERSION
  33. #include <limits.h>
  34. #if !defined(NGROUPS_MAX) || NGROUPS_MAX < 1
  35. #undef NGROUPS_MAX
  36. #define NGROUPS_MAX sysconf (_SC_NGROUPS_MAX)
  37. #endif /* !NGROUPS_MAX */
  38.  
  39. #else /* not _POSIX_VERSION */
  40. struct passwd *getpwuid ();
  41. struct group *getgrgid ();
  42. uid_t getuid ();
  43. gid_t getgid ();
  44. uid_t geteuid ();
  45. gid_t getegid ();
  46. #include <sys/param.h>
  47. #if !defined(NGROUPS_MAX) && defined(NGROUPS)
  48. #define NGROUPS_MAX NGROUPS
  49. #endif /* not NGROUPS_MAX and NGROUPS */
  50. #endif /* not _POSIX_VERSION */
  51.  
  52. char *xmalloc ();
  53. int getugroups ();
  54. void error ();
  55.  
  56. static void print_user ();
  57. static void print_group ();
  58. static void print_group_list ();
  59. static void print_full_info ();
  60. static void usage ();
  61.  
  62. /* The name this program was run with. */
  63. char *program_name;
  64.  
  65. /* If nonzero, output only the group ID(s). -g */
  66. static int just_group = 0;
  67.  
  68. /* If nonzero, output user/group name instead of ID number. -n */
  69. static int use_name = 0;
  70.  
  71. /* If nonzero, output real UID/GID instead of default effective UID/GID. -r */
  72. static int use_real = 0;
  73.  
  74. /* If nonzero, output only the user ID(s). -u */
  75. static int just_user = 0;
  76.  
  77. /* If nonzero, output only the supplementary groups. -G */
  78. static int just_group_list = 0;
  79.  
  80. /* The real and effective IDs of the user to print. */
  81. static uid_t ruid, euid;
  82. static gid_t rgid, egid;
  83.  
  84. /* The number of errors encountered so far. */
  85. static int problems = 0;
  86.  
  87. /* If non-zero, display usage information and exit.  */
  88. static int show_help;
  89.  
  90. /* If non-zero, print the version on standard output and exit.  */
  91. static int show_version;
  92.  
  93. static struct option const longopts[] =
  94. {
  95.   {"group", no_argument, NULL, 'g'},
  96.   {"groups", no_argument, NULL, 'G'},
  97.   {"help", no_argument, &show_help, 1},
  98.   {"name", no_argument, NULL, 'n'},
  99.   {"real", no_argument, NULL, 'r'},
  100.   {"user", no_argument, NULL, 'u'},
  101.   {"version", no_argument, &show_version, 1},
  102.   {NULL, 0, NULL, 0}
  103. };
  104.  
  105. main (argc, argv)
  106.      int argc;
  107.      char **argv;
  108. {
  109.   int optc;
  110.  
  111.   program_name = argv[0];
  112.  
  113.   while ((optc = getopt_long (argc, argv, "gnruG", longopts, (int *) 0))
  114.      != EOF)
  115.     {
  116.       switch (optc)
  117.     {
  118.     case 0:
  119.       break;
  120.     case 'g':
  121.       just_group = 1;
  122.       break;
  123.     case 'n':
  124.       use_name = 1;
  125.       break;
  126.     case 'r':
  127.       use_real = 1;
  128.       break;
  129.     case 'u':
  130.       just_user = 1;
  131.       break;
  132.     case 'G':
  133.       just_group_list = 1;
  134.       break;
  135.     default:
  136.       usage (1);
  137.     }
  138.     }
  139.  
  140.   if (show_version)
  141.     {
  142.       printf ("id - %s\n", version_string);
  143.       exit (0);
  144.     }
  145.  
  146.   if (show_help)
  147.     usage (0);
  148.  
  149.   if (just_user + just_group + just_group_list > 1)
  150.     error (1, 0, "cannot print only user and only group");
  151.  
  152.   if (just_user + just_group + just_group_list == 0 && (use_real || use_name))
  153.     error (1, 0, "cannot print only names or real IDs in default format");
  154.  
  155.   if (argc - optind > 1)
  156.     usage (1);
  157.  
  158.   if (argc - optind == 1)
  159.     {
  160.       struct passwd *pwd = getpwnam (argv[optind]);
  161.       if (pwd == NULL)
  162.     error (1, 0, "%s: No such user", argv[optind]);
  163.       ruid = euid = pwd->pw_uid;
  164.       rgid = egid = pwd->pw_gid;
  165.     }
  166.   else
  167.     {
  168.       euid = geteuid ();
  169.       ruid = getuid ();
  170.       egid = getegid ();
  171.       rgid = getgid ();
  172.     }
  173.  
  174.   if (just_user)
  175.     print_user (use_real ? ruid : euid);
  176.   else if (just_group)
  177.     print_group (use_real ? rgid : egid);
  178.   else if (just_group_list)
  179.     print_group_list (argv[optind]);
  180.   else
  181.     print_full_info (argv[optind]);
  182.   putchar ('\n');
  183.  
  184.   exit (problems != 0);
  185. }
  186.  
  187. /* Print the name or value of user ID UID. */
  188.  
  189. static void
  190. print_user (uid)
  191.      int uid;
  192. {
  193.   struct passwd *pwd = NULL;
  194.  
  195.   if (use_name)
  196.     {
  197.       pwd = getpwuid (uid);
  198.       if (pwd == NULL)
  199.     problems++;
  200.     }
  201.  
  202.   if (pwd == NULL)
  203.     printf ("%u", (unsigned) uid);
  204.   else
  205.     printf ("%s", pwd->pw_name);
  206. }
  207.  
  208. /* Print the name or value of group ID GID. */
  209.  
  210. static void
  211. print_group (gid)
  212.      int gid;
  213. {
  214.   struct group *grp = NULL;
  215.  
  216.   if (use_name)
  217.     {
  218.       grp = getgrgid (gid);
  219.       if (grp == NULL)
  220.     problems++;
  221.     }
  222.  
  223.   if (grp == NULL)
  224.     printf ("%u", (unsigned) gid);
  225.   else
  226.     printf ("%s", grp->gr_name);
  227. }
  228.  
  229. /* Print all of the distinct groups the user is in . */
  230.  
  231. static void
  232. print_group_list (username)
  233.      char *username;
  234. {
  235.   print_group (rgid);
  236.   if (egid != rgid)
  237.     {
  238.       putchar (' ');
  239.       print_group (egid);
  240.     }
  241.  
  242. #if defined(NGROUPS_MAX) && defined(HAVE_GETGROUPS)
  243.   {
  244.     int ngroups;
  245.     GETGROUPS_T *groups;
  246.     register int i;
  247.  
  248.     groups = (GETGROUPS_T *) xmalloc (NGROUPS_MAX * sizeof (GETGROUPS_T));
  249.     if (username == 0)
  250.       ngroups = getgroups (NGROUPS_MAX, groups);
  251.     else
  252.       ngroups = getugroups (NGROUPS_MAX, groups, username);
  253.     if (ngroups < 0)
  254.       {
  255.     error (0, errno, "cannot get supplemental group list");
  256.     problems++;
  257.     free (groups);
  258.     return;
  259.       }
  260.  
  261.     for (i = 0; i < ngroups; i++)
  262.       if (groups[i] != rgid && groups[i] != egid)
  263.     {
  264.       putchar (' ');
  265.       print_group (groups[i]);
  266.     }
  267.     free (groups);
  268.   }
  269. #endif
  270. }
  271.  
  272. /* Print all of the info about the user's user and group IDs. */
  273.  
  274. static void
  275. print_full_info (username)
  276.      char *username;
  277. {
  278.   struct passwd *pwd;
  279.   struct group *grp;
  280.  
  281.   printf ("uid=%u", (unsigned) ruid);
  282.   pwd = getpwuid (ruid);
  283.   if (pwd == NULL)
  284.     problems++;
  285.   else
  286.     printf ("(%s)", pwd->pw_name);
  287.   
  288.   printf (" gid=%u", (unsigned) rgid);
  289.   grp = getgrgid (rgid);
  290.   if (grp == NULL)
  291.     problems++;
  292.   else
  293.     printf ("(%s)", grp->gr_name);
  294.   
  295.   if (euid != ruid)
  296.     {
  297.       printf (" euid=%u", (unsigned) euid);
  298.       pwd = getpwuid (euid);
  299.       if (pwd == NULL)
  300.     problems++;
  301.       else
  302.     printf ("(%s)", pwd->pw_name);
  303.     }
  304.   
  305.   if (egid != rgid)
  306.     {
  307.       printf (" egid=%u", (unsigned) egid);
  308.       grp = getgrgid (egid);
  309.       if (grp == NULL)
  310.     problems++;
  311.       else
  312.     printf ("(%s)", grp->gr_name);
  313.     }
  314.  
  315. #if defined(NGROUPS_MAX) && defined(HAVE_GETGROUPS)
  316.   {
  317.     int ngroups;
  318.     GETGROUPS_T *groups;
  319.     register int i;
  320.  
  321.     groups = (GETGROUPS_T *) xmalloc (NGROUPS_MAX * sizeof (GETGROUPS_T));
  322.     if (username == 0)
  323.       ngroups = getgroups (NGROUPS_MAX, groups);
  324.     else
  325.       ngroups = getugroups (NGROUPS_MAX, groups, username);
  326.     if (ngroups < 0)
  327.       {
  328.     error (0, errno, "cannot get supplemental group list");
  329.     problems++;
  330.     free (groups);
  331.     return;
  332.       }
  333.  
  334.     if (ngroups > 0)
  335.       fputs (" groups=", stdout);
  336.     for (i = 0; i < ngroups; i++)
  337.       {
  338.     if (i > 0)
  339.       putchar (',');
  340.     printf ("%u", (unsigned) groups[i]);
  341.     grp = getgrgid (groups[i]);
  342.     if (grp == NULL)
  343.       problems++;
  344.     else
  345.       printf ("(%s)", grp->gr_name);
  346.       }
  347.     free (groups);
  348.   }
  349. #endif
  350. }
  351.  
  352. static void
  353. usage (status)
  354.      int status;
  355. {
  356.   if (status != 0)
  357.     fprintf (stderr, "Try `%s --help' for more information.\n",
  358.          program_name);
  359.   else
  360.     {
  361.       printf ("Usage: %s [OPTION]... [USERNAME]\n", program_name);
  362.       printf ("\
  363. \n\
  364.   -g, --group     print only the group ID\n\
  365.   -G, --groups    print only the supplementary groups\n\
  366.   -n, --name      print a name instead of a number, for -ugG\n\
  367.   -r, --real      print the real ID instead of effective ID, for -ugG\n\
  368.   -u, --user      print only the user ID\n\
  369.       --help      display this help and exit\n\
  370.       --version   output version information and exit\n\
  371. \n\
  372. Without any OPTION, print some useful set of identified information.\n\
  373. ");
  374.     }
  375.   exit (status);
  376. }
  377.