Bug 952655

Summary: dmesg ignores -w / --follow when run with user rights
Product: [Fedora] Fedora Reporter: Andrew <travneff>
Component: kernelAssignee: Kernel Maintainer List <kernel-maint>
Status: CLOSED ERRATA QA Contact: Fedora Extras Quality Assurance <extras-qa>
Severity: unspecified Docs Contact:
Priority: unspecified    
Version: 18CC: eparis, gansalmon, itamar, jonathan, kay, kernel-maint, kzak, madhu.chinakonda, mluscon, travneff
Target Milestone: ---Keywords: Regression, Triaged
Target Release: ---   
Hardware: x86_64   
OS: Linux   
Whiteboard:
Fixed In Version: kernel-3.8.12-100.fc17 Doc Type: Bug Fix
Doc Text:
Story Points: ---
Clone Of: Environment:
Last Closed: 2013-05-15 03:24:44 UTC Type: Bug
Regression: --- Mount Type: ---
Documentation: --- CRM:
Verified Versions: Category: ---
oVirt Team: --- RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: --- Target Upstream Version:
Embargoed:

Description Andrew 2013-04-16 11:21:43 UTC
dmesg -w or dmesg --follow doesn't wait for new messages and exit after printing the buffer.
Seems related to /dev/kmsg permissions, so I'm not sure dmesg does anything wrong here:

$ ll /dev/kmsg
crw-r--r--. 1 root root 1, 11 Apr 16 11:54 /dev/kmsg

but:

$ cat /dev/kmsg
cat: /dev/kmsg: Operation not permitted

dmesg strace snippet:

