Pipewire: Difference between revisions

From miki
Jump to navigation Jump to search
Line 246: Line 246:
* SBC_XQ profile works correctly (good audio)
* SBC_XQ profile works correctly (good audio)
* <code>headset-head-unit-msbc</code> profile works when using the microphone, but there is a audio loopback in the headset (we hear what the mic captures).
* <code>headset-head-unit-msbc</code> profile works when using the microphone, but there is a audio loopback in the headset (we hear what the mic captures).

Some background info:
* [https://www.freedesktop.org/wiki/Software/PulseAudio/Documentation/User/Bluetooth/] Check this page for background info on Bluetooth profiles, HSP vs HFP.
:* Basically HSP is older than HFP, the latter being more convenient.
:* Audio Gateway are basically the mobile phone itself.
* [https://www.redpill-linpro.com/techblog/2021/05/31/better-bluetooth-headset-audio-with-msbc.html Fix for battery level reporting on Sony WH-1000XM3]
* [https://blog.oblivioncoding.pro/sony-wh-1000mx3-linux-fix/ Pipewire fixes for WH-1000XM3].
:* Here they suggest to set
bluez5.headset-roles = [hsp_hs hsp_ag hfp_hf]

Revision as of 13:54, 26 April 2022

Pipewire is the new sound system on Linux, meant to replace Pulseaudio.

Links

WirePlumber
Nice examples on how to use the lua configuration files.

References

Configuration files:

  • /usr/share/pipewire
  • /usr/share/wireplumber

Commands

# View status
systemctl --user status pipewire

# Use PipeWire instead of JACK
pw-jack SOMEAPP

# PipeWire process viewer (quantum usage...)
pw-top

# Setup sinks, sources, audio devices
pw-link
qjackctl         # Graphical tool, leveraging on JACK
qpwgraph         # Alternative, pipewire native

# Get settings
pw-metadata -n settings

# Set settings
pw-metadata -n settings 0 clock.rate 48000
pw-metadata -n settings 0 clock.allowed-rates '[ 48000, 96000, 44100 ]'

# Command line
pw-cli
> info all

Configuration

  • Package configuration files are located in /usr/share/pipewire and /usr/share/wireplumber.
  • To change them, copy and edit them in /etc/pipewire (system-wide) or ~/.config/pipewire (local changes).
pipewire-pulse.conf
  • A single section can also be updated through a file in /etc/pipewire/pipewire-pulse.conf.d/ or ~/.config/pipewire/pipewire-pulse.conf.d/
cat /usr/share/pipewire/pipewire-pulse.conf
# # PulseAudio config file for PipeWire version "0.3.50" #
# #
# # Copy and edit this file in /etc/pipewire for system-wide changes
# # or in ~/.config/pipewire for local changes.
# #
# # It is also possible to place a file with an updated section in
# #  for system-wide changes or in
# # ~/.config/pipewire/pipewire-pulse.conf.d/ for local changes.
  • One can see current module configuration with pactl:
pactl list modules      # See active modules and their config

Troubleshooting

Setting and keeping bluetooth profile for headset

We want to use the profile sbc sbc_xq for our BT headset Sony WH-1000XM3.

Set the profile manually - profile should be persistent on reboot / reconnect.
  • In principe WirePlumber should remember the last selected profile.
  • See [1]
# See available profile and device id with 'pactl list'
pactl set-card-profile bluez_card.38_18_4C_4B_6A_3A a2dp-sink-sbc_xq
Configure profile
  • When using pipewire-media-session, the default profile could be selected in bluez-monitor.conf, but this file no longer exists with WirePlumber.
  • (UPDATE - Archlinux - Pipewire) Edit /etc/wireplumber/bluetooth.lua.d/51-bluez-config.lua (or ~/.config/wireplumber/bluetooth.lua.d/51-bluez-config.lua):
bluez_monitor.properties = {
  ["bluez5.enable-sbc-xq"] = true,
  ["bluez5.enable-msbc"] = true,
  ["bluez5.codecs"] = "[sbc sbc_xq]",
}

Crackling / Stuttering audio

This applies in a VM. Not sure these apply when PipeWire is run on the host.

Note that recent PipeWire already supports different auto-config if running in a vm [2].

Enable multi-user / network audio

References
An advanced config that allows to share the unix socket, for even lower latency. Use case was specifically for streaming audio coming from a VM!

Currently PipeWire support sharing through network using Pulse, but auth-anonymous is always turned on (auth-ip-acl not implemented).

  • (pipewire 0.3.50+) On the main user, create file ~/.config/pipewire/pipewire-pulse.conf.d/multi-user-zeroconf.conf
# This config file is a refinement of config file /usr/share/pipewire/pipewire-pulse.conf.

# We listen to network socket to enable multi-user / network playback.
# LIMITATION: The laptop speaker is advertised by zeroconf, but playback fails. Playback through BT headset is ok though.
# LIMITATION: auth-ip-acl might not work
# LIMITATION: We listen to ipv4 0.0.0.0 only, and use firewall to further restrict access to private network only.
context.exec = [
    { path = "pactl"        args = "load-module module-native-protocol-tcp auth-ip-acl=127.0.0.1 listen=0.0.0.0" }
    { path = "pactl"        args = "load-module module-zeroconf-publish" }
]

# # Below, an alternative way for multi-user / network (however we still need zeroconf above)
# # Note that this method doesn't load the native-protocol-tcp module
# pulse.properties = {
#     # the addresses this server listens on
#     server.address = [
#         "unix:native"
#         "tcp:4713"                         # IPv4 and IPv6 on all addresses
#         # "tcp:127.0.0.1:4713"               # IPv4 on a single address
#         #
#         #{ address = "tcp:4713"             # address
#         #  max-clients = 64                 # maximum number of clients
#         #  listen-backlog = 32              # backlog in the server listen queue
#         #  client.access = "restricted"     # permissions for clients
#         #}
#     ]
#     # vm.overrides = {
#     #     pulse.min.quantum = 1024/48000      # 22ms
#     # }
# }
Note: we CANNOT edit pipewire-pulse.conf or any system-level file (like in /etc/pipewire/pipewire-pulse.d) because the TCP socket would already be used, and service would fail to load.
Now, restart pipewire-pulse, and check it works:
# We must restart the SOCKET (this also restart the SERVICE)
systemctl --user restart pipewire-pulse.socket
PULSE_SERVER=tcp:127.0.0.1:4713 pactl info
PULSE_SERVER=unix:/run/user/1000/pulse/native pactl info
  • On the secondary user:
# We can either export this variable
export PULSE_SERVER=127.0.0.1            # OR ...
export PULSE_SERVER=tcp:127.0.0.1:4713
PULSE_SERVER=127.0.0.1 pactl info
Or we can edit ~/.pulse/client.conf like we did with PulseAudio:
default-server = 127.0.0.1
Note: make sure the port is allowed in the firewall as well.
# ################# NOT TESTED #############################
context.modules = [
{   name = libpipewire-module-pulse-tunnel
    args = {
        tunnel.mode = playback
        # Set the remote address to tunnel to
        pulse.server.address = "tcp:192.168.1.126"
        #audio.rate=<sample rate>
        #audio.channels=<number of channels>
        #audio.position=<channel map>
        #node.target=<remote target node>
        stream.props = {
            # extra sink properties
        }
    }
}
]
We can also use the PipeWire Module: Zeroconf Discover, that will automatically create sinks/sources to/from remote PulseAudio servers.
context.modules = [
{   name = libpipewire-module-zeroconf-discover
    args = { }
}
]
VMWare VM
  • We cannot get audio to work on VMWare VM, under user vbox, although same user can play audio file with eg mplayer.
  • Instead we share the pipewire unix socket, as explained here.
  • Pipewire unix socket for main user is located at /run/user/1000/pipewire-0:
ss -lpn | grep pipewire-0
# u_str LISTEN 0  4096  /run/user/1000/pipewire-0 26175  * 0  users:(("pipewire",pid=2207,fd=3),("systemd",pid=2190,fd=32))
  • We must share this socket with user vbox, but keeping some access control.
  • We create a folder /mnt/pipewire, with access for group audio, and we add user vbox to that group.
sudo mkdir /mnt/pipewire
sudo chgrp audio /mnt/pipewire
sudo chmod 750 /mnt/pipewire
sudo gpasswd -a vbox audio       # This also likely help to get access to ALSA
  • We add a binding mount point in fstab, that can be mounted by user (option user):
# Pipewire audio sharing (for user vbox). This requires:
#   sudo mkdir /mnt/pipewire
#   sudo chgrp audio /mnt/pipewire
#   sudo chmod 750 /mnt/pipewire
#   sudo gpasswd -a vbox audio
/run/user/1000/pipewire-0 /mnt/pipewire/pipewire-0 none bind,rw,user,noauto 0 0
  • We add systemd override to pipewire.socket, to mount/umount that point automatically.
systemctl edit --user pipewire.socket # or edit file '~/.config/systemd/user/pipewire.socket.d/override.conf'
# [Socket]
# ExecStartPost=/bin/mount /mnt/pipewire/pipewire-0
# ExecStopPre=/bin/umount /mnt/pipewire/pipewire-0
  • As user vbox, simply add to ~vbox/.profile:
export PIPEWIRE_RUNTIME_DIR=/mnt/pipewire
Check ALSA works:
aplay -L
  • Alternatively, we can tell sudo to keep variable PIPEWIRE_RUNTIME_DIR. Edit /etc/sudoers.d/envkeep:
visudo /etc/sudoers.d/envkeep
# Defaults env_keep += "http_proxy https_proxy GREP_OPTIONS DISPLAY XAUTHORITY HOME PIPEWIRE_RUNTIME_DIR"

troubleshooting Sony WH-1000XM3

Currently

  • SBC_XQ profile works correctly (good audio)
  • headset-head-unit-msbc profile works when using the microphone, but there is a audio loopback in the headset (we hear what the mic captures).

Some background info:

  • [3] Check this page for background info on Bluetooth profiles, HSP vs HFP.
  • Basically HSP is older than HFP, the latter being more convenient.
  • Audio Gateway are basically the mobile phone itself.
  • Here they suggest to set
bluez5.headset-roles = [hsp_hs hsp_ag hfp_hf]