lkml.org 
[lkml]   [2019]   [Nov]   [7]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH 09/63] perf evsel: Always preserve errno while cleaning up perf_event_open failures
    Date
    From: Andi Kleen <ak@linux.intel.com>

    In some cases when perf_event_open fails, it may do some closes to clean
    up. In special cases these closes can fail too, which overwrites the
    errno of the perf_event_open, which is then incorrectly reported.

    Save/restore errno around closes.

    Signed-off-by: Andi Kleen <ak@linux.intel.com>
    Acked-by: Jiri Olsa <jolsa@kernel.org>
    Cc: Kan Liang <kan.liang@linux.intel.com>
    Cc: Peter Zijlstra <peterz@infradead.org>
    Cc: Stephane Eranian <eranian@google.com>
    Link: http://lore.kernel.org/lkml/20191020175202.32456-2-andi@firstfloor.org
    Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
    ---
    tools/perf/util/evsel.c | 6 ++++--
    1 file changed, 4 insertions(+), 2 deletions(-)

    diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c
    index abc7fda4a0fe..d831038b55f2 100644
    --- a/tools/perf/util/evsel.c
    +++ b/tools/perf/util/evsel.c
    @@ -1574,7 +1574,7 @@ int evsel__open(struct evsel *evsel, struct perf_cpu_map *cpus,
    {
    int cpu, thread, nthreads;
    unsigned long flags = PERF_FLAG_FD_CLOEXEC;
    - int pid = -1, err;
    + int pid = -1, err, old_errno;
    enum { NO_CHANGE, SET_TO_MAX, INCREASED_MAX } set_rlimit = NO_CHANGE;

    if ((perf_missing_features.write_backward && evsel->core.attr.write_backward) ||
    @@ -1727,8 +1727,8 @@ int evsel__open(struct evsel *evsel, struct perf_cpu_map *cpus,
    */
    if (err == -EMFILE && set_rlimit < INCREASED_MAX) {
    struct rlimit l;
    - int old_errno = errno;

    + old_errno = errno;
    if (getrlimit(RLIMIT_NOFILE, &l) == 0) {
    if (set_rlimit == NO_CHANGE)
    l.rlim_cur = l.rlim_max;
    @@ -1812,6 +1812,7 @@ int evsel__open(struct evsel *evsel, struct perf_cpu_map *cpus,
    if (err)
    threads->err_thread = thread;

    + old_errno = errno;
    do {
    while (--thread >= 0) {
    close(FD(evsel, cpu, thread));
    @@ -1819,6 +1820,7 @@ int evsel__open(struct evsel *evsel, struct perf_cpu_map *cpus,
    }
    thread = nthreads;
    } while (--cpu >= 0);
    + errno = old_errno;
    return err;
    }

    --
    2.21.0
    \
     
     \ /
      Last update: 2019-11-07 20:02    [W:4.053 / U:0.880 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site