167 /* Needed to call settaskid(). */ |
167 /* Needed to call settaskid(). */ |
168 priv_set(PRIV_ON, PRIV_EFFECTIVE, PRIV_PROC_TASKID, NULL); |
168 priv_set(PRIV_ON, PRIV_EFFECTIVE, PRIV_PROC_TASKID, NULL); |
169 |
169 |
170 /* Needed to access /dev/urandom. */ |
170 /* Needed to access /dev/urandom. */ |
171 priv_set(PRIV_ON, PRIV_EFFECTIVE, PRIV_SYS_DEVICES, NULL); |
171 priv_set(PRIV_ON, PRIV_EFFECTIVE, PRIV_SYS_DEVICES, NULL); |
|
172 |
|
173 /* Needed for pam_unix_cred to chown files. */ |
|
174 priv_set(PRIV_ON, PRIV_EFFECTIVE, PRIV_FILE_CHOWN_SELF, NULL); |
|
175 |
|
176 /* Needed to access /var/adm/wtmpx. */ |
|
177 priv_set(PRIV_ON, PRIV_EFFECTIVE, PRIV_FILE_DAC_WRITE, NULL); |
172 } |
178 } |
173 |
179 |
174 /* Setup priviledges before the user responds to the user prompt |
180 /* Setup priviledges before the user responds to the user prompt |
175 * from the ftp server so that a secure Kerberos session can be |
181 * from the ftp server so that a secure Kerberos session can be |
176 * established and also the user can login as root |
182 * established and also the user can login as root |
179 MODRET solaris_priv_pre_pass(cmd_rec *cmd) { |
185 MODRET solaris_priv_pre_pass(cmd_rec *cmd) { |
180 set_privs(); |
186 set_privs(); |
181 return PR_DECLINED(cmd); |
187 return PR_DECLINED(cmd); |
182 } |
188 } |
183 |
189 |
|
190 static priv_set_t* allocset(void) { |
|
191 priv_set_t* ret; |
|
192 |
|
193 if ((ret = priv_allocset()) == NULL) { |
|
194 pr_log_pri(PR_LOG_ERR, MOD_SOLARIS_PRIV_VERSION ": priv_allocset: %s", |
|
195 strerror(errno)); |
|
196 pr_signals_unblock(); |
|
197 end_login(1); |
|
198 } |
|
199 |
|
200 return ret; |
|
201 } |
|
202 |
|
203 static void delset(priv_set_t *sp, const char *priv) { |
|
204 if (priv_delset(sp, priv) != 0) { |
|
205 pr_log_pri(PR_LOG_ERR, MOD_SOLARIS_PRIV_VERSION ": priv_delset: %s", |
|
206 strerror(errno)); |
|
207 pr_signals_unblock(); |
|
208 end_login(1); |
|
209 } |
|
210 } |
|
211 |
|
212 static void addset(priv_set_t *sp, const char *priv) { |
|
213 if (priv_addset(sp, priv) != 0) { |
|
214 pr_log_pri(PR_LOG_ERR, MOD_SOLARIS_PRIV_VERSION ": priv_addset: %s", |
|
215 strerror(errno)); |
|
216 pr_signals_unblock(); |
|
217 end_login(1); |
|
218 } |
|
219 } |
|
220 |
|
221 static void _setppriv(priv_op_t op, priv_ptype_t which, priv_set_t *set) { |
|
222 if (setppriv(op, which, set) != 0) { |
|
223 pr_log_pri(PR_LOG_ERR, MOD_SOLARIS_PRIV_VERSION ": setppriv: %s", |
|
224 strerror(errno)); |
|
225 pr_signals_unblock(); |
|
226 end_login(1); |
|
227 } |
|
228 } |
|
229 |
184 /* The POST_CMD handler for "PASS" is only called after PASS has |
230 /* The POST_CMD handler for "PASS" is only called after PASS has |
185 * successfully completed, which means authentication is successful, |
231 * successfully completed, which means authentication is successful, |
186 * so we can "tweak" our root access down to almost nothing. |
232 * so we can "tweak" our root access down to almost nothing. |
187 */ |
233 */ |
188 MODRET solaris_priv_post_pass(cmd_rec *cmd) { |
234 MODRET solaris_priv_post_pass(cmd_rec *cmd) { |
189 int res = 0; |
235 int res = 0; |
190 priv_set_t *p, *i; |
236 priv_set_t *ps = NULL; |
191 |
237 |
192 if (!use_privs) |
238 if (!use_privs) |
193 return PR_DECLINED(cmd); |
239 return PR_DECLINED(cmd); |
194 |
240 |
195 pr_signals_block(); |
241 pr_signals_block(); |
201 * |
247 * |
202 * We also remove the basic Solaris privileges we know we will |
248 * We also remove the basic Solaris privileges we know we will |
203 * never need. |
249 * never need. |
204 */ |
250 */ |
205 |
251 |
206 i = priv_allocset(); |
252 ps = allocset(); |
207 priv_basicset(i); |
253 priv_basicset(ps); |
208 priv_delset(i, PRIV_PROC_EXEC); |
254 delset(ps, PRIV_PROC_EXEC); |
209 priv_delset(i, PRIV_PROC_FORK); |
255 delset(ps, PRIV_PROC_FORK); |
210 priv_delset(i, PRIV_PROC_INFO); |
256 delset(ps, PRIV_PROC_INFO); |
211 priv_delset(i, PRIV_PROC_SESSION); |
257 delset(ps, PRIV_PROC_SESSION); |
212 setppriv(PRIV_SET, PRIV_INHERITABLE, i); |
258 _setppriv(PRIV_SET, PRIV_INHERITABLE, ps); |
213 |
259 |
214 p = priv_allocset(); |
260 priv_basicset(ps); |
215 priv_basicset(p); |
261 |
216 |
262 addset(ps, PRIV_NET_PRIVADDR); |
217 priv_addset(p, PRIV_NET_PRIVADDR); |
263 addset(ps, PRIV_PROC_AUDIT); |
218 priv_addset(p, PRIV_PROC_AUDIT); |
264 |
219 |
265 delset(ps, PRIV_PROC_EXEC); |
220 priv_delset(p, PRIV_PROC_EXEC); |
266 delset(ps, PRIV_PROC_FORK); |
221 priv_delset(p, PRIV_PROC_FORK); |
267 delset(ps, PRIV_PROC_INFO); |
222 priv_delset(p, PRIV_PROC_INFO); |
268 delset(ps, PRIV_PROC_SESSION); |
223 priv_delset(p, PRIV_PROC_SESSION); |
|
224 |
269 |
225 /* If the proftpd process is not running as root, but as user ftp, |
270 /* If the proftpd process is not running as root, but as user ftp, |
226 * then this is necessary in order to make the setreuid work. |
271 * then this is necessary in order to make the setreuid work. |
227 * Without this, the setreuid would fail. The PRIV_PROC_SETID privilege |
272 * Without this, the setreuid would fail. The PRIV_PROC_SETID privilege |
228 * is removed afterwards. |
273 * is removed afterwards. |
229 */ |
274 */ |
230 priv_addset(p, PRIV_PROC_SETID); |
275 addset(ps, PRIV_PROC_SETID); |
231 |
276 |
232 /* Add any of the configurable privileges. */ |
277 /* Add any of the configurable privileges. */ |
233 if (solaris_priv_flags & PRIV_USE_FILE_CHOWN) |
278 if (solaris_priv_flags & PRIV_USE_FILE_CHOWN) |
234 priv_addset(p, PRIV_FILE_CHOWN); |
279 addset(ps, PRIV_FILE_CHOWN); |
235 |
280 |
236 if (solaris_priv_flags & PRIV_USE_FILE_CHOWN_SELF) |
281 if (solaris_priv_flags & PRIV_USE_FILE_CHOWN_SELF) |
237 priv_addset(p, PRIV_FILE_CHOWN_SELF); |
282 addset(ps, PRIV_FILE_CHOWN_SELF); |
238 |
283 |
239 if (solaris_priv_flags & PRIV_USE_DAC_READ) |
284 if (solaris_priv_flags & PRIV_USE_DAC_READ) |
240 priv_addset(p, PRIV_FILE_DAC_READ); |
285 addset(ps, PRIV_FILE_DAC_READ); |
241 |
286 |
242 if (solaris_priv_flags & PRIV_USE_DAC_WRITE) |
287 if (solaris_priv_flags & PRIV_USE_DAC_WRITE) |
243 priv_addset(p, PRIV_FILE_DAC_WRITE); |
288 addset(ps, PRIV_FILE_DAC_WRITE); |
244 |
289 |
245 if (solaris_priv_flags & PRIV_USE_DAC_SEARCH) |
290 if (solaris_priv_flags & PRIV_USE_DAC_SEARCH) |
246 priv_addset(p, PRIV_FILE_DAC_SEARCH); |
291 addset(ps, PRIV_FILE_DAC_SEARCH); |
247 |
292 |
248 if (solaris_priv_flags & PRIV_USE_FILE_OWNER) |
293 if (solaris_priv_flags & PRIV_USE_FILE_OWNER) |
249 priv_addset(p, PRIV_FILE_OWNER); |
294 addset(ps, PRIV_FILE_OWNER); |
250 |
295 |
251 if (solaris_priv_flags & PRIV_DROP_FILE_WRITE) |
296 if (solaris_priv_flags & PRIV_DROP_FILE_WRITE) |
252 priv_delset(p, PRIV_FILE_WRITE); |
297 delset(ps, PRIV_FILE_WRITE); |
253 |
298 |
254 res = setppriv(PRIV_SET, PRIV_PERMITTED, p); |
299 _setppriv(PRIV_SET, PRIV_PERMITTED, ps); |
255 res = setppriv(PRIV_SET, PRIV_EFFECTIVE, p); |
300 _setppriv(PRIV_SET, PRIV_EFFECTIVE, ps); |
256 |
301 |
257 if (setreuid(session.uid, session.uid) == -1) { |
302 if (setreuid(session.uid, session.uid) == -1) { |
258 pr_log_pri(PR_LOG_ERR, MOD_SOLARIS_PRIV_VERSION ": setreuid: %s", |
303 pr_log_pri(PR_LOG_ERR, MOD_SOLARIS_PRIV_VERSION ": setreuid: %s", |
259 strerror(errno)); |
304 strerror(errno)); |
260 pr_signals_unblock(); |
305 pr_signals_unblock(); |
261 end_login(1); |
306 end_login(1); |
262 } |
307 } |
263 |
308 |
264 if (!(solaris_priv_flags & PRIV_USE_SETID)) { |
309 if (!(solaris_priv_flags & PRIV_USE_SETID)) { |
265 priv_delset(p, PRIV_PROC_SETID); |
310 delset(ps, PRIV_PROC_SETID); |
266 res = setppriv(PRIV_SET, PRIV_PERMITTED, p); |
311 _setppriv(PRIV_SET, PRIV_PERMITTED, ps); |
267 res = setppriv(PRIV_SET, PRIV_EFFECTIVE, p); |
312 _setppriv(PRIV_SET, PRIV_EFFECTIVE, ps); |
268 } |
313 } |
|
314 |
|
315 priv_freeset(ps); |
269 |
316 |
270 pr_signals_unblock(); |
317 pr_signals_unblock(); |
271 |
318 |
272 if (res != -1) { |
319 /* That's it! Disable all further id switching */ |
273 /* That's it! Disable all further id switching */ |
320 session.disable_id_switching = TRUE; |
274 session.disable_id_switching = TRUE; |
|
275 |
|
276 } else { |
|
277 pr_log_pri(PR_LOG_NOTICE, MOD_SOLARIS_PRIV_VERSION ": attempt to configure " |
|
278 "capabilities failed, reverting to normal operation"); |
|
279 } |
|
280 |
321 |
281 return PR_DECLINED(cmd); |
322 return PR_DECLINED(cmd); |
282 } |
323 } |
283 |
324 |
284 /* Initialization routines |
325 /* Initialization routines |