Find the code using your CPU and memory.

Explore continuous production profiles by function, and compare two releases to see what got more expensive. Where a trace names the slow span, a profile names the code inside it.

RunsContinuously, in production
CollectsCPU and allocations
AnswersWhich function, which line
checkout-api · cpudb.acquire · 78% self
v2.14.0cpu · wall clockLast 15mcompare · v2.13.9
main
handleCheckout
chargeCardrenderReceipt
db.acquirestripe.chargetemplate
pool.waithttp.postjsx
mutex.lockbackoff
futex_wait
syscall
Top by self time
db.acquire78%
pool.wait71%
mutex.lock40%
template9%
stripe.charge4%
vs v2.13.915m
p95+1.4s
cpu+38%
allocations−2%
Linked
Trace a41f…9c2 · db.acquire 1.90s

Narrow a slow span to a function

Profiling picks up where a trace stops: inside a span that is doing work rather than waiting. Here is one span, from the trace to the function that explains it.

INC-402 · Checkout latency above SLO
Resolved
14:02:11 → 14:19:44 · 17m 33s
14:07:40
The slow span has no obvious cause
The pricing span takes 1.4s and makes no external calls, so the time is going inside it.
Traces
14:09:02
One function holds 38% of CPU
PriceRules.evaluate re-parses the same rule set on every request, starting at the 13:58 deploy.
Profiles
14:10:15
Compared against the previous release
The same function was at 3% on the previous build, so the diff names what changed.
Profiles

Explore and compare production profiles

Continuous sampling profiles, joined to the traces and releases that explain them.

CPU profiles

Where wall time and CPU time go, by function, with self time and total time separated.

cpu
Allocation profiles

What allocates, how often, and what keeps it alive.

heap
Flame graphs

The call tree drawn to scale, so the width of a frame is the time spent in it.

flamegraph
Compare profiles across releases

See which functions use more CPU or allocate more memory after a deployment, as one ranked list.

diff
Joined to traces

From a slow span to the frames that were on the stack while it ran, on the same service and time range.

trace-link
Runtimes

Go, Java, Python, Node, Ruby and .NET, through pprof and OTLP profile signals.

pprof · otlp
Sampled, not instrumented

The profiler samples stacks on a timer rather than wrapping your functions, so it can stay on in production.

always-on

Compare two profiles side by side.

Pick two time windows or two releases and read the ranked list of what got more expensive between them, alongside the flame graph for each.

  • Pick two windows. Before a deploy and after it, or one host against a healthy one.
  • Read the movers. Functions ordered by how much they grew, not by how large they are.
  • Land on a line. File and line number, resolved from the binary you shipped.
  • Confirm the fix. Run the same comparison after the change to see the frame come back down.
Profile diff · 2f91c vs 8ad30self time, delta
PriceRules.evaluate
+35.1 pts
json.Unmarshal
+12.4 pts
runtime.mallocgc
+4.8 pts
sql.QueryContext
−1.2 pts
Total CPU, service
+41% at same RPS

Start profiling production.

Send pprof or OTLP profiles from Go, Java, Python, Node, Ruby or .NET and compare your next two releases. Start on the free plan with no card.