Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions pkg/plugin/common/common_linux.go
Original file line number Diff line number Diff line change
Expand Up @@ -138,3 +138,13 @@ func readIDField(path string) string {
}
return ""
}

// IsFtraceEnabled checks if ftrace is enabled in the kernel.
// This is required for fexit/fentry programs to work.
func IsFtraceEnabled() bool {
data, err := os.ReadFile("/proc/sys/kernel/ftrace_enabled")
if err != nil {
return false
}
return strings.TrimSpace(string(data)) == "1"
}
29 changes: 28 additions & 1 deletion pkg/plugin/dropreason/dropreason_linux_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -484,6 +484,7 @@ func TestResolveEbpfPayload(t *testing.T) {
kv semver.Version
isMariner bool
isPodLevel bool
ftraceEnabled bool
wantType string
wantSupportsFexit bool
}{
Expand All @@ -493,6 +494,7 @@ func TestResolveEbpfPayload(t *testing.T) {
kv: mustVersion("5.4.0"),
isMariner: false,
isPodLevel: false,
ftraceEnabled: true,
wantType: "*dropreason.allKprobeObjects",
wantSupportsFexit: false,
},
Expand All @@ -502,6 +504,7 @@ func TestResolveEbpfPayload(t *testing.T) {
kv: mustVersion("5.10.0"),
isMariner: false,
isPodLevel: false,
ftraceEnabled: true,
wantType: "*dropreason.allFexitObjects",
wantSupportsFexit: true,
},
Expand All @@ -511,6 +514,7 @@ func TestResolveEbpfPayload(t *testing.T) {
kv: mustVersion("5.10.0"),
isMariner: true,
isPodLevel: false,
ftraceEnabled: true,
wantType: "*dropreason.marinerObjects",
wantSupportsFexit: true,
},
Expand All @@ -520,6 +524,7 @@ func TestResolveEbpfPayload(t *testing.T) {
kv: mustVersion("5.8.0"),
isMariner: true,
isPodLevel: false,
ftraceEnabled: true,
wantType: "*dropreason.allKprobeObjects",
wantSupportsFexit: false,
},
Expand All @@ -529,6 +534,7 @@ func TestResolveEbpfPayload(t *testing.T) {
kv: mustVersion("6.1.0"),
isMariner: true,
isPodLevel: false,
ftraceEnabled: true,
wantType: "*dropreason.marinerObjects",
wantSupportsFexit: true,
},
Expand All @@ -538,14 +544,35 @@ func TestResolveEbpfPayload(t *testing.T) {
kv: mustVersion("5.15.0"),
isMariner: false,
isPodLevel: true,
ftraceEnabled: true,
wantType: "*dropreason.allKprobeObjects",
wantSupportsFexit: false,
},
{
name: "mariner with ftrace disabled - fallback to kprobes",
arch: "amd64",
kv: mustVersion("5.15.0"),
isMariner: true,
isPodLevel: false,
ftraceEnabled: false,
wantType: "*dropreason.allKprobeObjects",
wantSupportsFexit: false,
},
{
name: "ubuntu with ftrace disabled - fallback to kprobes",
arch: "amd64",
kv: mustVersion("6.6.0"),
isMariner: false,
isPodLevel: false,
ftraceEnabled: false,
wantType: "*dropreason.allKprobeObjects",
wantSupportsFexit: false,
},
}

for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
objs, _, isFexit := resolvePayload(tt.arch, tt.kv, tt.isMariner, tt.isPodLevel)
objs, _, isFexit := resolvePayload(tt.arch, tt.kv, tt.isMariner, tt.isPodLevel, tt.ftraceEnabled)

if isFexit != tt.wantSupportsFexit {
t.Errorf("isFexit = %v, want %v", isFexit, tt.wantSupportsFexit)
Expand Down
24 changes: 16 additions & 8 deletions pkg/plugin/dropreason/ebpfsetup_linux.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ eBPF Program Support Matrix

Program Type Selection:
- If:
- Ftrace is enabled AND
- Arch == amd64 and kernel >= 5.5
- Arch == arm64 and kernel >= 6.0
→ Use `fexit`
Expand All @@ -44,13 +45,15 @@ Scope Selection:
+-----------+------------------------+--------------+--------+
| Distro | Arch + Kernel | Prog | Scope |
+-----------+------------------------+--------------+--------+
| Mariner | amd64, kernel >= 5.5 | fexit | core |
| Mariner | arm64, kernel >= 6.0 | fexit | core |
| Non-Marin | amd64, kernel >= 5.5 | fexit | all |
| Non-Marin | arm64, kernel >= 6.0 | fexit | all |
| Mariner | amd64, kernel >= 5.5 | fexit* | core |
| Mariner | arm64, kernel >= 6.0 | fexit* | core |
| Non-Marin | amd64, kernel >= 5.5 | fexit* | all |
| Non-Marin | arm64, kernel >= 6.0 | fexit* | all |
| * | (otherwise) | kprobe | per OS |
+-----------+------------------------+--------------+--------+

* fexit requires ftrace to be enabled in the kernel

core kernel funcs:
- tcp_v4_connect
- inet_csk_accept
Expand All @@ -74,16 +77,21 @@ func (dr *dropReason) getEbpfPayload() (objs interface{}, maps *kprobeMaps, supp
}
dr.l.Info("Detected kernel", zap.String("version", kv.String()))

objs, maps, supportsFexit = resolvePayload(runtime.GOARCH, kv, isMariner, dr.cfg.EnablePodLevel)
// Check if ftrace is enabled (required for fexit programs)
ftraceEnabled := plugincommon.IsFtraceEnabled()
dr.l.Info("Ftrace status", zap.Bool("enabled", ftraceEnabled))

objs, maps, supportsFexit = resolvePayload(runtime.GOARCH, kv, isMariner, dr.cfg.EnablePodLevel, ftraceEnabled)
return objs, maps, supportsFexit, nil
}

func resolvePayload(arch string, kv semver.Version, isMariner, isPodLevel bool) (interface{}, *kprobeMaps, bool) {
func resolvePayload(arch string, kv semver.Version, isMariner, isPodLevel, ftraceEnabled bool) (interface{}, *kprobeMaps, bool) {
minVersionAmd64, _ := versioncheck.Version(MinAmdVersionNum)
minVersionArm64, _ := versioncheck.Version(MinArmVersionNum)

supportsFexit := (arch == "amd64" && kv.GTE(minVersionAmd64)) ||
(arch == "arm64" && kv.GTE(minVersionArm64))
supportsFexit := ftraceEnabled &&
((arch == "amd64" && kv.GTE(minVersionAmd64)) ||
(arch == "arm64" && kv.GTE(minVersionArm64)))

var objs interface{}
var maps *kprobeMaps
Expand Down
2 changes: 1 addition & 1 deletion test/plugin/dropreason/main_linux.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ func main() {

cfg := &kcfg.Config{
MetricsInterval: 1 * time.Second,
EnablePodLevel: true,
EnablePodLevel: true, // Set to false to test fexit programs
}

// Filtermanager.
Expand Down
Loading