diff options
author | rwatson <rwatson@FreeBSD.org> | 2001-09-26 20:39:48 +0000 |
---|---|---|
committer | rwatson <rwatson@FreeBSD.org> | 2001-09-26 20:39:48 +0000 |
commit | 90600b5b23c1efdeb657e94c049491223c25ff67 (patch) | |
tree | 3bc302f456b51025c1f852a7d74b8e173e7e91b6 /sys | |
parent | 96b0d9e4f30aaeb47a612701f910ec19a074caaa (diff) | |
download | FreeBSD-src-90600b5b23c1efdeb657e94c049491223c25ff67.zip FreeBSD-src-90600b5b23c1efdeb657e94c049491223c25ff67.tar.gz |
o Modify kern.securelevel MIB entry to return a local securelevel, if
one is present in the current jail, otherwise, to return the global
securelevel.
o If the securelevel is being updated, require that it be greater than
the maximum of local and global, if a local securelevel exists,
otherwise, just maximum of the global. If there is a local
securelevel, update the local one instead of the global one.
o Note: this does allow local securelevels to lag behind the global one
as long as the local one is not updated following a global increase.
Obtained from: TrustedBSD Project
Diffstat (limited to 'sys')
-rw-r--r-- | sys/kern/kern_mib.c | 33 |
1 files changed, 27 insertions, 6 deletions
diff --git a/sys/kern/kern_mib.c b/sys/kern/kern_mib.c index df38fff..b6eec4c 100644 --- a/sys/kern/kern_mib.c +++ b/sys/kern/kern_mib.c @@ -172,18 +172,39 @@ sysctl_kern_securelvl(SYSCTL_HANDLER_ARGS) { int error, level; - level = securelevel; + /* + * If the process is in jail, return the maximum of the + * global and local levels; otherwise, return the global + * level. + */ + if (req->p->p_ucred->cr_prison != NULL) + level = imax(securelevel, + req->p->p_ucred->cr_prison->pr_securelevel); + else + level = securelevel; error = sysctl_handle_int(oidp, &level, 0, req); if (error || !req->newptr) return (error); - if (level < securelevel) - return (EPERM); - securelevel = level; + /* + * Permit update only if the new securelevel exceeds the + * global level, and local level if any. + */ + if (req->p->p_ucred->cr_prison != NULL) { + if (level < imax(securelevel, + req->p->p_ucred->cr_prison->pr_securelevel)) + return (EPERM); + req->p->p_ucred->cr_prison->pr_securelevel = level; + } else { + if (level < securelevel) + return (EPERM); + securelevel = level; + } return (error); } -SYSCTL_PROC(_kern, KERN_SECURELVL, securelevel, CTLTYPE_INT|CTLFLAG_RW, - 0, 0, sysctl_kern_securelvl, "I", "Current secure level"); +SYSCTL_PROC(_kern, KERN_SECURELVL, securelevel, + CTLTYPE_INT|CTLFLAG_RW|CTLFLAG_PRISON, 0, 0, sysctl_kern_securelvl, + "I", "Current secure level"); char domainname[MAXHOSTNAMELEN]; SYSCTL_STRING(_kern, KERN_NISDOMAINNAME, domainname, CTLFLAG_RW, |