diff --git a/LICENSE-3rdparty.csv b/LICENSE-3rdparty.csv index edbcd576..d8977849 100644 --- a/LICENSE-3rdparty.csv +++ b/LICENSE-3rdparty.csv @@ -63,12 +63,16 @@ import,github.com/google/uuid,BSD-3-Clause,"Copyright (c) 2009,2014 Google Inc. import,github.com/hashicorp/go-version,MPL-2.0,"Copyright (c) 2014 HashiCorp, Inc." import,github.com/jonboulle/clockwork,Apache-2.0,unknown import,github.com/josharian/intern,MIT,Copyright (c) 2019 Josh Bleecher Snyder +import,github.com/josharian/native,MIT,Copyright 2020 Josh Bleecher Snyder import,github.com/json-iterator/go,MIT,Copyright (c) 2016 json-iterator import,github.com/klauspost/compress,MIT,Copyright (c) 2012 The Go Authors. All rights reserved. | Copyright (c) 2019 Klaus Post. All rights reserved. | Copyright 2016-2017 The New York Times Company | Copyright (c) 2015 Klaus Post | Copyright (c) 2011 The Snappy-Go Authors. All rights reserved. | Copyright 2016 The filepathx Authors import,github.com/klauspost/compress/internal/snapref,BSD-3-Clause,Copyright (c) 2011 The Snappy-Go Authors. All rights reserved. import,github.com/klauspost/compress/zstd/internal/xxhash,MIT,Copyright (c) 2016 Caleb Spare import,github.com/klauspost/cpuid/v2,MIT,Copyright (c) 2015 Klaus Post import,github.com/mailru/easyjson,MIT,Copyright (c) 2016 Mail.Ru Group +import,github.com/mdlayher/kobject,MIT,Copyright (C) 2017 Matt Layher +import,github.com/mdlayher/netlink,MIT,Copyright (C) 2016-2022 Matt Layher +import,github.com/mdlayher/socket,MIT,Copyright (C) 2021 Matt Layher import,github.com/minio/sha256-simd,Apache-2.0,unknown import,github.com/moby/docker-image-spec/specs-go/v1,Apache-2.0,unknown import,github.com/moby/locker,Apache-2.0,"Copyright 2013-2018 Docker, Inc." @@ -122,7 +126,7 @@ import,go.opentelemetry.io/otel/trace,Apache-2.0,unknown import,go.uber.org/atomic,MIT,"Copyright (c) 2016 Uber Technologies, Inc." import,go.uber.org/multierr,MIT,"Copyright (c) 2017-2021 Uber Technologies, Inc." import,go.uber.org/zap,MIT,"Copyright (c) 2016-2017 Uber Technologies, Inc." -import,golang.org/x/arch/arm64/arm64asm,BSD-3-Clause,Copyright 2015 The Go Authors. +import,golang.org/x/arch,BSD-3-Clause,Copyright 2015 The Go Authors. import,golang.org/x/exp/constraints,BSD-3-Clause,Copyright 2009 The Go Authors. import,golang.org/x/mod/semver,BSD-3-Clause,Copyright 2009 The Go Authors. import,golang.org/x/net,BSD-3-Clause,Copyright 2009 The Go Authors. diff --git a/cli_flags.go b/cli_flags.go index b656ebfb..e000645a 100644 --- a/cli_flags.go +++ b/cli_flags.go @@ -121,6 +121,7 @@ type arguments struct { goRuntimeMetricsStatsdAddress string enableSplitByService bool splitServiceSuffix string + collectContext bool cmd *cli.Command } @@ -418,6 +419,14 @@ func parseArgs() (*arguments, error) { Destination: &args.uploadSymbolsHTTP2, Sources: cli.EnvVars("DD_HOST_PROFILING_UPLOAD_SYMBOLS_HTTP2"), }, + &cli.BoolFlag{ + Name: "collect-context", + Value: false, + Hidden: true, + Usage: "Enable context collection.", + Destination: &args.collectContext, + Sources: cli.EnvVars("DD_HOST_PROFILING_COLLECT_CONTEXT"), + }, }, Action: func(_ context.Context, cmd *cli.Command) error { args.cmd = cmd diff --git a/containermetadata/container.go b/containermetadata/container.go index 63b47ed9..0614ea67 100644 --- a/containermetadata/container.go +++ b/containermetadata/container.go @@ -72,7 +72,8 @@ func (p *containerIDProvider) GetContainerMetadata(pid libpf.PID) (ContainerMeta isHostCgroupNamespace(cgroupNsFilePath)) } - return ContainerMetadata{ContainerID: containerID, EntityID: entityID}, nil + // Only fill EntityID, but not ContainerID, ContainerID is only used by containerMetadataProvider. + return ContainerMetadata{EntityID: entityID}, nil } // parseContainerID finds the first container ID reading from r and returns it. diff --git a/go.mod b/go.mod index 9895bceb..a3941ff0 100644 --- a/go.mod +++ b/go.mod @@ -17,8 +17,8 @@ require ( github.com/urfave/cli/v3 v3.1.1 github.com/zeebo/xxh3 v1.0.2 go.opentelemetry.io/ebpf-profiler v0.0.0-20241114112653-6d846a2023a0 - golang.org/x/sync v0.13.0 - golang.org/x/sys v0.33.0 + golang.org/x/sync v0.16.0 + golang.org/x/sys v0.34.0 k8s.io/api v0.32.3 k8s.io/apimachinery v0.32.3 k8s.io/client-go v0.32.3 @@ -49,7 +49,7 @@ require ( github.com/Microsoft/hcsshim v0.11.7 // indirect github.com/cespare/xxhash/v2 v2.3.0 // indirect github.com/cihub/seelog v0.0.0-20170130134532-f561c5e57575 // indirect - github.com/cilium/ebpf v0.16.0 // indirect + github.com/cilium/ebpf v0.19.0 // indirect github.com/containerd/cgroups v1.1.0 // indirect github.com/containerd/containerd/api v1.8.0 // indirect github.com/containerd/continuity v0.4.4 // indirect @@ -67,11 +67,11 @@ require ( github.com/dustin/go-humanize v1.0.1 // indirect github.com/eapache/queue/v2 v2.0.0-20230407133247-75960ed334e4 // indirect github.com/ebitengine/purego v0.8.3 // indirect - github.com/elastic/go-perf v0.0.0-20241016160959-1342461adb4a // indirect + github.com/elastic/go-perf v0.0.0-20241029065020-30bec95324b8 // indirect github.com/emicklei/go-restful/v3 v3.11.0 // indirect github.com/felixge/httpsnoop v1.0.4 // indirect github.com/fxamacker/cbor/v2 v2.7.0 // indirect - github.com/go-logr/logr v1.4.2 // indirect + github.com/go-logr/logr v1.4.3 // indirect github.com/go-logr/stdr v1.2.2 // indirect github.com/go-ole/go-ole v1.3.0 // indirect github.com/go-openapi/jsonpointer v0.21.0 // indirect @@ -87,11 +87,15 @@ require ( github.com/google/uuid v1.6.0 // indirect github.com/hashicorp/go-version v1.7.0 // indirect github.com/josharian/intern v1.0.0 // indirect + github.com/josharian/native v1.1.0 // indirect github.com/json-iterator/go v1.1.12 // indirect github.com/klauspost/compress v1.18.0 // indirect github.com/klauspost/cpuid/v2 v2.2.8 // indirect github.com/lufia/plan9stats v0.0.0-20240909124753-873cd0166683 // indirect github.com/mailru/easyjson v0.7.7 // indirect + github.com/mdlayher/kobject v0.0.0-20200520190114-19ca17470d7d // indirect + github.com/mdlayher/netlink v1.7.2 // indirect + github.com/mdlayher/socket v0.4.1 // indirect github.com/minio/sha256-simd v1.0.1 // indirect github.com/moby/docker-image-spec v1.3.1 // indirect github.com/moby/locker v1.0.1 // indirect @@ -127,36 +131,36 @@ require ( github.com/yusufpapurcu/wmi v1.2.4 // indirect go.opencensus.io v0.24.0 // indirect go.opentelemetry.io/auto/sdk v1.1.0 // indirect - go.opentelemetry.io/collector/component v1.31.0 // indirect - go.opentelemetry.io/collector/consumer v1.31.0 // indirect - go.opentelemetry.io/collector/consumer/xconsumer v0.125.0 // indirect - go.opentelemetry.io/collector/featuregate v1.31.0 // indirect - go.opentelemetry.io/collector/internal/telemetry v0.125.0 // indirect - go.opentelemetry.io/collector/pdata v1.31.0 // indirect - go.opentelemetry.io/collector/pdata/pprofile v0.125.0 // indirect + go.opentelemetry.io/collector/component v1.37.0 // indirect + go.opentelemetry.io/collector/consumer v1.37.0 // indirect + go.opentelemetry.io/collector/consumer/xconsumer v0.131.0 // indirect + go.opentelemetry.io/collector/featuregate v1.37.0 // indirect + go.opentelemetry.io/collector/internal/telemetry v0.131.0 // indirect + go.opentelemetry.io/collector/pdata v1.37.0 // indirect + go.opentelemetry.io/collector/pdata/pprofile v0.131.0 // indirect go.opentelemetry.io/collector/semconv v0.125.0 // indirect - go.opentelemetry.io/contrib/bridges/otelzap v0.10.0 // indirect + go.opentelemetry.io/contrib/bridges/otelzap v0.12.0 // indirect go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.49.0 // indirect - go.opentelemetry.io/otel v1.35.0 // indirect - go.opentelemetry.io/otel/log v0.11.0 // indirect - go.opentelemetry.io/otel/metric v1.35.0 // indirect - go.opentelemetry.io/otel/sdk v1.35.0 // indirect - go.opentelemetry.io/otel/trace v1.35.0 // indirect + go.opentelemetry.io/otel v1.37.0 // indirect + go.opentelemetry.io/otel/log v0.13.0 // indirect + go.opentelemetry.io/otel/metric v1.37.0 // indirect + go.opentelemetry.io/otel/sdk v1.37.0 // indirect + go.opentelemetry.io/otel/trace v1.37.0 // indirect go.uber.org/atomic v1.11.0 // indirect go.uber.org/multierr v1.11.0 // indirect go.uber.org/zap v1.27.0 // indirect - golang.org/x/arch v0.10.0 // indirect - golang.org/x/exp v0.0.0-20250408133849-7e4ce0ab07d0 // indirect - golang.org/x/mod v0.24.0 // indirect - golang.org/x/net v0.39.0 // indirect - golang.org/x/oauth2 v0.27.0 // indirect - golang.org/x/term v0.31.0 // indirect - golang.org/x/text v0.24.0 // indirect + golang.org/x/arch v0.19.0 // indirect + golang.org/x/exp v0.0.0-20250718183923-645b1fa84792 // indirect + golang.org/x/mod v0.26.0 // indirect + golang.org/x/net v0.40.0 // indirect + golang.org/x/oauth2 v0.30.0 // indirect + golang.org/x/term v0.32.0 // indirect + golang.org/x/text v0.25.0 // indirect golang.org/x/time v0.11.0 // indirect golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 // indirect google.golang.org/genproto v0.0.0-20240325203815-454cdb8f5daa // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20250425173222-7b384671a197 // indirect - google.golang.org/grpc v1.72.0 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20250528174236-200df99c418a // indirect + google.golang.org/grpc v1.74.2 // indirect google.golang.org/protobuf v1.36.6 // indirect gopkg.in/evanphx/json-patch.v4 v4.12.0 // indirect gopkg.in/inf.v0 v0.9.1 // indirect @@ -174,4 +178,4 @@ require ( // To update the Datadog/opentelemetry-ebpf-profiler dependency on latest commit on datadog branch, change the following line to: // replace go.opentelemetry.io/ebpf-profiler => github.com/DataDog/opentelemetry-ebpf-profiler datadog // and run `go mod tidy` -replace go.opentelemetry.io/ebpf-profiler => github.com/DataDog/opentelemetry-ebpf-profiler v0.0.0-20250728155009-e8783b5032af +replace go.opentelemetry.io/ebpf-profiler => github.com/DataDog/opentelemetry-ebpf-profiler v0.0.0-20250808130051-25ec00d52d7a diff --git a/go.sum b/go.sum index 80d544c5..b6de0b3a 100644 --- a/go.sum +++ b/go.sum @@ -40,8 +40,8 @@ github.com/DataDog/gostackparse v0.7.0 h1:i7dLkXHvYzHV308hnkvVGDL3BR4FWl7IsXNPz/ github.com/DataDog/gostackparse v0.7.0/go.mod h1:lTfqcJKqS9KnXQGnyQMCugq3u1FP6UZMfWR0aitKFMM= github.com/DataDog/jsonapi v0.12.0 h1:N4e9RpmUflcV5hzceltSz8XUpM3PMtQr5C9Bhv0g87s= github.com/DataDog/jsonapi v0.12.0/go.mod h1:FUSGF3bwMARlVfXEoFo9R/CVlYYy9BGL4C/Prf6Ke3M= -github.com/DataDog/opentelemetry-ebpf-profiler v0.0.0-20250728155009-e8783b5032af h1:BqRbIR0zfwMovN6pFVsHlh9nHnbCkA8qJVWf5rdiVhE= -github.com/DataDog/opentelemetry-ebpf-profiler v0.0.0-20250728155009-e8783b5032af/go.mod h1:zYNmE98qCkBe1U3RT8RakZE9zODxCDj6fc/rCaaCqK4= +github.com/DataDog/opentelemetry-ebpf-profiler v0.0.0-20250808130051-25ec00d52d7a h1:n6Fl2RHo1cNOxck7PMcJYMMmd+tdYBgEowydxGY0aro= +github.com/DataDog/opentelemetry-ebpf-profiler v0.0.0-20250808130051-25ec00d52d7a/go.mod h1:G0s9A43HDgTO5XuELD0pbSzuX5jPUcJ6nH2UBwVTdQI= github.com/DataDog/opentelemetry-mapping-go/pkg/otlp/attributes v0.27.0 h1:5US5SqqhfkZkg/E64uvn7YmeTwnudJHtlPEH/LOT99w= github.com/DataDog/opentelemetry-mapping-go/pkg/otlp/attributes v0.27.0/go.mod h1:VRo4D6rj92AExpVBlq3Gcuol9Nm1bber12KyxRjKGWw= github.com/DataDog/sketches-go v1.4.7 h1:eHs5/0i2Sdf20Zkj0udVFWuCrXGRFig2Dcfm5rtcTxc= @@ -63,8 +63,8 @@ github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UF github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/cihub/seelog v0.0.0-20170130134532-f561c5e57575 h1:kHaBemcxl8o/pQ5VM1c8PVE1PubbNx3mjUr09OqWGCs= github.com/cihub/seelog v0.0.0-20170130134532-f561c5e57575/go.mod h1:9d6lWj8KzO/fd/NrVaLscBKmPigpZpn5YawRPw+e3Yo= -github.com/cilium/ebpf v0.16.0 h1:+BiEnHL6Z7lXnlGUsXQPPAE7+kenAd4ES8MQ5min0Ok= -github.com/cilium/ebpf v0.16.0/go.mod h1:L7u2Blt2jMM/vLAVgjxluxtBKlz3/GWjB0dMOEngfwE= +github.com/cilium/ebpf v0.19.0 h1:Ro/rE64RmFBeA9FGjcTc+KmCeY6jXmryu6FfnzPRIao= +github.com/cilium/ebpf v0.19.0/go.mod h1:fLCgMo3l8tZmAdM3B2XqdFzXBpwkcSTroaVqN08OWVY= github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= github.com/containerd/cgroups v1.1.0 h1:v8rEWFl6EoqHB+swVNjVoCJE8o3jX7e8nqBGPLaDFBM= @@ -114,8 +114,8 @@ github.com/ebitengine/purego v0.8.3 h1:K+0AjQp63JEZTEMZiwsI9g0+hAMNohwUOtY0RPGex github.com/ebitengine/purego v0.8.3/go.mod h1:iIjxzd6CiRiOG0UyXP+V1+jWqUXVjPKLAI0mRfJZTmQ= github.com/elastic/go-freelru v0.16.0 h1:gG2HJ1WXN2tNl5/p40JS/l59HjvjRhjyAa+oFTRArYs= github.com/elastic/go-freelru v0.16.0/go.mod h1:bSdWT4M0lW79K8QbX6XY2heQYSCqD7THoYf82pT/H3I= -github.com/elastic/go-perf v0.0.0-20241016160959-1342461adb4a h1:ymmtaN4bVCmKKeu4XEf6JEWNZKRXPMng1zjpKd+8rCU= -github.com/elastic/go-perf v0.0.0-20241016160959-1342461adb4a/go.mod h1:Nt+pnRYvf0POC+7pXsrv8ubsEOSsaipJP0zlz1Ms1RM= +github.com/elastic/go-perf v0.0.0-20241029065020-30bec95324b8 h1:FD01NjsTes0RxZVQ22ebNYJA4KDdInVnR9cn1hmaMwA= +github.com/elastic/go-perf v0.0.0-20241029065020-30bec95324b8/go.mod h1:Nt+pnRYvf0POC+7pXsrv8ubsEOSsaipJP0zlz1Ms1RM= github.com/emicklei/go-restful/v3 v3.11.0 h1:rAQeMHw1c7zTmncogyy8VvRZwtkmkZ4FxERmMY4rD+g= github.com/emicklei/go-restful/v3 v3.11.0/go.mod h1:6n3XBCmQQb25CM2LCACGz8ukIrRry+4bhvbpWn3mrbc= github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= @@ -127,8 +127,8 @@ github.com/felixge/httpsnoop v1.0.4/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSw github.com/fxamacker/cbor/v2 v2.7.0 h1:iM5WgngdRBanHcxugY4JySA0nk1wZorNOpTgCMedv5E= github.com/fxamacker/cbor/v2 v2.7.0/go.mod h1:pxXPTn3joSm21Gbwsv0w9OSA2y1HFR9qXEeXQVeNoDQ= github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= -github.com/go-logr/logr v1.4.2 h1:6pFjapn8bFcIbiKo3XT4j/BhANplGihG6tvd+8rYgrY= -github.com/go-logr/logr v1.4.2/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= +github.com/go-logr/logr v1.4.3 h1:CjnDlHq8ikf6E492q6eKboGOC0T8CDaOvkHCIg8idEI= +github.com/go-logr/logr v1.4.3/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= github.com/go-ole/go-ole v1.2.6/go.mod h1:pprOEPIfldk/42T2oK7lQ4v4JSDwmV0As9GaiUsvbm0= @@ -142,8 +142,8 @@ github.com/go-openapi/jsonreference v0.20.2/go.mod h1:Bl1zwGIM8/wsvqjsOQLJ/SH+En github.com/go-openapi/swag v0.22.3/go.mod h1:UzaqsxGiab7freDnrUUra0MwWfN/q7tE4j+VcZ0yl14= github.com/go-openapi/swag v0.23.0 h1:vsEVJDUo2hPJ2tu0/Xc+4noaxyEffXNIs3cOULZ+GrE= github.com/go-openapi/swag v0.23.0/go.mod h1:esZ8ITTYEsH1V2trKHjAN8Ai7xHb8RV+YSZ577vPjgQ= -github.com/go-quicktest/qt v1.101.0 h1:O1K29Txy5P2OK0dGo59b7b0LR6wKfIhttaAhHUyn7eI= -github.com/go-quicktest/qt v1.101.0/go.mod h1:14Bz/f7NwaXPtdYEgzsx46kqSxVwTbzVZsDC26tQJow= +github.com/go-quicktest/qt v1.101.1-0.20240301121107-c6c8733fa1e6 h1:teYtXy9B7y5lHTp8V9KPxpYRAVA7dozigQcMiBust1s= +github.com/go-quicktest/qt v1.101.1-0.20240301121107-c6c8733fa1e6/go.mod h1:p4lGIVX+8Wa6ZPNDvqcxq36XpUDLh42FLetFU7odllI= github.com/go-task/slim-sprig/v3 v3.0.0 h1:sUs3vkvUymDpBKi3qH1YSqBQk9+9D/8M2mN1vB6EwHI= github.com/go-task/slim-sprig/v3 v3.0.0/go.mod h1:W848ghGpv3Qj3dhTPRyJypKRiqCdHZiAzKg9hl15HA8= github.com/go-viper/mapstructure/v2 v2.3.0 h1:27XbWsHIqhbdR5TIC911OfYvgSaW93HM+dX7970Q7jk= @@ -176,6 +176,7 @@ github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5a github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.4.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.3/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= @@ -204,9 +205,11 @@ github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8Hm github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y= github.com/josharian/native v1.1.0 h1:uuaP0hAbW7Y4l0ZRQ6C9zfb7Mg1mbFKry/xzDAfmtLA= github.com/josharian/native v1.1.0/go.mod h1:7X/raswPFr05uY3HiLlYeyQntB6OO7E/d2Cu7qoaN2w= -github.com/jsimonetti/rtnetlink v1.4.2 h1:Df9w9TZ3npHTyDn0Ev9e1uzmN2odmXd0QX+J5GTEn90= -github.com/jsimonetti/rtnetlink/v2 v2.0.1 h1:xda7qaHDSVOsADNouv7ukSuicKZO7GgVUCXxpaIEIlM= -github.com/jsimonetti/rtnetlink/v2 v2.0.1/go.mod h1:7MoNYNbb3UaDHtF8udiJo/RH6VsTKP1pqKLUTVCvToE= +github.com/jsimonetti/rtnetlink v0.0.0-20190606172950-9527aa82566a/go.mod h1:Oz+70psSo5OFh8DBl0Zv2ACw7Esh6pPUphlvZG9x7uw= +github.com/jsimonetti/rtnetlink v0.0.0-20200117123717-f846d4f6c1f4 h1:nwOc1YaOrYJ37sEBrtWZrdqzK22hiJs3GpDmP3sR2Yw= +github.com/jsimonetti/rtnetlink v0.0.0-20200117123717-f846d4f6c1f4/go.mod h1:WGuG/smIU4J/54PblvSbh+xvCZmpJnFgr3ds6Z55XMQ= +github.com/jsimonetti/rtnetlink/v2 v2.0.3 h1:Jcp7GTnTPepoUAJ9+LhTa7ZiebvNS56T1GtlEUaPNFE= +github.com/jsimonetti/rtnetlink/v2 v2.0.3/go.mod h1:atIkksp/9fqtf6rpAw45JnttnP2gtuH9X88WPfWfS9A= github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= @@ -228,6 +231,11 @@ github.com/mailru/easyjson v0.7.7 h1:UGYAvKxe3sBsEDzO8ZeWOSlIQfWFlxbzLZe7hwFURr0 github.com/mailru/easyjson v0.7.7/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= github.com/maxatome/go-testdeep v1.12.0 h1:Ql7Go8Tg0C1D/uMMX59LAoYK7LffeJQ6X2T04nTH68g= github.com/maxatome/go-testdeep v1.12.0/go.mod h1:lPZc/HAcJMP92l7yI6TRz1aZN5URwUBUAfUNvrclaNM= +github.com/mdlayher/kobject v0.0.0-20200520190114-19ca17470d7d h1:JmrZTpS0GAyMV4ZQVVH/AS0Y6r2PbnYNSRUuRX+HOLA= +github.com/mdlayher/kobject v0.0.0-20200520190114-19ca17470d7d/go.mod h1:+SexPO1ZvdbbWUdUnyXEWv3+4NwHZjKhxOmQqHY4Pqc= +github.com/mdlayher/netlink v0.0.0-20190409211403-11939a169225/go.mod h1:eQB3mZE4aiYnlUsyGGCOpPETfdQq4Jhsgf1fk3cwQaA= +github.com/mdlayher/netlink v1.0.0/go.mod h1:KxeJAFOFLG6AjpyDkQ/iIhxygIUKD+vcwqcnu43w/+M= +github.com/mdlayher/netlink v1.1.0/go.mod h1:H4WCitaheIsdF9yOYu8CFmCgQthAPIWZmcKp9uZHgmY= github.com/mdlayher/netlink v1.7.2 h1:/UtM3ofJap7Vl4QWCPDGXY8d3GIY2UGSDbK+QWmY8/g= github.com/mdlayher/netlink v1.7.2/go.mod h1:xraEF7uJbxLhc5fpHL4cPe221LI2bdttWlU+ZGLfQSw= github.com/mdlayher/socket v0.4.1 h1:eM9y2/jlbs1M615oshPQOHZzj6R6wMT7bX5NPiQvn2U= @@ -350,30 +358,30 @@ go.opencensus.io v0.24.0 h1:y73uSU6J157QMP2kn2r30vwW1A2W2WFwSCGnAVxeaD0= go.opencensus.io v0.24.0/go.mod h1:vNK8G9p7aAivkbmorf4v+7Hgx+Zs0yY+0fOtgBfjQKo= go.opentelemetry.io/auto/sdk v1.1.0 h1:cH53jehLUN6UFLY71z+NDOiNJqDdPRaXzTel0sJySYA= go.opentelemetry.io/auto/sdk v1.1.0/go.mod h1:3wSPjt5PWp2RhlCcmmOial7AvC4DQqZb7a7wCow3W8A= -go.opentelemetry.io/collector/component v1.31.0 h1:9LzU8X1RhV3h8/QsAoTX23aFUfoJ3EUc9O/vK+hFpSI= -go.opentelemetry.io/collector/component v1.31.0/go.mod h1:JbZl/KywXJxpUXPbt96qlEXJSym1zQ2hauMxYMuvlxM= +go.opentelemetry.io/collector/component v1.37.0 h1:yc5X0WhZwlpJ+W8Sg1fpRRjiUu3nByLe1wVOKWWRWRQ= +go.opentelemetry.io/collector/component v1.37.0/go.mod h1:SYHTXOzZLFwX075LEU6FMVBT15reVrwKHNB2En2URro= go.opentelemetry.io/collector/component/componentstatus v0.125.0 h1:zlxGQZYd9kknRZSjRpOYW5SBjl0a5zYFYRPbreobXoU= go.opentelemetry.io/collector/component/componentstatus v0.125.0/go.mod h1:bHXc2W8bqqo9adOvCgvhcO7pYzJOSpyV4cuQ1wiIl04= -go.opentelemetry.io/collector/component/componenttest v0.125.0 h1:E2mpnMQbkMpYoZ3Q8pHx4kod7kedjwRs1xqDpzCe/84= -go.opentelemetry.io/collector/component/componenttest v0.125.0/go.mod h1:pQtsE1u/SPZdTphP5BZP64XbjXSq6wc+mDut5Ws/JDI= -go.opentelemetry.io/collector/consumer v1.31.0 h1:L+y66ywxLHnAxnUxv0JDwUf5bFj53kMxCCyEfRKlM7s= -go.opentelemetry.io/collector/consumer v1.31.0/go.mod h1:rPsqy5ni+c6xNMUkOChleZYO/nInVY6eaBNZ1FmWJVk= -go.opentelemetry.io/collector/consumer/consumertest v0.125.0 h1:TUkxomGS4DAtjBvcWQd2UY4FDLLEKMQD6iOIDUr/5dM= -go.opentelemetry.io/collector/consumer/consumertest v0.125.0/go.mod h1:vkHf3y85cFLDHARO/cTREVjLjOPAV+cQg7lkC44DWOY= -go.opentelemetry.io/collector/consumer/xconsumer v0.125.0 h1:oTreUlk1KpMSWwuHFnstW+orrjGTyvs2xd3o/Dpy+hI= -go.opentelemetry.io/collector/consumer/xconsumer v0.125.0/go.mod h1:FX0G37r0W+wXRgxxFtwEJ4rlsCB+p0cIaxtU3C4hskw= -go.opentelemetry.io/collector/featuregate v1.31.0 h1:20q7plPQZwmAiaYAa6l1m/i2qDITZuWlhjr4EkmeQls= -go.opentelemetry.io/collector/featuregate v1.31.0/go.mod h1:Y/KsHbvREENKvvN9RlpiWk/IGBK+CATBYzIIpU7nccc= -go.opentelemetry.io/collector/internal/telemetry v0.125.0 h1:6lcGOxw3dAg7LfXTKdN8ZjR+l7KvzLdEiPMhhLwG4r4= -go.opentelemetry.io/collector/internal/telemetry v0.125.0/go.mod h1:5GyFslLqjZgq1DZTtFiluxYhhXrCofHgOOOybodDPGE= -go.opentelemetry.io/collector/pdata v1.31.0 h1:P5WuLr1l2JcIvr6Dw2hl01ltp2ZafPnC4Isv+BLTBqU= -go.opentelemetry.io/collector/pdata v1.31.0/go.mod h1:m41io9nWpy7aCm/uD1L9QcKiZwOP0ldj83JEA34dmlk= -go.opentelemetry.io/collector/pdata/pprofile v0.125.0 h1:Qqlx8w1HpiYZ9RQqjmMQIysI0cHNO1nh3E/fCTeFysA= -go.opentelemetry.io/collector/pdata/pprofile v0.125.0/go.mod h1:p/yK023VxAp8hm27/1G5DPTcMIpnJy3cHGAFUQZGyaQ= +go.opentelemetry.io/collector/component/componenttest v0.131.0 h1:pvBENFUdOSIikdIExUP2+2B4K3LbZIqdUI7Kh7jNGxI= +go.opentelemetry.io/collector/component/componenttest v0.131.0/go.mod h1:5RdiTb/UaiCp1RvKH2+B6SyggGNvcY8Yd5799lJcEe4= +go.opentelemetry.io/collector/consumer v1.37.0 h1:RqTqEcc95Fg7T3MRPPjUX2nxzn1X88yfFUQV+AjdMK0= +go.opentelemetry.io/collector/consumer v1.37.0/go.mod h1:vDA1JDXeb7vnQ02PXIjjR6dI9LTaya+Qr89Nyt2Gl7Y= +go.opentelemetry.io/collector/consumer/consumertest v0.131.0 h1:+lgAblWlItsaWhUW10mKCmt3vTrmwvAWRSTrvrPgN/Q= +go.opentelemetry.io/collector/consumer/consumertest v0.131.0/go.mod h1:t7eH0dWqxAeIPtyvzT7mOJTKM9km2YEMjFCtaIeIl/w= +go.opentelemetry.io/collector/consumer/xconsumer v0.131.0 h1:PgCoBVF5FN87Ef2wDqLpRU7QxxIDs8dNiy9jKNdpWzk= +go.opentelemetry.io/collector/consumer/xconsumer v0.131.0/go.mod h1:xh1XRXcwk4Hxm3KSUCw/IOA0dyEoZr7Q/h0gzLnYaQo= +go.opentelemetry.io/collector/featuregate v1.37.0 h1:CjsHzjktiqq/dxid4Xkhuf3yD6oB/c7yRBWhokBJqpE= +go.opentelemetry.io/collector/featuregate v1.37.0/go.mod h1:Y/KsHbvREENKvvN9RlpiWk/IGBK+CATBYzIIpU7nccc= +go.opentelemetry.io/collector/internal/telemetry v0.131.0 h1:dqKbiGpcO8V31aWq2GRQLO/eNCs2B1IGS+qbkPFkmyc= +go.opentelemetry.io/collector/internal/telemetry v0.131.0/go.mod h1:TzNVIkIolnk/Jq/3qc4uWhL0bOeaP56jpyrMlUOeA/Y= +go.opentelemetry.io/collector/pdata v1.37.0 h1:aEEpd03GgAS352xntcYMsaxYvRXvzqEWqdrSro+TSh4= +go.opentelemetry.io/collector/pdata v1.37.0/go.mod h1:aE9l1Lcdsg7nmSoiucnWHuPYIk6T0RKzOjPepNJC5AQ= +go.opentelemetry.io/collector/pdata/pprofile v0.131.0 h1:eQ2Yq1g6wOWHjRXum9Fm0dZax/klNmjtpL7UPsEXrPo= +go.opentelemetry.io/collector/pdata/pprofile v0.131.0/go.mod h1:g4IuRFVGC89n/2bTdw0CuMJkkCY4zDb0Hu37wCKlx0c= go.opentelemetry.io/collector/pdata/testdata v0.125.0 h1:due1Hl0EEVRVwfCkiamRy5E8lS6yalv0lo8Zl/SJtGw= go.opentelemetry.io/collector/pdata/testdata v0.125.0/go.mod h1:1GpEWlgdMrd+fWsBk37ZC2YmOP5YU3gFQ4rWuCu9g24= -go.opentelemetry.io/collector/pipeline v0.125.0 h1:oitBgcAFqntDB4ihQJUHJSQ8IHqKFpPkaTVbTYdIUzM= -go.opentelemetry.io/collector/pipeline v0.125.0/go.mod h1:TO02zju/K6E+oFIOdi372Wk0MXd+Szy72zcTsFQwXl4= +go.opentelemetry.io/collector/pipeline v0.131.0 h1:D2PhrZdXxYTVm3fOL6hZMKOhne8wI+2MsgyJNp7TTlk= +go.opentelemetry.io/collector/pipeline v0.131.0/go.mod h1:TO02zju/K6E+oFIOdi372Wk0MXd+Szy72zcTsFQwXl4= go.opentelemetry.io/collector/processor v1.31.0 h1:+u7sBUpnCBsHYoALp4hfr9VEjLHHYa4uKENGITe0K9Q= go.opentelemetry.io/collector/processor v1.31.0/go.mod h1:5hDYJ7/hTdfd2tF2Rj5Hs6+mfyFz2O7CaPzVvW1qHQc= go.opentelemetry.io/collector/processor/processorhelper v0.125.0 h1:QRpX7oFW88DAZhy+Q93npklRoaQr8ue0GKpeup7C/Fk= @@ -384,26 +392,28 @@ go.opentelemetry.io/collector/processor/xprocessor v0.125.0 h1:VWYPMW1VmDq6xB7M5 go.opentelemetry.io/collector/processor/xprocessor v0.125.0/go.mod h1:bCxUyFVlksANg8wjYZqWVsRB33lkLQ294rTrju/IZiM= go.opentelemetry.io/collector/semconv v0.125.0 h1:SyRP617YGvNSWRSKMy7Lbk9RaJSR+qFAAfyxJOeZe4s= go.opentelemetry.io/collector/semconv v0.125.0/go.mod h1:te6VQ4zZJO5Lp8dM2XIhDxDiL45mwX0YAQQWRQ0Qr9U= -go.opentelemetry.io/contrib/bridges/otelzap v0.10.0 h1:ojdSRDvjrnm30beHOmwsSvLpoRF40MlwNCA+Oo93kXU= -go.opentelemetry.io/contrib/bridges/otelzap v0.10.0/go.mod h1:oTTm4g7NEtHSV2i/0FeVdPaPgUIZPfQkFbq0vbzqnv0= +go.opentelemetry.io/contrib/bridges/otelzap v0.12.0 h1:FGre0nZh5BSw7G73VpT3xs38HchsfPsa2aZtMp0NPOs= +go.opentelemetry.io/contrib/bridges/otelzap v0.12.0/go.mod h1:X2PYPViI2wTPIMIOBjG17KNybTzsrATnvPJ02kkz7LM= go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.49.0 h1:jq9TW8u3so/bN+JPT166wjOI6/vQPF6Xe7nMNIltagk= go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.49.0/go.mod h1:p8pYQP+m5XfbZm9fxtSKAbM6oIllS7s2AfxrChvc7iw= -go.opentelemetry.io/otel v1.35.0 h1:xKWKPxrxB6OtMCbmMY021CqC45J+3Onta9MqjhnusiQ= -go.opentelemetry.io/otel v1.35.0/go.mod h1:UEqy8Zp11hpkUrL73gSlELM0DupHoiq72dR+Zqel/+Y= +go.opentelemetry.io/otel v1.37.0 h1:9zhNfelUvx0KBfu/gb+ZgeAfAgtWrfHJZcAqFC228wQ= +go.opentelemetry.io/otel v1.37.0/go.mod h1:ehE/umFRLnuLa/vSccNq9oS1ErUlkkK71gMcN34UG8I= go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.19.0 h1:Mne5On7VWdx7omSrSSZvM4Kw7cS7NQkOOmLcgscI51U= go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.19.0/go.mod h1:IPtUMKL4O3tH5y+iXVyAXqpAwMuzC1IrxVS81rummfE= go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp v1.19.0 h1:IeMeyr1aBvBiPVYihXIaeIZba6b8E1bYp7lbdxK8CQg= go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp v1.19.0/go.mod h1:oVdCUtjq9MK9BlS7TtucsQwUcXcymNiEDjgDD2jMtZU= -go.opentelemetry.io/otel/log v0.11.0 h1:c24Hrlk5WJ8JWcwbQxdBqxZdOK7PcP/LFtOtwpDTe3Y= -go.opentelemetry.io/otel/log v0.11.0/go.mod h1:U/sxQ83FPmT29trrifhQg+Zj2lo1/IPN1PF6RTFqdwc= -go.opentelemetry.io/otel/metric v1.35.0 h1:0znxYu2SNyuMSQT4Y9WDWej0VpcsxkuklLa4/siN90M= -go.opentelemetry.io/otel/metric v1.35.0/go.mod h1:nKVFgxBZ2fReX6IlyW28MgZojkoAkJGaE8CpgeAU3oE= -go.opentelemetry.io/otel/sdk v1.35.0 h1:iPctf8iprVySXSKJffSS79eOjl9pvxV9ZqOWT0QejKY= -go.opentelemetry.io/otel/sdk v1.35.0/go.mod h1:+ga1bZliga3DxJ3CQGg3updiaAJoNECOgJREo9KHGQg= -go.opentelemetry.io/otel/sdk/metric v1.35.0 h1:1RriWBmCKgkeHEhM7a2uMjMUfP7MsOF5JpUCaEqEI9o= -go.opentelemetry.io/otel/sdk/metric v1.35.0/go.mod h1:is6XYCUMpcKi+ZsOvfluY5YstFnhW0BidkR+gL+qN+w= -go.opentelemetry.io/otel/trace v1.35.0 h1:dPpEfJu1sDIqruz7BHFG3c7528f6ddfSWfFDVt/xgMs= -go.opentelemetry.io/otel/trace v1.35.0/go.mod h1:WUk7DtFp1Aw2MkvqGdwiXYDZZNvA/1J8o6xRXLrIkyc= +go.opentelemetry.io/otel/log v0.13.0 h1:yoxRoIZcohB6Xf0lNv9QIyCzQvrtGZklVbdCoyb7dls= +go.opentelemetry.io/otel/log v0.13.0/go.mod h1:INKfG4k1O9CL25BaM1qLe0zIedOpvlS5Z7XgSbmN83E= +go.opentelemetry.io/otel/log/logtest v0.13.0 h1:xxaIcgoEEtnwdgj6D6Uo9K/Dynz9jqIxSDu2YObJ69Q= +go.opentelemetry.io/otel/log/logtest v0.13.0/go.mod h1:+OrkmsAH38b+ygyag1tLjSFMYiES5UHggzrtY1IIEA8= +go.opentelemetry.io/otel/metric v1.37.0 h1:mvwbQS5m0tbmqML4NqK+e3aDiO02vsf/WgbsdpcPoZE= +go.opentelemetry.io/otel/metric v1.37.0/go.mod h1:04wGrZurHYKOc+RKeye86GwKiTb9FKm1WHtO+4EVr2E= +go.opentelemetry.io/otel/sdk v1.37.0 h1:ItB0QUqnjesGRvNcmAcU0LyvkVyGJ2xftD29bWdDvKI= +go.opentelemetry.io/otel/sdk v1.37.0/go.mod h1:VredYzxUvuo2q3WRcDnKDjbdvmO0sCzOvVAiY+yUkAg= +go.opentelemetry.io/otel/sdk/metric v1.37.0 h1:90lI228XrB9jCMuSdA0673aubgRobVZFhbjxHHspCPc= +go.opentelemetry.io/otel/sdk/metric v1.37.0/go.mod h1:cNen4ZWfiD37l5NhS+Keb5RXVWZWpRE+9WyVCpbo5ps= +go.opentelemetry.io/otel/trace v1.37.0 h1:HLdcFNbRQBE2imdSEgm/kwqmQj1Or1l/7bW6mxVK7z4= +go.opentelemetry.io/otel/trace v1.37.0/go.mod h1:TlgrlQ+PtQO5XFerSPUYG0JSgGyryXewPGyayAWSBS0= go.opentelemetry.io/proto/otlp v1.0.0 h1:T0TX0tmXU8a3CbNXzEKGeU5mIVOdf0oykP+u2lIVU/I= go.opentelemetry.io/proto/otlp v1.0.0/go.mod h1:Sy6pihPLfYHkr3NkUbEhGHFhINUSI/v80hjKIs5JXpM= go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= @@ -415,52 +425,60 @@ go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0= go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y= go.uber.org/zap v1.27.0 h1:aJMhYGrd5QSmlpLMr2MftRKl7t8J8PTZPA732ud/XR8= go.uber.org/zap v1.27.0/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E= -golang.org/x/arch v0.10.0 h1:S3huipmSclq3PJMNe76NGwkBR504WFkQ5dhzWzP8ZW8= -golang.org/x/arch v0.10.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= +golang.org/x/arch v0.19.0 h1:LmbDQUodHThXE+htjrnmVD73M//D9GTH6wFZjyDkjyU= +golang.org/x/arch v0.19.0/go.mod h1:bdwinDaKcfZUGpH09BB7ZmOfhalA8lQdzl62l8gGWsk= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.37.0 h1:kJNSjF/Xp7kU0iB2Z+9viTPMW4EqqsrywMXLJOOsXSE= -golang.org/x/crypto v0.37.0/go.mod h1:vg+k43peMZ0pUMhYmVAWysMK35e6ioLh3wB8ZCAfbVc= +golang.org/x/crypto v0.38.0 h1:jt+WWG8IZlBnVbomuhg2Mdq0+BBQaHbtqHEFEigjUV8= +golang.org/x/crypto v0.38.0/go.mod h1:MvrbAqul58NNYPKnOra203SB9vpuZW0e+RRZV+Ggqjw= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= -golang.org/x/exp v0.0.0-20250408133849-7e4ce0ab07d0 h1:R84qjqJb5nVJMxqWYb3np9L5ZsaDtB+a39EqjV0JSUM= -golang.org/x/exp v0.0.0-20250408133849-7e4ce0ab07d0/go.mod h1:S9Xr4PYopiDyqSyp5NjCrhFrqg6A5zA2E/iPHPhqnS8= +golang.org/x/exp v0.0.0-20250718183923-645b1fa84792 h1:R9PFI6EUdfVKgwKjZef7QIwGcBKu86OEFpJ9nUEP2l4= +golang.org/x/exp v0.0.0-20250718183923-645b1fa84792/go.mod h1:A+z0yzpGtvnG90cToK5n2tu8UJVP2XUATh+r+sfOOOc= golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= -golang.org/x/mod v0.24.0 h1:ZfthKaKaT4NrhGVZHO1/WDTwGES4De8KtWO0SIbNJMU= -golang.org/x/mod v0.24.0/go.mod h1:IXM97Txy2VM4PJ3gI61r1YEk/gAj6zAHN3AdZt6S9Ww= +golang.org/x/mod v0.26.0 h1:EGMPT//Ezu+ylkCijjPc+f4Aih7sZvaAr+O3EHBxvZg= +golang.org/x/mod v0.26.0/go.mod h1:/j6NAhSk8iQ723BGAUyoAcn7SlD7s15Dp9Nd/SfeaFQ= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20191007182048-72f939374954/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= -golang.org/x/net v0.39.0 h1:ZCu7HMWDxpXpaiKdhzIfaltL9Lp31x/3fCP11bc6/fY= -golang.org/x/net v0.39.0/go.mod h1:X7NRbYVEA+ewNkCNyJ513WmMdQ3BineSwVtN2zD/d+E= +golang.org/x/net v0.40.0 h1:79Xs7wF06Gbdcg4kdCCIQArK11Z1hr5POQ6+fIYHNuY= +golang.org/x/net v0.40.0/go.mod h1:y0hY0exeL2Pku80/zKK7tpntoX23cqL3Oa6njdgRtds= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= -golang.org/x/oauth2 v0.27.0 h1:da9Vo7/tDv5RH/7nZDz1eMGS/q1Vv1N/7FCrBhI9I3M= -golang.org/x/oauth2 v0.27.0/go.mod h1:onh5ek6nERTohokkhCD/y2cV4Do3fxFHFuAejCkRWT8= +golang.org/x/oauth2 v0.30.0 h1:dnDm7JmhM45NNpd8FDDeLhK6FwqbOf4MLCM9zb1BOHI= +golang.org/x/oauth2 v0.30.0/go.mod h1:B++QgG3ZKulg6sRPGD/mqlHQs5rB3Ml9erfeDY7xKlU= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.13.0 h1:AauUjRAJ9OSnvULf/ARrrVywoJDy0YS2AwQ98I37610= -golang.org/x/sync v0.13.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA= +golang.org/x/sync v0.16.0 h1:ycBJEhp9p4vXvUZNszeOq0kGTPghopOL8q0fq3vstxw= +golang.org/x/sync v0.16.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190411185658-b44545bcd369/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190826190057-c7b8b68b1456/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190916202348-b4ddaad3f8a3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191008105621-543471e840be/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200202164722-d101bd2416d5/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201204225414-ed752295db88/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -473,15 +491,15 @@ golang.org/x/sys v0.0.0-20220627191245-f75cf1eec38b/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.33.0 h1:q3i8TbbEz+JRD9ywIRlyRAQbM0qF7hu24q3teo2hbuw= -golang.org/x/sys v0.33.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= +golang.org/x/sys v0.34.0 h1:H5Y5sJ2L2JRdyv7ROF1he/lPdvFsd0mJHFw2ThKHxLA= +golang.org/x/sys v0.34.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/term v0.31.0 h1:erwDkOK1Msy6offm1mOgvspSkslFnIGsFnxOKoufg3o= -golang.org/x/term v0.31.0/go.mod h1:R4BeIy7D95HzImkxGkTW1UQTtP54tio2RyHz7PwK0aw= +golang.org/x/term v0.32.0 h1:DR4lr0TjUs3epypdhTOkMmuF5CDFJ/8pOnbzMZPQ7bg= +golang.org/x/term v0.32.0/go.mod h1:uZG1FhGx848Sqfsq4/DlJr3xGGsYMu/L5GW4abiaEPQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.24.0 h1:dd5Bzh4yt5KYA8f9CJHCP4FB4D51c2c6JvN37xJJkJ0= -golang.org/x/text v0.24.0/go.mod h1:L8rBsPeo2pSS+xqN0d5u2ikmjtmoJbDBT1b7nHvFCdU= +golang.org/x/text v0.25.0 h1:qVyWApTSYLk/drJRO5mDlNYskwQznZmkpV2c8q9zls4= +golang.org/x/text v0.25.0/go.mod h1:WEdwpYrmk1qmdHvhkSTNPm3app7v4rsT8F2UD6+VHIA= golang.org/x/time v0.11.0 h1:/bpjEDfN9tkoN/ryeYHnv5hcMlc8ncjMcM4XBk5NWV0= golang.org/x/time v0.11.0/go.mod h1:CDIdPxbZBQxdj6cxyCIdrNogrJKMJ7pr37NYpMcMDSg= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= @@ -493,8 +511,8 @@ golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtn golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= golang.org/x/tools v0.1.1/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= -golang.org/x/tools v0.32.0 h1:Q7N1vhpkQv7ybVzLFtTjvQya2ewbwNDZzUgfXGqtMWU= -golang.org/x/tools v0.32.0/go.mod h1:ZxrU41P/wAbZD8EDa6dDCa6XfpkhJ7HFMjHJXfBDu8s= +golang.org/x/tools v0.35.0 h1:mBffYraMEf7aa0sB+NuKnuCy8qI/9Bughn8dC2Gu5r0= +golang.org/x/tools v0.35.0/go.mod h1:NKdj5HkL/73byiZSJjqJgKn3ep7KjFkBOkR/Hps3VPw= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= @@ -510,17 +528,17 @@ google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98 google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo= google.golang.org/genproto v0.0.0-20240325203815-454cdb8f5daa h1:ePqxpG3LVx+feAUOx8YmR5T7rc0rdzK8DyxM8cQ9zq0= google.golang.org/genproto v0.0.0-20240325203815-454cdb8f5daa/go.mod h1:CnZenrTdRJb7jc+jOm0Rkywq+9wh0QC4U8tyiRbEPPM= -google.golang.org/genproto/googleapis/api v0.0.0-20250414145226-207652e42e2e h1:UdXH7Kzbj+Vzastr5nVfccbmFsmYNygVLSPk1pEfDoY= -google.golang.org/genproto/googleapis/api v0.0.0-20250414145226-207652e42e2e/go.mod h1:085qFyf2+XaZlRdCgKNCIZ3afY2p4HHZdoIRpId8F4A= -google.golang.org/genproto/googleapis/rpc v0.0.0-20250425173222-7b384671a197 h1:29cjnHVylHwTzH66WfFZqgSQgnxzvWE+jvBwpZCLRxY= -google.golang.org/genproto/googleapis/rpc v0.0.0-20250425173222-7b384671a197/go.mod h1:qQ0YXyHHx3XkvlzUtpXDkS29lDSafHMZBAZDc03LQ3A= +google.golang.org/genproto/googleapis/api v0.0.0-20250528174236-200df99c418a h1:SGktgSolFCo75dnHJF2yMvnns6jCmHFJ0vE4Vn2JKvQ= +google.golang.org/genproto/googleapis/api v0.0.0-20250528174236-200df99c418a/go.mod h1:a77HrdMjoeKbnd2jmgcWdaS++ZLZAEq3orIOAEIKiVw= +google.golang.org/genproto/googleapis/rpc v0.0.0-20250528174236-200df99c418a h1:v2PbRU4K3llS09c7zodFpNePeamkAwG3mPrAery9VeE= +google.golang.org/genproto/googleapis/rpc v0.0.0-20250528174236-200df99c418a/go.mod h1:qQ0YXyHHx3XkvlzUtpXDkS29lDSafHMZBAZDc03LQ3A= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQciAY= google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= google.golang.org/grpc v1.33.2/go.mod h1:JMHMWHQWaTccqQQlmk3MJZS+GWXOdAesneDmEnv2fbc= -google.golang.org/grpc v1.72.0 h1:S7UkcVa60b5AAQTaO6ZKamFp1zMZSU0fGDK2WZLbBnM= -google.golang.org/grpc v1.72.0/go.mod h1:wH5Aktxcg25y1I3w7H69nHfXdOG3UiadoBtjh3izSDM= +google.golang.org/grpc v1.74.2 h1:WoosgB65DlWVC9FqI82dGsZhWFNBSLjQ84bjROOpMu4= +google.golang.org/grpc v1.74.2/go.mod h1:CtQ+BGjaAIXHs/5YS3i473GqwBBa1zGQNevxdeBEXrM= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM= diff --git a/main.go b/main.go index f6fa4c20..bbcc27b3 100644 --- a/main.go +++ b/main.go @@ -67,7 +67,6 @@ const ( // Go 'flag' package calls os.Exit(2) on flag parse errors, if ExitOnError is set exitParseError exitCode = 2 - defaultFramesCacheSize = 65536 defaultExecutablesCacheSize = 65536 defaultProcessesCacheSize = 16384 ) @@ -196,6 +195,15 @@ func mainWithExitCode() exitCode { return failure("Failed to parse the included tracers: %v", err) } + // Disable Go interpreter because we are doing Go symbolization remotely. + includeTracers.Disable(tracertypes.GoTracer) + if args.collectContext { + includeTracers.Enable(tracertypes.Labels) + } else { + includeTracers.Disable(tracertypes.Labels) + } + log.Infof("Enabled tracers: %s", includeTracers.String()) + validatedTags := ValidateTags(args.tags) log.Debugf("Validated tags: %s", validatedTags) @@ -251,17 +259,15 @@ func mainWithExitCode() exitCode { Version: versionInfo.Version, ReportInterval: intervals.ReportInterval(), ExecutablesCacheElements: defaultExecutablesCacheSize, - // Next step: Calculate FramesCacheElements from numCores and samplingRate. - FramesCacheElements: defaultFramesCacheSize, - ProcessesCacheElements: defaultProcessesCacheSize, - SamplesPerSecond: int(args.samplesPerSecond), - PprofPrefix: args.pprofPrefix, - Tags: validatedTags, - Timeline: args.timeline, - APIKey: apiKey, - EnableSplitByService: args.enableSplitByService, - SplitServiceSuffix: args.splitServiceSuffix, - HostServiceName: args.hostServiceName, + ProcessesCacheElements: defaultProcessesCacheSize, + SamplesPerSecond: int(args.samplesPerSecond), + PprofPrefix: args.pprofPrefix, + Tags: validatedTags, + Timeline: args.timeline, + APIKey: apiKey, + EnableSplitByService: args.enableSplitByService, + SplitServiceSuffix: args.splitServiceSuffix, + HostServiceName: args.hostServiceName, SymbolUploaderConfig: reporter.SymbolUploaderConfig{ Enabled: args.uploadSymbols, UploadDynamicSymbols: args.uploadDynamicSymbols, @@ -298,7 +304,7 @@ func mainWithExitCode() exitCode { SamplesPerSecond: int(args.samplesPerSecond), MapScaleFactor: int(args.mapScaleFactor), KernelVersionCheck: !args.noKernelVersionCheck, - DebugTracer: args.verboseeBPF, + VerboseMode: args.verboseeBPF, BPFVerifierLogLevel: uint32(args.bpfVerifierLogLevel), ProbabilisticInterval: args.probabilisticInterval, ProbabilisticThreshold: uint(args.probabilisticThreshold), diff --git a/reporter/config.go b/reporter/config.go index 016a900a..43c2ca5c 100644 --- a/reporter/config.go +++ b/reporter/config.go @@ -30,8 +30,6 @@ type Config struct { IntakeURL string // ExecutablesCacheElements defines item capacity of the executables cache. ExecutablesCacheElements uint32 - // FramesCacheElements defines the item capacity of the frames cache. - FramesCacheElements uint32 // ProcessesCacheElements defines the item capacity of the processes cache. ProcessesCacheElements uint32 // samplesPerSecond defines the number of samples per second. diff --git a/reporter/datadog_reporter.go b/reporter/datadog_reporter.go index cf72a70d..a85acfd6 100644 --- a/reporter/datadog_reporter.go +++ b/reporter/datadog_reporter.go @@ -53,14 +53,6 @@ type execInfo struct { goBuildID string } -// sourceInfo allows mapping a frame to its source origin. -type sourceInfo struct { - lineNumber libpf.SourceLineno - functionOffset uint32 - functionName string - filePath string -} - // funcInfo is a helper to construct profile.Function messages. type funcInfo struct { name string @@ -80,17 +72,6 @@ type traceAndMetaKey struct { tid libpf.PID } -// traceEvents holds known information about a trace. -type traceEvents struct { - files []libpf.FileID - linenos []libpf.AddressOrLineno - frameTypes []libpf.FrameType - mappingStarts []libpf.Address - mappingEnds []libpf.Address - mappingFileOffsets []uint64 - timestamps []uint64 // in nanoseconds -} - type processMetadata struct { updatedAt time.Time executablePath string @@ -99,17 +80,15 @@ type processMetadata struct { } type uploadProfileData struct { - start time.Time - end time.Time - profile *pprofile.Profile - containerID string - entityID string - tags Tags + start time.Time + end time.Time + profile *pprofile.Profile + entityID string + tags Tags } type serviceEntity struct { service string - containerID string entityID string inferredService bool } @@ -133,11 +112,8 @@ type DatadogReporter struct { // executables stores metadata for executables. executables *lru.SyncedLRU[libpf.FileID, execInfo] - // frames maps frame information to its source location. - frames *lru.SyncedLRU[libpf.FileID, *xsync.RWMutex[map[libpf.AddressOrLineno]sourceInfo]] - // traceEvents stores reported trace events (trace metadata with frames and counts) - traceEvents xsync.RWMutex[map[traceAndMetaKey]*traceEvents] + traceEvents xsync.RWMutex[map[traceAndMetaKey]*samples.TraceEvents] // processes stores the metadata associated to a PID. processes *lru.SyncedLRU[libpf.PID, processMetadata] @@ -168,17 +144,6 @@ func NewDatadog(cfg *Config, p containermetadata.Provider) (*DatadogReporter, er } executables.SetLifetime(executableCacheLifetime) - frames, err := lru.NewSynced[libpf.FileID, - *xsync.RWMutex[map[libpf.AddressOrLineno]sourceInfo]](cfg.FramesCacheElements, libpf.FileID.Hash32) - if err != nil { - return nil, err - } - frames.SetLifetime(framesCacheLifetime) - // Using SetLifetime / GetAndRefresh on frames prevents useful information from being - // evicted from the cache. - // But it also means that active frames will never be evicted, and thus that their corresponding values - // (which are maps) may grow indefinitely (cf. https://github.com/open-telemetry/opentelemetry-ebpf-profiler/pull/260). - processes, err := lru.NewSynced[libpf.PID, processMetadata](cfg.ProcessesCacheElements, libpf.PID.Hash32) if err != nil { return nil, err @@ -204,9 +169,8 @@ func NewDatadog(cfg *Config, p containermetadata.Provider) (*DatadogReporter, er stopSignal: make(chan libpf.Void), }, executables: executables, - frames: frames, containerMetadataProvider: p, - traceEvents: xsync.NewRWMutex(map[traceAndMetaKey]*traceEvents{}), + traceEvents: xsync.NewRWMutex(map[traceAndMetaKey]*samples.TraceEvents{}), processes: processes, symbolUploader: symbolUploader, tags: createTags(cfg.Tags, runtimeTag, cfg.Version, cfg.EnableSplitByService), @@ -235,19 +199,14 @@ func (r *DatadogReporter) ReportTraceEvent(trace *libpf.Trace, meta *samples.Tra } if tr, exists := (*traceEventsMap)[key]; exists { - tr.timestamps = append(tr.timestamps, uint64(meta.Timestamp)) + tr.Timestamps = append(tr.Timestamps, uint64(meta.Timestamp)) (*traceEventsMap)[key] = tr return nil } - (*traceEventsMap)[key] = &traceEvents{ - files: trace.Files, - linenos: trace.Linenos, - frameTypes: trace.FrameTypes, - mappingStarts: trace.MappingStart, - mappingEnds: trace.MappingEnd, - mappingFileOffsets: trace.MappingFileOffsets, - timestamps: []uint64{uint64(meta.Timestamp)}, + (*traceEventsMap)[key] = &samples.TraceEvents{ + Frames: trace.Frames, + Timestamps: []uint64{uint64(meta.Timestamp)}, } return nil @@ -274,62 +233,6 @@ func (r *DatadogReporter) ExecutableMetadata(args *reporter.ExecutableMetadataAr } } -// FrameKnown returns true if the metadata of the Frame specified by frameID is -// cached in the reporter. -func (r *DatadogReporter) FrameKnown(frameID libpf.FrameID) bool { - known := false - if frameMapLock, exists := r.frames.GetAndRefresh(frameID.FileID(), framesCacheLifetime); exists { - frameMap := frameMapLock.RLock() - defer frameMapLock.RUnlock(&frameMap) - _, known = (*frameMap)[frameID.AddressOrLine()] - } - return known -} - -// FrameMetadata accepts metadata associated with a frame and caches this information. -func (r *DatadogReporter) FrameMetadata(args *reporter.FrameMetadataArgs) { - fileID := args.FrameID.FileID() - addressOrLine := args.FrameID.AddressOrLine() - - log.Debugf("FrameMetadata [%x] %v+%v at %v:%v", - fileID, args.FunctionName, args.FunctionOffset, - args.SourceFile, args.SourceLine) - - if frameMapLock, exists := r.frames.GetAndRefresh(fileID, framesCacheLifetime); exists { - frameMap := frameMapLock.WLock() - defer frameMapLock.WUnlock(&frameMap) - - sourceFile := args.SourceFile - - if sourceFile == "" { - // The new sourceFile may be empty, and we don't want to overwrite - // an existing filePath with it. - if s, exists := (*frameMap)[addressOrLine]; exists { - sourceFile = s.filePath - } - } - - (*frameMap)[addressOrLine] = sourceInfo{ - lineNumber: args.SourceLine, - filePath: sourceFile, - functionOffset: args.FunctionOffset, - functionName: args.FunctionName, - } - - return - } - - v := make(map[libpf.AddressOrLineno]sourceInfo) - v[addressOrLine] = sourceInfo{ - lineNumber: args.SourceLine, - filePath: args.SourceFile, - functionOffset: args.FunctionOffset, - functionName: args.FunctionName, - } - mu := xsync.NewRWMutex(v) - r.frames.Add(fileID, &mu) -} - // ReportHostMetadata is a NOP for DatadogReporter. func (r *DatadogReporter) ReportHostMetadata(_ map[string]string) {} @@ -360,7 +263,6 @@ func (r *DatadogReporter) Start(mainCtx context.Context) error { }, func() { // Allow the GC to purge expired entries to avoid memory leaks. r.executables.PurgeExpired() - r.frames.PurgeExpired() r.processes.PurgeExpired() }) @@ -426,10 +328,10 @@ func (r *DatadogReporter) reportProfile(ctx context.Context, data *uploadProfile return uploadProfiles(ctx, []profileData{{name: "cpu.pprof", data: b.Bytes()}}, data.start, data.end, r.config.IntakeURL, data.tags, r.config.Version, r.config.APIKey, - data.containerID, data.entityID, r.family) + data.entityID, r.family) } -func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*traceEvents, start, end time.Time) (*pprofile.Profile, profileStats) { +func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*samples.TraceEvents, start, end time.Time) (*pprofile.Profile, profileStats) { numSamples := len(hostSamples) const unknownStr = "UNKNOWN" @@ -455,31 +357,32 @@ func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*traceEv sample := &pprofile.Sample{} // Walk every frame of the trace. - for i := range traceInfo.frameTypes { - loc := createPProfLocation(profile, uint64(traceInfo.linenos[i])) + for _, uniqueFrame := range traceInfo.Frames { + frame := uniqueFrame.Value() + loc := createPProfLocation(profile, uint64(frame.AddressOrLineno)) - switch frameKind := traceInfo.frameTypes[i]; frameKind { + switch frameKind := frame.Type; frameKind { case libpf.NativeFrame: // As native frames are resolved in the backend, we use Mapping to // report these frames. - if tmpMapping, exists := fileIDtoMapping[traceInfo.files[i]]; exists { + if tmpMapping, exists := fileIDtoMapping[frame.FileID]; exists { loc.Mapping = tmpMapping } else { - executionInfo, exists := r.executables.GetAndRefresh(traceInfo.files[i], executableCacheLifetime) + executionInfo, exists := r.executables.GetAndRefresh(frame.FileID, executableCacheLifetime) // Next step: Select a proper default value, // if the name of the executable is not known yet. var fileName = unknownStr - var buildID = traceInfo.files[i].StringNoQuotes() + var buildID = frame.FileID.StringNoQuotes() if exists { fileName = executionInfo.fileName buildID = getBuildID(executionInfo.gnuBuildID, executionInfo.goBuildID, buildID) } - tmpMapping := createPprofMapping(profile, uint64(traceInfo.linenos[i]), + tmpMapping := createPprofMapping(profile, uint64(frame.AddressOrLineno), fileName, buildID) - fileIDtoMapping[traceInfo.files[i]] = tmpMapping + fileIDtoMapping[frame.FileID] = tmpMapping loc.Mapping = tmpMapping } line := pprofile.Line{Function: createPprofFunctionEntry(funcMap, profile, "", @@ -492,32 +395,15 @@ func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*traceEv // program. default: // Store interpreted frame information as Line message: - line := pprofile.Line{} - - fileIDInfoLock, exists := r.frames.GetAndRefresh(traceInfo.files[i], framesCacheLifetime) - if !exists { - // At this point, we do not have enough information for the frame. - // Therefore, we report a dummy entry and use the interpreter as filename. - line.Function = createPprofFunctionEntry(funcMap, profile, - "UNREPORTED", frameKind.String()) - } else { - fileIDInfo := fileIDInfoLock.RLock() - if si, exists := (*fileIDInfo)[traceInfo.linenos[i]]; exists { - line.Line = int64(si.lineNumber) - line.Function = createPprofFunctionEntry(funcMap, profile, - si.functionName, si.filePath) - } else { - // At this point, we do not have enough information for the frame. - // Therefore, we report a dummy entry and use the interpreter as filename. - line.Function = createPprofFunctionEntry(funcMap, profile, - "UNRESOLVED", frameKind.String()) - } - fileIDInfoLock.RUnlock(&fileIDInfo) + line := pprofile.Line{ + Line: int64(frame.SourceLine), + Function: createPprofFunctionEntry(funcMap, profile, + frame.FunctionName.String(), frame.SourceFile.String()), } - loc.Line = append(loc.Line, line) + loc.Line = append(loc.Line, line) // To be compliant with the protocol generate a dummy mapping entry. - loc.Mapping = getDummyMapping(fileIDtoMapping, profile, traceInfo.files[i]) + loc.Mapping = getDummyMapping(fileIDtoMapping, profile, frame.FileID) } sample.Location = append(sample.Location, loc) } @@ -529,8 +415,7 @@ func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*traceEv execPath := getExecutablePath(&processMeta, &traceKey) // Check if the last frame is a kernel frame. - if len(traceInfo.frameTypes) > 0 && - traceInfo.frameTypes[len(traceInfo.frameTypes)-1] == libpf.KernelFrame { + if isKernel(traceInfo) { // If the last frame is a kernel frame, we need to add a dummy // location with the kernel as the function name. execPath = "kernel" @@ -544,20 +429,16 @@ func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*traceEv sample.Location = append(sample.Location, loc) } - containerMetadata := containermetadata.ContainerMetadata{} - if !r.config.EnableSplitByService { - containerMetadata = processMeta.containerMetadata - } if !r.config.Timeline { - count := int64(len(traceInfo.timestamps)) + count := int64(len(traceInfo.Timestamps)) labels := make(map[string][]string) - addTraceLabels(labels, traceKey, containerMetadata, baseExec, 0) + addTraceLabels(labels, traceKey, processMeta.containerMetadata, baseExec, 0) sample.Value = append(sample.Value, count, count*samplingPeriod) sample.Label = labels profile.Sample = append(profile.Sample, sample) } else { sample.Value = append(sample.Value, 1, samplingPeriod) - for _, ts := range traceInfo.timestamps { + for _, ts := range traceInfo.Timestamps { sampleWithTimestamp := &pprofile.Sample{} *sampleWithTimestamp = *sample labels := make(map[string][]string) @@ -566,7 +447,7 @@ func (r *DatadogReporter) createProfile(hostSamples map[traceAndMetaKey]*traceEv profile.Sample = append(profile.Sample, sampleWithTimestamp) } } - totalSampleCount += len(traceInfo.timestamps) + totalSampleCount += len(traceInfo.Timestamps) } profile.DurationNanos = end.Sub(start).Nanoseconds() @@ -595,7 +476,7 @@ func (r *DatadogReporter) getPprofProfile() { } r.traceEvents.WUnlock(&events) - entityToSample := make(map[serviceEntity]map[traceAndMetaKey]*traceEvents) + entityToSample := make(map[serviceEntity]map[traceAndMetaKey]*samples.TraceEvents) if !r.config.EnableSplitByService { profile, stats := r.createProfile(hostSamples, intervalStart, intervalEnd) @@ -625,8 +506,7 @@ func (r *DatadogReporter) getPprofProfile() { inferredService = true } - if service == "" && len(traceInfo.frameTypes) > 0 && - traceInfo.frameTypes[len(traceInfo.frameTypes)-1] == libpf.KernelFrame { + if service == "" && isKernel(traceInfo) { service = "system" } @@ -637,13 +517,12 @@ func (r *DatadogReporter) getPprofProfile() { entity := serviceEntity{ service: service + r.config.SplitServiceSuffix, - containerID: processMeta.containerMetadata.ContainerID, entityID: processMeta.containerMetadata.EntityID, inferredService: inferredService, } serviceSamples, exists := entityToSample[entity] if !exists { - serviceSamples = make(map[traceAndMetaKey]*traceEvents) + serviceSamples = make(map[traceAndMetaKey]*samples.TraceEvents) entityToSample[entity] = serviceSamples } @@ -658,12 +537,11 @@ func (r *DatadogReporter) getPprofProfile() { totalPIDsWithNoProcessMetadata += stats.pidWithNoMetadata tags := createTagsForProfile(r.tags, profileSeq, e.service, e.inferredService) r.profiles <- &uploadProfileData{ - profile: profile, - start: intervalStart, - end: intervalEnd, - containerID: e.containerID, - entityID: e.entityID, - tags: tags, + profile: profile, + start: intervalStart, + end: intervalEnd, + entityID: e.entityID, + tags: tags, } log.Debugf("Reporting profile for service %s: %d samples, %d PIDs with no process metadata, tags: %v", e.service, stats.totalSampleCount, stats.pidWithNoMetadata, tags) } @@ -751,6 +629,7 @@ func addTraceLabels(labels map[string][]string, i traceAndMetaKey, containerMeta labels["pod_name"] = append(labels["pod_name"], containerMetadata.PodName) } + // In split by service, ContainerID always empty. if containerMetadata.ContainerID != "" { labels["container_id"] = append(labels["container_id"], containerMetadata.ContainerID) } @@ -852,10 +731,21 @@ func (r *DatadogReporter) addProcessMetadata(meta *samples.TraceEventMeta) { ddService = getServiceName(pid) } - containerMetadata, err := r.containerMetadataProvider.GetContainerMetadata(pid) - if err != nil { - log.Debugf("Failed to get container metadata for PID %d: %v", pid, err) - // Even upon failure, we might still have managed to get the containerID + var containerMetadata containermetadata.ContainerMetadata + if meta.ContainerID != "" && r.config.EnableSplitByService { + // Use containerID when found by the eBPF profiler and not other container metadata is needed + // (ie. split by service is enabled). + // eBPF profiler only supports cgroup v2 and even with cgroup v2, depending on Kubernetes settings, + // containerID might not be available in /proc//cgroup. + containerMetadata = containermetadata.ContainerMetadata{ + EntityID: "ci-" + meta.ContainerID, + } + } else { + containerMetadata, err = r.containerMetadataProvider.GetContainerMetadata(pid) + if err != nil { + log.Debugf("Failed to get container metadata for PID %d: %v", pid, err) + // Even upon failure, we might still have managed to get the containerID + } } r.processes.Add(pid, processMetadata{ @@ -916,3 +806,11 @@ func parseServiceNameFromEnvironData(envData []byte) string { func getServiceName(pid libpf.PID) string { return getServiceNameFromProcPath(pid, "") } + +func isKernel(traceInfo *samples.TraceEvents) bool { + if len(traceInfo.Frames) == 0 { + return false + } + + return traceInfo.Frames[len(traceInfo.Frames)-1].Value().Type == libpf.KernelFrame +} diff --git a/reporter/datadog_upload.go b/reporter/datadog_upload.go index a347855e..5d93fc51 100644 --- a/reporter/datadog_upload.go +++ b/reporter/datadog_upload.go @@ -14,6 +14,7 @@ import ( "mime/multipart" "net/http" "net/textproto" + "strings" "time" ) @@ -23,8 +24,7 @@ type profileData struct { } func uploadProfiles(ctx context.Context, profiles []profileData, startTime, endTime time.Time, - url string, tags Tags, profilerVersion string, apiKey string, containerID string, entityID string, - family string) error { + url string, tags Tags, profilerVersion string, apiKey string, entityID string, family string) error { contentType, body, err := buildMultipartForm(profiles, startTime, endTime, tags, family) if err != nil { return err @@ -41,11 +41,11 @@ func uploadProfiles(ctx context.Context, profiles []profileData, startTime, endT if apiKey != "" { req.Header.Set("Dd-Api-Key", apiKey) } - if containerID != "" { - req.Header.Set("Datadog-Container-Id", containerID) - } if entityID != "" { req.Header.Set("Datadog-Entity-Id", entityID) + if strings.HasPrefix(entityID, "ci-") { + req.Header.Set("Datadog-Container-Id", entityID[3:]) + } } resp, err := http.DefaultClient.Do(req) if err != nil {