diff options
Diffstat (limited to 'lib/stackdepot.c')
| -rw-r--r-- | lib/stackdepot.c | 54 | 
1 files changed, 33 insertions, 21 deletions
diff --git a/lib/stackdepot.c b/lib/stackdepot.c index e513459a5601..605c61f65d94 100644 --- a/lib/stackdepot.c +++ b/lib/stackdepot.c @@ -194,40 +194,52 @@ static inline struct stack_record *find_stack(struct stack_record *bucket,  	return NULL;  } -void depot_fetch_stack(depot_stack_handle_t handle, struct stack_trace *trace) +/** + * stack_depot_fetch - Fetch stack entries from a depot + * + * @handle:		Stack depot handle which was returned from + *			stack_depot_save(). + * @entries:		Pointer to store the entries address + * + * Return: The number of trace entries for this depot. + */ +unsigned int stack_depot_fetch(depot_stack_handle_t handle, +			       unsigned long **entries)  {  	union handle_parts parts = { .handle = handle };  	void *slab = stack_slabs[parts.slabindex];  	size_t offset = parts.offset << STACK_ALLOC_ALIGN;  	struct stack_record *stack = slab + offset; -	trace->nr_entries = trace->max_entries = stack->size; -	trace->entries = stack->entries; -	trace->skip = 0; +	*entries = stack->entries; +	return stack->size;  } -EXPORT_SYMBOL_GPL(depot_fetch_stack); +EXPORT_SYMBOL_GPL(stack_depot_fetch);  /** - * depot_save_stack - save stack in a stack depot. - * @trace - the stacktrace to save. - * @alloc_flags - flags for allocating additional memory if required. + * stack_depot_save - Save a stack trace from an array + * + * @entries:		Pointer to storage array + * @nr_entries:		Size of the storage array + * @alloc_flags:	Allocation gfp flags   * - * Returns the handle of the stack struct stored in depot. + * Return: The handle of the stack struct stored in depot   */ -depot_stack_handle_t depot_save_stack(struct stack_trace *trace, -				    gfp_t alloc_flags) +depot_stack_handle_t stack_depot_save(unsigned long *entries, +				      unsigned int nr_entries, +				      gfp_t alloc_flags)  { -	u32 hash; -	depot_stack_handle_t retval = 0;  	struct stack_record *found = NULL, **bucket; -	unsigned long flags; +	depot_stack_handle_t retval = 0;  	struct page *page = NULL;  	void *prealloc = NULL; +	unsigned long flags; +	u32 hash; -	if (unlikely(trace->nr_entries == 0)) +	if (unlikely(nr_entries == 0))  		goto fast_exit; -	hash = hash_stack(trace->entries, trace->nr_entries); +	hash = hash_stack(entries, nr_entries);  	bucket = &stack_table[hash & STACK_HASH_MASK];  	/* @@ -235,8 +247,8 @@ depot_stack_handle_t depot_save_stack(struct stack_trace *trace,  	 * The smp_load_acquire() here pairs with smp_store_release() to  	 * |bucket| below.  	 */ -	found = find_stack(smp_load_acquire(bucket), trace->entries, -			   trace->nr_entries, hash); +	found = find_stack(smp_load_acquire(bucket), entries, +			   nr_entries, hash);  	if (found)  		goto exit; @@ -264,10 +276,10 @@ depot_stack_handle_t depot_save_stack(struct stack_trace *trace,  	spin_lock_irqsave(&depot_lock, flags); -	found = find_stack(*bucket, trace->entries, trace->nr_entries, hash); +	found = find_stack(*bucket, entries, nr_entries, hash);  	if (!found) {  		struct stack_record *new = -			depot_alloc_stack(trace->entries, trace->nr_entries, +			depot_alloc_stack(entries, nr_entries,  					  hash, &prealloc, alloc_flags);  		if (new) {  			new->next = *bucket; @@ -297,4 +309,4 @@ exit:  fast_exit:  	return retval;  } -EXPORT_SYMBOL_GPL(depot_save_stack); +EXPORT_SYMBOL_GPL(stack_depot_save);  |