// Copyright 2016 The Go Authors. All rights reserved.// Use of this source code is governed by a BSD-style// license that can be found in the LICENSE file.package pprofimport ()type label struct { key string value string}// LabelSet is a set of labels.typeLabelSetstruct { list []label}// labelContextKey is the type of contextKeys used for profiler labels.type labelContextKey struct{}func labelValue( context.Context) labelMap { , := .Value(labelContextKey{}).(*labelMap)if == nil {returnlabelMap{} }return *}// labelMap is the representation of the label set held in the context type.// This is an initial implementation, but it will be replaced with something// that admits incremental immutable modification more efficiently.type labelMap struct {LabelSet}// String satisfies Stringer and returns key, value pairs in a consistent// order.func ( *labelMap) () string {if == nil {return"" } := make([]string, 0, len(.list))for , := range .list { = append(, fmt.Sprintf("%q:%q", .key, .value)) }slices.Sort()return"{" + strings.Join(, ", ") + "}"}// WithLabels returns a new [context.Context] with the given labels added.// A label overwrites a prior label with the same key.func ( context.Context, LabelSet) context.Context { := labelValue()returncontext.WithValue(, labelContextKey{}, &labelMap{mergeLabelSets(.LabelSet, )})}func mergeLabelSets(, LabelSet) LabelSet {iflen(.list) == 0 {return } elseiflen(.list) == 0 {return } , := 0, 0 := make([]label, 0, len(.list))for < len(.list) && < len(.list) {switchstrings.Compare(.list[].key, .list[].key) {case -1: // left key < right key = append(, .list[]) ++case1: // right key < left key = append(, .list[]) ++case0: // keys are equal, right value overwrites left value = append(, .list[]) ++ ++ } }// Append the remaining elements = append(, .list[:]...) = append(, .list[:]...)returnLabelSet{list: }}// Labels takes an even number of strings representing key-value pairs// and makes a [LabelSet] containing them.// A label overwrites a prior label with the same key.// Currently only the CPU and goroutine profiles utilize any labels// information.// See https://golang.org/issue/23458 for details.func ( ...string) LabelSet {iflen()%2 != 0 {panic("uneven number of arguments to pprof.Labels") } := make([]label, 0, len()/2) := truefor := 0; +1 < len(); += 2 { = append(, label{key: [], value: [+1]}) = && ( < 2 || [] > [-2]) }if ! {// slow path: keys are unsorted, contain duplicates, or bothslices.SortStableFunc(, func(, label) int {returnstrings.Compare(.key, .key) }) := make([]label, 0, len())for , := range {if == 0 || .key != [-1].key { = append(, ) } else { [len()-1] = } } = }returnLabelSet{list: }}// Label returns the value of the label with the given key on ctx, and a boolean indicating// whether that label exists.func ( context.Context, string) (string, bool) { := labelValue()for , := range .list {if .key == {return .value, true } }return"", false}// ForLabels invokes f with each label set on the context.// The function f should return true to continue iteration or false to stop iteration early.func ( context.Context, func(, string) bool) { := labelValue()for , := range .list {if !(.key, .value) {break } }}
The pages are generated with Goldsv0.7.3. (GOOS=linux GOARCH=amd64)
Golds is a Go 101 project developed by Tapir Liu.
PR and bug reports are welcome and can be submitted to the issue list.
Please follow @zigo_101 (reachable from the left QR code) to get the latest news of Golds.