Whamcloud - gitweb
merge b_devel into HEAD. Includes:
[fs/lustre-release.git] / lustre / tests / runas.c
1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2  * vim:expandtab:shiftwidth=8:tabstop=8:
3  */
4 #include <stdio.h>
5 #include <stdlib.h>
6 #include <unistd.h>
7 #include <string.h>
8 #include <errno.h>
9 #include <sys/types.h>
10 #include <sys/wait.h>
11
12 #define DEBUG 0
13
14 void
15 Usage_and_abort()
16 {
17        fprintf(stderr, "Usage: runas -u user_id [ -g grp_id ]" \
18            " command_to_be_run \n");
19        exit(-1);
20 }
21
22 // Usage: runas -u user_id [ -g grp_id ] "command_to_be_run"
23 // return: the return value of "command_to_be_run"
24 // NOTE: returning -1 might be the return code of this program itself or
25 // the "command_to_be_run"
26
27 // ROOT runs "runas" for free
28 // Other users run "runas" requires  chmod 6755 "command_to_be_run"
29
30 int 
31 main(int argc, char**argv)
32 {
33         char command[1024];
34         char *cmd_ptr;
35         int status;
36         int c,i;
37         int gid_is_set = 0;
38         int uid_is_set = 0;
39         uid_t user_id;
40         gid_t grp_id;
41
42         if(argc == 1) {
43                 Usage_and_abort();
44         }
45
46         // get UID and GID
47         while ((c = getopt (argc, argv, "u:g:h")) != -1) {
48                 switch (c) {
49                 case 'u':
50                         user_id = (uid_t)atoi(optarg);
51                         uid_is_set = 1;
52                         if(!gid_is_set) {
53                                   grp_id = user_id;
54                         }
55                  break;
56
57                  case 'g':
58                          grp_id = (gid_t)atoi(optarg);
59                          gid_is_set = 1;
60                  break;
61
62                  case 'h':
63                          Usage_and_abort ();
64                  break;
65
66                  default:
67                  //      fprintf(stderr, "Bad parameters.\n");
68                  //      Usage_and_abort ();
69                  }
70         }
71
72         if (!uid_is_set){
73                 Usage_and_abort ();
74         }
75   
76
77         if(optind == argc) {
78                 fprintf(stderr, "Bad parameters.\n");
79                 Usage_and_abort();
80         }
81
82
83         // assemble the command
84         cmd_ptr = command ;
85         for (i = optind; i < argc; i++)
86                  cmd_ptr += sprintf(cmd_ptr,  "%s ", argv[i]);
87
88
89 #if DEBUG
90   system("whoami");
91 #endif
92
93         // set GID
94         status = setregid(grp_id, grp_id );
95         if( status == -1) {
96                  fprintf(stderr, "Cannot change grp_ID to %d, errno=%d (%s)\n",
97                    grp_id, errno, strerror(errno) );
98                  exit(-1);
99         }
100
101         // set UID
102         status = setreuid(user_id, user_id );
103         if(status == -1) {
104                   fprintf(stderr,"Cannot change user_ID to %d, errno=%d (%s)\n",
105                     user_id, errno, strerror(errno) );
106                   exit(-1);
107         }
108
109 #if DEBUG
110   system("whoami");
111 #endif
112
113         fprintf(stdout, "running as USER(%d), Grp (%d):  \"%s\" \n", 
114            user_id, grp_id, command );
115
116         // run the command
117         status = system(command);
118
119         // pass the return code of command_to_be_run out of this wrapper
120         if (status == -1) {
121                  fprintf(stderr, "%s: system() command failed to run\n",
122                            argv[0]);
123         }
124         else{
125                  status = WEXITSTATUS(status);
126                  fprintf(stderr, "[%s #%d] \"%s\" returns %d (%s).\n", argv[0],
127                         user_id, argv[optind], status, strerror(status));
128
129         }
130
131         return(status);
132 }
133