xref: /linux/kernel/trace/fprobe.c (revision bf40f4b87761e2ec16efc8e49b9ca0d81f4115d8)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * fprobe - Simple ftrace probe wrapper for function entry.
4  */
5 #define pr_fmt(fmt) "fprobe: " fmt
6 
7 #include <linux/err.h>
8 #include <linux/fprobe.h>
9 #include <linux/kallsyms.h>
10 #include <linux/kprobes.h>
11 #include <linux/list.h>
12 #include <linux/mutex.h>
13 #include <linux/slab.h>
14 #include <linux/sort.h>
15 
16 #include <asm/fprobe.h>
17 
18 #include "trace.h"
19 
20 #define FPROBE_IP_HASH_BITS 8
21 #define FPROBE_IP_TABLE_SIZE (1 << FPROBE_IP_HASH_BITS)
22 
23 #define FPROBE_HASH_BITS 6
24 #define FPROBE_TABLE_SIZE (1 << FPROBE_HASH_BITS)
25 
26 #define SIZE_IN_LONG(x) ((x + sizeof(long) - 1) >> (sizeof(long) == 8 ? 3 : 2))
27 
28 /*
29  * fprobe_table: hold 'fprobe_hlist::hlist' for checking the fprobe still
30  *   exists. The key is the address of fprobe instance.
31  * fprobe_ip_table: hold 'fprobe_hlist::array[*]' for searching the fprobe
32  *   instance related to the funciton address. The key is the ftrace IP
33  *   address.
34  *
35  * When unregistering the fprobe, fprobe_hlist::fp and fprobe_hlist::array[*].fp
36  * are set NULL and delete those from both hash tables (by hlist_del_rcu).
37  * After an RCU grace period, the fprobe_hlist itself will be released.
38  *
39  * fprobe_table and fprobe_ip_table can be accessed from either
40  *  - Normal hlist traversal and RCU add/del under 'fprobe_mutex' is held.
41  *  - RCU hlist traversal under disabling preempt
42  */
43 static struct hlist_head fprobe_table[FPROBE_TABLE_SIZE];
44 static struct hlist_head fprobe_ip_table[FPROBE_IP_TABLE_SIZE];
45 static DEFINE_MUTEX(fprobe_mutex);
46 
47 /*
48  * Find first fprobe in the hlist. It will be iterated twice in the entry
49  * probe, once for correcting the total required size, the second time is
50  * calling back the user handlers.
51  * Thus the hlist in the fprobe_table must be sorted and new probe needs to
52  * be added *before* the first fprobe.
53  */
find_first_fprobe_node(unsigned long ip)54 static struct fprobe_hlist_node *find_first_fprobe_node(unsigned long ip)
55 {
56 	struct fprobe_hlist_node *node;
57 	struct hlist_head *head;
58 
59 	head = &fprobe_ip_table[hash_ptr((void *)ip, FPROBE_IP_HASH_BITS)];
60 	hlist_for_each_entry_rcu(node, head, hlist,
61 				 lockdep_is_held(&fprobe_mutex)) {
62 		if (node->addr == ip)
63 			return node;
64 	}
65 	return NULL;
66 }
67 NOKPROBE_SYMBOL(find_first_fprobe_node);
68 
69 /* Node insertion and deletion requires the fprobe_mutex */
insert_fprobe_node(struct fprobe_hlist_node * node)70 static void insert_fprobe_node(struct fprobe_hlist_node *node)
71 {
72 	unsigned long ip = node->addr;
73 	struct fprobe_hlist_node *next;
74 	struct hlist_head *head;
75 
76 	lockdep_assert_held(&fprobe_mutex);
77 
78 	next = find_first_fprobe_node(ip);
79 	if (next) {
80 		hlist_add_before_rcu(&node->hlist, &next->hlist);
81 		return;
82 	}
83 	head = &fprobe_ip_table[hash_ptr((void *)ip, FPROBE_IP_HASH_BITS)];
84 	hlist_add_head_rcu(&node->hlist, head);
85 }
86 
87 /* Return true if there are synonims */
delete_fprobe_node(struct fprobe_hlist_node * node)88 static bool delete_fprobe_node(struct fprobe_hlist_node *node)
89 {
90 	lockdep_assert_held(&fprobe_mutex);
91 
92 	/* Avoid double deleting */
93 	if (READ_ONCE(node->fp) != NULL) {
94 		WRITE_ONCE(node->fp, NULL);
95 		hlist_del_rcu(&node->hlist);
96 	}
97 	return !!find_first_fprobe_node(node->addr);
98 }
99 
100 /* Check existence of the fprobe */
is_fprobe_still_exist(struct fprobe * fp)101 static bool is_fprobe_still_exist(struct fprobe *fp)
102 {
103 	struct hlist_head *head;
104 	struct fprobe_hlist *fph;
105 
106 	head = &fprobe_table[hash_ptr(fp, FPROBE_HASH_BITS)];
107 	hlist_for_each_entry_rcu(fph, head, hlist,
108 				 lockdep_is_held(&fprobe_mutex)) {
109 		if (fph->fp == fp)
110 			return true;
111 	}
112 	return false;
113 }
114 NOKPROBE_SYMBOL(is_fprobe_still_exist);
115 
add_fprobe_hash(struct fprobe * fp)116 static int add_fprobe_hash(struct fprobe *fp)
117 {
118 	struct fprobe_hlist *fph = fp->hlist_array;
119 	struct hlist_head *head;
120 
121 	lockdep_assert_held(&fprobe_mutex);
122 
123 	if (WARN_ON_ONCE(!fph))
124 		return -EINVAL;
125 
126 	if (is_fprobe_still_exist(fp))
127 		return -EEXIST;
128 
129 	head = &fprobe_table[hash_ptr(fp, FPROBE_HASH_BITS)];
130 	hlist_add_head_rcu(&fp->hlist_array->hlist, head);
131 	return 0;
132 }
133 
del_fprobe_hash(struct fprobe * fp)134 static int del_fprobe_hash(struct fprobe *fp)
135 {
136 	struct fprobe_hlist *fph = fp->hlist_array;
137 
138 	lockdep_assert_held(&fprobe_mutex);
139 
140 	if (WARN_ON_ONCE(!fph))
141 		return -EINVAL;
142 
143 	if (!is_fprobe_still_exist(fp))
144 		return -ENOENT;
145 
146 	fph->fp = NULL;
147 	hlist_del_rcu(&fph->hlist);
148 	return 0;
149 }
150 
151 #ifdef ARCH_DEFINE_ENCODE_FPROBE_HEADER
152 
153 /* The arch should encode fprobe_header info into one unsigned long */
154 #define FPROBE_HEADER_SIZE_IN_LONG	1
155 
write_fprobe_header(unsigned long * stack,struct fprobe * fp,unsigned int size_words)156 static inline bool write_fprobe_header(unsigned long *stack,
157 					struct fprobe *fp, unsigned int size_words)
158 {
159 	if (WARN_ON_ONCE(size_words > MAX_FPROBE_DATA_SIZE_WORD ||
160 			 !arch_fprobe_header_encodable(fp)))
161 		return false;
162 
163 	*stack = arch_encode_fprobe_header(fp, size_words);
164 	return true;
165 }
166 
read_fprobe_header(unsigned long * stack,struct fprobe ** fp,unsigned int * size_words)167 static inline void read_fprobe_header(unsigned long *stack,
168 					struct fprobe **fp, unsigned int *size_words)
169 {
170 	*fp = arch_decode_fprobe_header_fp(*stack);
171 	*size_words = arch_decode_fprobe_header_size(*stack);
172 }
173 
174 #else
175 
176 /* Generic fprobe_header */
177 struct __fprobe_header {
178 	struct fprobe *fp;
179 	unsigned long size_words;
180 } __packed;
181 
182 #define FPROBE_HEADER_SIZE_IN_LONG	SIZE_IN_LONG(sizeof(struct __fprobe_header))
183 
write_fprobe_header(unsigned long * stack,struct fprobe * fp,unsigned int size_words)184 static inline bool write_fprobe_header(unsigned long *stack,
185 					struct fprobe *fp, unsigned int size_words)
186 {
187 	struct __fprobe_header *fph = (struct __fprobe_header *)stack;
188 
189 	if (WARN_ON_ONCE(size_words > MAX_FPROBE_DATA_SIZE_WORD))
190 		return false;
191 
192 	fph->fp = fp;
193 	fph->size_words = size_words;
194 	return true;
195 }
196 
read_fprobe_header(unsigned long * stack,struct fprobe ** fp,unsigned int * size_words)197 static inline void read_fprobe_header(unsigned long *stack,
198 					struct fprobe **fp, unsigned int *size_words)
199 {
200 	struct __fprobe_header *fph = (struct __fprobe_header *)stack;
201 
202 	*fp = fph->fp;
203 	*size_words = fph->size_words;
204 }
205 
206 #endif
207 
208 /*
209  * fprobe shadow stack management:
210  * Since fprobe shares a single fgraph_ops, it needs to share the stack entry
211  * among the probes on the same function exit. Note that a new probe can be
212  * registered before a target function is returning, we can not use the hash
213  * table to find the corresponding probes. Thus the probe address is stored on
214  * the shadow stack with its entry data size.
215  *
216  */
__fprobe_handler(unsigned long ip,unsigned long parent_ip,struct fprobe * fp,struct ftrace_regs * fregs,void * data)217 static inline int __fprobe_handler(unsigned long ip, unsigned long parent_ip,
218 				   struct fprobe *fp, struct ftrace_regs *fregs,
219 				   void *data)
220 {
221 	if (!fp->entry_handler)
222 		return 0;
223 
224 	return fp->entry_handler(fp, ip, parent_ip, fregs, data);
225 }
226 
__fprobe_kprobe_handler(unsigned long ip,unsigned long parent_ip,struct fprobe * fp,struct ftrace_regs * fregs,void * data)227 static inline int __fprobe_kprobe_handler(unsigned long ip, unsigned long parent_ip,
228 					  struct fprobe *fp, struct ftrace_regs *fregs,
229 					  void *data)
230 {
231 	int ret;
232 	/*
233 	 * This user handler is shared with other kprobes and is not expected to be
234 	 * called recursively. So if any other kprobe handler is running, this will
235 	 * exit as kprobe does. See the section 'Share the callbacks with kprobes'
236 	 * in Documentation/trace/fprobe.rst for more information.
237 	 */
238 	if (unlikely(kprobe_running())) {
239 		fp->nmissed++;
240 		return 0;
241 	}
242 
243 	kprobe_busy_begin();
244 	ret = __fprobe_handler(ip, parent_ip, fp, fregs, data);
245 	kprobe_busy_end();
246 	return ret;
247 }
248 
fprobe_entry(struct ftrace_graph_ent * trace,struct fgraph_ops * gops,struct ftrace_regs * fregs)249 static int fprobe_entry(struct ftrace_graph_ent *trace, struct fgraph_ops *gops,
250 			struct ftrace_regs *fregs)
251 {
252 	struct fprobe_hlist_node *node, *first;
253 	unsigned long *fgraph_data = NULL;
254 	unsigned long func = trace->func;
255 	unsigned long ret_ip;
256 	int reserved_words;
257 	struct fprobe *fp;
258 	int used, ret;
259 
260 	if (WARN_ON_ONCE(!fregs))
261 		return 0;
262 
263 	first = node = find_first_fprobe_node(func);
264 	if (unlikely(!first))
265 		return 0;
266 
267 	reserved_words = 0;
268 	hlist_for_each_entry_from_rcu(node, hlist) {
269 		if (node->addr != func)
270 			break;
271 		fp = READ_ONCE(node->fp);
272 		if (!fp || !fp->exit_handler)
273 			continue;
274 		/*
275 		 * Since fprobe can be enabled until the next loop, we ignore the
276 		 * fprobe's disabled flag in this loop.
277 		 */
278 		reserved_words +=
279 			FPROBE_HEADER_SIZE_IN_LONG + SIZE_IN_LONG(fp->entry_data_size);
280 	}
281 	node = first;
282 	if (reserved_words) {
283 		fgraph_data = fgraph_reserve_data(gops->idx, reserved_words * sizeof(long));
284 		if (unlikely(!fgraph_data)) {
285 			hlist_for_each_entry_from_rcu(node, hlist) {
286 				if (node->addr != func)
287 					break;
288 				fp = READ_ONCE(node->fp);
289 				if (fp && !fprobe_disabled(fp))
290 					fp->nmissed++;
291 			}
292 			return 0;
293 		}
294 	}
295 
296 	/*
297 	 * TODO: recursion detection has been done in the fgraph. Thus we need
298 	 * to add a callback to increment missed counter.
299 	 */
300 	ret_ip = ftrace_regs_get_return_address(fregs);
301 	used = 0;
302 	hlist_for_each_entry_from_rcu(node, hlist) {
303 		int data_size;
304 		void *data;
305 
306 		if (node->addr != func)
307 			break;
308 		fp = READ_ONCE(node->fp);
309 		if (!fp || fprobe_disabled(fp))
310 			continue;
311 
312 		data_size = fp->entry_data_size;
313 		if (data_size && fp->exit_handler)
314 			data = fgraph_data + used + FPROBE_HEADER_SIZE_IN_LONG;
315 		else
316 			data = NULL;
317 
318 		if (fprobe_shared_with_kprobes(fp))
319 			ret = __fprobe_kprobe_handler(func, ret_ip, fp, fregs, data);
320 		else
321 			ret = __fprobe_handler(func, ret_ip, fp, fregs, data);
322 
323 		/* If entry_handler returns !0, nmissed is not counted but skips exit_handler. */
324 		if (!ret && fp->exit_handler) {
325 			int size_words = SIZE_IN_LONG(data_size);
326 
327 			if (write_fprobe_header(&fgraph_data[used], fp, size_words))
328 				used += FPROBE_HEADER_SIZE_IN_LONG + size_words;
329 		}
330 	}
331 	if (used < reserved_words)
332 		memset(fgraph_data + used, 0, reserved_words - used);
333 
334 	/* If any exit_handler is set, data must be used. */
335 	return used != 0;
336 }
337 NOKPROBE_SYMBOL(fprobe_entry);
338 
fprobe_return(struct ftrace_graph_ret * trace,struct fgraph_ops * gops,struct ftrace_regs * fregs)339 static void fprobe_return(struct ftrace_graph_ret *trace,
340 			  struct fgraph_ops *gops,
341 			  struct ftrace_regs *fregs)
342 {
343 	unsigned long *fgraph_data = NULL;
344 	unsigned long ret_ip;
345 	struct fprobe *fp;
346 	int size, curr;
347 	int size_words;
348 
349 	fgraph_data = (unsigned long *)fgraph_retrieve_data(gops->idx, &size);
350 	if (WARN_ON_ONCE(!fgraph_data))
351 		return;
352 	size_words = SIZE_IN_LONG(size);
353 	ret_ip = ftrace_regs_get_instruction_pointer(fregs);
354 
355 	preempt_disable_notrace();
356 
357 	curr = 0;
358 	while (size_words > curr) {
359 		read_fprobe_header(&fgraph_data[curr], &fp, &size);
360 		if (!fp)
361 			break;
362 		curr += FPROBE_HEADER_SIZE_IN_LONG;
363 		if (is_fprobe_still_exist(fp) && !fprobe_disabled(fp)) {
364 			if (WARN_ON_ONCE(curr + size > size_words))
365 				break;
366 			fp->exit_handler(fp, trace->func, ret_ip, fregs,
367 					 size ? fgraph_data + curr : NULL);
368 		}
369 		curr += size;
370 	}
371 	preempt_enable_notrace();
372 }
373 NOKPROBE_SYMBOL(fprobe_return);
374 
375 static struct fgraph_ops fprobe_graph_ops = {
376 	.entryfunc	= fprobe_entry,
377 	.retfunc	= fprobe_return,
378 };
379 static int fprobe_graph_active;
380 
381 /* Add @addrs to the ftrace filter and register fgraph if needed. */
fprobe_graph_add_ips(unsigned long * addrs,int num)382 static int fprobe_graph_add_ips(unsigned long *addrs, int num)
383 {
384 	int ret;
385 
386 	lockdep_assert_held(&fprobe_mutex);
387 
388 	ret = ftrace_set_filter_ips(&fprobe_graph_ops.ops, addrs, num, 0, 0);
389 	if (ret)
390 		return ret;
391 
392 	if (!fprobe_graph_active) {
393 		ret = register_ftrace_graph(&fprobe_graph_ops);
394 		if (WARN_ON_ONCE(ret)) {
395 			ftrace_free_filter(&fprobe_graph_ops.ops);
396 			return ret;
397 		}
398 	}
399 	fprobe_graph_active++;
400 	return 0;
401 }
402 
403 /* Remove @addrs from the ftrace filter and unregister fgraph if possible. */
fprobe_graph_remove_ips(unsigned long * addrs,int num)404 static void fprobe_graph_remove_ips(unsigned long *addrs, int num)
405 {
406 	lockdep_assert_held(&fprobe_mutex);
407 
408 	fprobe_graph_active--;
409 	/* Q: should we unregister it ? */
410 	if (!fprobe_graph_active)
411 		unregister_ftrace_graph(&fprobe_graph_ops);
412 
413 	if (num)
414 		ftrace_set_filter_ips(&fprobe_graph_ops.ops, addrs, num, 1, 0);
415 }
416 
417 #ifdef CONFIG_MODULES
418 
419 #define FPROBE_IPS_BATCH_INIT 8
420 /* instruction pointer address list */
421 struct fprobe_addr_list {
422 	int index;
423 	int size;
424 	unsigned long *addrs;
425 };
426 
fprobe_addr_list_add(struct fprobe_addr_list * alist,unsigned long addr)427 static int fprobe_addr_list_add(struct fprobe_addr_list *alist, unsigned long addr)
428 {
429 	unsigned long *addrs;
430 
431 	/* Previously we failed to expand the list. */
432 	if (alist->index == alist->size)
433 		return -ENOSPC;
434 
435 	alist->addrs[alist->index++] = addr;
436 	if (alist->index < alist->size)
437 		return 0;
438 
439 	/* Expand the address list */
440 	addrs = kcalloc(alist->size * 2, sizeof(*addrs), GFP_KERNEL);
441 	if (!addrs)
442 		return -ENOMEM;
443 
444 	memcpy(addrs, alist->addrs, alist->size * sizeof(*addrs));
445 	alist->size *= 2;
446 	kfree(alist->addrs);
447 	alist->addrs = addrs;
448 
449 	return 0;
450 }
451 
fprobe_remove_node_in_module(struct module * mod,struct hlist_head * head,struct fprobe_addr_list * alist)452 static void fprobe_remove_node_in_module(struct module *mod, struct hlist_head *head,
453 					struct fprobe_addr_list *alist)
454 {
455 	struct fprobe_hlist_node *node;
456 	int ret = 0;
457 
458 	hlist_for_each_entry_rcu(node, head, hlist,
459 				 lockdep_is_held(&fprobe_mutex)) {
460 		if (!within_module(node->addr, mod))
461 			continue;
462 		if (delete_fprobe_node(node))
463 			continue;
464 		/*
465 		 * If failed to update alist, just continue to update hlist.
466 		 * Therefore, at list user handler will not hit anymore.
467 		 */
468 		if (!ret)
469 			ret = fprobe_addr_list_add(alist, node->addr);
470 	}
471 }
472 
473 /* Handle module unloading to manage fprobe_ip_table. */
fprobe_module_callback(struct notifier_block * nb,unsigned long val,void * data)474 static int fprobe_module_callback(struct notifier_block *nb,
475 				  unsigned long val, void *data)
476 {
477 	struct fprobe_addr_list alist = {.size = FPROBE_IPS_BATCH_INIT};
478 	struct module *mod = data;
479 	int i;
480 
481 	if (val != MODULE_STATE_GOING)
482 		return NOTIFY_DONE;
483 
484 	alist.addrs = kcalloc(alist.size, sizeof(*alist.addrs), GFP_KERNEL);
485 	/* If failed to alloc memory, we can not remove ips from hash. */
486 	if (!alist.addrs)
487 		return NOTIFY_DONE;
488 
489 	mutex_lock(&fprobe_mutex);
490 	for (i = 0; i < FPROBE_IP_TABLE_SIZE; i++)
491 		fprobe_remove_node_in_module(mod, &fprobe_ip_table[i], &alist);
492 
493 	if (alist.index > 0)
494 		ftrace_set_filter_ips(&fprobe_graph_ops.ops,
495 				      alist.addrs, alist.index, 1, 0);
496 	mutex_unlock(&fprobe_mutex);
497 
498 	kfree(alist.addrs);
499 
500 	return NOTIFY_DONE;
501 }
502 
503 static struct notifier_block fprobe_module_nb = {
504 	.notifier_call = fprobe_module_callback,
505 	.priority = 0,
506 };
507 
init_fprobe_module(void)508 static int __init init_fprobe_module(void)
509 {
510 	return register_module_notifier(&fprobe_module_nb);
511 }
512 early_initcall(init_fprobe_module);
513 #endif
514 
symbols_cmp(const void * a,const void * b)515 static int symbols_cmp(const void *a, const void *b)
516 {
517 	const char **str_a = (const char **) a;
518 	const char **str_b = (const char **) b;
519 
520 	return strcmp(*str_a, *str_b);
521 }
522 
523 /* Convert ftrace location address from symbols */
get_ftrace_locations(const char ** syms,int num)524 static unsigned long *get_ftrace_locations(const char **syms, int num)
525 {
526 	unsigned long *addrs;
527 
528 	/* Convert symbols to symbol address */
529 	addrs = kcalloc(num, sizeof(*addrs), GFP_KERNEL);
530 	if (!addrs)
531 		return ERR_PTR(-ENOMEM);
532 
533 	/* ftrace_lookup_symbols expects sorted symbols */
534 	sort(syms, num, sizeof(*syms), symbols_cmp, NULL);
535 
536 	if (!ftrace_lookup_symbols(syms, num, addrs))
537 		return addrs;
538 
539 	kfree(addrs);
540 	return ERR_PTR(-ENOENT);
541 }
542 
543 struct filter_match_data {
544 	const char *filter;
545 	const char *notfilter;
546 	size_t index;
547 	size_t size;
548 	unsigned long *addrs;
549 	struct module **mods;
550 };
551 
filter_match_callback(void * data,const char * name,unsigned long addr)552 static int filter_match_callback(void *data, const char *name, unsigned long addr)
553 {
554 	struct filter_match_data *match = data;
555 
556 	if (!glob_match(match->filter, name) ||
557 	    (match->notfilter && glob_match(match->notfilter, name)))
558 		return 0;
559 
560 	if (!ftrace_location(addr))
561 		return 0;
562 
563 	if (match->addrs) {
564 		struct module *mod = __module_text_address(addr);
565 
566 		if (mod && !try_module_get(mod))
567 			return 0;
568 
569 		match->mods[match->index] = mod;
570 		match->addrs[match->index] = addr;
571 	}
572 	match->index++;
573 	return match->index == match->size;
574 }
575 
576 /*
577  * Make IP list from the filter/no-filter glob patterns.
578  * Return the number of matched symbols, or errno.
579  * If @addrs == NULL, this just counts the number of matched symbols. If @addrs
580  * is passed with an array, we need to pass the an @mods array of the same size
581  * to increment the module refcount for each symbol.
582  * This means we also need to call `module_put` for each element of @mods after
583  * using the @addrs.
584  */
get_ips_from_filter(const char * filter,const char * notfilter,unsigned long * addrs,struct module ** mods,size_t size)585 static int get_ips_from_filter(const char *filter, const char *notfilter,
586 			       unsigned long *addrs, struct module **mods,
587 			       size_t size)
588 {
589 	struct filter_match_data match = { .filter = filter, .notfilter = notfilter,
590 		.index = 0, .size = size, .addrs = addrs, .mods = mods};
591 	int ret;
592 
593 	if (addrs && !mods)
594 		return -EINVAL;
595 
596 	ret = kallsyms_on_each_symbol(filter_match_callback, &match);
597 	if (ret < 0)
598 		return ret;
599 	if (IS_ENABLED(CONFIG_MODULES)) {
600 		ret = module_kallsyms_on_each_symbol(NULL, filter_match_callback, &match);
601 		if (ret < 0)
602 			return ret;
603 	}
604 
605 	return match.index ?: -ENOENT;
606 }
607 
fprobe_fail_cleanup(struct fprobe * fp)608 static void fprobe_fail_cleanup(struct fprobe *fp)
609 {
610 	kfree(fp->hlist_array);
611 	fp->hlist_array = NULL;
612 }
613 
614 /* Initialize the fprobe data structure. */
fprobe_init(struct fprobe * fp,unsigned long * addrs,int num)615 static int fprobe_init(struct fprobe *fp, unsigned long *addrs, int num)
616 {
617 	struct fprobe_hlist *hlist_array;
618 	unsigned long addr;
619 	int size, i;
620 
621 	if (!fp || !addrs || num <= 0)
622 		return -EINVAL;
623 
624 	size = ALIGN(fp->entry_data_size, sizeof(long));
625 	if (size > MAX_FPROBE_DATA_SIZE)
626 		return -E2BIG;
627 	fp->entry_data_size = size;
628 
629 	hlist_array = kzalloc(struct_size(hlist_array, array, num), GFP_KERNEL);
630 	if (!hlist_array)
631 		return -ENOMEM;
632 
633 	fp->nmissed = 0;
634 
635 	hlist_array->size = num;
636 	fp->hlist_array = hlist_array;
637 	hlist_array->fp = fp;
638 	for (i = 0; i < num; i++) {
639 		hlist_array->array[i].fp = fp;
640 		addr = ftrace_location(addrs[i]);
641 		if (!addr) {
642 			fprobe_fail_cleanup(fp);
643 			return -ENOENT;
644 		}
645 		hlist_array->array[i].addr = addr;
646 	}
647 	return 0;
648 }
649 
650 #define FPROBE_IPS_MAX	INT_MAX
651 
fprobe_count_ips_from_filter(const char * filter,const char * notfilter)652 int fprobe_count_ips_from_filter(const char *filter, const char *notfilter)
653 {
654 	return get_ips_from_filter(filter, notfilter, NULL, NULL, FPROBE_IPS_MAX);
655 }
656 
657 /**
658  * register_fprobe() - Register fprobe to ftrace by pattern.
659  * @fp: A fprobe data structure to be registered.
660  * @filter: A wildcard pattern of probed symbols.
661  * @notfilter: A wildcard pattern of NOT probed symbols.
662  *
663  * Register @fp to ftrace for enabling the probe on the symbols matched to @filter.
664  * If @notfilter is not NULL, the symbols matched the @notfilter are not probed.
665  *
666  * Return 0 if @fp is registered successfully, -errno if not.
667  */
register_fprobe(struct fprobe * fp,const char * filter,const char * notfilter)668 int register_fprobe(struct fprobe *fp, const char *filter, const char *notfilter)
669 {
670 	unsigned long *addrs __free(kfree) = NULL;
671 	struct module **mods __free(kfree) = NULL;
672 	int ret, num;
673 
674 	if (!fp || !filter)
675 		return -EINVAL;
676 
677 	num = get_ips_from_filter(filter, notfilter, NULL, NULL, FPROBE_IPS_MAX);
678 	if (num < 0)
679 		return num;
680 
681 	addrs = kcalloc(num, sizeof(*addrs), GFP_KERNEL);
682 	if (!addrs)
683 		return -ENOMEM;
684 
685 	mods = kcalloc(num, sizeof(*mods), GFP_KERNEL);
686 	if (!mods)
687 		return -ENOMEM;
688 
689 	ret = get_ips_from_filter(filter, notfilter, addrs, mods, num);
690 	if (ret < 0)
691 		return ret;
692 
693 	ret = register_fprobe_ips(fp, addrs, ret);
694 
695 	for (int i = 0; i < num; i++) {
696 		if (mods[i])
697 			module_put(mods[i]);
698 	}
699 	return ret;
700 }
701 EXPORT_SYMBOL_GPL(register_fprobe);
702 
703 /**
704  * register_fprobe_ips() - Register fprobe to ftrace by address.
705  * @fp: A fprobe data structure to be registered.
706  * @addrs: An array of target function address.
707  * @num: The number of entries of @addrs.
708  *
709  * Register @fp to ftrace for enabling the probe on the address given by @addrs.
710  * The @addrs must be the addresses of ftrace location address, which may be
711  * the symbol address + arch-dependent offset.
712  * If you unsure what this mean, please use other registration functions.
713  *
714  * Return 0 if @fp is registered successfully, -errno if not.
715  */
register_fprobe_ips(struct fprobe * fp,unsigned long * addrs,int num)716 int register_fprobe_ips(struct fprobe *fp, unsigned long *addrs, int num)
717 {
718 	struct fprobe_hlist *hlist_array;
719 	int ret, i;
720 
721 	ret = fprobe_init(fp, addrs, num);
722 	if (ret)
723 		return ret;
724 
725 	mutex_lock(&fprobe_mutex);
726 
727 	hlist_array = fp->hlist_array;
728 	ret = fprobe_graph_add_ips(addrs, num);
729 	if (!ret) {
730 		add_fprobe_hash(fp);
731 		for (i = 0; i < hlist_array->size; i++)
732 			insert_fprobe_node(&hlist_array->array[i]);
733 	}
734 	mutex_unlock(&fprobe_mutex);
735 
736 	if (ret)
737 		fprobe_fail_cleanup(fp);
738 
739 	return ret;
740 }
741 EXPORT_SYMBOL_GPL(register_fprobe_ips);
742 
743 /**
744  * register_fprobe_syms() - Register fprobe to ftrace by symbols.
745  * @fp: A fprobe data structure to be registered.
746  * @syms: An array of target symbols.
747  * @num: The number of entries of @syms.
748  *
749  * Register @fp to the symbols given by @syms array. This will be useful if
750  * you are sure the symbols exist in the kernel.
751  *
752  * Return 0 if @fp is registered successfully, -errno if not.
753  */
register_fprobe_syms(struct fprobe * fp,const char ** syms,int num)754 int register_fprobe_syms(struct fprobe *fp, const char **syms, int num)
755 {
756 	unsigned long *addrs;
757 	int ret;
758 
759 	if (!fp || !syms || num <= 0)
760 		return -EINVAL;
761 
762 	addrs = get_ftrace_locations(syms, num);
763 	if (IS_ERR(addrs))
764 		return PTR_ERR(addrs);
765 
766 	ret = register_fprobe_ips(fp, addrs, num);
767 
768 	kfree(addrs);
769 
770 	return ret;
771 }
772 EXPORT_SYMBOL_GPL(register_fprobe_syms);
773 
fprobe_is_registered(struct fprobe * fp)774 bool fprobe_is_registered(struct fprobe *fp)
775 {
776 	if (!fp || !fp->hlist_array)
777 		return false;
778 	return true;
779 }
780 
781 /**
782  * unregister_fprobe() - Unregister fprobe.
783  * @fp: A fprobe data structure to be unregistered.
784  *
785  * Unregister fprobe (and remove ftrace hooks from the function entries).
786  *
787  * Return 0 if @fp is unregistered successfully, -errno if not.
788  */
unregister_fprobe(struct fprobe * fp)789 int unregister_fprobe(struct fprobe *fp)
790 {
791 	struct fprobe_hlist *hlist_array;
792 	unsigned long *addrs = NULL;
793 	int ret = 0, i, count;
794 
795 	mutex_lock(&fprobe_mutex);
796 	if (!fp || !is_fprobe_still_exist(fp)) {
797 		ret = -EINVAL;
798 		goto out;
799 	}
800 
801 	hlist_array = fp->hlist_array;
802 	addrs = kcalloc(hlist_array->size, sizeof(unsigned long), GFP_KERNEL);
803 	if (!addrs) {
804 		ret = -ENOMEM;	/* TODO: Fallback to one-by-one loop */
805 		goto out;
806 	}
807 
808 	/* Remove non-synonim ips from table and hash */
809 	count = 0;
810 	for (i = 0; i < hlist_array->size; i++) {
811 		if (!delete_fprobe_node(&hlist_array->array[i]))
812 			addrs[count++] = hlist_array->array[i].addr;
813 	}
814 	del_fprobe_hash(fp);
815 
816 	fprobe_graph_remove_ips(addrs, count);
817 
818 	kfree_rcu(hlist_array, rcu);
819 	fp->hlist_array = NULL;
820 
821 out:
822 	mutex_unlock(&fprobe_mutex);
823 
824 	kfree(addrs);
825 	return ret;
826 }
827 EXPORT_SYMBOL_GPL(unregister_fprobe);
828