PortAudio ALSA Backend Reports Different Channel Count for Plug/Asym Devices
Describe the bug
PortAudio reports 128 channels for ALSA virtual devices configured with 32-channel limits via plug/asym wrappers, even though the underlying dmix/dsnoop devices correctly report 32 channels.
| Device |
Type |
Reported |
Actual Limit |
my_32ch_dmix |
dmix |
32 ch |
32 ch ✅ |
my_32ch_dsnoop |
dsnoop |
32 ch |
32 ch ✅ |
My_32ch_MultiClient |
plug → asym → dmix/dsnoop |
128 ch |
32 ch ❌ |
The dmix and dsnoop devices individually report correct channel counts. When combined via asym plugin and wrapped with plug, PortAudio reports 128 (hardware max) instead of 32.
To Reproduce
- Create an
.asoundrc with a plug → asym → dmix/dsnoop device chain (config below)
- Run this Python script:
import pyaudio
p = pyaudio.PyAudio()
for i in range(p.get_device_count()):
info = p.get_device_info_by_index(i)
if 'MultiClient' in info['name']:
print(f"{info['name']}: {info['maxOutputChannels']} channels")
p.terminate()
- Observe that
maxOutputChannels reports 128 instead of 32
ALSA Configuration (.asoundrc)
pcm.my_32ch_dmix {
type dmix
ipc_key 1024
slave {
pcm { type hw; card "MyCard" }
channels 32
period_size 1024
buffer_size 4096
rate 48000
format S32_LE
}
}
pcm.my_32ch_dsnoop {
type dsnoop
ipc_key 1025
slave {
pcm { type hw; card "MyCard" }
channels 32
period_size 1024
buffer_size 4096
rate 48000
format S32_LE
}
}
pcm.My_32ch_MultiClient {
type plug
slave {
pcm {
type asym
playback.pcm "my_32ch_dmix"
capture.pcm "my_32ch_dsnoop"
}
channels 32
rate 48000
format S32_LE
}
}
Expected behavior
PortAudio should report 32 channels for My_32ch_MultiClient to match the configured channel limit in the plug/dmix/dsnoop chain.
Actual behavior
PortAudio reports 128 channels (hardware maximum) instead of 32 (configured limit). Opening a stream with >32 channels fails even though PortAudio reports 128 available.
Impact:
- Applications trust reported channel count and request more than supported
- Runtime errors when opening streams with 33-128 channels
- Automatic device selection fails when filtering by channel count
Desktop
- OS: Linux (Ubuntu 24.04 LTS)
- OS Version: Tested on Kernel 6.14.0-37-generic and 6.19-rc5
- PortAudio version: 19.6.0 (libportaudio2 19.6.0-1.2build3, Ubuntu package)
- Host API: ALSA
- Audio Device: 128-channel USB audio interface
Additional context
Root Cause: PortAudio uses snd_pcm_hw_params_get_channels_max() which queries hardware capabilities. This is expected ALSA behavior — the plug plugin passes through hardware capabilities rather than enforcing configured constraints during capability queries. Constraints are only applied at stream open time.
Possible solutions (since ALSA's plug behavior is by design):
- Recognize plug devices may have constraints not reflected in hardware queries
- Document this limitation for ALSA users
- Implement detection of plug/dmix/dsnoop constraints
PortAudio ALSA Backend Reports Different Channel Count for Plug/Asym Devices
Describe the bug
PortAudio reports 128 channels for ALSA virtual devices configured with 32-channel limits via plug/asym wrappers, even though the underlying dmix/dsnoop devices correctly report 32 channels.
my_32ch_dmixmy_32ch_dsnoopMy_32ch_MultiClientThe dmix and dsnoop devices individually report correct channel counts. When combined via
asymplugin and wrapped withplug, PortAudio reports 128 (hardware max) instead of 32.To Reproduce
.asoundrcwith a plug → asym → dmix/dsnoop device chain (config below)maxOutputChannelsreports 128 instead of 32ALSA Configuration (.asoundrc)
Expected behavior
PortAudio should report 32 channels for
My_32ch_MultiClientto match the configured channel limit in the plug/dmix/dsnoop chain.Actual behavior
PortAudio reports 128 channels (hardware maximum) instead of 32 (configured limit). Opening a stream with >32 channels fails even though PortAudio reports 128 available.
Impact:
Desktop
Additional context
Root Cause: PortAudio uses
snd_pcm_hw_params_get_channels_max()which queries hardware capabilities. This is expected ALSA behavior — the plug plugin passes through hardware capabilities rather than enforcing configured constraints during capability queries. Constraints are only applied at stream open time.Possible solutions (since ALSA's plug behavior is by design):