pprof

package
v2.0.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Apr 20, 2026 License: AGPL-3.0 Imports: 26 Imported by: 0

Documentation

Index

Constants

View Source
const (
	ProfileIDLabelName = "profile_id" // For compatibility with the existing clients.
	SpanIDLabelName    = "span_id"    // Will be supported in the future.
	TraceIDLabelName   = "trace_id"
)

Variables

This section is empty.

Functions

func CompareSampleLabels

func CompareSampleLabels(a, b []*profilev1.Label) int

CompareSampleLabels compares sample label pairs. It's expected that sample labels are sorted. The result will be 0 if a == b, < 0 if a < b, and > 0 if a > b.

func DropGoTypeParameters

func DropGoTypeParameters(p *profilev1.Profile) *profilev1.Profile

DropGoTypeParameters removes of type parameters from Go function names.

In go 1.21 and above, function names include type parameters, however, due to a bug, a function name could include any of the type instances regardless of the call site. Thus, e.g., x[T1].foo and x[T2].foo can't be distinguished in a profile. This leads to incorrect profiles and incorrect flame graphs, and hugely increases cardinality of stack traces.

The function renames x[T1].foo and x[T2].foo to x[...].foo and normalizes the profile, if type parameters are present in the profile. Otherwise, the profile returns unchanged.

See https://github.com/golang/go/issues/64528.

func FilterLabelsInPlace

func FilterLabelsInPlace(labels []*profilev1.Label, keys []int64) int

func FixGoProfile

func FixGoProfile(p *profilev1.Profile) *profilev1.Profile

FixGoProfile fixes known issues with profiles collected with the standard Go profiler.

Note that the function presumes that p is a Go profile and does not verify this. It is expected that the function is called very early in the profile processing chain and normalized after, regardless of the function outcome.

func FromBytes

func FromBytes(input []byte, fn func(*profilev1.Profile, int) error) error

func FromBytesWithLimit

func FromBytesWithLimit(input []byte, maxSize int64, fn func(*profilev1.Profile, int) error) error

FromBytesWithLimit reads a profile from bytes with an optional size limit and calls fn with the result. maxSize limits the decompressed size in bytes. Use 0 for no limit. This prevents zip bomb attacks where small compressed data expands to huge sizes.

func FromProfile

func FromProfile(p *profile.Profile) (*profilev1.Profile, error)

func FromTree

func FromTree(t *model.FunctionNameTree, ty *typesv1.ProfileType, timeNanos int64) *profilev1.Profile

func GetLanguage

func GetLanguage(profile *Profile) string

func LabelID

func LabelID(p *profilev1.Profile, name string) int64

func LabelKeysByString

func LabelKeysByString(p *profilev1.Profile, keys ...string) []int64

func LabelKeysMapByString

func LabelKeysMapByString(p *profilev1.Profile, keys ...string) map[string]int64

func LabelsWithout

func LabelsWithout(labels []*profilev1.Label, keys []int64) []*profilev1.Label

func Marshal

func Marshal(p *profilev1.Profile, compress bool) ([]byte, error)

func MustMarshal

func MustMarshal(p *profilev1.Profile, compress bool) []byte

func PotentialTruncatedGoStacktraces

func PotentialTruncatedGoStacktraces(p *profilev1.Profile) bool

PotentialTruncatedGoStacktraces reports whether there are any chances that the profile may have truncated stack traces.

func ProfileSpans

func ProfileSpans(p *profilev1.Profile) []uint64

func ProfileTraceIDs

func ProfileTraceIDs(p *profilev1.Profile) [][16]byte

func RenameLabel

func RenameLabel(p *profilev1.Profile, oldName, newName string)

func RepairGoTruncatedStacktraces

func RepairGoTruncatedStacktraces(p *profilev1.Profile)

RepairGoTruncatedStacktraces repairs truncated stack traces in Go heap profiles.

Go heap profile has a depth limit of 32 frames, which often renders profiles unreadable, and also increases cardinality of stack traces.

The function guesses truncated frames based on neighbors and repairs stack traces if there are high chances that this part is present in the profile. The heuristic is as follows:

For each stack trace S taller than 24 frames: if there is another stack trace R taller than 24 frames that overlaps with the given one by at least 16 frames in a row from the top, and has frames above its root, stack S considered truncated, and the missing part is copied from R.

func RewriteFunctions

func RewriteFunctions(p *profilev1.Profile, n []uint32)

func RewriteLocations

func RewriteLocations(p *profilev1.Profile, n []uint32)

func RewriteMappings

func RewriteMappings(p *profilev1.Profile, n []uint32)

func RewriteStrings

func RewriteStrings(p *profilev1.Profile, n []uint32)

func SetProfileMetadata

func SetProfileMetadata(p *profilev1.Profile, ty *typesv1.ProfileType, timeNanos int64, period int64)

SetProfileMetadata sets the metadata on the profile.

func Spans

func Spans(p *profilev1.Profile, spanIDLabelIdx int64) []uint64

func TraceIDs

func TraceIDs(p *profilev1.Profile, traceIDLabelIdx int64) [][16]byte

func Unmarshal

func Unmarshal(data []byte, p *profilev1.Profile) error

func UnmarshalWithLimit

func UnmarshalWithLimit(data []byte, p *profilev1.Profile, maxSize int64) error

UnmarshalWithLimit unmarshals a profile from bytes with an optional size limit. maxSize limits the decompressed size in bytes. Use 0 for no limit. This prevents zip bomb attacks where small compressed data expands to huge sizes.

func ZeroLabelStrings

func ZeroLabelStrings(p *profilev1.Profile)

Types

type ErrDecompressedSizeExceedsLimit

type ErrDecompressedSizeExceedsLimit struct {
	Limit int64
}

func (*ErrDecompressedSizeExceedsLimit) Error

type FunctionKey

type FunctionKey struct {
	// contains filtered or unexported fields
}

func GetFunctionKey

func GetFunctionKey(fn *profilev1.Function) FunctionKey

type LabelsByKeyValue

type LabelsByKeyValue []*profilev1.Label

func (LabelsByKeyValue) Len

func (l LabelsByKeyValue) Len() int

func (LabelsByKeyValue) Less

func (l LabelsByKeyValue) Less(i, j int) bool

func (LabelsByKeyValue) Swap

func (l LabelsByKeyValue) Swap(i, j int)

type LocationKey

type LocationKey struct {
	// contains filtered or unexported fields
}

func GetLocationKey

func GetLocationKey(loc *profilev1.Location) LocationKey

type MappingKey

type MappingKey struct {
	// contains filtered or unexported fields
}

func GetMappingKey

func GetMappingKey(m *profilev1.Mapping) MappingKey

type Profile

type Profile struct {
	*profilev1.Profile
	// contains filtered or unexported fields
}

func NewProfile

func NewProfile() *Profile

func OpenFile

func OpenFile(path string) (*Profile, error)

func RawFromBytes

func RawFromBytes(input []byte) (_ *Profile, err error)

func RawFromBytesWithLimit

func RawFromBytesWithLimit(input []byte, maxSize int64) (_ *Profile, err error)

RawFromBytesWithLimit reads a profile from bytes with an optional size limit. maxSize limits the decompressed size in bytes. Use 0 for no limit. This prevents zip bomb attacks where small compressed data expands to huge sizes.

func RawFromProto

func RawFromProto(pbp *profilev1.Profile) *Profile

func (*Profile) DebugString

func (p *Profile) DebugString() string

func (*Profile) Normalize

func (p *Profile) Normalize()

Normalize normalizes the profile by:

  • Removing all duplicate samples (summing their values).
  • Removing redundant profile labels (byte => unique of an allocation site) todo: We should reassess if this was a good choice because by merging duplicate stacktrace samples we cannot recompute the allocation per site ("bytes") profile label.
  • Removing empty samples.
  • Then remove unused references.
  • Ensure that the profile has a time_nanos set
  • Removes addresses from symbolized profiles.
  • Removes elements with invalid references.
  • Converts identifiers to indices.
  • Ensures that string_table[0] is "".

func (*Profile) RawSize

func (p *Profile) RawSize() int

RawSize of the profile

func (*Profile) Stats

func (p *Profile) Stats() string

func (*Profile) WriteTo

func (p *Profile) WriteTo(w io.Writer) (int64, error)

WriteTo writes the profile to the given writer.

type ProfileMerge

type ProfileMerge struct {
	// contains filtered or unexported fields
}

func (*ProfileMerge) Merge

func (m *ProfileMerge) Merge(p *profilev1.Profile, sanitize bool) error

Merge adds p to the profile merge, cloning new objects. Profile p is modified in place but not retained by the function.

func (*ProfileMerge) MergeBytes

func (m *ProfileMerge) MergeBytes(b []byte, sanitize bool) error

func (*ProfileMerge) Profile

func (m *ProfileMerge) Profile() *profilev1.Profile

type RewriteTable

type RewriteTable[K comparable, V, M any] struct {
	// contains filtered or unexported fields
}

RewriteTable maintains unique values V and their indices. V is never modified nor retained, K and M are kept in memory.

func NewRewriteTable

func NewRewriteTable[K comparable, V, M any](
	size int,
	k func(V) K,
	v func(V) M,
) RewriteTable[K, V, M]

func (*RewriteTable[K, V, M]) Append

func (t *RewriteTable[K, V, M]) Append(values []V)

func (*RewriteTable[K, V, M]) Index

func (t *RewriteTable[K, V, M]) Index(dst []uint32, values []V)

func (*RewriteTable[K, V, M]) Values

func (t *RewriteTable[K, V, M]) Values() []M

type SampleExporter

type SampleExporter struct {
	// contains filtered or unexported fields
}

func NewSampleExporter

func NewSampleExporter(p *profilev1.Profile) *SampleExporter

func (*SampleExporter) ExportSamples

func (e *SampleExporter) ExportSamples(dst *profilev1.Profile, samples []*profilev1.Sample) *profilev1.Profile

ExportSamples creates a new complete profile with the subset of samples provided. It is assumed that those are part of the source profile. Provided samples are modified in place.

The same exporter instance can be used to export non-overlapping sample sets from a single profile.

type SampleGroup

type SampleGroup struct {
	Labels  []*profilev1.Label
	Samples []*profilev1.Sample
}

SampleGroup refers to a group of samples that share the same labels. Note that the Span ID label is handled in a special way and is not included in the Labels member but is kept as as a sample label.

func GroupSamplesByLabels

func GroupSamplesByLabels(p *profilev1.Profile) []SampleGroup

GroupSamplesByLabels splits samples into groups by labels. It's expected that sample labels are sorted.

func GroupSamplesWithoutLabels

func GroupSamplesWithoutLabels(p *profilev1.Profile, labels ...string) []SampleGroup

GroupSamplesWithoutLabels splits samples into groups by labels ignoring ones from the list: those are preserved as sample labels. It's expected that sample labels are sorted.

func GroupSamplesWithoutLabelsByKey

func GroupSamplesWithoutLabelsByKey(p *profilev1.Profile, keys []int64) []SampleGroup

type SampleHasher

type SampleHasher struct {
	// contains filtered or unexported fields
}

func (SampleHasher) Hashes

func (h SampleHasher) Hashes(samples []*profilev1.Sample) []uint64

type SampleKey

type SampleKey struct {
	// contains filtered or unexported fields
}

func GetSampleKey

func GetSampleKey(s *profilev1.Sample) SampleKey

type SamplesByLabels

type SamplesByLabels []*profilev1.Sample

func (SamplesByLabels) Len

func (s SamplesByLabels) Len() int

func (SamplesByLabels) Less

func (s SamplesByLabels) Less(i, j int) bool

func (SamplesByLabels) Swap

func (s SamplesByLabels) Swap(i, j int)

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL