Dual ZED X on AGX Orin: capped at 15fps despite idle CPU/GPU, single-camera hits 30fps cleanlySetup

Dual ZED X on AGX Orin: capped at 15fps despite idle CPU/GPU, single-camera hits 30fps cleanly
Setup

• Jetson AGX Orin Developer Kit (64GB), JetPack (ROS 2 Humble).
• 2x ZED X (serials 47903798, 41704206) on ZED Link Duo capture card.
• ZED SDK 5.2.3, zed-ros2-wrapper (latest master).
• NITROS not installed.
• Launched via zed_multi_camera.launch.py (stock tutorial launch file, both cameras composed into one zed_multi_container).
Config

• grab_resolution: HD1200, grab_frame_rate: 30, pub_frame_rate: 30, grab_compute_capping_fps: 30.
• depth_mode: NONE (also tested with PERFORMANCE, no difference to the symptom).
• pos_tracking_enabled auto-disabled by depth_mode: NONE.
• enable_24bit_output: true (tested both true/false, no difference).
• enable_ipc left at wrapper default (true) — not overridden by zed_multi_camera.launch.py, which does not forward this argument to the underlying zed_camera.launch.py includes.
System-level fixes already applied (confirmed necessary)

• Switched nvpmodel from MODE_30W to MAXN (mode 0).
• Ran jetson_clocks (locks GPU/CPU/EMC to max).
• Forced performance governor on all 12 CPU cores (schedutil was not sustaining high clocks under load even with jetson_clocks applied).
• All three now persisted via systemd services.
Isolation testing performed

  1. Single ZED X (cam0) alone, via zed_camera.launch.py directly (not multi-camera):.
    ◦ Before power-mode fix: hard-capped at ~15.0-15.3 Hz, extremely tight std dev (0.002-0.02s), regardless of grab_frame_rate/pub_frame_rate/depth_mode settings..
    ◦ After MAXN + jetson_clocks + forced performance governor: sustains a clean, stable ~29.8 Hz over 30+ second windows. This fully resolved the single-camera case..
  2. Both cameras together, via zed_multi_camera.launch.py, same system-level fixes applied:.
    ◦ Still capped at exactly ~15.0 Hz (confirmed via multiple bag recordings, 60s-730s durations)..
    ◦ tegrastats during a live dual-camera recording shows CPU at 0-11% across all 12 cores, GR3D_FREQ at 17-20%, temps stable ~55-58°C — system is essentially idle. This rules out compute/thermal/power throttling as the cause for the dual-camera case specifically..
  3. Cam0/cam1 timestamp offset analysis (nearest-neighbor matching on header.stamp from left/color/rect/image/compressed):.
    ◦ Confirms both cameras are decimating to 15Hz from an underlying (presumably still 30Hz-triggered) hardware clock, but each camera’s internal “keep every other tick” decimation locks onto its own phase independently..
    ◦ When both cameras happen to lock onto the same phase, timestamp offsets are excellent: median offset ~7-12us, p99 under 150-200us — consistent with the ~15us GMSL2 hardware sync guarantee documented at https://support.stereolabs.com (grab period tolerance)..
    ◦ When they lock onto opposite phases, offsets sit at a clean, tight cluster at exactly one grab period (~33.3ms at 30fps-underlying-clock), both +33ms and -33ms clusters observed across different recordings and even within a single long recording (see attached offset_over_time.png — a single sharp phase-flip event partway through a 12-minute recording, followed by continued occasional flips)..