perf: Make promise stack trace collection opt-in.
Some checks failed
Build Tilde Friends / Build-All (push) Has been cancelled
Some checks failed
Build Tilde Friends / Build-All (push) Has been cancelled
This commit is contained in:
parent
8912212d8e
commit
8b47938238
@ -22,8 +22,6 @@ static int64_t s_tls_malloc_size;
|
|||||||
static int64_t s_js_malloc_size;
|
static int64_t s_js_malloc_size;
|
||||||
static int64_t s_sqlite_malloc_size;
|
static int64_t s_sqlite_malloc_size;
|
||||||
|
|
||||||
extern uint32_t fnv32a(const void* buffer, int length, uint32_t start);
|
|
||||||
|
|
||||||
static size_t _tf_mem_round_up(size_t size)
|
static size_t _tf_mem_round_up(size_t size)
|
||||||
{
|
{
|
||||||
return (size + 7) & ~7;
|
return (size + 7) & ~7;
|
||||||
@ -156,7 +154,7 @@ static void _tf_mem_summarize(void* ptr, size_t size, int frames_count, void* co
|
|||||||
{
|
{
|
||||||
summary_t* summary = user_data;
|
summary_t* summary = user_data;
|
||||||
tf_mem_allocation_t allocation = {
|
tf_mem_allocation_t allocation = {
|
||||||
.stack_hash = fnv32a(frames, sizeof(void*) * frames_count, 0),
|
.stack_hash = tf_util_fnv32a(frames, sizeof(void*) * frames_count, 0),
|
||||||
.count = 1,
|
.count = 1,
|
||||||
.size = size,
|
.size = size,
|
||||||
.frames_count = frames_count,
|
.frames_count = frames_count,
|
||||||
|
57
src/task.c
57
src/task.c
@ -164,6 +164,7 @@ typedef struct _tf_task_t
|
|||||||
|
|
||||||
promise_stack_t* _promise_stacks;
|
promise_stack_t* _promise_stacks;
|
||||||
int _promise_stack_count;
|
int _promise_stack_count;
|
||||||
|
bool _promise_stack_debug;
|
||||||
|
|
||||||
timeout_t* timeouts;
|
timeout_t* timeouts;
|
||||||
|
|
||||||
@ -1252,10 +1253,13 @@ static void _add_promise_stack(tf_task_t* task, uint32_t hash, const char* stack
|
|||||||
|
|
||||||
static void _remove_promise_stack(tf_task_t* task, uint32_t hash)
|
static void _remove_promise_stack(tf_task_t* task, uint32_t hash)
|
||||||
{
|
{
|
||||||
promise_stack_t* found = bsearch(&hash, task->_promise_stacks, task->_promise_stack_count, sizeof(promise_stack_t), _promise_stack_compare);
|
if (task->_promise_stack_debug)
|
||||||
if (found)
|
|
||||||
{
|
{
|
||||||
found->count--;
|
promise_stack_t* found = bsearch(&hash, task->_promise_stacks, task->_promise_stack_count, sizeof(promise_stack_t), _promise_stack_compare);
|
||||||
|
if (found)
|
||||||
|
{
|
||||||
|
found->count--;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1271,33 +1275,26 @@ static void _tf_task_free_promise(tf_task_t* task, promiseid_t id)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t fnv32a(const void* buffer, int length, uint32_t start)
|
|
||||||
{
|
|
||||||
uint32_t result = 0x811c9dc5;
|
|
||||||
for (int i = 0; i < length; i++)
|
|
||||||
{
|
|
||||||
result ^= ((const uint8_t*)buffer)[i];
|
|
||||||
result += (result << 1) + (result << 4) + (result << 7) + (result << 8) + (result << 24);
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
JSValue tf_task_allocate_promise(tf_task_t* task, promiseid_t* out_promise)
|
JSValue tf_task_allocate_promise(tf_task_t* task, promiseid_t* out_promise)
|
||||||
{
|
{
|
||||||
JSValue error = JS_ThrowInternalError(task->_context, "promise callstack");
|
uint32_t stack_hash = 0;
|
||||||
JSValue exception = JS_GetException(task->_context);
|
if (task->_promise_stack_debug)
|
||||||
JSValue stack_value = JS_GetPropertyStr(task->_context, exception, "stack");
|
{
|
||||||
size_t length = 0;
|
JSValue error = JS_ThrowInternalError(task->_context, "promise callstack");
|
||||||
const char* stack = JS_ToCStringLen(task->_context, &length, stack_value);
|
JSValue exception = JS_GetException(task->_context);
|
||||||
uint32_t stack_hash = fnv32a((const void*)stack, (int)length, 0);
|
JSValue stack_value = JS_GetPropertyStr(task->_context, exception, "stack");
|
||||||
void* buffer[32];
|
size_t length = 0;
|
||||||
int count = tf_util_backtrace(buffer, sizeof(buffer) / sizeof(*buffer));
|
const char* stack = JS_ToCStringLen(task->_context, &length, stack_value);
|
||||||
stack_hash = fnv32a((const void*)buffer, sizeof(void*) * count, stack_hash);
|
stack_hash = tf_util_fnv32a((const void*)stack, (int)length, 0);
|
||||||
_add_promise_stack(task, stack_hash, stack, buffer, count);
|
void* buffer[32];
|
||||||
JS_FreeCString(task->_context, stack);
|
int count = tf_util_backtrace(buffer, sizeof(buffer) / sizeof(*buffer));
|
||||||
JS_FreeValue(task->_context, stack_value);
|
stack_hash = tf_util_fnv32a((const void*)buffer, sizeof(void*) * count, stack_hash);
|
||||||
JS_FreeValue(task->_context, exception);
|
_add_promise_stack(task, stack_hash, stack, buffer, count);
|
||||||
JS_FreeValue(task->_context, error);
|
JS_FreeCString(task->_context, stack);
|
||||||
|
JS_FreeValue(task->_context, stack_value);
|
||||||
|
JS_FreeValue(task->_context, exception);
|
||||||
|
JS_FreeValue(task->_context, error);
|
||||||
|
}
|
||||||
|
|
||||||
promiseid_t promiseId;
|
promiseid_t promiseId;
|
||||||
do
|
do
|
||||||
@ -1592,6 +1589,10 @@ tf_task_t* tf_task_create()
|
|||||||
*task = (tf_task_t) { 0 };
|
*task = (tf_task_t) { 0 };
|
||||||
++_count;
|
++_count;
|
||||||
|
|
||||||
|
char buffer[8] = { 0 };
|
||||||
|
size_t buffer_size = sizeof(buffer);
|
||||||
|
task->_promise_stack_debug = uv_os_getenv("TF_PROMISE_DEBUG", buffer, &buffer_size) == 0 && strcmp(buffer, "1") == 0;
|
||||||
|
|
||||||
JSMallocFunctions funcs = { 0 };
|
JSMallocFunctions funcs = { 0 };
|
||||||
tf_get_js_malloc_functions(&funcs);
|
tf_get_js_malloc_functions(&funcs);
|
||||||
task->_runtime = JS_NewRuntime2(&funcs, NULL);
|
task->_runtime = JS_NewRuntime2(&funcs, NULL);
|
||||||
|
@ -683,3 +683,14 @@ bool tf_util_is_mobile()
|
|||||||
{
|
{
|
||||||
return TF_IS_MOBILE != 0;
|
return TF_IS_MOBILE != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint32_t tf_util_fnv32a(const void* buffer, int length, uint32_t start)
|
||||||
|
{
|
||||||
|
uint32_t result = 0x811c9dc5;
|
||||||
|
for (int i = 0; i < length; i++)
|
||||||
|
{
|
||||||
|
result ^= ((const uint8_t*)buffer)[i];
|
||||||
|
result += (result << 1) + (result << 4) + (result << 7) + (result << 8) + (result << 24);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
@ -224,4 +224,13 @@ void tf_util_document_settings(const char* line_prefix);
|
|||||||
*/
|
*/
|
||||||
bool tf_util_is_mobile();
|
bool tf_util_is_mobile();
|
||||||
|
|
||||||
|
/**
|
||||||
|
** Compute a 32-bit hash of a buffer.
|
||||||
|
** @param buffer The data.
|
||||||
|
** @param length The size of the buffer in bytes.
|
||||||
|
** @param start The hash seed.
|
||||||
|
** @return The computed hash.
|
||||||
|
*/
|
||||||
|
uint32_t tf_util_fnv32a(const void* buffer, int length, uint32_t start);
|
||||||
|
|
||||||
/** @} */
|
/** @} */
|
||||||
|
Loading…
x
Reference in New Issue
Block a user