Unbreak LTTng for kernel 5.7
[lttng-modules.git] / wrapper / kallsyms.c
1 /* SPDX-License-Identifier: (GPL-2.0-only OR LGPL-2.1-only)
2 *
3 * wrapper/kallsyms.c
4 *
5 * Wrapper around kallsyms. Using kprobes to get its address when available.
6 *
7 * Can we mainline LTTng already so we don't have to waste our time doing this
8 * kind of hack ?
9 *
10 * Copyright (C) 2020 Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
11 */
12
13 #include <linux/kprobes.h>
14 #include <linux/module.h>
15 #include <wrapper/kallsyms.h>
16
17 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(5,7,0))
18
19 #ifndef CONFIG_KPROBES
20 # error "LTTng-modules requires CONFIG_KPROBES on kernels >= 5.7.0"
21 #endif
22
23 static
24 unsigned long (*kallsyms_lookup_name_sym)(const char *name);
25
26 static
27 int dummy_kprobe_handler(struct kprobe *p, struct pt_regs *regs)
28 {
29 return 0;
30 }
31
32 static
33 unsigned long do_get_kallsyms(void)
34 {
35 struct kprobe probe;
36 int ret;
37 unsigned long addr;
38
39 memset(&probe, 0, sizeof(probe));
40 probe.pre_handler = dummy_kprobe_handler;
41 probe.symbol_name = "kallsyms_lookup_name";
42 ret = register_kprobe(&probe);
43 if (ret)
44 return 0;
45 addr = (unsigned long)probe.addr;
46 #ifdef CONFIG_ARM
47 #ifdef CONFIG_THUMB2_KERNEL
48 if (addr)
49 addr |= 1; /* set bit 0 in address for thumb mode */
50 #endif
51 #endif
52 unregister_kprobe(&probe);
53 return addr;
54 }
55
56 unsigned long wrapper_kallsyms_lookup_name(const char *name)
57 {
58 if (!kallsyms_lookup_name_sym) {
59 kallsyms_lookup_name_sym = (void *)do_get_kallsyms();
60 }
61 if (kallsyms_lookup_name_sym)
62 return kallsyms_lookup_name_sym(name);
63 else {
64 printk_once(KERN_WARNING "LTTng requires kallsyms_lookup_name\n");
65 return 0;
66 }
67 }
68 EXPORT_SYMBOL_GPL(wrapper_kallsyms_lookup_name);
69
70 #endif
This page took 0.032105 seconds and 4 git commands to generate.