diff options
author | Masami Hiramatsu <mhiramat@redhat.com> | 2007-10-16 01:27:49 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-10-16 09:43:10 -0700 |
commit | f438d914b220051d4cbc65cbc5d98e163c85c93b (patch) | |
tree | 75e7fda155a8494595f6ae0539bbb64ef98230f6 /kernel/kprobes.c | |
parent | 49dce689ad4ef0fd1f970ef762168e4bd46f69a3 (diff) | |
download | op-kernel-dev-f438d914b220051d4cbc65cbc5d98e163c85c93b.zip op-kernel-dev-f438d914b220051d4cbc65cbc5d98e163c85c93b.tar.gz |
kprobes: support kretprobe blacklist
Introduce architecture dependent kretprobe blacklists to prohibit users
from inserting return probes on the function in which kprobes can be
inserted but kretprobes can not.
This patch also removes "__kprobes" mark from "__switch_to" on x86_64 and
registers "__switch_to" to the blacklist on x86-64, because that mark is to
prohibit user from inserting only kretprobe.
Signed-off-by: Masami Hiramatsu <mhiramat@redhat.com>
Cc: Prasanna S Panchamukhi <prasanna@in.ibm.com>
Acked-by: Ananth N Mavinakayanahalli <ananth@in.ibm.com>
Cc: Anil S Keshavamurthy <anil.s.keshavamurthy@intel.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'kernel/kprobes.c')
-rw-r--r-- | kernel/kprobes.c | 23 |
1 files changed, 23 insertions, 0 deletions
diff --git a/kernel/kprobes.c b/kernel/kprobes.c index f9798ff..e3a5d81 100644 --- a/kernel/kprobes.c +++ b/kernel/kprobes.c @@ -716,6 +716,18 @@ int __kprobes register_kretprobe(struct kretprobe *rp) int ret = 0; struct kretprobe_instance *inst; int i; + void *addr = rp->kp.addr; + + if (kretprobe_blacklist_size) { + if (addr == NULL) + kprobe_lookup_name(rp->kp.symbol_name, addr); + addr += rp->kp.offset; + + for (i = 0; kretprobe_blacklist[i].name != NULL; i++) { + if (kretprobe_blacklist[i].addr == addr) + return -EINVAL; + } + } rp->kp.pre_handler = pre_handler_kretprobe; rp->kp.post_handler = NULL; @@ -794,6 +806,17 @@ static int __init init_kprobes(void) INIT_HLIST_HEAD(&kretprobe_inst_table[i]); } + if (kretprobe_blacklist_size) { + /* lookup the function address from its name */ + for (i = 0; kretprobe_blacklist[i].name != NULL; i++) { + kprobe_lookup_name(kretprobe_blacklist[i].name, + kretprobe_blacklist[i].addr); + if (!kretprobe_blacklist[i].addr) + printk("kretprobe: lookup failed: %s\n", + kretprobe_blacklist[i].name); + } + } + /* By default, kprobes are enabled */ kprobe_enabled = true; |