syslog: check cap_syslog when dmesg_restrict

Eric Paris pointed out that it doesn't make sense to require
both CAP_SYS_ADMIN and CAP_SYSLOG for certain syslog actions.
So require CAP_SYSLOG, not CAP_SYS_ADMIN, when dmesg_restrict
is set.

(I'm also consolidating the now common error path)

Signed-off-by: Serge E. Hallyn <serge.hallyn@canonical.com>
Acked-by: Eric Paris <eparis@redhat.com>
Acked-by: Kees Cook <kees.cook@canonical.com>
Signed-off-by: James Morris <jmorris@namei.org>
This commit is contained in:
Serge E. Hallyn 2010-12-08 15:19:01 +00:00 committed by James Morris
parent 5c6d1125f8
commit 38ef4c2e43
2 changed files with 11 additions and 11 deletions

View File

@ -219,7 +219,7 @@ dmesg_restrict:
This toggle indicates whether unprivileged users are prevented from using This toggle indicates whether unprivileged users are prevented from using
dmesg(8) to view messages from the kernel's log buffer. When dmesg(8) to view messages from the kernel's log buffer. When
dmesg_restrict is set to (0) there are no restrictions. When dmesg_restrict is set to (0) there are no restrictions. When
dmesg_restrict is set set to (1), users must have CAP_SYS_ADMIN to use dmesg_restrict is set set to (1), users must have CAP_SYSLOG to use
dmesg(8). dmesg(8).
The kernel config option CONFIG_SECURITY_DMESG_RESTRICT sets the default The kernel config option CONFIG_SECURITY_DMESG_RESTRICT sets the default

View File

@ -279,18 +279,12 @@ int do_syslog(int type, char __user *buf, int len, bool from_file)
* at open time. * at open time.
*/ */
if (type == SYSLOG_ACTION_OPEN || !from_file) { if (type == SYSLOG_ACTION_OPEN || !from_file) {
if (dmesg_restrict && !capable(CAP_SYS_ADMIN)) if (dmesg_restrict && !capable(CAP_SYSLOG))
return -EPERM; goto warn; /* switch to return -EPERM after 2.6.39 */
if ((type != SYSLOG_ACTION_READ_ALL && if ((type != SYSLOG_ACTION_READ_ALL &&
type != SYSLOG_ACTION_SIZE_BUFFER) && type != SYSLOG_ACTION_SIZE_BUFFER) &&
!capable(CAP_SYSLOG)) { !capable(CAP_SYSLOG))
/* remove after 2.6.38 */ goto warn; /* switch to return -EPERM after 2.6.39 */
if (capable(CAP_SYS_ADMIN))
WARN_ONCE(1, "Attempt to access syslog with "
"CAP_SYS_ADMIN but no CAP_SYSLOG "
"(deprecated and denied).\n");
return -EPERM;
}
} }
error = security_syslog(type); error = security_syslog(type);
@ -434,6 +428,12 @@ int do_syslog(int type, char __user *buf, int len, bool from_file)
} }
out: out:
return error; return error;
warn:
/* remove after 2.6.39 */
if (capable(CAP_SYS_ADMIN))
WARN_ONCE(1, "Attempt to access syslog with CAP_SYS_ADMIN "
"but no CAP_SYSLOG (deprecated and denied).\n");
return -EPERM;
} }
SYSCALL_DEFINE3(syslog, int, type, char __user *, buf, int, len) SYSCALL_DEFINE3(syslog, int, type, char __user *, buf, int, len)