~ubuntu-branches/ubuntu/quantal/shadow/quantal

« back to all changes in this revision

Viewing changes to libmisc/find_new_gid.c

  • Committer: Bazaar Package Importer
  • Author(s): Nicolas Valcárcel Scerpella (Canonical)
  • Date: 2009-11-07 04:55:18 UTC
  • mfrom: (1.1.8 upstream) (18.1.2 sid)
  • Revision ID: james.westby@ubuntu.com-20091107045518-qqclg1lhinz6zv1i
Tags: 1:4.1.4.2-1ubuntu1
* Merged with debian unstable. Remaning changes (LP: #477299):
  - Ubuntu specific:
    + debian/login.defs: use SHA512 by default for password crypt routine.
  - debian/patches/495_stdout-encrypted-password: chpasswd can report
    password hashes on stdout (Debian bug 505640).
  - Rework 495_stdout-encrypted-password to cope with chpasswd using PAM.

Show diffs side-by-side

added added

removed removed

Lines of Context:
52
52
                  /*@null@*/gid_t const *preferred_gid)
53
53
{
54
54
        const struct group *grp;
55
 
        gid_t gid_min, gid_max, group_id;
 
55
        gid_t gid_min, gid_max, group_id, id;
56
56
        bool *used_gids;
57
57
 
58
58
        assert (gid != NULL);
61
61
                gid_min = (gid_t) getdef_ulong ("GID_MIN", 1000UL);
62
62
                gid_max = (gid_t) getdef_ulong ("GID_MAX", 60000UL);
63
63
        } else {
64
 
                gid_min = (gid_t) getdef_ulong ("SYS_GID_MIN", 1UL);
 
64
                gid_min = (gid_t) getdef_ulong ("SYS_GID_MIN", 101UL);
65
65
                gid_max = (gid_t) getdef_ulong ("GID_MIN", 1000UL) - 1;
66
66
                gid_max = (gid_t) getdef_ulong ("SYS_GID_MAX", (unsigned long) gid_max);
67
67
        }
80
80
                return 0;
81
81
        }
82
82
 
83
 
        group_id = gid_min;
84
83
 
85
84
        /*
86
85
         * Search the entire group file,
90
89
         * but we also check the local database (gr_rewind/gr_next) in case
91
90
         * some groups were created but the changes were not committed yet.
92
91
         */
93
 
        setgrent ();
94
 
        while ((grp = getgrent ()) != NULL) {
95
 
                if ((grp->gr_gid >= group_id) && (grp->gr_gid <= gid_max)) {
96
 
                        group_id = grp->gr_gid + 1;
97
 
                }
98
 
                /* create index of used GIDs */
99
 
                if (grp->gr_gid <= gid_max) {
100
 
                        used_gids[grp->gr_gid] = true;
101
 
                }
102
 
        }
103
 
        endgrent ();
104
 
        gr_rewind ();
105
 
        while ((grp = gr_next ()) != NULL) {
106
 
                if ((grp->gr_gid >= group_id) && (grp->gr_gid <= gid_max)) {
107
 
                        group_id = grp->gr_gid + 1;
108
 
                }
109
 
                /* create index of used GIDs */
110
 
                if (grp->gr_gid <= gid_max) {
111
 
                        used_gids[grp->gr_gid] = true;
112
 
                }
113
 
        }
114
 
 
115
 
        /* find free system account in reverse order */
