Skip to content

Commit 2b35ff4

Browse files
committed
add ability to subscribe to cgroup change
In order to prepare for synchronisation of interested cgroup id with bpf programs, this adds a way to subscribe to cgroup change via a channel share with cgroup monitor.
1 parent 001f2ba commit 2b35ff4

File tree

4 files changed

+51
-0
lines changed

4 files changed

+51
-0
lines changed

cgroup/fanotify.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -199,6 +199,10 @@ func (m *fanotifyMonitor) Resolve(id int) string {
199199
return m.observer.lookup(id)
200200
}
201201

202+
func (m *fanotifyMonitor) SubscribeCgroupChange(ch chan<- CgroupChange) error {
203+
return m.observer.subscribeCgroupChange(ch)
204+
}
205+
202206
// The following kernel patch is required to take advantage of this (included in v6.6-rc1):
203207
// * https://git.kernel.org/torvalds/c/0ce7c12e88cf ("kernfs: attach uuid for every kernfs and report it in fsid")
204208
func attachFanotify(path string) (io.Reader, error) {

cgroup/monitor.go

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,21 @@
11
package cgroup
22

33
import (
4+
"errors"
45
"log"
56
)
67

8+
var ErrCgroupIdMapUnsupported = errors.New("cgroup change subscription failed (fanotify not available)")
9+
10+
type CgroupChange struct {
11+
Id int
12+
Path string
13+
Remove bool
14+
}
15+
716
type monitor interface {
817
Resolve(id int) string
18+
SubscribeCgroupChange(chan<- CgroupChange) error
919
}
1020

1121
// Monitor resolves cgroup ids into their respective paths
@@ -34,3 +44,7 @@ func NewMonitor(path string) (*Monitor, error) {
3444
func (m *Monitor) Resolve(id int) string {
3545
return m.inner.Resolve(id)
3646
}
47+
48+
func (m *Monitor) SubscribeCgroupChange(ch chan<- CgroupChange) error {
49+
return m.inner.SubscribeCgroupChange(ch)
50+
}

cgroup/observer.go

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,13 +19,15 @@ type observer struct {
1919
lock sync.Mutex
2020
inodeToPath map[int]*resolved
2121
pathToInode map[string]int
22+
cgroupChans []chan<- CgroupChange
2223
}
2324

2425
func newObserver(initial map[int]string) *observer {
2526
observer := observer{
2627
lock: sync.Mutex{},
2728
inodeToPath: map[int]*resolved{},
2829
pathToInode: map[string]int{},
30+
cgroupChans: []chan<- CgroupChange{},
2931
}
3032

3133
for inode, name := range initial {
@@ -83,6 +85,12 @@ func (o *observer) add(inode int, path string) {
8385

8486
o.inodeToPath[inode] = r
8587
o.pathToInode[path] = inode
88+
for _, ch := range o.cgroupChans {
89+
ch <- CgroupChange{
90+
ID: inode,
91+
Path: path,
92+
}
93+
}
8694
}
8795

8896
func (o *observer) remove(path string) {
@@ -96,6 +104,13 @@ func (o *observer) remove(path string) {
96104

97105
r := o.inodeToPath[inode]
98106
r.dead = time.Now()
107+
for _, ch := range o.cgroupChans {
108+
ch <- CgroupChange{
109+
ID: inode,
110+
Path: path,
111+
Remove: true,
112+
}
113+
}
99114
}
100115

101116
func (o *observer) lookup(inode int) string {
@@ -113,3 +128,17 @@ func (o *observer) lookup(inode int) string {
113128

114129
return r.path
115130
}
131+
132+
func (o *observer) subscribeCgroupChange(ch chan<- CgroupChange) error {
133+
o.cgroupChans = append(o.cgroupChans, ch)
134+
// send the initial cgroup mapping
135+
go func() {
136+
for path, inode := range o.pathToInode {
137+
ch <- CgroupChange{
138+
ID: inode,
139+
Path: path,
140+
}
141+
}
142+
}()
143+
return nil
144+
}

cgroup/walker.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,10 @@ func (m *walkerMonitor) Resolve(id int) string {
4545
return m.mapping[id]
4646
}
4747

48+
func (m *walkerMonitor) SubscribeCgroupChange(_ chan<- CgroupChange) error {
49+
return ErrCgroupIDMapUnsupported
50+
}
51+
4852
func walk(dir string) (map[int]string, error) {
4953
mapping := map[int]string{}
5054

0 commit comments

Comments
 (0)