Skip to content

Commit e3701b3

Browse files
committed
execsnoop: use the new bpfprogs skeleton package
Switch the new model which will allow us to put all bpf programs either cilium/ebpf or libbpf built on the same models.BpfPrograms map. Signed-off-by: Djalal Harouni <[email protected]>
1 parent 51d8857 commit e3701b3

File tree

1 file changed

+86
-34
lines changed

1 file changed

+86
-34
lines changed

bpf/gobpf/execsnoop/execsnoop.go

+86-34
Original file line numberDiff line numberDiff line change
@@ -7,15 +7,19 @@
77
package execsnoop
88

99
import (
10+
"fmt"
1011
"os"
1112
"path/filepath"
13+
"strings"
14+
"sync"
1215

1316
"github.com/cilium/ebpf"
1417
"github.com/cilium/ebpf/link"
1518
"github.com/cilium/ebpf/ringbuf"
1619
"github.com/cilium/ebpf/rlimit"
1720

1821
"github.com/linux-lock/bpflock/bpf/gobpf/bpfevents"
22+
"github.com/linux-lock/bpflock/bpf/gobpf/bpfprogs"
1923

2024
"github.com/linux-lock/bpflock/pkg/components"
2125
"github.com/linux-lock/bpflock/pkg/defaults"
@@ -66,29 +70,45 @@ type ExecSnoopBpf struct {
6670
pinPath string
6771

6872
args []string
73+
74+
attachOnce sync.Once
75+
destroyOnce sync.Once
76+
attached bool
77+
}
78+
79+
func init() {
80+
bpfprogs.Register(bpfProgram, Init)
6981
}
7082

71-
func NewBpf() (*ExecSnoopBpf, error) {
83+
func Init() (bpfprogs.BpfProg, error) {
7284
return &ExecSnoopBpf{
7385
name: components.ExecSnoop,
74-
description: "trace process exec()",
86+
description: components.BpfProgDescriptions[components.ExecSnoop],
7587
args: make([]string, 0),
7688
}, nil
7789
}
7890

79-
func (e *ExecSnoopBpf) GetName() string {
91+
func (e *ExecSnoopBpf) SetPinPath(pinPath string) {
92+
e.pinPath = pinPath
93+
}
94+
95+
func (e *ExecSnoopBpf) Name() string {
8096
return e.name
8197
}
8298

83-
func (e *ExecSnoopBpf) GetDescription() string {
99+
func (e *ExecSnoopBpf) Description() string {
84100
return e.description
85101
}
86102

103+
func (e *ExecSnoopBpf) SetArgs(args []string) {
104+
e.args = args
105+
}
106+
87107
func (e *ExecSnoopBpf) GetArgs() []string {
88108
return e.args
89109
}
90110

91-
func (e *ExecSnoopBpf) Load(pinPath string) error {
111+
func (e *ExecSnoopBpf) Load() error {
92112
// Load pre-compiled programs and maps into the kernel.
93113
objs := bpfObjects{}
94114

@@ -99,20 +119,28 @@ func (e *ExecSnoopBpf) Load(pinPath string) error {
99119

100120
if err := loadBpfObjects(&objs, &ebpf.CollectionOptions{
101121
Maps: ebpf.MapOptions{
102-
PinPath: pinPath,
122+
PinPath: e.pinPath,
103123
},
104124
}); err != nil {
105125
log.WithError(err).Errorf("loading '%s' objects failed", e.name)
106126
return err
107127
}
108128

109129
e.objs = objs
110-
e.pinPath = pinPath
111130

112131
return nil
113132
}
114133

115-
func (e *ExecSnoopBpf) SetArgs(traceTarget string) error {
134+
func (e *ExecSnoopBpf) setupMaps() error {
135+
target := ""
136+
137+
// We support only one argument for now
138+
a := strings.Split(e.args[0], "=")
139+
if len(a) != 2 {
140+
return nil
141+
}
142+
target = a[1]
143+
116144
key := uint32(ExecSnoopTraceTarget)
117145
path := filepath.Join(e.pinPath, ExecSnoopArgsMap)
118146
loadOpts := &ebpf.LoadPinOptions{}
@@ -123,7 +151,7 @@ func (e *ExecSnoopBpf) SetArgs(traceTarget string) error {
123151
return nil
124152
}
125153

126-
switch traceTarget {
154+
switch target {
127155
case defaults.ExecSnoopByFilter:
128156
value := uint32(ExecSnoopTraceByFilter)
129157
err = m.Put(key, value)
@@ -133,20 +161,38 @@ func (e *ExecSnoopBpf) SetArgs(traceTarget string) error {
133161
}
134162

135163
if err != nil {
136-
log.Warnf("Execsnoop ignored, updating map '%s' failed: %v", path, err)
164+
log.Warnf("bpf program %s ignored, updating map '%s' failed: %v", e.Name(), path, err)
137165
return nil
138166
}
139167

140-
e.args = append(e.args, traceTarget)
168+
return nil
169+
}
170+
171+
func (e *ExecSnoopBpf) Attach() error {
172+
if e.attached {
173+
return nil
174+
}
175+
176+
e.attachOnce.Do(func() {
177+
err := e.attach()
178+
if err != nil {
179+
log.WithError(err).Warnf("attach bpf program '%s' failed", e.Name())
180+
}
181+
})
182+
183+
if e.attached == false {
184+
return fmt.Errorf("attach bpf program %s failed", e.Name())
185+
}
141186

142187
return nil
143188
}
144189

145-
func (e *ExecSnoopBpf) Attach(target string) error {
190+
func (e *ExecSnoopBpf) attach() error {
191+
e.attached = true
146192
tp, err := link.Tracepoint("syscalls", "sys_enter_execve",
147193
e.objs.TracepointSyscallsSysEnterExecve)
148194
if err != nil {
149-
e.Detach()
195+
e.Destroy()
150196
log.WithError(err).Errorf("opening tracepoint 'sys_enter_execve' failed")
151197
return err
152198
}
@@ -156,15 +202,16 @@ func (e *ExecSnoopBpf) Attach(target string) error {
156202
tp, err = link.Tracepoint("syscalls", "sys_exit_execve",
157203
e.objs.TracepointSyscallsSysExitExecve)
158204
if err != nil {
159-
e.Detach()
205+
e.Destroy()
160206
log.WithError(err).Errorf("opening tracepoint 'sys_exit_execve' failed")
207+
return err
161208
}
162209
e.sysExitExecve = tp
163210

164211
tp, err = link.Tracepoint("syscalls", "sys_enter_execveat",
165212
e.objs.TracepointSyscallsSysEnterExecveat)
166213
if err != nil {
167-
e.Detach()
214+
e.Destroy()
168215
log.WithError(err).Errorf("opening tracepoint 'sys_enter_execveat' failed")
169216
return err
170217
}
@@ -173,22 +220,22 @@ func (e *ExecSnoopBpf) Attach(target string) error {
173220
tp, err = link.Tracepoint("syscalls", "sys_exit_execveat",
174221
e.objs.TracepointSyscallsSysExitExecveat)
175222
if err != nil {
176-
e.Detach()
223+
e.Destroy()
177224
log.WithError(err).Errorf("opening tracepoint 'sys_exit_execveat' failed")
178225
return err
179226
}
180227
e.sysExitExecveAt = tp
181228

182-
err = e.SetArgs(target)
229+
err = e.setupMaps()
183230
if err != nil {
184-
e.Detach()
185-
log.WithError(err).Errorf("setArgs() failed")
231+
e.Destroy()
232+
log.WithError(err).Errorf("setupMaps() failed")
186233
return err
187234
}
188235

189236
rd, err := ringbuf.NewReader(e.objs.BpflockEvents)
190237
if err != nil {
191-
e.Detach()
238+
e.Destroy()
192239
log.WithError(err).Errorf("opening ringbuffer reader")
193240
return err
194241
}
@@ -197,23 +244,23 @@ func (e *ExecSnoopBpf) Attach(target string) error {
197244
return nil
198245
}
199246

200-
func (e *ExecSnoopBpf) GetRingBufferPath() string {
247+
func (e *ExecSnoopBpf) GetOutputBufPath() string {
201248
return filepath.Join(e.pinPath, bpfevents.SharedEvents)
202249
}
203250

204-
func (e *ExecSnoopBpf) GetRingBuffer() *ringbuf.Reader {
251+
func (e *ExecSnoopBpf) GetOutputBuf() *ringbuf.Reader {
205252
return e.ring
206253
}
207254

208-
func (e *ExecSnoopBpf) CloseBuffer() {
255+
func (e *ExecSnoopBpf) closeBuffer() {
209256
if e.ring != nil {
210257
e.ring.Close()
211258
e.ring = nil
212259
}
213260
}
214261

215-
// UnpinLocalMaps removes non shared maps only
216-
func (e *ExecSnoopBpf) UnpinLocalMaps() {
262+
// unpinLocalMaps removes non shared maps only
263+
func (e *ExecSnoopBpf) unpinLocalMaps() {
217264
pinnedMap := filepath.Join(e.pinPath, "bpflock_execsnoop_storage")
218265
log.Infof("Cleaning remove bpf-map=%s", pinnedMap)
219266
os.RemoveAll(pinnedMap)
@@ -223,7 +270,7 @@ func (e *ExecSnoopBpf) UnpinLocalMaps() {
223270
os.RemoveAll(pinnedMap)
224271
}
225272

226-
func _ExecSnoopCloseLinks(links ...link.Link) {
273+
func _execSnoopCloseLinks(links ...link.Link) {
227274
for _, l := range links {
228275
if l != nil {
229276
l.Close()
@@ -233,24 +280,29 @@ func _ExecSnoopCloseLinks(links ...link.Link) {
233280
}
234281

235282
func (e *ExecSnoopBpf) closeLinks() {
236-
_ExecSnoopCloseLinks(
283+
_execSnoopCloseLinks(
237284
e.sysEnterExecve,
238285
e.sysEnterExecveAt,
239286
e.sysExitExecve,
240287
e.sysExitExecveAt,
241288
)
242289
}
243290

244-
// CloseExecSnoop remove and detach execsnoop resources
245-
func (e *ExecSnoopBpf) Detach() {
246-
e.CloseBuffer()
291+
// Detach remove and detach execsnoop program
292+
func (e *ExecSnoopBpf) detach() {
293+
e.closeBuffer()
247294
e.closeLinks()
248295
e.objs.Close()
249-
log.Infof("Cleaning remove bpf-program=%s", e.GetName())
296+
log.Infof("Cleaning remove bpf-program=%s", e.Name())
250297
}
251298

252-
// Clean cleans up everything related to execsnoop and closes ring buffer
299+
// Destroy cleans up everything related to execsnoop and remove ring buffer
253300
func (e *ExecSnoopBpf) Destroy() {
254-
e.Detach()
255-
e.UnpinLocalMaps()
301+
if e.attached {
302+
e.destroyOnce.Do(func() {
303+
e.detach()
304+
e.unpinLocalMaps()
305+
})
306+
e.attached = false
307+
}
256308
}

0 commit comments

Comments
 (0)