Skip to content

fix: remove syscalls from isEmpty() to prevent 0-CVE overwrites#757

Closed
slashben wants to merge 1 commit intomainfrom
fix/remove-syscalls-from-isEmpty
Closed

fix: remove syscalls from isEmpty() to prevent 0-CVE overwrites#757
slashben wants to merge 1 commit intomainfrom
fix/remove-syscalls-from-isEmpty

Conversation

@slashben
Copy link
Copy Markdown
Contributor

@slashben slashben commented Mar 26, 2026

Summary

  • PR add new metadata to CPs #745 added cd.syscalls != nil to isEmpty(), causing syscall-only container profile snapshots to be saved. These snapshots have no file opens, so kubevuln finds 0 relevant CVEs and overwrites the filtered VulnerabilityManifest — destroying previously-correct results.
  • This one-line fix removes cd.syscalls from isEmpty(). Syscalls are still saved when other events (opens, execs, etc.) trigger a save, so no data is lost.
  • Adds unit tests proving the bug (syscalls-only incorrectly triggers save) and the fix (syscalls-only correctly skipped).

Root cause

After emptyEvents() clears all data on save, running processes regenerate syscalls within milliseconds (read, write, epoll_wait, etc.). With the PR #745 change, isEmpty() returns false → profile saved with opens=nil → kubevuln matches 0 files → overwrites filtered VM with 0 CVEs.

This caused the relevant_data_is_appended E2E test to fail 5/5 times (redis-sleep test: CVEs drop from 57 to 0 after redis-server starts generating steady-state syscalls).

Test plan

  • go test ./pkg/containerprofilemanager/v1/ -run TestIsEmpty -v — all 4 new tests pass
  • go test ./pkg/containerprofilemanager/... -v -count=1 — all existing tests pass (no regression)
  • E2E test relevant_data_is_appended should pass with this fix

🤖 Generated with Claude Code

Summary by CodeRabbit

Release Notes

  • Bug Fixes

    • Improved container profile data validation by refining how syscall events are considered during emptiness checks. This correction ensures more accurate profile persistence decisions and prevents unintended overwrite scenarios in profile snapshots.
  • Tests

    • Added comprehensive unit test coverage for container profile data state validation, including tests for syscall event handling, event combinations, status change detection, and completion tracking.

PR #745 added `cd.syscalls != nil` to isEmpty(), which caused
container profile snapshots to be saved whenever new syscalls
accumulated — even with no new file opens. These syscall-only
snapshots produce 0 relevant CVEs when scanned by kubevuln
(which matches file opens, not syscalls), and the 0-CVE result
overwrites the previously-correct filtered VulnerabilityManifest.

Syscalls are still saved when other events (opens, execs, etc.)
trigger a save, so no syscall data is lost.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Ben <ben@armosec.io>
@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Mar 26, 2026

📝 Walkthrough

Walkthrough

The isEmpty() method in containerData was modified to exclude syscall events from the emptiness determination. Previously, the presence of syscalls marked data as non-empty; now syscalls alone do not trigger that condition. Corresponding unit tests were added to verify the updated behavior.

Changes

Cohort / File(s) Summary
Container Data Logic
pkg/containerprofilemanager/v1/container_data.go
Removed cd.syscalls != nil check from isEmpty() method, allowing container data to be considered empty when only syscall events are present.
Container Data Tests
pkg/containerprofilemanager/v1/container_data_test.go
Added four unit tests validating isEmpty() behavior: empty state with no events, syscalls-only returns true, opens trigger non-empty state, and status/completion mismatch detection.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

Poem

A syscall whispered soft and low,
But didn't make the data show—
Now emptiness rings clear and true,
When only syscalls came through! 🐰✨
The container breathes, untouched, unbowed,
No snapshot clouds this logic now.

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and specifically describes the main change: removing syscalls from isEmpty() to prevent 0-CVE overwrites, which directly matches the core modification in the changeset.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch fix/remove-syscalls-from-isEmpty

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@pkg/containerprofilemanager/v1/container_data_test.go`:
- Around line 106-108: Update the stale test comment in
TestIsEmpty_StatusChangeTriggersFirstSave to reflect the actual values used in
the test (status/completion are set to Ready/Full), not "" to "Learning"; locate
the comment immediately above the TestIsEmpty_StatusChangeTriggersFirstSave
function and change its description to state that the status/completion changes
to Ready/Full and that this triggers the first profile save, so the comment
matches the test behavior.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: d0778482-398c-4e2a-ba1b-02188347e263

📥 Commits

Reviewing files that changed from the base of the PR and between 1a85870 and e749388.

📒 Files selected for processing (2)
  • pkg/containerprofilemanager/v1/container_data.go
  • pkg/containerprofilemanager/v1/container_data_test.go
💤 Files with no reviewable changes (1)
  • pkg/containerprofilemanager/v1/container_data.go

Comment on lines +106 to +108
// TestIsEmpty_StatusChangeTriggersFirstSave verifies that a status change
// (from "" to "Learning") correctly triggers the first profile save.
func TestIsEmpty_StatusChangeTriggersFirstSave(t *testing.T) {
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Update stale test comment to match actual status values

The comment says the status changes from "" to "Learning", but the test sets status/completion to Ready/Full. Please align the comment text to avoid confusion.

✏️ Suggested comment fix
-// TestIsEmpty_StatusChangeTriggersFirstSave verifies that a status change
-// (from "" to "Learning") correctly triggers the first profile save.
+// TestIsEmpty_StatusChangeTriggersFirstSave verifies that a status/completion
+// change (from empty last-reported values to current Ready/Full) triggers
+// the first profile save.
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
// TestIsEmpty_StatusChangeTriggersFirstSave verifies that a status change
// (from "" to "Learning") correctly triggers the first profile save.
func TestIsEmpty_StatusChangeTriggersFirstSave(t *testing.T) {
// TestIsEmpty_StatusChangeTriggersFirstSave verifies that a status/completion
// change (from empty last-reported values to current Ready/Full) triggers
// the first profile save.
func TestIsEmpty_StatusChangeTriggersFirstSave(t *testing.T) {
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@pkg/containerprofilemanager/v1/container_data_test.go` around lines 106 -
108, Update the stale test comment in TestIsEmpty_StatusChangeTriggersFirstSave
to reflect the actual values used in the test (status/completion are set to
Ready/Full), not "" to "Learning"; locate the comment immediately above the
TestIsEmpty_StatusChangeTriggersFirstSave function and change its description to
state that the status/completion changes to Ready/Full and that this triggers
the first profile save, so the comment matches the test behavior.

@matthyx
Copy link
Copy Markdown
Contributor

matthyx commented Mar 27, 2026

fixed with kubescape/operator#362

@matthyx matthyx closed this Mar 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants