On Mon, Jul 01, 2019 at 11:59:49PM -0700, Ian Rogers wrote: > The current __perf_install_in_context can fail and the error is ignored. > Changing __perf_install_in_context can add new failure modes that need > errors propagating up. This change prepares for this. > > Signed-off-by: Ian Rogers <[email protected]> > --- > kernel/events/core.c | 38 +++++++++++++++++++++++++------------- > 1 file changed, 25 insertions(+), 13 deletions(-) > > diff --git a/kernel/events/core.c b/kernel/events/core.c > index 785d708f8553..4faa90f5a934 100644 > --- a/kernel/events/core.c > +++ b/kernel/events/core.c > @@ -2558,11 +2558,12 @@ static int __perf_install_in_context(void *info) > * > * Very similar to event_function_call, see comment there. > */ > -static void > +static int > perf_install_in_context(struct perf_event_context *ctx, > struct perf_event *event, > int cpu) > { > + int err; > struct task_struct *task = READ_ONCE(ctx->task); > > lockdep_assert_held(&ctx->mutex); > @@ -2577,15 +2578,15 @@ perf_install_in_context(struct perf_event_context > *ctx, > smp_store_release(&event->ctx, ctx); > > if (!task) { > - cpu_function_call(cpu, __perf_install_in_context, event); > - return; > + err = cpu_function_call(cpu, __perf_install_in_context, event); > + return err; > } > > /* > * Should not happen, we validate the ctx is still alive before calling. > */ > if (WARN_ON_ONCE(task == TASK_TOMBSTONE)) > - return; > + return 0; > > /* > * Installing events is tricky because we cannot rely on ctx->is_active > @@ -2619,8 +2620,9 @@ perf_install_in_context(struct perf_event_context *ctx, > */ > smp_mb(); > again: > - if (!task_function_call(task, __perf_install_in_context, event)) > - return; > + err = task_function_call(task, __perf_install_in_context, event); > + if (err) > + return err;
you need to return in here if task_function_call succeeds and continue in case of error, not the other way round, otherwise bad things will happen ;-) jirka > > raw_spin_lock_irq(&ctx->lock); > task = ctx->task; > @@ -2631,7 +2633,7 @@ perf_install_in_context(struct perf_event_context *ctx, > * against perf_event_exit_task_context(). > */ > raw_spin_unlock_irq(&ctx->lock); > - return; > + return 0; > } > /* > * If the task is not running, ctx->lock will avoid it becoming so, > @@ -2643,6 +2645,7 @@ perf_install_in_context(struct perf_event_context *ctx, > } > add_event_to_ctx(event, ctx); > raw_spin_unlock_irq(&ctx->lock); > + return 0; > } > > /* SNIP

