@@ -47,7 +47,7 @@ const (
47
47
// Manager handles the management of [probe.Probe] instances.
48
48
type Manager struct {
49
49
logger * slog.Logger
50
- probes map [probe.ID ]probe. Probe
50
+ probes map [probe.ID ]ProbeReference
51
51
otelController * opentelemetry.Controller
52
52
cp ConfigProvider
53
53
exe * link.Executable
@@ -61,6 +61,14 @@ type Manager struct {
61
61
collectionOpts * ebpf.CollectionOptions
62
62
}
63
63
64
+ // ProbeReference is used by the Manager to track an initialized reference
65
+ // to a Probe and its related resources such as its ebpf.Collection and io.Closers.
66
+ type ProbeReference struct {
67
+ probe probe.Probe
68
+ collection * ebpf.Collection
69
+ closers []io.Closer
70
+ }
71
+
64
72
// NewManager returns a new [Manager].
65
73
func NewManager (
66
74
logger * slog.Logger ,
@@ -71,7 +79,7 @@ func NewManager(
71
79
) (* Manager , error ) {
72
80
m := & Manager {
73
81
logger : logger ,
74
- probes : make (map [probe.ID ]probe. Probe ),
82
+ probes : make (map [probe.ID ]ProbeReference ),
75
83
otelController : otelController ,
76
84
cp : cp ,
77
85
}
@@ -99,12 +107,6 @@ func NewManager(
99
107
},
100
108
}
101
109
102
- alloc , err := process .Allocate (logger , pid )
103
- if err != nil {
104
- return nil , err
105
- }
106
- m .proc .Allocation = alloc
107
-
108
110
m .logger .Info ("loaded process info" , "process" , m .proc )
109
111
110
112
m .filterUnusedProbes ()
@@ -145,7 +147,10 @@ func (m *Manager) registerProbe(p probe.Probe) error {
145
147
return err
146
148
}
147
149
148
- m .probes [id ] = p
150
+ m .probes [id ] = ProbeReference {
151
+ probe : p ,
152
+ closers : make ([]io.Closer , 0 ),
153
+ }
149
154
return nil
150
155
}
151
156
@@ -159,7 +164,7 @@ func (m *Manager) filterUnusedProbes() {
159
164
160
165
for name , inst := range m .probes {
161
166
funcsFound := false
162
- for _ , s := range inst .Manifest ().Symbols {
167
+ for _ , s := range inst .probe . Manifest ().Symbols {
163
168
if len (s .DependsOn ) == 0 {
164
169
if _ , exists := existingFuncMap [s .Symbol ]; exists {
165
170
funcsFound = true
@@ -226,15 +231,15 @@ func (m *Manager) applyConfig(c Config) error {
226
231
227
232
if currentlyEnabled && ! newEnabled {
228
233
m .logger .Info ("Disabling probe" , "id" , id )
229
- err = errors .Join (err , p . Close ( ))
234
+ err = errors .Join (err , m . CloseProbe ( p ))
230
235
continue
231
236
}
232
237
233
238
if ! currentlyEnabled && newEnabled {
234
239
m .logger .Info ("Enabling probe" , "id" , id )
235
240
err = errors .Join (err , m .LoadProbe (p , id , c ))
236
241
if err == nil {
237
- m .runProbe (p )
242
+ m .runProbe (p . probe )
238
243
}
239
244
continue
240
245
}
@@ -313,7 +318,7 @@ func (m *Manager) runProbes(ctx context.Context) (context.Context, error) {
313
318
314
319
for id , p := range m .probes {
315
320
if isProbeEnabled (id , m .currentConfig ) {
316
- m .runProbe (p )
321
+ m .runProbe (p . probe )
317
322
}
318
323
}
319
324
@@ -414,29 +419,31 @@ func (m *Manager) loadProbes() error {
414
419
return nil
415
420
}
416
421
417
- func (m * Manager ) LoadProbe (i probe. Probe , name probe.ID , cfg Config ) error {
422
+ func (m * Manager ) LoadProbe (i ProbeReference , name probe.ID , cfg Config ) error {
418
423
m .logger .Info ("loading probe" , "name" , name )
419
424
420
- err := i .Init ( cfg . SamplingConfig )
425
+ spec , err := i .probe . Spec ( )
421
426
if err != nil {
422
427
return errors .Join (err , m .cleanup ())
423
428
}
424
429
425
- spec , err := i . Spec ( )
430
+ err = m . InjectProbeConsts ( i . probe , spec )
426
431
if err != nil {
427
432
return errors .Join (err , m .cleanup ())
428
433
}
429
434
430
- err = m . InjectProbeConsts ( i , spec )
435
+ c , err := utils . InitializeEBPFCollection ( spec , m . collectionOpts )
431
436
if err != nil {
432
- return err
437
+ return errors . Join ( err , m . cleanup ())
433
438
}
439
+ i .collection = c
434
440
435
- c , err := utils . InitializeEBPFCollection ( spec , m . collectionOpts )
441
+ reader , err := i . probe . InitStartupConfig ( c , cfg . SamplingConfig )
436
442
if err != nil {
437
- return err
443
+ return errors . Join ( err , m . cleanup ())
438
444
}
439
- i .SetCollection (c )
445
+ i .closers = append (i .closers , reader )
446
+
440
447
return nil
441
448
}
442
449
@@ -461,8 +468,8 @@ func (m *Manager) InjectProbeConsts(i probe.Probe, spec *ebpf.CollectionSpec) er
461
468
return inject .Constants (spec , opts ... )
462
469
}
463
470
464
- func (m * Manager ) loadUprobesFromProbe (i probe. Probe ) error {
465
- for _ , up := range i .GetUprobes () {
471
+ func (m * Manager ) loadUprobesFromProbe (i ProbeReference ) error {
472
+ for _ , up := range i .probe . GetUprobes () {
466
473
var skip bool
467
474
for _ , pc := range up .PackageConstraints {
468
475
if pc .Constraints .Check (m .proc .Modules [pc .Package ]) {
@@ -472,9 +479,9 @@ func (m *Manager) loadUprobesFromProbe(i probe.Probe) error {
472
479
var logFn func (string , ... any )
473
480
switch pc .FailureMode {
474
481
case probe .FailureModeIgnore :
475
- logFn = i .GetLogger ().Debug
482
+ logFn = i .probe . GetLogger ().Debug
476
483
case probe .FailureModeWarn :
477
- logFn = i .GetLogger ().Warn
484
+ logFn = i .probe . GetLogger ().Warn
478
485
default :
479
486
// Unknown and FailureModeError.
480
487
return fmt .Errorf (
@@ -486,7 +493,7 @@ func (m *Manager) loadUprobesFromProbe(i probe.Probe) error {
486
493
487
494
logFn (
488
495
"package constraint not meet, skipping uprobe" ,
489
- "probe" , i .Manifest ().ID ,
496
+ "probe" , i .probe . Manifest ().ID ,
490
497
"symbol" , up .Sym ,
491
498
"package" , pc .Package ,
492
499
"constraint" , pc .Constraints .String (),
@@ -500,22 +507,23 @@ func (m *Manager) loadUprobesFromProbe(i probe.Probe) error {
500
507
continue
501
508
}
502
509
503
- err := m .loadUprobe (up , i .GetCollection () )
510
+ err := m .loadUprobe (up , i .collection )
504
511
if err != nil {
505
512
var logFn func (string , ... any )
506
513
switch up .FailureMode {
507
514
case probe .FailureModeIgnore :
508
- logFn = i .GetLogger ().Debug
515
+ logFn = i .probe . GetLogger ().Debug
509
516
case probe .FailureModeWarn :
510
- logFn = i .GetLogger ().Warn
517
+ logFn = i .probe . GetLogger ().Warn
511
518
default :
512
519
// Unknown and FailureModeError.
513
520
return err
514
521
}
515
- logFn ("failed to load uprobe" , "probe" , i .Manifest ().ID , "symbol" , up .Sym , "error" , err )
522
+ logFn ("failed to load uprobe" , "probe" , i .probe . Manifest ().ID , "symbol" , up .Sym , "error" , err )
516
523
continue
517
524
}
518
- _ = i .UpdateClosers (up )
525
+
526
+ i .closers = append (i .closers , up )
519
527
}
520
528
return nil
521
529
}
@@ -574,20 +582,26 @@ func (m *Manager) loadUprobe(u *probe.Uprobe, c *ebpf.Collection) error {
574
582
return nil
575
583
}
576
584
577
- func (m * Manager ) mount () error {
578
- if m .proc .Allocation != nil {
579
- m .logger .Debug ("Mounting bpffs" , "allocation" , m .proc .Allocation )
580
- } else {
581
- m .logger .Debug ("Mounting bpffs" )
585
+ func (m * Manager ) CloseProbe (p ProbeReference ) error {
586
+ if p .collection != nil {
587
+ p .collection .Close ()
582
588
}
583
- return bpffsMount (m .proc )
589
+
590
+ var err error
591
+ for _ , c := range p .closers {
592
+ err = errors .Join (err , c .Close ())
593
+ }
594
+ if err == nil {
595
+ p .probe .GetLogger ().Debug ("Closed" , "Probe" , p .probe .Manifest ().ID )
596
+ }
597
+ return err
584
598
}
585
599
586
600
func (m * Manager ) cleanup () error {
587
601
ctx := context .Background ()
588
602
err := m .cp .Shutdown (context .Background ())
589
603
for _ , i := range m .probes {
590
- err = errors .Join (err , i . Close ( ))
604
+ err = errors .Join (err , m . CloseProbe ( i ))
591
605
}
592
606
593
607
// Wait for all probes to close so we know there is no more telemetry being
0 commit comments