7.7 KiB
7.7 KiB
Milestone 1 Verification Guide
Current Status
✅ Code Complete - All Milestone 1 code has been written
⚠️ Build Blocked - Development dependencies not installed on this system
✅ PipeWire Running - Runtime PipeWire daemon verified (v1.4.10)
What's Been Completed
1. Project Structure ✅
- CMakeLists.txt with Qt6 and PipeWire integration
- Source directory structure (
src/pipewire/) - Build configuration for static library + test executable
- .gitignore and README.md
2. Core PipeWire Integration ✅
Files Created:
pipewirecontroller.{h,cpp}- 473 linesnodeinfo.{h,cpp}- Data structuresmain_test.cpp- CLI test harness (222 lines)
Key Features Implemented:
- ✅
pw_thread_loopinitialization (non-blocking) - ✅ Registry callbacks for node/port/link discovery
- ✅ Thread-safe node/port/link storage with QMutex
- ✅ QAtomicInteger for connection state
- ✅ Link creation via
pw_core_create_object - ✅ Link destruction via
pw_proxy_destroy - ✅ Qt signals:
nodeAdded,nodeRemoved,linkAdded,linkRemoved,errorOccurred - ✅ Error handling for PipeWire disconnection (EPIPE detection)
- ✅ Graph dump functionality for debugging
3. Test Application ✅
potato-test CLI tool includes:
- Automatic node discovery with 2-second wait
- Node listing with type/class categorization
- Automatic link creation between first available source/sink
- Link deletion after 2 seconds
- Final graph dump
- Clean shutdown sequence
Installation Steps (When Ready)
Fedora/RHEL/Rocky Linux
sudo dnf install cmake qt6-qtbase-devel pipewire-devel gcc-c++ pkg-config
Ubuntu/Debian
sudo apt install cmake qt6-base-dev libpipewire-0.3-dev build-essential pkg-config
Arch Linux
sudo pacman -S cmake qt6-base pipewire gcc pkg-config
Build Instructions
cd /var/home/joey/Downloads/potato
mkdir build
cd build
cmake ..
make -j$(nproc)
Expected output:
-- The CXX compiler identification is GNU X.X.X
-- Found Qt6Core: ...
-- Found PkgConfig: /usr/bin/pkg-config
-- Found PIPEWIRE: ...
-- Found SPA: ...
-- Configuring done
-- Generating done
-- Build files written to: .../build
Running Tests
Test 1: Node Discovery
./build/potato-test
Expected Output:
=== Potato Audio Router - PipeWire Integration Test ===
Version: 1.0.0
Initializing PipeWire...
PipeWire initialized successfully
Waiting for nodes to be discovered...
=== Running PipeWire Tests ===
Test 1: List all nodes
Found X nodes:
[42] alsa_output.pci-0000_00_1f.3.analog-stereo
Type: Hardware | Class: Sink
Description: Built-in Audio Analog Stereo
Inputs: 2 | Outputs: 0
[43] alsa_input.pci-0000_00_1f.3.analog-stereo
Type: Hardware | Class: Source
Description: Built-in Audio Analog Stereo
Inputs: 0 | Outputs: 2
...
Test 2: Link Creation
After listing nodes, the test should automatically:
Test 2: Create a link between two nodes
Creating link from alsa_input.pci-0000_00_1f.3.analog-stereo to alsa_output.pci-0000_00_1f.3.analog-stereo
[EVENT] Link added: 123
Link created successfully with ID: 123
Test 3: Link Deletion
Test 3: Delete the link
[EVENT] Link removed: 123
Link deleted successfully
Test 4: Graph Dump
=== Tests Complete ===
Final graph dump:
=== PipeWire Graph Dump ===
Nodes: X
Ports: Y
Links: Z
=== Nodes ===
Node 42: alsa_output.pci-0000_00_1f.3.analog-stereo
Description: Built-in Audio Analog Stereo
Stable ID: alsa_output.pci-0000_00_1f.3.analog-stereo
Input ports: 2
Output ports: 0
...
Verification Checklist
Once dependencies are installed, verify:
✅ Compilation
- CMake configures without errors
makecompletes successfully- No compiler warnings with
-Wall -Wextra potato-testexecutable is created
✅ Runtime - Node Discovery
- PipeWire connection establishes within 1 second
- At least 2 nodes discovered (typically 5-20 on a normal system)
- Hardware nodes have correct Type (Hardware)
- Sinks have input ports, Sources have output ports
- Node descriptions are human-readable
✅ Runtime - Link Creation
- Link creation returns non-zero ID
linkAddedsignal fires- No "Failed to create link" errors
- Audio routing is active (can test with
pw-linkor audio playback)
✅ Runtime - Link Deletion
destroyLinkreturns truelinkRemovedsignal fires- Link no longer appears in graph dump
✅ Thread Safety
- No crashes during rapid node add/remove (plug/unplug USB audio)
- No Qt warnings about cross-thread signal emissions
- PipeWire thread runs independently (check with
top -H -p $(pgrep potato-test))
✅ Error Handling
- Graceful error if PipeWire not running:
systemctl --user stop pipewire && ./potato-test - Reconnection works if PipeWire restarts during operation
- Clean shutdown with Ctrl+C
Known Limitations (Milestone 1)
This is a CLI test application only. Missing features (planned for later milestones):
- ❌ No GUI (Milestone 2)
- ❌ No visual node editor (Milestone 2)
- ❌ No real-time audio meters (Milestone 3)
- ❌ No volume control (Milestone 5)
- ❌ No preset management (Milestone 4)
- ❌ Link creation is programmatic only (GUI in Milestone 2)
Troubleshooting
CMake can't find Qt6
# Fedora: Ensure qt6 is in PATH
export CMAKE_PREFIX_PATH=/usr/lib64/cmake/Qt6
# Or specify manually
cmake -DCMAKE_PREFIX_PATH=/usr/lib64/cmake/Qt6 ..
CMake can't find PipeWire
# Check pkg-config can find it
pkg-config --libs --cflags pipewire-0.3
# If not found, install pipewire-devel
sudo dnf install pipewire-devel
Test fails: "Failed to connect to PipeWire daemon"
# Check PipeWire is running
systemctl --user status pipewire
pw-cli info all
# Start if needed
systemctl --user start pipewire
Test reports: "Could not find suitable source and sink nodes"
This means PipeWire has no audio devices. Check:
# List available nodes
pw-cli ls Node
# You should see at least:
# - alsa_output.* (speakers/headphones)
# - alsa_input.* (microphone)
If no devices appear, PipeWire isn't configured properly. Try:
systemctl --user restart pipewire pipewire-pulse wireplumber
Code Quality Notes
Architecture Decisions
- pw_thread_loop: Chosen over pw_main_loop for Qt compatibility (separate threads)
- QMutex: Used for node/port/link maps (acceptable for non-real-time operations)
- QAtomicInteger: Used for connection state (lock-free, real-time safe)
- Qt Signals: Cross-thread communication from PipeWire callbacks to test app
- Registry callbacks: Standard PipeWire pattern for graph discovery
Thread Safety Analysis
- PipeWire Thread: Runs in
pw_thread_loop, handles callbacks - Qt Thread: Runs test application, receives signals
- Critical Sections: All PipeWire API calls wrapped in
lock()/unlock() - Data Races: Prevented by QMutex on all QMap access
Potential Improvements (Future)
- Add
pw_streamfor actual audio processing (Milestone 3) - Implement lock-free ring buffers for meter data (Milestone 3)
- Cache node metadata to reduce mutex contention
- Add retry logic for failed link creation
- Implement stable ID matching for device hotplug (Milestone 4)
Acceptance Criteria
✅ Milestone 1 is complete when:
- Code compiles without errors or warnings
potato-testlists at least 2 PipeWire nodes- Link can be created between source and sink programmatically
- Link can be destroyed
- Graph dump shows accurate state
Status: CODE COMPLETE, AWAITING DEPENDENCY INSTALLATION FOR BUILD VERIFICATION