On Fri, 7 Dec 2018 18:00:26 +0100 Andrea Righi <righi.and...@gmail.com> wrote:
> On Sat, Dec 08, 2018 at 01:01:20AM +0900, Masami Hiramatsu wrote: > > Hi Andrea and Ingo, > > > > Here is the patch what I meant. I just ran it on qemu-x86, and seemed > > working. > > After introducing this patch, I will start adding > > arch_populate_kprobe_blacklist() > > to some arches. > > > > Thank you, > > > > [RFC] kprobes: x86/kprobes: Blacklist symbols in arch-defined prohibited > > area > > > > From: Masami Hiramatsu <mhira...@kernel.org> > > > > Blacklist symbols in arch-defined probe-prohibited areas. > > With this change, user can see all symbols which are prohibited > > to probe in debugfs. > > > > All archtectures which have custom prohibit areas should define > > its own arch_populate_kprobe_blacklist() function, but unless that, > > all symbols marked __kprobes are blacklisted. > > > > Reported-by: Andrea Righi <righi.and...@gmail.com> > > Signed-off-by: Masami Hiramatsu <mhira...@kernel.org> > > --- > > [snip] > > > +int kprobe_add_ksym_blacklist(unsigned long entry) > > +{ > > + struct kprobe_blacklist_entry *ent; > > + unsigned long offset = 0, size = 0; > > + > > + if (!kernel_text_address(entry) || > > + !kallsyms_lookup_size_offset(entry, &size, &offset)) > > + return -EINVAL; > > + > > + ent = kmalloc(sizeof(*ent), GFP_KERNEL); > > + if (!ent) > > + return -ENOMEM; > > + ent->start_addr = entry - offset; > > + ent->end_addr = entry - offset + size; > > Do we need to take offset into account? The code before wasn't using it. Yes, if we hit an alias symbol (zero-size), we forcibly increment address and retry it. In that case, offset will be 1. > > > + INIT_LIST_HEAD(&ent->list); > > + list_add_tail(&ent->list, &kprobe_blacklist); > > + > > + return (int)size; > > +} > > + > > +/* Add functions in arch defined probe-prohibited area */ > > +int __weak arch_populate_kprobe_blacklist(void) > > +{ > > + unsigned long entry; > > + int ret = 0; > > + > > + for (entry = (unsigned long)__kprobes_text_start; > > + entry < (unsigned long)__kprobes_text_end; > > + entry += ret) { > > + ret = kprobe_add_ksym_blacklist(entry); > > + if (ret < 0) > > + return ret; > > + if (ret == 0) /* In case of alias symbol */ > > + ret = 1; Here, we incremented. Thank you, > > + } > > + return 0; > > +} > > + > > /* > > * Lookup and populate the kprobe_blacklist. > > * > > @@ -2104,26 +2142,20 @@ NOKPROBE_SYMBOL(dump_kprobe); > > static int __init populate_kprobe_blacklist(unsigned long *start, > > unsigned long *end) > > { > > + unsigned long entry; > > unsigned long *iter; > > - struct kprobe_blacklist_entry *ent; > > - unsigned long entry, offset = 0, size = 0; > > + int ret; > > > > for (iter = start; iter < end; iter++) { > > entry = arch_deref_entry_point((void *)*iter); > > - > > - if (!kernel_text_address(entry) || > > - !kallsyms_lookup_size_offset(entry, &size, &offset)) > > + ret = kprobe_add_ksym_blacklist(entry); > > + if (ret == -EINVAL) > > continue; > > - > > - ent = kmalloc(sizeof(*ent), GFP_KERNEL); > > - if (!ent) > > - return -ENOMEM; > > - ent->start_addr = entry; > > - ent->end_addr = entry + size; > > - INIT_LIST_HEAD(&ent->list); > > - list_add_tail(&ent->list, &kprobe_blacklist); > > + if (ret < 0) > > + return ret; > > } > > - return 0; > > + > > + return arch_populate_kprobe_blacklist(); > > } > > > > /* Module notifier call back, checking kprobes on the module */ -- Masami Hiramatsu <mhira...@kernel.org>