On Sun, Oct 20, 2019 at 10:51:54AM -0700, Andi Kleen wrote: > From: Andi Kleen <[email protected]> > > 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 <[email protected]>
Acked-by: Jiri Olsa <[email protected]> thanks, jirka > --- > 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 >

