[gjs: 7/14] profiler: Adapt to new GeckoProfiler API
- From: Philip Chimento <pchimento src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gjs: 7/14] profiler: Adapt to new GeckoProfiler API
- Date: Sun, 29 Jul 2018 16:54:52 +0000 (UTC)
commit 94e1c78dba4abbe5e8f77bbac4d164e1cd8d7dbc
Author: Philip Chimento <philip chimento gmail com>
Date: Sun Jun 24 00:58:08 2018 -0700
profiler: Adapt to new GeckoProfiler API
Instead of providing the GeckoProfiler (renamed from SPSProfiler) with a
flat array of profile entries in which to write out the stack,
SpiderMonkey 60 now takes care of the array of entries internally, and
encapsulates them in a class called PseudoStack.
This means we don't have to keep track of the stack depth anymore, and
we also don't have to choose a maximum stack depth.
See: #161
gjs/profiler.cpp | 48 ++++++++----------------------------------------
1 file changed, 8 insertions(+), 40 deletions(-)
---
diff --git a/gjs/profiler.cpp b/gjs/profiler.cpp
index 1b6817d1..27864fc3 100644
--- a/gjs/profiler.cpp
+++ b/gjs/profiler.cpp
@@ -83,7 +83,7 @@ struct _GjsProfiler {
* information while executing. We will look into this during our
* SIGPROF handler.
*/
- js::ProfileEntry stack[1024];
+ PseudoStack stack;
/* The context being profiled */
JSContext *cx;
@@ -99,12 +99,6 @@ struct _GjsProfiler {
/* Our POSIX timer to wakeup SIGPROF */
timer_t timer;
- /* The depth of @stack. This value may be larger than the
- * number of elements in stack, and so you MUST ensure you
- * don't walk past the end of stack[] when iterating.
- */
- uint32_t stack_depth;
-
/* Cached copy of our pid */
GPid pid;
@@ -272,21 +266,6 @@ _gjs_profiler_is_running(GjsProfiler *self)
#ifdef ENABLE_PROFILER
-/* Run from a signal handler */
-static inline unsigned
-gjs_profiler_get_stack_size(GjsProfiler *self)
-{
- g_assert(((void) "Profiler must be set up before getting stack size", self));
-
- /*
- * Note that stack_depth could be larger than the number of
- * items we have in our stack space. We must protect ourselves
- * against overflowing by discarding anything after that depth
- * of the stack.
- */
- return std::min(self->stack_depth, uint32_t(G_N_ELEMENTS(self->stack)));
-}
-
static void
gjs_profiler_sigprof(int signum,
siginfo_t *info,
@@ -309,33 +288,26 @@ gjs_profiler_sigprof(int signum,
if (!self || info->si_code != SI_TIMER)
return;
- size_t depth = gjs_profiler_get_stack_size(self);
+ uint32_t depth = self->stack.stackSize();
if (depth == 0)
return;
- static_assert(G_N_ELEMENTS(self->stack) < G_MAXUSHORT,
- "Number of elements in profiler stack should be expressible"
- "in an unsigned short");
-
int64_t now = g_get_monotonic_time() * 1000L;
/* NOTE: cppcheck warns that alloca() is not recommended since it can
* easily overflow the stack; however, dynamic allocation is not an option
* here since we are in a signal handler.
- * Another option would be to always allocate G_N_ELEMENTS(self->stack),
- * but that is by definition at least as large of an allocation and
- * therefore is more likely to overflow.
*/
// cppcheck-suppress allocaCalled
SpCaptureAddress *addrs = static_cast<SpCaptureAddress *>(alloca(sizeof *addrs * depth));
- for (size_t ix = 0; ix < depth; ix++) {
- js::ProfileEntry& entry = self->stack[ix];
+ for (uint32_t ix = 0; ix < depth; ix++) {
+ js::ProfileEntry& entry = self->stack.entries[ix];
const char *label = entry.label();
- size_t flipped = depth - 1 - ix;
+ uint32_t flipped = depth - 1 - ix;
/*
- * SPSProfiler will put "js::RunScript" on the stack, but it has
+ * GeckoProfiler will put "js::RunScript" on the stack, but it has
* a stack address of "this", which is not terribly useful since
* everything will show up as [stack] when building callgraphs.
*/
@@ -399,8 +371,6 @@ gjs_profiler_start(GjsProfiler *self)
return;
}
- self->stack_depth = 0;
-
/* Setup our signal handler for SIGPROF delivery */
sa.sa_flags = SA_RESTART | SA_SIGINFO;
sa.sa_sigaction = gjs_profiler_sigprof;
@@ -449,8 +419,7 @@ gjs_profiler_start(GjsProfiler *self)
self->running = true;
/* Notify the JS runtime of where to put stack info */
- js::SetContextProfilingStack(self->cx, self->stack, &self->stack_depth,
- G_N_ELEMENTS(self->stack));
+ js::SetContextProfilingStack(self->cx, &self->stack);
/* Start recording stack info */
js::EnableContextProfilingStack(self->cx, true);
@@ -496,13 +465,12 @@ gjs_profiler_stop(GjsProfiler *self)
timer_delete(self->timer);
js::EnableContextProfilingStack(self->cx, false);
- js::SetContextProfilingStack(self->cx, nullptr, nullptr, 0);
+ js::SetContextProfilingStack(self->cx, nullptr);
sp_capture_writer_flush(self->capture);
g_clear_pointer(&self->capture, sp_capture_writer_unref);
- self->stack_depth = 0;
g_message("Profiler stopped");
#endif /* ENABLE_PROFILER */
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]