Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  * kernel/stacktrace.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  * Stack trace management functions
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7)  *  Copyright (C) 2006 Red Hat, Inc., Ingo Molnar <mingo@redhat.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) #include <linux/sched/task_stack.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) #include <linux/sched/debug.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) #include <linux/sched.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) #include <linux/export.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) #include <linux/kallsyms.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) #include <linux/stacktrace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18)  * stack_trace_print - Print the entries in the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19)  * @entries:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20)  * @nr_entries:	Number of entries in the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21)  * @spaces:	Number of leading spaces to print
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) void stack_trace_print(const unsigned long *entries, unsigned int nr_entries,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) 		       int spaces)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) 	unsigned int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) 	if (WARN_ON(!entries))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 		return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 	for (i = 0; i < nr_entries; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) 		printk("%*c%pS\n", 1 + spaces, ' ', (void *)entries[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) EXPORT_SYMBOL_GPL(stack_trace_print);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37)  * stack_trace_snprint - Print the entries in the stack trace into a buffer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38)  * @buf:	Pointer to the print buffer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39)  * @size:	Size of the print buffer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40)  * @entries:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41)  * @nr_entries:	Number of entries in the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42)  * @spaces:	Number of leading spaces to print
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44)  * Return: Number of bytes printed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) int stack_trace_snprint(char *buf, size_t size, const unsigned long *entries,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 			unsigned int nr_entries, int spaces)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 	unsigned int generated, i, total = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 	if (WARN_ON(!entries))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) 	for (i = 0; i < nr_entries && size; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 		generated = snprintf(buf, size, "%*c%pS\n", 1 + spaces, ' ',
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 				     (void *)entries[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) 		total += generated;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) 		if (generated >= size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) 			buf += size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) 			size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) 			buf += generated;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 			size -= generated;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 	return total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) EXPORT_SYMBOL_GPL(stack_trace_snprint);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) #ifdef CONFIG_ARCH_STACKWALK
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) struct stacktrace_cookie {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 	unsigned long	*store;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 	unsigned int	size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 	unsigned int	skip;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 	unsigned int	len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) static bool stack_trace_consume_entry(void *cookie, unsigned long addr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 	struct stacktrace_cookie *c = cookie;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 	if (c->len >= c->size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 		return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 	if (c->skip > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		c->skip--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 		return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 	c->store[c->len++] = addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 	return c->len < c->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) static bool stack_trace_consume_entry_nosched(void *cookie, unsigned long addr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 	if (in_sched_functions(addr))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 		return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 	return stack_trace_consume_entry(cookie, addr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104)  * stack_trace_save - Save a stack trace into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107)  * @skipnr:	Number of entries to skip at the start of the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109)  * Return: Number of trace entries stored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) unsigned int stack_trace_save(unsigned long *store, unsigned int size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 			      unsigned int skipnr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 	stack_trace_consume_fn consume_entry = stack_trace_consume_entry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 	struct stacktrace_cookie c = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 		.store	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 		.size	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 		.skip	= skipnr + 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 	arch_stack_walk(consume_entry, &c, current, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 	return c.len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) EXPORT_SYMBOL_GPL(stack_trace_save);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127)  * stack_trace_save_tsk - Save a task stack trace into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128)  * @task:	The task to examine
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131)  * @skipnr:	Number of entries to skip at the start of the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133)  * Return: Number of trace entries stored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) unsigned int stack_trace_save_tsk(struct task_struct *tsk, unsigned long *store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 				  unsigned int size, unsigned int skipnr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 	stack_trace_consume_fn consume_entry = stack_trace_consume_entry_nosched;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 	struct stacktrace_cookie c = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 		.store	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 		.size	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 		/* skip this function if they are tracing us */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 		.skip	= skipnr + (current == tsk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 	if (!try_get_task_stack(tsk))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) 	arch_stack_walk(consume_entry, &c, tsk, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 	put_task_stack(tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) 	return c.len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) EXPORT_SYMBOL_GPL(stack_trace_save_tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156)  * stack_trace_save_regs - Save a stack trace based on pt_regs into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157)  * @regs:	Pointer to pt_regs to examine
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160)  * @skipnr:	Number of entries to skip at the start of the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162)  * Return: Number of trace entries stored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) unsigned int stack_trace_save_regs(struct pt_regs *regs, unsigned long *store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 				   unsigned int size, unsigned int skipnr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 	stack_trace_consume_fn consume_entry = stack_trace_consume_entry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 	struct stacktrace_cookie c = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 		.store	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 		.size	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 		.skip	= skipnr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 	arch_stack_walk(consume_entry, &c, current, regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 	return c.len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) EXPORT_SYMBOL_GPL(stack_trace_save_regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) #ifdef CONFIG_HAVE_RELIABLE_STACKTRACE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181)  * stack_trace_save_tsk_reliable - Save task stack with verification
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182)  * @tsk:	Pointer to the task to examine
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186)  * Return:	An error if it detects any unreliable features of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187)  *		stack. Otherwise it guarantees that the stack trace is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188)  *		reliable and returns the number of entries stored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190)  * If the task is not 'current', the caller *must* ensure the task is inactive.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) int stack_trace_save_tsk_reliable(struct task_struct *tsk, unsigned long *store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 				  unsigned int size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 	stack_trace_consume_fn consume_entry = stack_trace_consume_entry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 	struct stacktrace_cookie c = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 		.store	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 		.size	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	 * If the task doesn't have a stack (e.g., a zombie), the stack is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 	 * "reliably" empty.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 	if (!try_get_task_stack(tsk))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	ret = arch_stack_walk_reliable(consume_entry, &c, tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 	put_task_stack(tsk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 	return ret ? ret : c.len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) #ifdef CONFIG_USER_STACKTRACE_SUPPORT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217)  * stack_trace_save_user - Save a user space stack trace into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221)  * Return: Number of trace entries stored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) unsigned int stack_trace_save_user(unsigned long *store, unsigned int size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 	stack_trace_consume_fn consume_entry = stack_trace_consume_entry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 	struct stacktrace_cookie c = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 		.store	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 		.size	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 	mm_segment_t fs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 	/* Trace user stack if not a kernel thread */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 	if (current->flags & PF_KTHREAD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	fs = force_uaccess_begin();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 	arch_stack_walk_user(consume_entry, &c, task_pt_regs(current));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 	force_uaccess_end(fs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 	return c.len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) #else /* CONFIG_ARCH_STACKWALK */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247)  * Architectures that do not implement save_stack_trace_*()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248)  * get these weak aliases and once-per-bootup warnings
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249)  * (whenever this facility is utilized - for example by procfs):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) __weak void
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) save_stack_trace_tsk(struct task_struct *tsk, struct stack_trace *trace)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 	WARN_ONCE(1, KERN_INFO "save_stack_trace_tsk() not implemented yet.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) __weak void
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) save_stack_trace_regs(struct pt_regs *regs, struct stack_trace *trace)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 	WARN_ONCE(1, KERN_INFO "save_stack_trace_regs() not implemented yet.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264)  * stack_trace_save - Save a stack trace into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267)  * @skipnr:	Number of entries to skip at the start of the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269)  * Return: Number of trace entries stored
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) unsigned int stack_trace_save(unsigned long *store, unsigned int size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 			      unsigned int skipnr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 	struct stack_trace trace = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 		.entries	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) 		.max_entries	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 		.skip		= skipnr + 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) 	save_stack_trace(&trace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) 	return trace.nr_entries;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) EXPORT_SYMBOL_GPL(stack_trace_save);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286)  * stack_trace_save_tsk - Save a task stack trace into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287)  * @task:	The task to examine
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290)  * @skipnr:	Number of entries to skip at the start of the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292)  * Return: Number of trace entries stored
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) unsigned int stack_trace_save_tsk(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 				  unsigned long *store, unsigned int size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 				  unsigned int skipnr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 	struct stack_trace trace = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 		.entries	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 		.max_entries	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 		/* skip this function if they are tracing us */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 		.skip	= skipnr + (current == task),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 	save_stack_trace_tsk(task, &trace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 	return trace.nr_entries;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310)  * stack_trace_save_regs - Save a stack trace based on pt_regs into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311)  * @regs:	Pointer to pt_regs to examine
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314)  * @skipnr:	Number of entries to skip at the start of the stack trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316)  * Return: Number of trace entries stored
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) unsigned int stack_trace_save_regs(struct pt_regs *regs, unsigned long *store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) 				   unsigned int size, unsigned int skipnr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 	struct stack_trace trace = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 		.entries	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 		.max_entries	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 		.skip		= skipnr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 	save_stack_trace_regs(regs, &trace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 	return trace.nr_entries;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) #ifdef CONFIG_HAVE_RELIABLE_STACKTRACE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333)  * stack_trace_save_tsk_reliable - Save task stack with verification
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334)  * @tsk:	Pointer to the task to examine
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338)  * Return:	An error if it detects any unreliable features of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339)  *		stack. Otherwise it guarantees that the stack trace is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340)  *		reliable and returns the number of entries stored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342)  * If the task is not 'current', the caller *must* ensure the task is inactive.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) int stack_trace_save_tsk_reliable(struct task_struct *tsk, unsigned long *store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 				  unsigned int size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) 	struct stack_trace trace = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 		.entries	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) 		.max_entries	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 	int ret = save_stack_trace_tsk_reliable(tsk, &trace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 	return ret ? ret : trace.nr_entries;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) #ifdef CONFIG_USER_STACKTRACE_SUPPORT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359)  * stack_trace_save_user - Save a user space stack trace into a storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360)  * @store:	Pointer to storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361)  * @size:	Size of the storage array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363)  * Return: Number of trace entries stored
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) unsigned int stack_trace_save_user(unsigned long *store, unsigned int size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 	struct stack_trace trace = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 		.entries	= store,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 		.max_entries	= size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 	};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 	save_stack_trace_user(&trace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 	return trace.nr_entries;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) #endif /* CONFIG_USER_STACKTRACE_SUPPORT */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) #endif /* !CONFIG_ARCH_STACKWALK */