2 * Copyright 1991 - 1994, Julianne Frances Haugh
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * 3. Neither the name of Julianne F. Haugh nor the names of its contributors
14 * may be used to endorse or promote products derived from this software
15 * without specific prior written permission.
17 * THIS SOFTWARE IS PROVIDED BY JULIE HAUGH AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL JULIE HAUGH OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
47 #include <sys/types.h>
55 #include "prototypes.h"
64 #define SKEL_DIR "/etc/skel"
66 #ifndef USER_DEFAULTS_FILE
67 #define USER_DEFAULTS_FILE "/etc/default/useradd"
68 #define NEW_USER_FILE "/etc/default/nuaddXXXXXX"
71 * Needed for MkLinux DR1/2/2.1 - J.
74 #define LASTLOG_FILE "/var/log/lastlog"
80 * These defaults are used if there is no defaults file.
82 static gid_t def_group = 100;
83 static const char *def_gname = "other";
84 static const char *def_home = "/home";
85 static const char *def_shell = "";
86 static const char *def_template = SKEL_DIR;
87 static const char *def_create_mail_spool = "no";
89 static long def_inactive = -1;
90 static const char *def_expire = "";
92 static char def_file[] = USER_DEFAULTS_FILE;
94 #define VALID(s) (strcspn (s, ":\n") == strlen (s))
96 static const char *user_name = "";
97 static const char *user_pass = "!";
99 static gid_t user_gid;
100 static const char *user_comment = "";
101 static const char *user_home = "";
102 static const char *user_shell = "";
103 static const char *create_mail_spool = "";
105 static long user_expire = -1;
106 static int is_shadow_pwd;
109 static int is_shadow_grp;
111 static char **user_groups; /* NULL-terminated list */
112 static long sys_ngroups;
113 static int do_grp_update = 0; /* group files need to be updated */
118 bflg = 0, /* new default root of home directory */
119 cflg = 0, /* comment (GECOS) field for new account */
120 dflg = 0, /* home directory for new account */
121 Dflg = 0, /* set/show new user default values */
122 eflg = 0, /* days since 1970-01-01 when account is locked */
123 fflg = 0, /* days until account with expired password is locked */
124 gflg = 0, /* primary group ID for new account */
125 Gflg = 0, /* secondary group set for new account */
126 kflg = 0, /* specify a directory to fill new user directory */
127 lflg = 0, /* do not add user to lastlog database file */
128 mflg = 0, /* create user's home directory if it doesn't exist */
129 nflg = 0, /* create a group having the same name as the user */
130 oflg = 0, /* permit non-unique user ID to be specified with -u */
131 sflg = 0, /* shell program for new account */
132 uflg = 0; /* specify user ID for new account */
137 static int home_added;
142 #define E_SUCCESS 0 /* success */
143 #define E_PW_UPDATE 1 /* can't update password file */
144 #define E_USAGE 2 /* invalid command syntax */
145 #define E_BAD_ARG 3 /* invalid argument to option */
146 #define E_UID_IN_USE 4 /* UID already in use (and no -o) */
147 #define E_NOTFOUND 6 /* specified group doesn't exist */
148 #define E_NAME_IN_USE 9 /* username already in use */
149 #define E_GRP_UPDATE 10 /* can't update group file */
150 #define E_HOMEDIR 12 /* can't create home directory */
151 #define E_MAIL_SPOOL 13 /* can't create mail spool */
153 #define DGROUP "GROUP="
155 #define SHELL "SHELL="
156 #define INACT "INACTIVE="
157 #define EXPIRE "EXPIRE="
159 #define CREATE_MAIL_SPOOL "CREATE_MAIL_SPOOL="
161 /* local function prototypes */
162 static void fail_exit (int);
163 static struct group *getgr_nam_gid (const char *);
164 static long get_number (const char *);
165 static uid_t get_uid (const char *);
166 static void get_defaults (void);
167 static void show_defaults (void);
168 static int set_defaults (void);
169 static int get_groups (char *);
170 static void usage (void);
171 static void new_pwent (struct passwd *);
173 static long scale_age (long);
174 static void new_spent (struct spwd *);
175 static void grp_update (void);
176 static void find_new_uid (void);
178 static void process_flags (int argc, char **argv);
179 static void close_files (void);
180 static void open_files (void);
181 static void faillog_reset (uid_t);
182 static void lastlog_reset (uid_t);
183 static void usr_update (void);
184 static void create_home (void);
185 static void create_mail (void);
188 * fail_exit - undo as much as possible
190 static void fail_exit (int code)
196 audit_logger (AUDIT_USER_CHAUTHTOK, Prog, "adding user", user_name, -1,
199 SYSLOG ((LOG_INFO, "failed adding user `%s', data deleted", user_name));
203 static struct group *getgr_nam_gid (const char *grname)
208 gid = strtol (grname, &errptr, 10);
209 if (*grname != '\0' && *errptr == '\0' && errno != ERANGE && gid >= 0)
210 return xgetgrgid (gid);
211 return xgetgrnam (grname);
214 static long get_number (const char *numstr)
219 val = strtol (numstr, &errptr, 10);
220 if (*errptr || errno == ERANGE) {
221 fprintf (stderr, _("%s: invalid numeric argument '%s'\n"), Prog,
228 static uid_t get_uid (const char *uidstr)
233 val = strtol (uidstr, &errptr, 10);
234 if (*errptr || errno == ERANGE || val < 0) {
236 _("%s: invalid numeric argument '%s'\n"), Prog,
243 #define MATCH(x,y) (strncmp((x),(y),strlen(y)) == 0)
246 * get_defaults - read the defaults file
248 * get_defaults() reads the defaults file for this command. It sets the
249 * various values from the file, or uses built-in default values if the
250 * file does not exist.
252 static void get_defaults (void)
259 * Open the defaults file for reading.
262 if (!(fp = fopen (def_file, "r")))
266 * Read the file a line at a time. Only the lines that have relevant
267 * values are used, everything else can be ignored.
269 while (fgets (buf, sizeof buf, fp)) {
270 if ((cp = strrchr (buf, '\n')))
273 if (!(cp = strchr (buf, '=')))
279 * Primary GROUP identifier
281 if (MATCH (buf, DGROUP)) {
282 unsigned int val = (unsigned int) strtoul (cp, &ep, 10);
283 const struct group *grp;
285 if (*cp != '\0' && *ep == '\0') { /* valid number */
287 /* local, no need for xgetgrgid */
288 if ((grp = getgrgid (def_group))) {
289 def_gname = xstrdup (grp->gr_name);
292 _("%s: unknown GID %s\n"),
295 /* local, no need for xgetgrnam */
296 } else if ((grp = getgrnam (cp))) {
297 def_group = grp->gr_gid;
298 def_gname = xstrdup (cp);
301 _("%s: unknown group %s\n"), Prog, cp);
306 * Default HOME filesystem
308 else if (MATCH (buf, HOME)) {
309 def_home = xstrdup (cp);
313 * Default Login Shell command
315 else if (MATCH (buf, SHELL)) {
316 def_shell = xstrdup (cp);
320 * Default Password Inactive value
322 else if (MATCH (buf, INACT)) {
323 long val = strtol (cp, &ep, 10);
325 if (*cp || errno == ERANGE)
332 * Default account expiration date
334 else if (MATCH (buf, EXPIRE)) {
335 def_expire = xstrdup (cp);
339 * Default Skeleton information
341 else if (MATCH (buf, SKEL)) {
343 cp = SKEL_DIR; /* XXX warning: const */
345 def_template = xstrdup (cp);
349 * Create by default user mail spool or not ?
351 else if (MATCH (buf, CREATE_MAIL_SPOOL)) {
353 cp = CREATE_MAIL_SPOOL; /* XXX warning: const */
355 def_create_mail_spool = xstrdup (cp);
361 * show_defaults - show the contents of the defaults file
363 * show_defaults() displays the values that are used from the default
364 * file and the built-in values.
366 static void show_defaults (void)
368 printf ("GROUP=%u\n", (unsigned int) def_group);
369 printf ("HOME=%s\n", def_home);
370 printf ("INACTIVE=%ld\n", def_inactive);
371 printf ("EXPIRE=%s\n", def_expire);
372 printf ("SHELL=%s\n", def_shell);
373 printf ("SKEL=%s\n", def_template);
374 printf ("CREATE_MAIL_SPOOL=%s\n", def_create_mail_spool);
378 * set_defaults - write new defaults file
380 * set_defaults() re-writes the defaults file using the values that
381 * are currently set. Duplicated lines are pruned, missing lines are
382 * added, and unrecognized lines are copied as is.
384 static int set_defaults (void)
389 static char new_file[] = NEW_USER_FILE;
394 int out_inactive = 0;
398 int out_create_mail_spool = 0;
401 * Create a temporary file to copy the new output to.
403 if ((ofd = mkstemp (new_file)) == -1) {
405 _("%s: cannot create new defaults file\n"), Prog);
409 if (!(ofp = fdopen (ofd, "w"))) {
410 fprintf (stderr, _("%s: cannot open new defaults file\n"),
416 * Open the existing defaults file and copy the lines to the
417 * temporary file, using any new values. Each line is checked
418 * to insure that it is not output more than once.
420 if (!(ifp = fopen (def_file, "r"))) {
421 fprintf (ofp, "# useradd defaults file\n");
425 while (fgets (buf, sizeof buf, ifp)) {
426 if ((cp = strrchr (buf, '\n')))
429 if (!out_group && MATCH (buf, DGROUP)) {
430 fprintf (ofp, DGROUP "%u\n", (unsigned int) def_group);
432 } else if (!out_home && MATCH (buf, HOME)) {
433 fprintf (ofp, HOME "%s\n", def_home);
435 } else if (!out_inactive && MATCH (buf, INACT)) {
436 fprintf (ofp, INACT "%ld\n", def_inactive);
438 } else if (!out_expire && MATCH (buf, EXPIRE)) {
439 fprintf (ofp, EXPIRE "%s\n", def_expire);
441 } else if (!out_shell && MATCH (buf, SHELL)) {
442 fprintf (ofp, SHELL "%s\n", def_shell);
444 } else if (!out_skel && MATCH (buf, SKEL)) {
445 fprintf (ofp, SKEL "%s\n", def_template);
447 } else if (!out_create_mail_spool
448 && MATCH (buf, CREATE_MAIL_SPOOL)) {
449 fprintf (ofp, CREATE_MAIL_SPOOL "%s\n",
450 def_create_mail_spool);
451 out_create_mail_spool++;
453 fprintf (ofp, "%s\n", buf);
459 * Check each line to insure that every line was output. This
460 * causes new values to be added to a file which did not previously
461 * have an entry for that value.
464 fprintf (ofp, DGROUP "%u\n", (unsigned int) def_group);
466 fprintf (ofp, HOME "%s\n", def_home);
468 fprintf (ofp, INACT "%ld\n", def_inactive);
470 fprintf (ofp, EXPIRE "%s\n", def_expire);
472 fprintf (ofp, SHELL "%s\n", def_shell);
474 fprintf (ofp, SKEL "%s\n", def_template);
476 if (!out_create_mail_spool)
477 fprintf (ofp, CREATE_MAIL_SPOOL "%s\n", def_create_mail_spool);
480 * Flush and close the file. Check for errors to make certain
481 * the new file is intact.
484 if (ferror (ofp) || fclose (ofp)) {
490 * Rename the current default file to its backup name.
492 snprintf (buf, sizeof buf, "%s-", def_file);
493 if (rename (def_file, buf) && errno != ENOENT) {
494 snprintf (buf, sizeof buf, _("%s: rename: %s"), Prog, def_file);
501 * Rename the new default file to its correct name.
503 if (rename (new_file, def_file)) {
504 snprintf (buf, sizeof buf, _("%s: rename: %s"), Prog, new_file);
509 audit_logger (AUDIT_USER_CHAUTHTOK, Prog, "changing user defaults",
513 "useradd defaults: GROUP=%u, HOME=%s, SHELL=%s, INACTIVE=%ld, "
514 "EXPIRE=%s, SKEL=%s, CREATE_MAIL_SPOOL=%s",
515 (unsigned int) def_group, def_home, def_shell,
516 def_inactive, def_expire, def_template,
517 def_create_mail_spool));
522 * get_groups - convert a list of group names to an array of group IDs
524 * get_groups() takes a comma-separated list of group names and
525 * converts it to a NULL-terminated array. Any unknown group
526 * names are reported as errors.
528 static int get_groups (char *list)
531 const struct group *grp;
539 * So long as there is some data to be converted, strip off
540 * each name and look it up. A mix of numerical and string
541 * values for group identifiers is permitted.
545 * Strip off a single name from the list
547 if ((cp = strchr (list, ',')))
551 * Names starting with digits are treated as numerical
552 * GID values, otherwise the string is looked up as is.
554 grp = getgr_nam_gid (list);
557 * There must be a match, either by GID value or by
561 fprintf (stderr, _("%s: unknown group %s\n"),
568 * If the group doesn't exist, don't dump core...
569 * Instead, try the next one. --marekm
576 * Don't add this group if they are an NIS group. Tell
577 * the user to go to the server for this group.
581 _("%s: group '%s' is a NIS group.\n"),
587 if (ngroups == sys_ngroups) {
590 ("%s: too many groups specified (max %d).\n"),
596 * Add the group name to the user's list of groups.
598 user_groups[ngroups++] = xstrdup (grp->gr_name);
601 user_groups[ngroups] = (char *) 0;
604 * Any errors in finding group names are fatal
613 * usage - display usage message and exit
615 static void usage (void)
617 fprintf (stderr, _("Usage: useradd [options] LOGIN\n"
620 " -b, --base-dir BASE_DIR base directory for the new user account\n"
622 " -c, --comment COMMENT set the GECOS field for the new user account\n"
623 " -d, --home-dir HOME_DIR home directory for the new user account\n"
624 " -D, --defaults print or save modified default useradd\n"
626 " -e, --expiredate EXPIRE_DATE set account expiration date to EXPIRE_DATE\n"
627 " -f, --inactive INACTIVE set password inactive after expiration\n"
629 " -g, --gid GROUP force use GROUP for the new user account\n"
630 " -G, --groups GROUPS list of supplementary groups for the new\n"
632 " -h, --help display this help message and exit\n"
633 " -k, --skel SKEL_DIR specify an alternative skel directory\n"
634 " -K, --key KEY=VALUE overrides /etc/login.defs defaults\n"
635 " -l, do not add the user to the lastlog and\n"
636 " faillog databases\n"
637 " -m, --create-home create home directory for the new user\n"
639 " -o, --non-unique allow create user with duplicate\n"
640 " (non-unique) UID\n"
641 " -p, --password PASSWORD use encrypted password for the new user\n"
643 " -s, --shell SHELL the login shell for the new user account\n"
644 " -u, --uid UID force use the UID for the new user account\n"
650 * new_pwent - initialize the values in a password file entry
652 * new_pwent() takes all of the values that have been entered and
653 * fills in a (struct passwd) with them.
655 static void new_pwent (struct passwd *pwent)
657 memzero (pwent, sizeof *pwent);
658 pwent->pw_name = (char *) user_name;
660 pwent->pw_passwd = (char *) SHADOW_PASSWD_STRING;
662 pwent->pw_passwd = (char *) user_pass;
664 pwent->pw_uid = user_id;
665 pwent->pw_gid = user_gid;
666 pwent->pw_gecos = (char *) user_comment;
667 pwent->pw_dir = (char *) user_home;
668 pwent->pw_shell = (char *) user_shell;
671 static long scale_age (long x)
676 return x * (DAY / SCALE);
680 * new_spent - initialize the values in a shadow password file entry
682 * new_spent() takes all of the values that have been entered and
683 * fills in a (struct spwd) with them.
685 static void new_spent (struct spwd *spent)
687 memzero (spent, sizeof *spent);
688 spent->sp_namp = (char *) user_name;
689 spent->sp_pwdp = (char *) user_pass;
690 spent->sp_lstchg = time ((time_t *) 0) / SCALE;
691 spent->sp_min = scale_age (getdef_num ("PASS_MIN_DAYS", -1));
692 spent->sp_max = scale_age (getdef_num ("PASS_MAX_DAYS", -1));
693 spent->sp_warn = scale_age (getdef_num ("PASS_WARN_AGE", -1));
694 spent->sp_inact = scale_age (def_inactive);
695 spent->sp_expire = scale_age (user_expire);
700 * grp_update - add user to secondary group set
702 * grp_update() takes the secondary group set given in user_groups
703 * and adds the user to each group given by that set.
705 * The group files are opened and locked in open_files().
707 * close_files() should be called afterwards to commit the changes
708 * and unlocking the group files.
710 static void grp_update (void)
712 const struct group *grp;
716 const struct sgrp *sgrp;
721 * Scan through the entire group file looking for the groups that
722 * the user is a member of.
724 for (gr_rewind (), grp = gr_next (); grp; grp = gr_next ()) {
727 * See if the user specified this group as one of their
730 if (!is_on_list (user_groups, grp->gr_name))
734 * Make a copy - gr_update() will free() everything
735 * from the old entry, and we need it later.
737 ngrp = __gr_dup (grp);
740 _("%s: Out of memory. Cannot update the group database.\n"),
742 fail_exit (E_GRP_UPDATE); /* XXX */
746 * Add the username to the list of group members and
747 * update the group entry to reflect the change.
749 ngrp->gr_mem = add_list (ngrp->gr_mem, user_name);
750 if (!gr_update (ngrp)) {
752 _("%s: error adding new group entry\n"), Prog);
753 fail_exit (E_GRP_UPDATE);
756 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
757 "adding user to group", user_name, -1, 1);
759 SYSLOG ((LOG_INFO, "add `%s' to group `%s'",
760 user_name, ngrp->gr_name));
768 * Scan through the entire shadow group file looking for the groups
769 * that the user is a member of. The administrative list isn't
772 for (sgr_rewind (), sgrp = sgr_next (); sgrp; sgrp = sgr_next ()) {
775 * See if the user specified this group as one of their
778 if (!gr_locate (sgrp->sg_name))
781 if (!is_on_list (user_groups, sgrp->sg_name))
785 * Make a copy - sgr_update() will free() everything
786 * from the old entry, and we need it later.
788 nsgrp = __sgr_dup (sgrp);
791 _("%s: Out of memory. Cannot update the shadow group database.\n"),
793 fail_exit (E_GRP_UPDATE); /* XXX */
797 * Add the username to the list of group members and
798 * update the group entry to reflect the change.
800 nsgrp->sg_mem = add_list (nsgrp->sg_mem, user_name);
801 if (!sgr_update (nsgrp)) {
803 _("%s: error adding new group entry\n"), Prog);
804 fail_exit (E_GRP_UPDATE);
807 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
808 "adding user to shadow group", user_name, -1, 1);
810 SYSLOG ((LOG_INFO, "add `%s' to shadow group `%s'",
811 user_name, nsgrp->sg_name));
813 #endif /* SHADOWGRP */
817 * find_new_uid - find the next available UID
819 * find_new_uid() locates the next highest unused UID in the password
822 static void find_new_uid (void)
824 const struct passwd *pwd;
825 uid_t uid_min, uid_max;
828 * It doesn't make sense to use find_new_uid(),
829 * if an UID is specified via "-u" option.
833 uid_min = getdef_unum ("UID_MIN", 1000);
834 uid_max = getdef_unum ("UID_MAX", 60000);
839 * Search the entire password file,
840 * looking for the largest unused value.
843 while ((pwd = getpwent ()) != NULL) {
844 if ((pwd->pw_uid >= user_id) && (pwd->pw_uid <= uid_max)) {
845 user_id = pwd->pw_uid + 1;
850 * If a user with UID equal to UID_MAX exists, the above algorithm
851 * will give us UID_MAX+1 even if not unique. Search for the first
852 * free UID starting with UID_MIN (it's O(n*n) but can be avoided
853 * by not having users with UID equal to UID_MAX). --marekm
855 if (user_id == uid_max + 1) {
856 for (user_id = uid_min; user_id < uid_max; user_id++) {
857 /* local, no need for xgetpwuid */
858 if (!getpwuid (user_id))
861 if (user_id == uid_max) {
862 fprintf (stderr, _("%s: can't get unique UID (run out of UIDs)\n"), Prog);
863 fail_exit (E_UID_IN_USE);
869 * find_new_gid - find the next available GID
871 * find_new_gid() locates the next highest unused GID in the group
874 static void find_new_gid ()
876 const struct group *grp;
877 gid_t gid_min, gid_max;
880 * It doesn't make sense to use find_new_gid(),
881 * if a group is specified via "-g" option.
885 gid_min = getdef_num ("GID_MIN", 500);
886 gid_max = getdef_num ("GID_MAX", 60000);
891 * Search the entire group file, either looking for this
892 * GID (if the user specified one with -g) or looking for the
893 * largest unused value.
896 while ((grp = getgrent ())) {
897 if ((grp->gr_gid >= user_gid) && (grp->gr_gid <= gid_max)) {
898 user_gid = grp->gr_gid + 1;
901 if (user_gid == gid_max + 1) {
902 for (user_gid = gid_min; user_gid < gid_max; user_gid++) {
903 /* local, no need for xgetgrgid */
904 if (!getgrgid (user_gid))
907 if (user_gid == gid_max) {
909 "%s: can't get unique gid (run out of GIDs)\n",
917 * process_flags - perform command line argument setting
919 * process_flags() interprets the command line arguments and sets
920 * the values that the user will be created with accordingly. The
921 * values are checked for sanity.
923 static void process_flags (int argc, char **argv)
925 const struct group *grp;
931 * Parse the command line options.
934 static struct option long_options[] = {
935 {"base-dir", required_argument, NULL, 'b'},
936 {"comment", required_argument, NULL, 'c'},
937 {"home-dir", required_argument, NULL, 'd'},
938 {"defaults", required_argument, NULL, 'D'},
939 {"expiredate", required_argument, NULL, 'e'},
940 {"inactive", required_argument, NULL, 'f'},
941 {"gid", required_argument, NULL, 'g'},
942 {"groups", required_argument, NULL, 'G'},
943 {"help", no_argument, NULL, 'h'},
944 {"skel", required_argument, NULL, 'k'},
945 {"key", required_argument, NULL, 'K'},
946 {"create-home", no_argument, NULL, 'm'},
947 {"non-unique", no_argument, NULL, 'o'},
948 {"password", required_argument, NULL, 'p'},
949 {"shell", required_argument, NULL, 's'},
950 {"uid", required_argument, NULL, 'u'},
951 {NULL, 0, NULL, '\0'}
954 getopt_long (argc, argv, "b:c:d:De:f:g:G:k:K:lmMop:s:u:",
955 long_options, NULL)) != -1) {
959 || optarg[0] != '/') {
962 ("%s: invalid base directory '%s'\n"),
970 if (!VALID (optarg)) {
973 ("%s: invalid comment '%s'\n"),
977 user_comment = optarg;
982 || optarg[0] != '/') {
985 ("%s: invalid home directory '%s'\n"),
999 user_expire = strtoday (optarg);
1000 if (user_expire == -1) {
1003 ("%s: invalid date '%s'\n"),
1011 * -e "" is allowed - it's a no-op without /etc/shadow
1013 if (*optarg && !is_shadow_pwd) {
1016 ("%s: shadow passwords required for -e\n"),
1021 def_expire = optarg;
1025 def_inactive = get_number (optarg);
1027 * -f -1 is allowed - it's a no-op without /etc/shadow
1029 if (def_inactive != -1 && !is_shadow_pwd) {
1032 ("%s: shadow passwords required for -f\n"),
1039 grp = getgr_nam_gid (optarg);
1043 ("%s: unknown group %s\n"),
1048 def_group = grp->gr_gid;
1051 user_gid = grp->gr_gid;
1056 if (get_groups (optarg))
1066 def_template = optarg;
1071 * override login.defs defaults (-K name=value)
1072 * example: -K UID_MIN=100 -K UID_MAX=499
1073 * note: -K UID_MIN=10,UID_MAX=499 doesn't work yet
1075 cp = strchr (optarg, '=');
1079 ("%s: -K requires KEY=VALUE\n"),
1083 /* terminate name, point to value */
1085 if (putdef_str (optarg, cp) < 0)
1097 case 'p': /* set encrypted password */
1098 if (!VALID (optarg)) {
1101 ("%s: invalid field '%s'\n"),
1110 && (optarg[0] != '/'
1111 && optarg[0] != '*'))) {
1114 ("%s: invalid shell '%s'\n"),
1118 user_shell = optarg;
1123 user_id = get_uid (optarg);
1134 * Certain options are only valid in combination with others.
1135 * Check it here so that they can be specified in any order.
1137 if ((oflg && !uflg) || (kflg && !mflg))
1141 * Either -D or username is required. Defaults can be set with -D
1142 * for the -b, -e, -f, -g, -s options only.
1148 if (uflg || oflg || Gflg || dflg || cflg || mflg)
1151 if (optind != argc - 1)
1154 user_name = argv[optind];
1155 if (!check_user_name (user_name)) {
1158 ("%s: invalid user name '%s'\n"),
1161 audit_logger (AUDIT_USER_CHAUTHTOK, Prog, "adding user",
1169 uh = xmalloc (strlen (def_home) +
1170 strlen (user_name) + 2);
1171 sprintf (uh, "%s/%s", def_home, user_name);
1177 user_expire = strtoday (def_expire);
1180 user_gid = def_group;
1183 user_shell = def_shell;
1185 /* TODO: add handle change default spool mail creation by
1186 -K CREATE_MAIL_SPOOL={yes,no}. It need rewrite internal API for handle
1187 shadow tools configuration */
1188 create_mail_spool = def_create_mail_spool;
1192 * close_files - close all of the files that were opened
1194 * close_files() closes all of the files that were opened for this
1195 * new user. This causes any modified entries to be written out.
1197 static void close_files (void)
1200 fprintf (stderr, _("%s: cannot rewrite password file\n"), Prog);
1201 fail_exit (E_PW_UPDATE);
1203 if (is_shadow_pwd && !spw_close ()) {
1205 _("%s: cannot rewrite shadow password file\n"), Prog);
1206 fail_exit (E_PW_UPDATE);
1208 if (do_grp_update) {
1211 _("%s: cannot rewrite group file\n"), Prog);
1212 fail_exit (E_GRP_UPDATE);
1215 if (is_shadow_grp && !sgr_close ()) {
1218 ("%s: cannot rewrite shadow group file\n"),
1220 fail_exit (E_GRP_UPDATE);
1235 * open_files - lock and open the password files
1237 * open_files() opens the two password files.
1239 static void open_files (void)
1242 fprintf (stderr, _("%s: unable to lock password file\n"), Prog);
1244 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1245 "locking password file", user_name, user_id, 0);
1249 if (!pw_open (O_RDWR)) {
1250 fprintf (stderr, _("%s: unable to open password file\n"), Prog);
1252 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1253 "opening password file", user_name, user_id, 0);
1258 if (is_shadow_pwd && !spw_lock ()) {
1260 _("%s: cannot lock shadow password file\n"), Prog);
1262 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1263 "locking shadow password file", user_name,
1269 if (is_shadow_pwd && !spw_open (O_RDWR)) {
1271 _("%s: cannot open shadow password file\n"), Prog);
1273 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1274 "opening shadow password file", user_name,
1282 * Lock and open the group file.
1286 fprintf (stderr, _("%s: error locking group file\n"), Prog);
1287 fail_exit (E_GRP_UPDATE);
1289 if (!gr_open (O_RDWR)) {
1290 fprintf (stderr, _("%s: error opening group file\n"), Prog);
1291 fail_exit (E_GRP_UPDATE);
1294 if (is_shadow_grp && !sgr_lock ()) {
1296 _("%s: error locking shadow group file\n"), Prog);
1297 fail_exit (E_GRP_UPDATE);
1299 if (is_shadow_grp && !sgr_open (O_RDWR)) {
1301 _("%s: error opening shadow group file\n"), Prog);
1302 fail_exit (E_GRP_UPDATE);
1307 static char *empty_list = NULL;
1310 * new_grent - initialize the values in a group file entry
1312 * new_grent() takes all of the values that have been entered and fills
1313 * in a (struct group) with them.
1316 static void new_grent (struct group *grent)
1318 memzero (grent, sizeof *grent);
1319 grent->gr_name = (char *) user_name;
1320 grent->gr_passwd = SHADOW_PASSWD_STRING; /* XXX warning: const */
1321 grent->gr_gid = user_gid;
1322 grent->gr_mem = &empty_list;
1327 * new_sgent - initialize the values in a shadow group file entry
1329 * new_sgent() takes all of the values that have been entered and fills
1330 * in a (struct sgrp) with them.
1333 static void new_sgent (struct sgrp *sgent)
1335 memzero (sgent, sizeof *sgent);
1336 sgent->sg_name = (char *) user_name;
1337 sgent->sg_passwd = "!"; /* XXX warning: const */
1338 sgent->sg_adm = &empty_list;
1339 sgent->sg_mem = &empty_list;
1341 #endif /* SHADOWGRP */
1345 * grp_add - add new group file entries
1347 * grp_add() writes the new records to the group files.
1350 static void grp_add (void)
1356 #endif /* SHADOWGRP */
1359 * Create the initial entries for this new group.
1364 #endif /* SHADOWGRP */
1367 * Write out the new group file entry.
1369 if (!gr_update (&grp)) {
1370 fprintf (stderr, _("%s: error adding new group entry\n"), Prog);
1371 fail_exit (E_GRP_UPDATE);
1375 * Write out the new shadow group entries as well.
1377 if (is_shadow_grp && !sgr_update (&sgrp)) {
1378 fprintf (stderr, _("%s: error adding new group entry\n"), Prog);
1379 fail_exit (E_GRP_UPDATE);
1381 #endif /* SHADOWGRP */
1382 SYSLOG ((LOG_INFO, "new group: name=%s, GID=%u", user_name, user_gid));
1386 static void faillog_reset (uid_t uid)
1391 fd = open (FAILLOG_FILE, O_RDWR);
1393 memzero (&fl, sizeof (fl));
1394 lseek (fd, (off_t) sizeof (fl) * uid, SEEK_SET);
1395 write (fd, &fl, sizeof (fl));
1400 static void lastlog_reset (uid_t uid)
1405 fd = open (LASTLOG_FILE, O_RDWR);
1407 memzero (&ll, sizeof (ll));
1408 lseek (fd, (off_t) sizeof (ll) * uid, SEEK_SET);
1409 write (fd, &ll, sizeof (ll));
1415 * usr_update - create the user entries
1417 * usr_update() creates the password file entries for this user
1418 * and will update the group entries if required.
1420 static void usr_update (void)
1422 struct passwd pwent;
1426 * Fill in the password structure with any new fields, making
1427 * copies of strings.
1433 * Create a syslog entry. We need to do this now in case anything
1434 * happens so we know what we were trying to accomplish.
1437 "new user: name=%s, UID=%u, GID=%u, home=%s, shell=%s",
1438 user_name, (unsigned int) user_id,
1439 (unsigned int) user_gid, user_home, user_shell));
1442 * Initialize faillog and lastlog entries for this UID in case
1443 * it belongs to a previously deleted user. We do it only if
1444 * no user with this UID exists yet (entries for shared UIDs
1445 * are left unchanged). --marekm
1447 /* local, no need for xgetpwuid */
1448 if ((!lflg) && (getpwuid (user_id) == NULL)) {
1449 faillog_reset (user_id);
1450 lastlog_reset (user_id);
1454 * Put the new (struct passwd) in the table.
1456 if (!pw_update (&pwent)) {
1458 _("%s: error adding new password entry\n"), Prog);
1463 * Put the new (struct spwd) in the table.
1465 if (is_shadow_pwd && !spw_update (&spent)) {
1468 ("%s: error adding new shadow password entry\n"),
1471 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1472 "adding shadow password", user_name, user_id, 0);
1477 audit_logger (AUDIT_USER_CHAUTHTOK, Prog, "adding user", user_name,
1482 * Do any group file updates for this user.
1489 * create_home - create the user's home directory
1491 * create_home() creates the user's home directory if it does not
1492 * already exist. It will be created mode 755 owned by the user
1493 * with the user's default group.
1495 static void create_home (void)
1497 if (access (user_home, F_OK)) {
1498 /* XXX - create missing parent directories. --marekm */
1499 if (mkdir (user_home, 0)) {
1502 ("%s: cannot create directory %s\n"),
1505 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1506 "adding home directory", user_name,
1509 fail_exit (E_HOMEDIR);
1511 chown (user_home, user_id, user_gid);
1513 0777 & ~getdef_num ("UMASK", GETDEF_DEFAULT_UMASK));
1516 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1517 "adding home directory", user_name, user_id, 1);
1523 * create_mail - create the user's mail spool
1525 * create_mail() creates the user's mail spool if it does not already
1526 * exist. It will be created mode 660 owned by the user and group
1529 static void create_mail (void)
1537 if (strcasecmp (create_mail_spool, "yes") == 0) {
1538 spool = getdef_str ("MAIL_DIR");
1539 if (NULL == spool) {
1540 spool = "/var/mail";
1542 file = alloca (strlen (spool) + strlen (user_name) + 2);
1543 sprintf (file, "%s/%s", spool, user_name);
1544 fd = open (file, O_CREAT | O_WRONLY | O_TRUNC | O_EXCL, 0);
1546 perror (_("Creating mailbox file"));
1550 gr = getgrnam ("mail"); /* local, no need for xgetgrnam */
1554 ("Group 'mail' not found. Creating the user mailbox file with 0600 mode.\n"));
1562 if (fchown (fd, user_id, gid) || fchmod (fd, mode))
1563 perror (_("Setting mailbox file permissions"));
1570 * main - useradd command
1572 int main (int argc, char **argv)
1575 pam_handle_t *pamh = NULL;
1584 * Get my name so that I can use it to report errors.
1586 Prog = Basename (argv[0]);
1588 setlocale (LC_ALL, "");
1589 bindtextdomain (PACKAGE, LOCALEDIR);
1590 textdomain (PACKAGE);
1592 OPENLOG ("useradd");
1594 sys_ngroups = sysconf (_SC_NGROUPS_MAX);
1595 user_groups = malloc ((1 + sys_ngroups) * sizeof (char *));
1597 * Initialize the list to be empty
1599 user_groups[0] = (char *) 0;
1602 is_shadow_pwd = spw_file_present ();
1604 is_shadow_grp = sgr_file_present ();
1609 process_flags (argc, argv);
1612 retval = PAM_SUCCESS;
1615 struct passwd *pampw;
1616 pampw = getpwuid (getuid ()); /* local, no need for xgetpwuid */
1617 if (pampw == NULL) {
1618 retval = PAM_USER_UNKNOWN;
1621 if (retval == PAM_SUCCESS) {
1622 retval = pam_start ("useradd", pampw->pw_name,
1627 if (retval == PAM_SUCCESS) {
1628 retval = pam_authenticate (pamh, 0);
1629 if (retval != PAM_SUCCESS) {
1630 pam_end (pamh, retval);
1634 if (retval == PAM_SUCCESS) {
1635 retval = pam_acct_mgmt (pamh, 0);
1636 if (retval != PAM_SUCCESS) {
1637 pam_end (pamh, retval);
1641 if (retval != PAM_SUCCESS) {
1642 fprintf (stderr, _("%s: PAM authentication failed\n"), Prog);
1645 #endif /* USE_PAM */
1648 * See if we are messing with the defaults file, or creating
1652 if (gflg || bflg || fflg || eflg || sflg)
1653 exit (set_defaults ()? 1 : 0);
1660 * Start with a quick check to see if the user exists.
1662 if (getpwnam (user_name)) { /* local, no need for xgetpwnam */
1663 fprintf (stderr, _("%s: user %s exists\n"), Prog, user_name);
1665 audit_logger (AUDIT_USER_CHAUTHTOK, Prog, "adding user",
1668 exit (E_NAME_IN_USE);
1672 * Don't blindly overwrite a group when a user is added...
1673 * If you already have a group username, and want to add the user
1674 * to that group, use useradd -g username username.
1678 if (getgrnam (user_name)) { /* local, no need for xgetgrnam */
1681 ("%s: group %s exists - if you want to add this user to that group, use -g.\n"),
1684 audit_logger (AUDIT_USER_CHAUTHTOK, Prog,
1685 "adding group", user_name, -1, 0);
1687 exit (E_NAME_IN_USE);
1692 * Do the hard stuff:
1694 * - create the user entries,
1695 * - create the home directory,
1696 * - create user mail spool,
1697 * - flush nscd caches for passwd and group services,
1698 * - then close and update the files.
1703 /* first, seek for a valid uid to use for this user.
1704 * We do this because later we can use the uid we found as
1705 * gid too ... --gafton */
1709 if (getpwuid (user_id) != NULL) {
1710 fprintf (stderr, _("%s: UID %u is not unique\n"), Prog, (unsigned int) user_id);
1712 audit_logger (AUDIT_USER_CHAUTHTOK, Prog, "adding user", user_name, user_id, 0);
1714 exit (E_UID_IN_USE);
1719 /* do we have to add a group for that user? This is why we need to
1720 * open the group files in the open_files() function --gafton */
1721 if (!(nflg || gflg)) {
1731 copy_tree (def_template, user_home, user_id, user_gid);
1735 ("%s: warning: the home directory already exists.\n"
1736 "Not copying any file from skel directory into it.\n"),
1739 } else if (getdef_str ("CREATE_HOME")) {
1741 * RedHat added the CREATE_HOME option in login.defs in their
1742 * version of shadow-utils (which makes -m the default, with
1743 * new -M option to turn it off). Unfortunately, this
1744 * changes the way useradd works (it can be run by scripts
1745 * expecting some standard behaviour), compared to other
1746 * Unices and other Linux distributions, and also adds a lot
1748 * So we now recognize CREATE_HOME and give a warning here
1749 * (better than "configuration error ... notify administrator"
1750 * errors in every program that reads /etc/login.defs). -MM
1754 ("%s: warning: CREATE_HOME not supported, please use -m instead.\n"),
1762 nscd_flush_cache ("passwd");
1763 nscd_flush_cache ("group");
1766 if (retval == PAM_SUCCESS)
1767 pam_end (pamh, PAM_SUCCESS);
1768 #endif /* USE_PAM */