116
92
        if (sys_group) {
117
 
                for (group_id = gid_max; group_id >= gid_min; group_id--) {
118
 
                        if (false == used_gids[group_id]) {
119
 
                                break;
120
 
                        }
121
 
                }
122
 
                if ( group_id < gid_min ) {
123
 
                        fprintf (stderr,
124
 
                                 _("%s: Can't get unique GID (no more available GIDs)\n"),
125
 
                                 Prog);
126
 
                        SYSLOG ((LOG_WARN,
127
 
                                 "no more available GID on the system"));
128
 
                        return -1;
 
93
                /* setgrent / getgrent / endgrent can be very slow with
 
94
                 * LDAP configurations (and many accounts).
 
95
                 * Since there is a limited amount of IDs to be tested
 
96
                 * for system accounts, we just check the existence
 
97
                 * of IDs with getgrgid.
 
98
                 */
 
99
                group_id = gid_max;
 
100
                for (id = gid_max; id >= gid_min; id--) {
 
101
                        if (getgrgid (id) != NULL) {
 
102
                                group_id = id - 1;
 
103
                                used_gids[id] = true;
 
104
                        }
 
105
                }
 
106
 
 
107
                gr_rewind ();
 
108
                while ((grp = gr_next ()) != NULL) {
 
109
                        if ((grp->gr_gid <= group_id) && (grp->gr_gid >= gid_min)) {
 
110
                                group_id = grp->gr_gid - 1;
 
111
                        }
 
112
                        /* create index of used GIDs */
 
113
                        if (grp->gr_gid <= gid_max) {
 
114
                                used_gids[grp->gr_gid] = true;
 
115
                        }
 
116
                }
 
117
        } else {
 
118
                group_id = gid_min;
 
119
                setgrent ();
 
120
                while ((grp = getgrent ()) != NULL) {
 
121
                        if ((grp->gr_gid >= group_id) && (grp->gr_gid <= gid_max)) {
 
122
                                group_id = grp->gr_gid + 1;
 
123
                        }
 
124
                        /* create index of used GIDs */
 
125
                        if (grp->gr_gid <= gid_max) {
 
126
                                used_gids[grp->gr_gid] = true;
 
127
                        }
 
128
                }
 
129
                endgrent ();
 
130
 
 
131
                gr_rewind ();
 
132
                while ((grp = gr_next ()) != NULL) {
 
133
                        if ((grp->gr_gid >= group_id) && (grp->gr_gid <= gid_max)) {
 
134
                                group_id = grp->gr_gid + 1;
 
135
                        }
 
136
                        /* create index of used GIDs */
 
137
                        if (grp->gr_gid <= gid_max) {
 
138
                                used_gids[grp->gr_gid] = true;
 
139
                        }
129
140
                }
130
141
        }
131
142
 
134
145
         * will give us GID_MAX+1 even if not unique. Search for the first
135
146
         * free GID starting with GID_MIN.
136
147
         */
137
 
        if (group_id == gid_max + 1) {
138
 
                for (group_id = gid_min; group_id < gid_max; group_id++) {
139
 
                        if (false == used_gids[group_id]) {
140
 
                                break;
 
148
        if (sys_group) {
 
149
                if (group_id == gid_min - 1) {
 
150
                        for (group_id = gid_max; group_id >= gid_min; group_id--) {
 
151
                                if (false == used_gids[group_id]) {
 
152
                                        break;
 
153
                                }
 
154
                        }
 
155
                        if ( group_id < gid_min ) {
 
156
                                fprintf (stderr,
 
157
                                         _("%s: Can't get unique system GID (no more available GIDs)\n"),
 
158
                                         Prog);
 
159
                                SYSLOG ((LOG_WARN,
 
160
                                         "no more available GID on the system"));
 
161
                                return -1;
141
162
                        }
142
163
                }
143
 
                if (group_id == gid_max) {
144
 
                        fprintf (stderr, _("%s: Can't get unique GID (no more available GIDs)\n"), Prog);
145
 
                        SYSLOG ((LOG_WARN, "no more available GID on the system"));
146
 
                        return -1;
 
164
        } else {
 
165
                if (group_id == gid_max + 1) {
 
166
                        for (group_id = gid_min; group_id < gid_max; group_id++) {
 
167
                                if (false == used_gids[group_id]) {
 
168
                                        break;
 
169
                                }
 
170
                        }
 
171
                        if (group_id == gid_max) {
 
172
                                fprintf (stderr,
 
173
                                         _("%s: Can't get unique GID (no more available GIDs)\n"),
 
174
                                         Prog);
 
175
                                SYSLOG ((LOG_WARN, "no more available GID on the system"));
 
176
                                return -1;
 
177
                        }
147
178
                }
148
179
        }
149
180