forked from Minki/linux
perf: Set owner pointer for kernel events
Adding fake EVENT_OWNER_KERNEL owner pointer value for kernel perf events, so we could distinguish it from user events, which needs special care in following patch. Signed-off-by: Jiri Olsa <jolsa@kernel.org> Signed-off-by: Peter Zijlstra <peterz@infradead.org> Cc: Arnaldo Carvalho de Melo <acme@kernel.org> Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com> Cc: Frederic Weisbecker <fweisbec@gmail.com> Cc: Mark Rutland <mark.rutland@arm.com> Cc: Paul Mackerras <paulus@samba.org> Cc: Arnaldo Carvalho de Melo <acme@kernel.org> Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com> Cc: Frederic Weisbecker <fweisbec@gmail.com> Cc: Mark Rutland <mark.rutland@arm.com> Cc: Linus Torvalds <torvalds@linux-foundation.org> Link: http://lkml.kernel.org/r/1406896382-18404-3-git-send-email-jolsa@kernel.org Signed-off-by: Ingo Molnar <mingo@kernel.org>
This commit is contained in:
parent
0f7c29ce90
commit
f86977620e
@ -119,6 +119,13 @@ static int cpu_function_call(int cpu, int (*func) (void *info), void *info)
|
||||
return data.ret;
|
||||
}
|
||||
|
||||
#define EVENT_OWNER_KERNEL ((void *) -1)
|
||||
|
||||
static bool is_kernel_event(struct perf_event *event)
|
||||
{
|
||||
return event->owner == EVENT_OWNER_KERNEL;
|
||||
}
|
||||
|
||||
#define PERF_FLAG_ALL (PERF_FLAG_FD_NO_GROUP |\
|
||||
PERF_FLAG_FD_OUTPUT |\
|
||||
PERF_FLAG_PID_CGROUP |\
|
||||
@ -3312,16 +3319,12 @@ static void free_event(struct perf_event *event)
|
||||
}
|
||||
|
||||
/*
|
||||
* Called when the last reference to the file is gone.
|
||||
* Remove user event from the owner task.
|
||||
*/
|
||||
static void put_event(struct perf_event *event)
|
||||
static void perf_remove_from_owner(struct perf_event *event)
|
||||
{
|
||||
struct perf_event_context *ctx = event->ctx;
|
||||
struct task_struct *owner;
|
||||
|
||||
if (!atomic_long_dec_and_test(&event->refcount))
|
||||
return;
|
||||
|
||||
rcu_read_lock();
|
||||
owner = ACCESS_ONCE(event->owner);
|
||||
/*
|
||||
@ -3354,6 +3357,20 @@ static void put_event(struct perf_event *event)
|
||||
mutex_unlock(&owner->perf_event_mutex);
|
||||
put_task_struct(owner);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Called when the last reference to the file is gone.
|
||||
*/
|
||||
static void put_event(struct perf_event *event)
|
||||
{
|
||||
struct perf_event_context *ctx = event->ctx;
|
||||
|
||||
if (!atomic_long_dec_and_test(&event->refcount))
|
||||
return;
|
||||
|
||||
if (!is_kernel_event(event))
|
||||
perf_remove_from_owner(event);
|
||||
|
||||
WARN_ON_ONCE(ctx->parent_ctx);
|
||||
/*
|
||||
@ -7366,6 +7383,9 @@ perf_event_create_kernel_counter(struct perf_event_attr *attr, int cpu,
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* Mark owner so we could distinguish it from user events. */
|
||||
event->owner = EVENT_OWNER_KERNEL;
|
||||
|
||||
account_event(event);
|
||||
|
||||
ctx = find_get_context(event->pmu, task, cpu);
|
||||
|
Loading…
Reference in New Issue
Block a user