Hi Jiri, On Mon, Dec 12, 2016 at 11:35:42AM +0100, Jiri Olsa wrote: > Adding perf_evsel::ignore_missing_cpu_thread bool. > > When set true, it allows perf to ignore error of missing > pid of perf event syscall. > > We remove missing thread id from the thread_map, so the > rest of the processing like ioctl and mmap won't get > disturbed with -1 fd. > > The reason for supporting this is to ease up monitoring > group of pids, that 'disappear' before perf opens their > event. This currently leads perf to report error and exit > and makes perf record's -u option unusable under certain > setup. > > With this change we will allow this race and ignore such > failure with following warning: > > WARNING: Ignored open failure for pid 8605 > > Signed-off-by: Jiri Olsa <jo...@kernel.org> > Cc: David Ahern <dsah...@gmail.com> > Cc: Namhyung Kim <namhy...@kernel.org> > Cc: Peter Zijlstra <a.p.zijls...@chello.nl> > Link: http://lkml.kernel.org/n/tip-atmzsjyhrt1j6xjwwmb84...@git.kernel.org > --- > tools/perf/perf.h | 1 + > tools/perf/util/evsel.c | 44 ++++++++++++++++++++++++++++++++++++++++++++ > tools/perf/util/evsel.h | 1 + > 3 files changed, 46 insertions(+) > > diff --git a/tools/perf/perf.h b/tools/perf/perf.h > index 9a0236a4cf95..1c27d947c2fe 100644 > --- a/tools/perf/perf.h > +++ b/tools/perf/perf.h > @@ -55,6 +55,7 @@ struct record_opts { > bool all_user; > bool tail_synthesize; > bool overwrite; > + bool ignore_missing_thread; > unsigned int freq; > unsigned int mmap_pages; > unsigned int auxtrace_mmap_pages; > diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c > index fd61ebd77c26..ac87f1637ae9 100644 > --- a/tools/perf/util/evsel.c > +++ b/tools/perf/util/evsel.c > @@ -990,6 +990,8 @@ void perf_evsel__config(struct perf_evsel *evsel, struct > record_opts *opts, > * it overloads any global configuration. > */ > apply_config_terms(evsel, opts); > + > + evsel->ignore_missing_thread = opts->ignore_missing_thread; > } > > static int perf_evsel__alloc_fd(struct perf_evsel *evsel, int ncpus, int > nthreads) > @@ -1419,6 +1421,33 @@ static int __open_attr__fprintf(FILE *fp, const char > *name, const char *val, > return fprintf(fp, " %-32s %s\n", name, val); > } > > +static bool ignore_missing_thread(struct perf_evsel *evsel, > + struct thread_map *threads, > + int thread, int err) > +{ > + if (!evsel->ignore_missing_thread) > + return false; > + > + /* The system wide setup does not work with threads. */ > + if (!evsel->system_wide) > + return false;
I'm bit confused with this. Shouldn't the condition be positive? Thanks, Namhyung > + > + /* The -ESRCH is perf event syscall errno for pid's not found. */ > + if (err != -ESRCH) > + return false; > + > + /* If there's only one thread, let it fail. */ > + if (threads->nr == 1) > + return false; > + > + if (thread_map__remove(threads, thread)) > + return false; > + > + pr_warning("WARNING: Ignored open failure for pid %d\n", > + thread_map__pid(threads, thread)); > + return true; > +} > + > static int __perf_evsel__open(struct perf_evsel *evsel, struct cpu_map *cpus, > struct thread_map *threads) > { > @@ -1491,6 +1520,21 @@ static int __perf_evsel__open(struct perf_evsel > *evsel, struct cpu_map *cpus, > > if (fd < 0) { > err = -errno; > + > + if (ignore_missing_thread(evsel, threads, > thread, err)) { > + /* > + * We just removed 1 thread, so take a > step > + * back on thread index and lower the > upper > + * nthreads limit. > + */ > + nthreads--; > + thread--; > + > + /* ... and pretend like nothing have > happened. */ > + err = 0; > + continue; > + } > + > pr_debug2("\nsys_perf_event_open failed, error > %d\n", > err); > goto try_fallback; > diff --git a/tools/perf/util/evsel.h b/tools/perf/util/evsel.h > index 6abb89cd27f9..06ef6f29efa1 100644 > --- a/tools/perf/util/evsel.h > +++ b/tools/perf/util/evsel.h > @@ -120,6 +120,7 @@ struct perf_evsel { > bool tracking; > bool per_pkg; > bool precise_max; > + bool ignore_missing_thread; > /* parse modifier helper */ > int exclude_GH; > int nr_members; > -- > 2.7.4 >