open("/dev/kmsg", O_RDONLY)             = -1 EPERM (Operation not permitted)
syslog(SYSLOG_ACTION_SIZE_BUFFER, 0, 0) = 262144
mmap(NULL, 266240, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f14da9c3000
syslog(SYSLOG_ACTION_READ_ALL, "<7>[ 4796.761621] ALSA sound/usb"..., 262152) = 262116

Problem is absent when run from root, /dev/kmsg is opened ok in this case.

Selinux set to permissive mode.

util-linux-2.22.2-6.fc18.x86_64
kernel 3.8.6-203.fc18.x86_64

Comment 1 Karel Zak 2013-04-17 14:32:37 UTC
hmm... it works for me

open("/dev/kmsg", O_RDONLY|O_NONBLOCK)  = 3
lseek(3, 0, 0x3 /* SEEK_??? */)         = 0
read(3, 0x607298, 8191)                 = -1 EPIPE (Broken pipe)
read(3, "4,265939,1413181203466,-;Add. Se"..., 8191) = 91

tested on machine with and without SeLinux. Do you see anything in logs?

Comment 2 Andrew 2013-04-21 11:49:35 UTC
No, dmesg and /var/log/messages don't contain anything related.
Found the reason with ftrace: absent CAP_SYSLOG capability. Related pull request is created on github.
Besides that, %caps(cap_syslog=ep) for dmesg should be placed to util-linux rpm spec, I think.

Comment 3 Karel Zak 2013-04-22 18:36:25 UTC
Thanks for investigation.

Comment 4 Karel Zak 2013-04-24 07:47:06 UTC
I'm able to reproduce the problem after update to kernel 3.8.8-202 where is not possible to open /dev/kmsg without CAP_SYSLOG.

  open("/dev/kmsg", O_RDONLY)= -1 EPERM (Operation not permitted)

the system is:

  - with selinux=0
  - /proc/sys/kernel/dmesg_restrict is NOT set
  - CONFIG_SECURITY_DMESG_RESTRICT is NOT set
  - the traditional syslog API works as expected without CAP_SYSLOG

from my point of view is it kernel regression. 

The CAP_SYSLOG should be required only on systems where is enabled restricted dmesg (and this paranoid feature should not be enabled for Fedora). 

The current state also seems inconsistent -- CAP_SYSLOG is required for /dev/kmsg, but syslog(2) works as expected.


Note that I have discussed this issue with Andrew at github, for more details see: https://github.com/karelzak/util-linux/pull/32

Comment 5 Andrew 2013-04-24 12:05:50 UTC
Related upstream kernel logic is quite old:
http://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/commit/?id=ee24aebffb75a7f940cf52c8cf6910947b3130c0

Our case seems related here:
https://bugzilla.redhat.com/show_bug.cgi?id=903192

My previous trace was wrong since I didn't realize two kmsg files (in /dev and /proc). BTW, what's the purpose of the latter one while we have the former? /proc/kmsg can't be written and doesn't contain previous messages...
The right way starts in devkmsg_open() and the issue seems to be here (patch from the above issue):

@@ -624,7 +670,7 @@ static int devkmsg_open(struct inode *inode, struct file *file)
        if ((file->f_flags & O_ACCMODE) == O_WRONLY)
                return 0;
 
-       err = security_syslog(SYSLOG_ACTION_READ_ALL);
+       err = check_syslog_permissions(SYSLOG_ACTION_OPEN, SYSLOG_FROM_FILE);
        if (err)
                return err;

check_syslog_permissions() returns -EPERM when called with SYSLOG_ACTION_OPEN.

Besides that, there is one point in dmesg which should be changed anyway, as for me. In case of a file open error it shouldn't switch to (non-following) syslog method if --follow is given. More proper way may be just to exit with error print.

Comment 6 Kay Sievers 2013-04-24 13:06:44 UTC
(In reply to comment #5)
> My previous trace was wrong since I didn't realize two kmsg files (in /dev
> and /proc). BTW, what's the purpose of the latter one while we have the
> former?

Reading from /dev/kmsg is much younger than /proc/kmsg. We can look at
/proc/kmsg as the legacy interface, it is used by legacy syslog daemons.
It has pretty broken single-reader semantics, it cannot provide structured
log data, it should just not be used today.

I would expect this Fedora patch to cause the issue:
  http://pkgs.fedoraproject.org/cgit/kernel.git/tree/0001-kmsg-Honor-dmesg_restrict-sysctl-on-dev-kmsg.patch

Comment 7 Josh Boyer 2013-04-24 13:27:32 UTC
Full thread on this is here:

http://thread.gmane.org/gmane.linux.kernel.stable/43485/

Comment 8 Andrew 2013-04-24 13:50:34 UTC
(In reply to comment #6)
> I would expect this Fedora patch to cause the issue:
>  
> http://pkgs.fedoraproject.org/cgit/kernel.git/tree/0001-kmsg-Honor-
> dmesg_restrict-sysctl-on-dev-kmsg.patch

Yes, I quoted the changes chunk from it.

Comment 9 Kay Sievers 2013-04-24 14:52:00 UTC
(In reply to comment #7)
> Full thread on this is here:
> 
> http://thread.gmane.org/gmane.linux.kernel.stable/43485/

Hmm, so what's the plan here? The user who can do
syslog(SYSLOG_ACTION_READ_ALL) should also be able to directly read /dev/kmsg.

It was intentionally designed to allow that interface for dmesg(1), and it
should still work that way today.

Comment 10 Andrew 2013-04-24 15:20:11 UTC
(In reply to comment #9)
> The user who can do
> syslog(SYSLOG_ACTION_READ_ALL) should also be able to directly read
> /dev/kmsg.

Agree. I'm not a security expert but I can't find any reason to differ that behaviour. Same for open and read operations for /dev/kmsg: they should depend on CAP_SYSLOG in a similar manner. Current case isn't clear from this point.

Seems like CAP_SYSLOG shall be taken into account just with dmesg_restrict enabled. In this case the required action is to allow opening /dev/kmsg when both CAP_SYSLOG and dmesg_restrict are unset.

Comment 11 Karel Zak 2013-04-24 16:50:43 UTC
Josh, we need consistent solution -- now I can use syslog(2), but I cannot open(/dev/kmsg). It's pretty unexpected to force people to use CAP_SYSLOG by *default*. We have introduced /dev/kmsg to have a better interface, now it's useless.

Comment 12 Josh Boyer 2013-04-24 17:22:09 UTC
(In reply to comment #11)
> Josh, we need consistent solution -- now I can use syslog(2), but I cannot
> open(/dev/kmsg). It's pretty unexpected to force people to use CAP_SYSLOG by
> *default*. We have introduced /dev/kmsg to have a better interface, now it's
> useless.

My original patch allowed that I believe.  Eric and others upstream thought /dev/kmsg and /proc/kmsg should use the same permission checks and asked to rewrite it.

I can code it either way, but I can't make everyone agree.  It's probably best to bring this up as a follow up on the upstream thread.

Comment 13 Kay Sievers 2013-04-24 17:36:03 UTC
(In reply to comment #12)
> (In reply to comment #11)
> > Josh, we need consistent solution -- now I can use syslog(2), but I cannot
> > open(/dev/kmsg). It's pretty unexpected to force people to use CAP_SYSLOG by
> > *default*. We have introduced /dev/kmsg to have a better interface, now it's
> > useless.
> 
> My original patch allowed that I believe.  Eric and others upstream thought
> /dev/kmsg and /proc/kmsg should use the same permission checks and asked to
> rewrite it.

/dev/kmsg is meant as a sane replacement for syslog(), not so much for
/proc/kmsg. The also broken /proc/kmsg interface should just not be used
at all today.

> I can code it either way, but I can't make everyone agree.  It's probably
> best to bring this up as a follow up on the upstream thread.

We added the /dev/kmsg interface exactly for the reason to get rid of the
conceptually broken syslog() interface.

I don't think the patch would survive upstream anyway, it is just not how
things are meant to work, and they actually break existing tools used today.

I don't think there is really an option for the patch as it is. If you could
just make /dev/kmsg by default behave like the permissions of syslog() grants
to the user, that would be great.

Thanks!

Comment 14 Josh Boyer 2013-05-07 13:56:42 UTC
I should hopefully have a fix for this in today.  Testing the latest version that Kees sent out.

Comment 15 Josh Boyer 2013-05-07 16:35:32 UTC
Fixed in Fedora git.

Comment 16 Fedora Update System 2013-05-08 20:41:49 UTC
kernel-3.9.1-301.fc19 has been submitted as an update for Fedora 19.
https://admin.fedoraproject.org/updates/kernel-3.9.1-301.fc19

Comment 17 Fedora Update System 2013-05-09 13:08:09 UTC
kernel-3.8.12-100.fc17 has been submitted as an update for Fedora 17.
https://admin.fedoraproject.org/updates/kernel-3.8.12-100.fc17

Comment 18 Fedora Update System 2013-05-09 17:55:13 UTC
Package kernel-3.9.1-301.fc19:
* should fix your issue,
* was pushed to the Fedora 19 testing repository,
* should be available at your local mirror within two days.
Update it with:
# su -c 'yum update --enablerepo=updates-testing kernel-3.9.1-301.fc19'
as soon as you are able to, then reboot.
Please go to the following url:
https://admin.fedoraproject.org/updates/FEDORA-2013-7750/kernel-3.9.1-301.fc19
then log in and leave karma (feedback).

Comment 19 Fedora Update System 2013-05-15 03:24:44 UTC
kernel-3.8.12-100.fc17 has been pushed to the Fedora 17 stable repository.  If problems still persist, please make note of it in this bug report.