Replace the dynamic allocation in os_backtrace_symbols() with a static buffer embedded in struct backtrace_ctx. This avoids malloc recursion when backtrace is called from within dlmalloc (e.g., for the upcoming mcheck caller-tracking). The API gets a complete rework as part of this: - Combine addrs[] and syms[] arrays into struct backtrace_frame with addr and sym fields - Store the strings in a unified buffer, with pointers from an array - Change os_backtrace_symbols() to take ctx pointer and fill sym_buf - Remove os_backtrace_symbols_free() as nothing needs freeing - Rename BACKTRACE_MAX to BACKTRACE_MAX_FRAMES Co-developed-by: Claude <noreply@anthropic.com> Signed-off-by: Simon Glass <simon.glass@canonical.com>
41 lines
792 B
C
41 lines
792 B
C
// SPDX-License-Identifier: GPL-2.0+
|
|
/*
|
|
* Backtrace support for sandbox
|
|
*
|
|
* Copyright 2025 Canonical Ltd
|
|
* Written by Simon Glass <simon.glass@canonical.com>
|
|
*/
|
|
|
|
#include <backtrace.h>
|
|
#include <errno.h>
|
|
#include <os.h>
|
|
#include <string.h>
|
|
|
|
int backtrace_init(struct backtrace_ctx *ctx, uint skip)
|
|
{
|
|
void *addrs[BACKTRACE_MAX_FRAMES];
|
|
uint i;
|
|
|
|
/* +1 to skip this function */
|
|
ctx->count = os_backtrace(addrs, BACKTRACE_MAX_FRAMES, skip + 1);
|
|
|
|
for (i = 0; i < ctx->count; i++) {
|
|
ctx->frame[i].addr = addrs[i];
|
|
ctx->frame[i].sym = NULL;
|
|
}
|
|
|
|
return ctx->count;
|
|
}
|
|
|
|
int backtrace_get_syms(struct backtrace_ctx *ctx, char *buf, int size)
|
|
{
|
|
os_backtrace_symbols(ctx);
|
|
|
|
return 0;
|
|
}
|
|
|
|
void backtrace_uninit(struct backtrace_ctx *ctx)
|
|
{
|
|
/* Nothing to free - caller owns the buffer */
|
|
}
|