Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a3d4fd7a authored by Ingo Molnar's avatar Ingo Molnar
Browse files

Merge branch 'uprobes/core' of...

Merge branch 'uprobes/core' of git://git.kernel.org/pub/scm/linux/kernel/git/oleg/misc

 into perf/core

Improve uprobes performance by adding 'pre-filtering' support,
by Oleg Nesterov:

	# time perl -e 'syscall -1 for 1..100_000'
	real    0m0.040s
	user    0m0.027s
	sys     0m0.010s

	# perf probe -x /lib/libc.so.6 syscall
	# perf record -e probe_libc:syscall sleep 100 &

Before this series:

	# time perl -e 'syscall -1 for 1..100_000'
	real    0m1.714s
	user    0m0.103s
	sys     0m1.607s

After:

	# time perl -e 'syscall -1 for 1..100_000'
	real    0m0.037s
	user    0m0.013s
	sys     0m0.023s

Signed-off-by: default avatarIngo Molnar <mingo@kernel.org>
parents 661e5915 b2fe8ba6
Loading
Loading
Loading
Loading
+3 −1
Original line number Diff line number Diff line
@@ -680,8 +680,10 @@ static bool __skip_sstep(struct arch_uprobe *auprobe, struct pt_regs *regs)
		if (auprobe->insn[i] == 0x66)
			continue;

		if (auprobe->insn[i] == 0x90)
		if (auprobe->insn[i] == 0x90) {
			regs->ip += i + 1;
			return true;
		}

		break;
	}
+7 −2
Original line number Diff line number Diff line
@@ -135,16 +135,21 @@ struct hw_perf_event {
		struct { /* software */
			struct hrtimer	hrtimer;
		};
		struct { /* tracepoint */
			struct task_struct	*tp_target;
			/* for tp_event->class */
			struct list_head	tp_list;
		};
#ifdef CONFIG_HAVE_HW_BREAKPOINT
		struct { /* breakpoint */
			struct arch_hw_breakpoint	info;
			struct list_head		bp_list;
			/*
			 * Crufty hack to avoid the chicken and egg
			 * problem hw_breakpoint has with context
			 * creation and event initalization.
			 */
			struct task_struct		*bp_target;
			struct arch_hw_breakpoint	info;
			struct list_head		bp_list;
		};
#endif
	};
+18 −5
Original line number Diff line number Diff line
@@ -35,13 +35,20 @@ struct inode;
# include <asm/uprobes.h>
#endif

#define UPROBE_HANDLER_REMOVE		1
#define UPROBE_HANDLER_MASK		1

enum uprobe_filter_ctx {
	UPROBE_FILTER_REGISTER,
	UPROBE_FILTER_UNREGISTER,
	UPROBE_FILTER_MMAP,
};

struct uprobe_consumer {
	int (*handler)(struct uprobe_consumer *self, struct pt_regs *regs);
	/*
	 * filter is optional; If a filter exists, handler is run
	 * if and only if filter returns true.
	 */
	bool (*filter)(struct uprobe_consumer *self, struct task_struct *task);
	bool (*filter)(struct uprobe_consumer *self,
				enum uprobe_filter_ctx ctx,
				struct mm_struct *mm);

	struct uprobe_consumer *next;
};
@@ -94,6 +101,7 @@ extern int __weak set_swbp(struct arch_uprobe *aup, struct mm_struct *mm, unsign
extern int __weak set_orig_insn(struct arch_uprobe *aup, struct mm_struct *mm, unsigned long vaddr);
extern bool __weak is_swbp_insn(uprobe_opcode_t *insn);
extern int uprobe_register(struct inode *inode, loff_t offset, struct uprobe_consumer *uc);
extern int uprobe_apply(struct inode *inode, loff_t offset, struct uprobe_consumer *uc, bool);
extern void uprobe_unregister(struct inode *inode, loff_t offset, struct uprobe_consumer *uc);
extern int uprobe_mmap(struct vm_area_struct *vma);
extern void uprobe_munmap(struct vm_area_struct *vma, unsigned long start, unsigned long end);
@@ -117,6 +125,11 @@ uprobe_register(struct inode *inode, loff_t offset, struct uprobe_consumer *uc)
{
	return -ENOSYS;
}
static inline int
uprobe_apply(struct inode *inode, loff_t offset, struct uprobe_consumer *uc, bool add)
{
	return -ENOSYS;
}
static inline void
uprobe_unregister(struct inode *inode, loff_t offset, struct uprobe_consumer *uc)
{
+4 −1
Original line number Diff line number Diff line
@@ -6162,11 +6162,14 @@ perf_event_alloc(struct perf_event_attr *attr, int cpu,

	if (task) {
		event->attach_state = PERF_ATTACH_TASK;

		if (attr->type == PERF_TYPE_TRACEPOINT)
			event->hw.tp_target = task;
#ifdef CONFIG_HAVE_HW_BREAKPOINT
		/*
		 * hw_breakpoint is a bit difficult here..
		 */
		if (attr->type == PERF_TYPE_BREAKPOINT)
		else if (attr->type == PERF_TYPE_BREAKPOINT)
			event->hw.bp_target = task;
#endif
	}
+252 −213

File changed.

Preview size limit exceeded, changes collapsed.

Loading