| From cbe08bcbbe787315c425dde284dcb715cfbf3f39 Mon Sep 17 00:00:00 2001 |
| From: Elazar Leibovich <elazar@lightbitslabs.com> |
| Date: Mon, 31 Dec 2018 13:58:37 +0200 |
| Subject: tracing: Fix partial reading of trace event's id file |
| |
| From: Elazar Leibovich <elazar@lightbitslabs.com> |
| |
| commit cbe08bcbbe787315c425dde284dcb715cfbf3f39 upstream. |
| |
| When reading only part of the id file, the ppos isn't tracked correctly. |
| This is taken care by simple_read_from_buffer. |
| |
| Reading a single byte, and then the next byte would result EOF. |
| |
| While this seems like not a big deal, this breaks abstractions that |
| reads information from files unbuffered. See for example |
| https://github.com/golang/go/issues/29399 |
| |
| This code was mentioned as problematic in |
| commit cd458ba9d5a5 |
| ("tracing: Do not (ab)use trace_seq in event_id_read()") |
| |
| An example C code that show this bug is: |
| |
| #include <stdio.h> |
| #include <stdint.h> |
| |
| #include <sys/types.h> |
| #include <sys/stat.h> |
| #include <fcntl.h> |
| #include <unistd.h> |
| |
| int main(int argc, char **argv) { |
| if (argc < 2) |
| return 1; |
| int fd = open(argv[1], O_RDONLY); |
| char c; |
| read(fd, &c, 1); |
| printf("First %c\n", c); |
| read(fd, &c, 1); |
| printf("Second %c\n", c); |
| } |
| |
| Then run with, e.g. |
| |
| sudo ./a.out /sys/kernel/debug/tracing/events/tcp/tcp_set_state/id |
| |
| You'll notice you're getting the first character twice, instead of the |
| first two characters in the id file. |
| |
| Link: http://lkml.kernel.org/r/20181231115837.4932-1-elazar@lightbitslabs.com |
| |
| Cc: Orit Wasserman <orit.was@gmail.com> |
| Cc: Oleg Nesterov <oleg@redhat.com> |
| Cc: Ingo Molnar <mingo@redhat.com> |
| Cc: stable@vger.kernel.org |
| Fixes: 23725aeeab10b ("ftrace: provide an id file for each event") |
| Signed-off-by: Elazar Leibovich <elazar@lightbitslabs.com> |
| Signed-off-by: Steven Rostedt (VMware) <rostedt@goodmis.org> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| |
| --- |
| kernel/trace/trace_events.c | 3 --- |
| 1 file changed, 3 deletions(-) |
| |
| --- a/kernel/trace/trace_events.c |
| +++ b/kernel/trace/trace_events.c |
| @@ -1310,9 +1310,6 @@ event_id_read(struct file *filp, char __ |
| char buf[32]; |
| int len; |
| |
| - if (*ppos) |
| - return 0; |
| - |
| if (unlikely(!id)) |
| return -ENODEV; |
| |