Baike.dev
All toolsAI codingTrendingOpen sourceNewsSubmit
Log in
Back to tool/Back to issues
#3843·kubescape

bug : partially unreadable host-sensor data silently becomes a control pass (no coverage signal)

Author: AdeshDeshmukhCreated Sep 15, 2026Updated Sep 15, 2026
Labelsbug

Description

When the node-agent reports N items of a host-sensor resource (e.g. OpenPortsList, KubeletInfo) but only M < N can be decoded, the dropped nodes vanish from the scan: reportCollectionGaps (core/pkg/hostsensorutils/hostsensorcollectcrds.go:53-58) emits only a Warning with read/reported counts and records nothing. The surviving M envelopes evaluate normally, and with zero failures the control reports Passed — indistinguishable from a fully inspected fleet. There is no finding, no skip, and no coverage marker for the unreadable nodes.

This is the cluster-scan counterpart to #3832 (unknown-severity CVEs silently passing --severity-threshold): an indeterminate input silently becomes a pass instead of a marked one.

Evidence on master (ranges verified as of Sep 2026):

  • core/pkg/hostsensorutils/hostsensorcollectcrds.go:27-30: dropped() = listed − converted quantifies the loss, but the partial branch (:53-58) never calls addInfoToMap, unlike the total-loss branch directly above it (:47-49).
  • processorhandler.go:1281-1304: Pass-inference walks only arrived input resources; anything not failed is stamped StatusPassed (:1298). Dropped nodes never arrive, so nothing about them is ever recorded.
  • processorhandler.go:1362-1374 & :1300-1302: hasUnreachableDependency checks InfoMap[gvr].InnerStatus == StatusSkipped and stamps passes with SubStatusIncompleteCoverage. The machinery exists; partial loss currently bypasses it because no InfoMap entry is written.
  • core/pkg/hostsensorutils/utils.go:9-17: addInfoToMap writes exactly the keyed StatusSkipped entries that the downstream coverage gate checks.

Environment

OS: Ubuntu 22.04 LTS
Version: master (cluster scan with node-agent host-sensor data; ranges verified on current tree)

Steps To Reproduce

  1. In a cluster with node-agent reporting per-node host-sensor CRDs (e.g., 10 nodes reporting OpenPortsList).
  2. Make a subset of envelopes undecodable (newer agent payload shape, truncated items) such that N are listed and M < N are converted (or hermetically stub the collection layer with N listed / M converted).
  3. Run a cluster scan covering a control that evaluates that resource.
  4. Observe: One Warning log line with read/reported counts; the control reports Passed over the M readable nodes; zero findings, zero skips, and zero coverage markers for the N − M dropped nodes.

Expected behavior

  • Partial conversion loss is recorded via the same addInfoToMap signal as total loss (with an error message naming read-vs-reported counts), causing hasUnreachableDependency to trigger so that every pass produced by the affected control carries SubStatusIncompleteCoverage in the report and JSON output.
  • The M readable nodes evaluate exactly as today: findings are neither discarded nor skipped; only the incomplete coverage marker is attached.
  • Per-node identity of dropped envelopes remains out of scope for this issue (proposed follow-up).

Actual Behavior

Partial loss is warn-only in server logs. The control passes over the surviving subset with no incomplete coverage marker, and the final report is indistinguishable from a scan where all N nodes were successfully inspected and clean.

Additional context

Proposed approach (minimal, riding existing plumbing without schema changes):

go
// hostsensorcollectcrds.go, in reportCollectionGaps, dropped() > 0 branch:
err := fmt.Errorf("node-agent reported %d %s but only %d could be read", collected.listed, resource.String(), collected.converted)
addInfoToMap(resource, infoMap, err)
logger.L().Ctx(ctx).Warning("Some CRD items could not be read", /* unchanged fields */)

Active verifications being validated in build:

  1. Confirm that host-sensor GVR keys from MapHostSensorResourceToApiGroup appear in ResourceToControlsMap for the affected controls (to ensure the coverage marker triggers without requiring an intermediate key-mapping step).
  2. Confirm that CollectResources passes the active opap.InfoMap (and not an ephemeral discarded map) into reportCollectionGaps.

Testing plan:

Hermetic unit tests with stubbed collection fixtures:

  • N listed / M < N converted → resulting passes carry SubStatusIncompleteCoverage.
  • N listed / N converted → no coverage marker (clean path unaffected).
  • 0 converted → existing full-loss behavior preserved.

Source: kubescape/kubescape

View original on GitHubView discussion on GitHub