Skip to content

KVM: packet capture of Instance NICs via operator-defined script - #13767

Open
wido wants to merge 1 commit into
apache:mainfrom
wido:packet-capture
Open

KVM: packet capture of Instance NICs via operator-defined script#13767
wido wants to merge 1 commit into
apache:mainfrom
wido:packet-capture

Conversation

@wido

@wido wido commented Aug 2, 2026

Copy link
Copy Markdown
Contributor

Description

Adds root-admin-only APIs to capture the traffic of an Instance NIC on the KVM host it is running on, for debugging and lawful interception:

  • enablePacketCapture nicid=
  • disablePacketCapture nicid=
  • getPacketCaptureStatus nicid=

Packet capture is a flag on the NIC (stored as a nic detail). When enabled, the agent resolves the host-side tap device by MAC address, writes the NIC context (VM name/UUID, NIC UUID/MAC, IPv4/IPv6, bridge, network UUID) to /run/cloudstack/pcap-.env and starts the systemd template unit cloudstack-pcap@.service. The flag follows the Instance: a VM state listener restarts the capture after start and migration, and BindsTo= on the tap device stops the unit when the VM stops, migrates away or the NIC is unplugged.

The unit executes pcap-capture.sh, shipped between the other KVM scripts in /usr/share/cloudstack-common as an example that runs tcpdump writing to /tmp with 256 MB rotation. What to capture and what to do with the data differs too much per environment for CloudStack to decide it, so operators run their own script by copying the unit, pointing its ExecStart at it and naming their unit in packet.capture.service.

New agent.properties keys:

  • packet.capture.service (systemd template unit name)
  • packet.capture.env.dir (environment file directory)

This is in no way a "fits all" solution as capturing traffic will really differ per environment. I thought about storing it on Secondary Storage, but that would add so many different API calls and logic to CloudStack while in most cases every admin wants to do this differently. Therefor I have choosen this option.

Admins can override the packet capture script with a version that suits their environment.

Types of changes

  • Breaking change (fix or feature that would cause existing functionality to change)
  • New feature (non-breaking change which adds functionality)
  • Bug fix (non-breaking change which fixes an issue)
  • Enhancement (improves an existing feature and functionality)
  • Cleanup (Code refactoring and cleanup, that may add test cases)
  • Build/CI
  • Test (unit or integration test code)

Feature/Enhancement Scale or Bug Severity

Feature/Enhancement Scale

  • Major
  • Minor

Bug Severity

  • BLOCKER
  • Critical
  • Major
  • Minor
  • Trivial

Adds root-admin-only APIs to capture the traffic of an Instance NIC on
the KVM host it is running on, for debugging and lawful interception:

  * enablePacketCapture nicid=<uuid>
  * disablePacketCapture nicid=<uuid>
  * getPacketCaptureStatus nicid=<uuid>

Packet capture is a flag on the NIC (stored as a nic detail). When
enabled, the agent resolves the host-side tap device by MAC address,
writes the NIC context (VM name/UUID, NIC UUID/MAC, IPv4/IPv6, bridge,
network UUID) to /run/cloudstack/pcap-<dev>.env and starts the systemd
template unit cloudstack-pcap@<dev>.service. The flag follows the
Instance: a VM state listener restarts the capture after start and
migration, and BindsTo= on the tap device stops the unit when the VM
stops, migrates away or the NIC is unplugged.

The unit executes pcap-capture.sh, shipped between the other KVM
scripts in /usr/share/cloudstack-common as an example that runs tcpdump
writing to /tmp with 256 MB rotation. What to capture and what to do
with the data differs too much per environment for CloudStack to decide
it, so operators run their own script by copying the unit, pointing its
ExecStart at it and naming their unit in packet.capture.service.

New agent.properties keys: packet.capture.service (systemd template
unit name) and packet.capture.env.dir (environment file directory).
@codecov

codecov Bot commented Aug 2, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 3.41%. Comparing base (4f11707) to head (759bab3).

❗ There is a different number of reports uploaded between BASE (4f11707) and HEAD (759bab3). Click for more details.

HEAD has 1 upload less than BASE
Flag BASE (4f11707) HEAD (759bab3)
unittests 1 0
Additional details and impacted files
@@              Coverage Diff              @@
##               main   #13767       +/-   ##
=============================================
- Coverage     19.65%    3.41%   -16.24%     
=============================================
  Files          6368      487     -5881     
  Lines        574881    41867   -533014     
  Branches      70351     7912    -62439     
=============================================
- Hits         112970     1429   -111541     
+ Misses       449639    40238   -409401     
+ Partials      12272      200    -12072     
Flag Coverage Δ
uitests 3.41% <ø> (ø)
unittests ?

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant