aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/perf_event.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2010-05-28 13:07:48 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2010-05-28 13:07:48 -0400
commit89ad6a6173127e5d31bea7a4a45ec23fa5bf4a17 (patch)
tree6feb3d663ee48b790a0be2420647e43bc20c31ad /kernel/perf_event.c
parentaa36c7bf987dfa5597c0f7c46f8fca46b2dd33d2 (diff)
parent49837a80b38b79a7c06217b2c40842aeb6fa13b9 (diff)
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs-2.6
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs-2.6: remove detritus left by "mm: make read_cache_page synchronous" fix fs/sysv s_dirt handling fat: convert to use the new truncate convention. ext2: convert to use the new truncate convention. tmpfs: convert to use the new truncate convention fs: convert simple fs to new truncate kill spurious reference to vmtruncate fs: introduce new truncate sequence fs/super: fix kernel-doc warning fs/minix: bugfix, number of indirect block ptrs per block depends on block size rename the generic fsync implementations drop unused dentry argument to ->fsync fs: Add missing mutex_unlock Fix racy use of anon_inode_getfd() in perf_event.c get rid of the magic around f_count in aio VFS: fix recent breakage of FS_REVAL_DOT Revert "anon_inode: set S_IFREG on the anon_inode"
Diffstat (limited to 'kernel/perf_event.c')
-rw-r--r--kernel/perf_event.c40
1 files changed, 22 insertions, 18 deletions
diff --git a/kernel/perf_event.c b/kernel/perf_event.c
index e099650cd249..bd7ce8ca5bb9 100644
--- a/kernel/perf_event.c
+++ b/kernel/perf_event.c
@@ -4999,8 +4999,8 @@ SYSCALL_DEFINE5(perf_event_open,
4999 struct perf_event_context *ctx; 4999 struct perf_event_context *ctx;
5000 struct file *event_file = NULL; 5000 struct file *event_file = NULL;
5001 struct file *group_file = NULL; 5001 struct file *group_file = NULL;
5002 int event_fd;
5002 int fput_needed = 0; 5003 int fput_needed = 0;
5003 int fput_needed2 = 0;
5004 int err; 5004 int err;
5005 5005
5006 /* for future expandability... */ 5006 /* for future expandability... */
@@ -5021,12 +5021,18 @@ SYSCALL_DEFINE5(perf_event_open,
5021 return -EINVAL; 5021 return -EINVAL;
5022 } 5022 }
5023 5023
5024 event_fd = get_unused_fd_flags(O_RDWR);
5025 if (event_fd < 0)
5026 return event_fd;
5027
5024 /* 5028 /*
5025 * Get the target context (task or percpu): 5029 * Get the target context (task or percpu):
5026 */ 5030 */
5027 ctx = find_get_context(pid, cpu); 5031 ctx = find_get_context(pid, cpu);
5028 if (IS_ERR(ctx)) 5032 if (IS_ERR(ctx)) {
5029 return PTR_ERR(ctx); 5033 err = PTR_ERR(ctx);
5034 goto err_fd;
5035 }
5030 5036
5031 /* 5037 /*
5032 * Look up the group leader (we will attach this event to it): 5038 * Look up the group leader (we will attach this event to it):
@@ -5066,13 +5072,11 @@ SYSCALL_DEFINE5(perf_event_open,
5066 if (IS_ERR(event)) 5072 if (IS_ERR(event))
5067 goto err_put_context; 5073 goto err_put_context;
5068 5074
5069 err = anon_inode_getfd("[perf_event]", &perf_fops, event, O_RDWR); 5075 event_file = anon_inode_getfile("[perf_event]", &perf_fops, event, O_RDWR);
5070 if (err < 0) 5076 if (IS_ERR(event_file)) {
5071 goto err_free_put_context; 5077 err = PTR_ERR(event_file);
5072
5073 event_file = fget_light(err, &fput_needed2);
5074 if (!event_file)
5075 goto err_free_put_context; 5078 goto err_free_put_context;
5079 }
5076 5080
5077 if (flags & PERF_FLAG_FD_OUTPUT) { 5081 if (flags & PERF_FLAG_FD_OUTPUT) {
5078 err = perf_event_set_output(event, group_fd); 5082 err = perf_event_set_output(event, group_fd);
@@ -5093,19 +5097,19 @@ SYSCALL_DEFINE5(perf_event_open,
5093 list_add_tail(&event->owner_entry, &current->perf_event_list); 5097 list_add_tail(&event->owner_entry, &current->perf_event_list);
5094 mutex_unlock(&current->perf_event_mutex); 5098 mutex_unlock(&current->perf_event_mutex);
5095 5099
5096err_fput_free_put_context: 5100 fput_light(group_file, fput_needed);
5097 fput_light(event_file, fput_needed2); 5101 fd_install(event_fd, event_file);
5102 return event_fd;
5098 5103
5104err_fput_free_put_context:
5105 fput(event_file);
5099err_free_put_context: 5106err_free_put_context:
5100 if (err < 0) 5107 free_event(event);
5101 free_event(event);
5102
5103err_put_context: 5108err_put_context:
5104 if (err < 0)
5105 put_ctx(ctx);
5106
5107 fput_light(group_file, fput_needed); 5109 fput_light(group_file, fput_needed);
5108 5110 put_ctx(ctx);
5111err_fd:
5112 put_unused_fd(event_fd);
5109 return err; 5113 return err;
5110} 5114}
5111 5115