Jump to content
From ArchWiki
Состояние перевода: На этой странице представлен перевод статьи PipeWire. Дата последней синхронизации: 6 октября 2022. Вы можете помочь синхронизировать перевод, если в английской версии произошли изменения.

Ссылки по теме

- PipeWire/Примеры
- WirePlumber (Русский)

PipeWire — это новый низкоуровневый мультимедийный фреймворк. Он предназначен для захвата и воспроизведения аудио и видео с минимальной задержкой и поддерживает PulseAudio, JACK, ALSA и приложения, использующие GStreamer.

Демон, основанный на этом фреймровке, может быть использован как звуковой сервер (с поддержкой возможностей PulseAudio и JACK) и как сервер для захвата видео.

PipeWire также поддерживает контейнеры по типу Flatpak и не зависит от пользовательских групп `audio` и `video`. Вместо них он использует модель безопасности, основанную на Polkit, для запроса у Flatpak или Wayland разрешений для записи экрана или звука.

## Установка

Установите пакет pipewire. Также есть пакет lib32-pipewire для поддержки multilib.

PipeWire использует пользовательский экземпляр systemd для управления сервером и автоматической активации через сокет.

Документация есть в пакете pipewire-docs.

Pipewire может работать как прозрачная замена других звуковых серверов; подробнее в разделе #Аудио.

### Менеджер сеансов

Как и JACK, PipeWire не реализует никакой внутренней логики подключения. Бремя отслеживания новых потоков и подключения их к соответствующему устройству вывода или приложению возлагается на внешний компонент, известный как менеджер сеансов.

На данный момент доступны два менеджера сеансов:

- WirePlumber — Менеджер, основанный на модульной конструкции, с плагинами Lua, которые реализуют фактическую функциональность управления. Он более мощный чем PipeWire Media Session и рекомендуется к использованию по умолчанию.

  https://pipewire.pages.freedesktop.org/wireplumber/ || wireplumber

- PipeWire Media Session — Очень простой менеджер, подходящий для простых случаев. Он был реализован в основном для тестирования и в качестве примера для создания новых менеджеров сеансов.

  https://gitlab.freedesktop.org/pipewire/media-session || pipewire-media-session

Переключиться на другой менеджер можно простой установкой соответствующего пакета, который будет конфликтовать с пакетом прошлого менеджера и заменит его.

### GUI

- Helvum — GTK обёртка для pipewire, вдохновленная подобным инструментом для JACK catia.

  https://gitlab.freedesktop.org/pipewire/helvum || helvum

- qpwgraph — Graph/Patchbay для PipeWire на базе Qt, вдохновлённый JACK-инструментом QjackCtl.

  https://gitlab.freedesktop.org/rncbc/qpwgraph || qpwgraph

## Настройка

Пакет PipeWire предоставляет начальный набор конфигурационных файлов в `/usr/share/pipewire`. Не редактируйте эти файлы напрямую, так как обновления пакета перезапишут ваши изменения. Для настройки PipeWire можно скопировать файлы из `/usr/share/pipewire` в другой общесистемный каталог `/etc/pipewire` или в пользовательский каталог `~/.config/pipewire`. Файл из каталога с более высоким приоритетом заменяет собой файлы с таким же именем из других каталогов. [1]

### Профили

Pipewire добавляет пользовательский профиль "Pro Audio" в дополнение к профилям PulseAudio, выбираемым через pavucontrol. Эффект от этого описан здесь: https://gitlab.freedesktop.org/pipewire/pipewire/-/wikis/FAQ#what-is-the-pro-audio-profile

## Использование

### Аудио

PipeWire может быть использован как звуковой сервер наподобие PulseAudio и JACK. Он нацелен их на полную замену путем предоставления реализации PulseAudio-совместимого сервера и ABI-совместимых библиотек для клиентов JACK. Подробнее смотреть здесь.

#### Клиенты ALSA

Установите pipewire-alsa (и удалите pulseaudio-alsa, если он установлен) для перенаправления приложений, использующих ALSA API, через PipeWire.

#### Клиенты PulseAudio

Установите pipewire-pulse. Этот пакет заменит установленные pulseaudio и pulseaudio-bluetooth. Необходимо перезагрузиться или запустить пользовательский юнит `pipewire-pulse.service` для работы.

Как правило, этого достаточно для дальнейшей работы, так как сервис `pipewire-pulse.socket` должен быть автоматически включен. Для проверки работоспособности, выполните следующую команду и изучите вывод:

    $ pactl info

    ...
    Имя сервера: PulseAudio (on PipeWire 0.3.16)
    ...

Информация о дальнейшей настройке (например, касательно модулей) есть в официальной Wiki проекта: Migration from PulseAudio, Configuration of Pipewire-Pulse.

#### Клиенты JACK

Установите пакет pipewire-jack. Также есть пакет lib32-pipewire-jack для поддержки multilib.

Можно использовать pw-jack(1) для запуска клиентов JACK, но технически это не обязательно, так как он служит лишь обёрткой для переменных окружения `PIPEWIRE_REMOTE`, `PIPEWIRE_DEBUG` и `PIPEWIRE_LATENCY`.

Также вы можете использовать другой размер буфера путем установления нужного соотношения размера буфера и частоты дискретизации (что равно задержке в секнудах):

    PIPEWIRE_LATENCY="128/48000" приложение

#### Устройства Bluetooth

Для управления Bluetooth audio устройствами PipeWire использует pipewire-pulse. Говоря более конкретно, сервис PipeWire проверяет наличие `/etc/pipewire/media-session.d/with-pulseaudio` и подключает модуль `bluez5` автоматически, если он установлен в системе.

##### Автоматический выбор профиля

И pipewire-media-session, и WirePlumber могут автоматически переключаться между профилями HSP/HFP и A2DP при обнаружении входного потока.

В pipewire-media-session это по умолчанию отключено. Для включения установите параметр `bluez5.autoswitch-profile` в значение `true`:

    /etc/pipewire/media-session.d/bluez-monitor.conf (или ~/.config/pipewire/media-session.d/bluez-monitor.conf)

    ...
    rules = [
        {
            ...
            actions = {
                update-props = {
                    ...
                    bluez5.autoswitch-profile = true
    ...

В WirePlumber это по умолчанию включено. Отключить можно так:

    /etc/wireplumber/policy.lua.d/11-bluetooth-policy.lua (или ~/.config/wireplumber/policy.lua.d/11-bluetooth-policy.lua)

    bluetooth_policy.policy["media-role.use-headset-profile"] = false

#### PipeWire native patch sets

У нас есть Helvum для графической визуализации и создания соединений, но всего остального пока нет. Ниже приведены bash-скрипты, которые сохраняют наборы связей, загружают их и разрывают все соединения. Для сохранения и загрузки укажите имя файла в качестве аргумента.

    pw-savewires

    #!/bin/bash

    if [[ "$#" -ne 1 ]]; then
    	echo
    	echo 'usage: pw-savewires filename'
    	echo
    	exit 0
    fi

    rm $1 &> /dev/null
    while IFS= read -r line; do
    	link_on=`echo $line | cut -f 4 -d '"'`
    	link_op=`echo $line | cut -f 6 -d '"'`
    	link_in=`echo $line | cut -f 8 -d '"'`
    	link_ip=`echo $line | cut -f 10 -d '"'`
    	echo "Saving: " "'"$link_on:$link_op"','"$link_in:$link_ip"'"
    	echo "'"$link_on:$link_op"','"$link_in:$link_ip"'" >> $1
    done < <(pw-cli dump short link)

    pw-loadwires

    #!/bin/python

    import sys
    import csv
    import os

    if len(sys.argv) < 2:
    	print('\n usage: pw-loadwires filename\n')
    	quit()

    with open(sys.argv[1], newline='') as csvfile:
    	pwwreader = csv.reader(csvfile, delimiter=',', quotechar='"')
    	for row in pwwreader:
    		print('Loading:  ' + row[0] + ' --> ' + row[1])
    		process = os.popen('pw-link ' + row[0] + ' ' + row[1])

    pw-dewire

    #!/bin/bash
    while read -r line; do
    	echo 'Dewiring: ' $line '...'
    	pw-link -d $line
    done < <(pw-cli dump short link {{!}} grep -Eo '^[0-9]+')

#### Совместное использование аудиоустройств по сети

Хотя в само́м PipeWire нет сетевой прозрачности, его реализация PulseAudio поддерживает передачу звука по сети. Простым способом обмена аудио между компьютерами в сети является использование демона Avahi для обнаружения устройств. Убедитесь, что служба `avahi-daemon.service` запущена на всех компьютерах, которые будут совместно использовать аудио.

Чтобы сделать аудиоустройства доступными через сеть, загрузите соответствующие модули на хосте (убедитесь, что используется локальный IP-адрес):

    $ pactl load-module module-native-protocol-tcp listen=192.168.1.10
    $ pactl load-module module-zeroconf-publish

А на клиентах загрузите модуль обнаружения:

    $ pactl load-module module-zeroconf-discover

#### Работа PipeWire поверх JACK

PipeWire также может работать как клиент JACK, если это необходимо. Подробнее смотреть здесь

#### Использование ALSA dmix в качестве вывода PipeWire

Можно использовать сервер PipeWire (или несколько, отдельно для каждого пользователя) для вывода звука на ALSA через ALSA dmix. Это позволяет использовать ALSA в качестве основной системы вывода звука, но при этом использовать устройства, не относящиеся к ALSA, например Bluetooth-наушники.

##### Настройка dmix в ALSA

Допустим, у вас есть две звуковые карты, `PCH` и `HDMI`:

    /proc/asound/cards

     0 [PCH            ]: HDA-Intel - HDA Intel PCH
                          HDA Intel PCH at 0xdff40000 irq 146
     1 [HDMI           ]: HDA-Intel - HDA ATI HDMI
                          HDA ATI HDMI at 0xdfe60000 irq 147

и PCM выглядит примерно так:

    /proc/asound/pcm

    00-00: ALC1220 Analog : ALC1220 Analog : playback 1 : capture 1
    00-02: ALC1220 Alt Analog : ALC1220 Alt Analog : capture 1
    01-03: HDMI 0 : HDMI 0 : playback 1
    01-07: HDMI 1 : HDMI 1 : playback 1
    01-08: HDMI 2 : HDMI 2 : playback 1
    01-09: HDMI 3 : HDMI 3 : playback 1
    01-10: HDMI 4 : HDMI 4 : playback 1
    01-11: HDMI 5 : HDMI 5 : playback 1

и настройки ALSA примерно такие:

    /etc/asound.conf

    ctl.!default {
      type hw
      card PCH
    }

    pcm.!default {
      type plug
      slave.pcm "dmix:PCH,0"
    }

    pcm.dhdmi {
      type plug
      slave.pcm "dmix:HDMI,9"
    }

В примерах ниже будут использоваться dmix-устройства `dmix:PCH,0` и `dmix:HDMI,9`.

##### Настройка dmix в PipeWire

Сперва нужно отключить автоматический мониторинг устройств ALSA в WirePlumber. Закомментируйте строку `alsa_monitor.enable()`:

    /etc/wireplumber/main.lua.d/90-enable-all.lua (или ~/.config/wireplumber/main.lua.d/90-enable-all.lua)

    ...
    -- Load devices
    -- alsa_monitor.enable()
    v4l2_monitor.enable()
    libcamera_monitor.enable()
    ...

Теперь нужно настроить PipeWire на использование dmix. В стандартном файле настроек (`/usr/share/pipewire/pipewire.conf`) есть закомментированный пример, который можно использовать в качестве основы.

Добавьте свой элемент в массив `context.objects`:

    /etc/pipewire/pipewire.conf.d/alsa-dmix.conf (или ~/.config/pipewire/pipewire.conf.d/alsa-dmix.conf)

    context.objects = [
        # Начинаем не с dmix, а с устройства ввода. Не забудьте его добавить.
        # Без настроенного устройства ввода наблюдались проблемы в Zoom.
        { factory = adapter
            args = {
                factory.name           = api.alsa.pcm.source
                node.name              = "alsa-mic-internal" # название устройства pulse (mpv)
                node.description       = "Mic Internal" # название устройства pulse (pavucontrol)
                media.class            = "Audio/Source"
                api.alsa.path          = "hw:PCH,0"
            }
        }
        # Теперь можно добавить dmix PCM
        { factory = adapter
            args = {
                factory.name           = api.alsa.pcm.sink # Вывод в dmix
                node.name              = "alsa-dmix-internal" # название устройства pulse (mpv)
                node.description       = "PCM Internal" # название устройства pulse (pavucontrol)
                media.class            = "Audio/Sink" # Вывод в dmix
                api.alsa.path          = "dmix:PCH,0"
            }
        }

        { factory = adapter
            args = {
                factory.name           = api.alsa.pcm.sink # Вывод в dmix
                node.name              = "alsa-dmix-hdmi" # название устройства pulse (mpv)
                node.description       = "PCM HDMI" # название устройства pulse (pavucontrol)
                media.class            = "Audio/Sink" # Вывод в dmix
                # это dmix из файла /etc/asound.conf
                api.alsa.path          = "dmix:HDMI,9"
            }
        }
    ]

Как обычный пользователь (не root) проверьте вывод `wpctl status` и настройте источник (source) и вывод (sink) устройства по умолчанию по своему вкусу с помощью `wpctl set-default ID`, где `ID` - это число перед именем источника/вывода.

Теперь можно полноценно протестировать изменения.

### Демонстрация экрана WebRTC

Большинство браузеров для работы WebRTC и захвата рабочего стола или отдельных приложений используют X11. На Wayland используется подход, основанный на механизме разрешений.

Для этого требуются пакет xdg-desktop-portal и один из следующих бэкендов:

- xdg-desktop-portal-gnome для GNOME, который зависит от
- xdg-desktop-portal-gtk для приложений GTK.
- xdg-desktop-portal-kde для KDE.
- xdg-desktop-portal-lxqt for LXQt.
- xdg-desktop-portal-wlr для оболочек, использующих композитор wlroots (напр. Sway, dwlAUR)

После установки бэкенда перезапустите пользовательский юнит `xdg-desktop-portal.service`.

Примечание: В xdg-desktop-portal 1.10.0 исправлено несоответствие между спецификацией и реализацией интерфейса D-Bus. [2] Как следствие, некоторые клиенты могут не работать с xdg-desktop-portal 1.10.0 или более новыми версиями.

Firefox (84+) поддерживает данный механизм по умолчанию. Для Chromium (73+) нужно активировать поддержку вручную включением экспериментального флага:

    chrome://flags/#enable-webrtc-pipewire-capturer

В obs-studio (27+) этот метод реализован в виде источника «Захват экрана (PipeWire)».

Обратите внимание, что поддерживается только захват экрана целиком, а не отдельного окна/приложения [3][4].

#### xdg-desktop-portal-wlr

Для работы `xdg-desktop-portal-wlr` необходимо, чтобы в пользовательском сеансе systemd присутствовали переменные окружения `XDG_CURRENT_DESKTOP` и `WAYLAND_DISPLAY`. Переменная `XDG_CURRENT_DESKTOP` должна содержать название используемого вами композитора, например `XDG_CURRENT_DESKTOP=sway`. Переменную `WAYLAND_DISPLAY` композитор прописывает автоматически. Рекомендуемый способ перенести эти переменные окружения в пользовательский сеанс systemd — выполнить команду `systemctl --user import-environment WAYLAND_DISPLAY XDG_CURRENT_DESKTOP` после запуска композитора, например, в файле настроек композитора. Смотрите [5] и [6] для более подробной информации.

Совет: Если у вас несколько мониторов, то, чтобы выбрать один из них, установите slurp и добавьте следующую конфигурацию (смотрите xdg-desktop-portal-wlr(5) § SCREENCAST OPTIONS):

    ~/.config/xdg-desktop-portal-wlr/config

    chooser_type = simple
    chooser_cmd = slurp -f %o -ro

Когда запрашивается доступ к экрану, `slurp` покажет вам курсор с перекрестием, и вам нужно будет щёлкнуть на экран, к которому вы хотите предоставить доступ. После выбора `xdg-desktop-portal-wlr` предоставит доступ к этому экрану.

### Видео

Большинство приложений, которые полагаются на GStreamer для обработки, например, видеопотоков, должны работать «из коробки», используя плагин PipeWire GStreamer; смотрите GStreamer#PipeWire. Поэтому такие приложения, как, например, cheese, уже могут использовать его для захвата видео.

Скрипт `pw-v4l2` из пакета pipewire-v4l2 выполняет предзагрузку библиотеки (`/lib/pipewire-0.3/v4l2/libpw-v4l2.so`), которая перехватывает вызовы v4l2 и направляет видео через pipewire.

## Постобработка аудио

### EasyEffects

EasyEffects (ранее PulseEffects) это GTK утилита предоставляющая большой набор аудио эффектов и фильтров для использования в потоках отдельных приложений и микрофона. Присутствуют большинство основных эффектов, таких как эквалайзер, выравнивание громкости, усиления низких частот, дэ-эссер и подавления шумов. Полный список эффектов и фильтров можно посмотреть на GitHub.

Для использования установите easyeffects. Так же можете посмотреть коллекцию пользовательских пресетов для настройки. Смотрите также AutoEq — коллекция предустановок эквалайзера для наушников, созданная искусственным интеллектом.

Примечание: Про старую версию — PulseEffects — можно прочитать здесь: PulseAudio (Русский)#PulseEffects.

### NoiseTorch

NoiseTorch это альтернативный способ для шумоподавления. Для использования установите noisetorchAUR, либо одну из этих версий пакета noisetorch-binAUR noisetorch-gitAUR

После запуска модуля требуется выбрать нужный микрофон. Имеется возможность выбора нужного порога активации. Для того, что бы не фильтровать голос, установите максимальный уровень.

Можно сделать автозапуск с помощью systemd; смотрите [7]. Обратите внимание, что путь к исполняемому файлу noisetorch другой при установке из AUR.

### Шумоподавление для голоса

Установите noise-suppression-for-voice и смотрите https://github.com/werman/noise-suppression-for-voice#pipewire для настройки. После, установите источник подавления шумов по умолчанию в настройках аудио. Возможно потребуется перезапустить приложение.

### JamesDSP

JamesDSP for Linux (пакет jamesdspAUR) предоставляет звуковые эффекты с открытым исходным кодом для PipeWire и PulseAudio. Он использует свой собственный движок эффектов и не зависит от LADSPA, Calf и т.д. Изначально JamesDSP был опубликован как обработчик звуковых эффектов для устройств Android.

### Плагины LADSPA, LV2 и VST

Если вы хотите использовать плагины LADSPA, LV2 и VST, вы можете применить их используя виртуальный аудиовход Pulseaudio и хост Jack Carla. Установите pipewire-pulse, pipewire-jack и carla. Для начала создайте новый аудиовход в Pulseaudio под названием `default_null_sink`.

    pactl load-module module-null-sink object.linger=1 media.class=Audio/Sink sink_name=default_null_sink channel_map=FL,FR

Запустите Carla через PipeWire `pw-jack carla-rack`. Во вкладке Rack добавьте плагины по желанию. Удостоверьтесь, что они имеют тип stereo. Вы можете поменять их очередность, в которой они будут работать, начиная с верха списка. После этого переместитесь во вкладку Patchbay и подключите `default_null_sink` к вводу Carla, а вывод Carla к нужному устройству воспроизведения (наушники, колонки, HDMI и т.п.). Сохраните конфигурацию в домашнюю директорию, напр. в `~/Documents/carla_sink_effects.carxp`.

Вы можете протестировать эффекты в любом медиа приложение, производящем звук, например просмотром видео в браузере. Есть два способа сделать это. Открыть в Carla вкладку Patchbay, и перенаправить соединения нужного приложения к `default_null_sink`. Второй способ через pavucontrol, так же перенаправить аудио поток нужного приложения к аудиовходу `default_null_sink` (Этот способ запомнит перенаправление, поэтому последующие экземпляры приложения автоматически перенаправится на `default_null_sink`).

Для применения вышеописанных настроек, необходимо создать два пользовательских systemd юнита:

    ~/.config/systemd/user/jack-carla-rack.service

    [Unit]
    Description=Load Carla Rack JACK host

    [Service]
    PassEnvironment="PIPEWIRE_LINK_PASSIVE=true"
    Type=exec
    ExecStart=/usr/bin/pw-jack carla-rack -n

    [Install]
    WantedBy=default.target

    ~/.config/systemd/user/pulseaudio-null-sink@.service

    [Unit]
    Description=Load %i Pulseaudio null sink
    Before=jack-carla-rack.service
    After=pipewire-pulse.service

    [Service]
    Type=oneshot
    ExecStart=/usr/bin/pactl load-module module-null-sink object.linger=1 media.class=Audio/Sink sink_name=%i channel_map=FL,FR
    ExecStop=/usr/bin/pactl unload-module module-null-sink
    RemainAfterExit=yes

    [Install]
    WantedBy=default.target

Затем измените сервис jack-carla-rack, указав полный путь к вашему сохраненному файлу конфигурации в строке Environment:

    ~/.config/systemd/user/jack-carla-rack.service.d/override.conf

    [Service]
    Environment="CARLA_CONFIG_FILE=/home/username/Documents/carla_sink_effects.carxp"
    ExecStart=
    ExecStart=/usr/bin/pw-jack carla-rack -n $CARLA_CONFIG_FILE

И наконец, включите пользовательские юниты `pulseaudio-null-sink@default_null_sink.service` и `jack-carla-rack.service`.

Обратите внимание, если вы установите `default_null_sink` как устройство по умолчанию, все приложения будут автоматически перенаправляться к этому аудиовходу и клавиши громкости будут менять его уровень, а не громкость устройств воспроизведения. Для того, чтобы изменять клавишами уровень громкости устройства, необходимо оставить его по умолчанию и перенаправлять аудиопоток приложения к `default_null_sink` через pavucontrol. (PipeWire запомнит перенаправление и использует его для последующих экземпляров приложений).

## Решение проблем

### Аудио

#### PipeWire не видит микрофон

Модуль `alsa-monitor` по умолчанию использует alsa-card-profiles для обнаружения устройств. Если этот метод не работает, попробуйте выключить `api.alsa.use-acp` и/или включить `api.alsa.use-ucm`.

Если используется pipewire-media-session:

    /etc/pipewire/media-session.d/alsa-monitor.conf (или ~/.config/pipewire/media-session.d/alsa-monitor.conf)

    ...
    rules = [
        {
            ...
            actions = {
            update-props = {
                ...
                api.alsa.use-acp = false
    ...

Если используется wireplumber:

    /etc/wireplumber/main.lua.d/50-alsa-config.lua (или ~/.config/wireplumber/main.lua.d/50-alsa-config.lua)

    ...
    alsa_monitor.rules = {
        {
            ...
            apply_properties = {
                -- Использование устройств ALSA-Card-Profile. Они используют UCM или
                -- конфигурацию профиля для настройки параметров устройства и микшера.
                -- ["api.alsa.use-acp"] = true,

                -- Использование UCM вместо profile по возможности. Можно отключить,
                -- чтобы не пытаться использовать профиль UCM.
                ["api.alsa.use-ucm"] = true,
    ...

Затем перезапустите PipeWire и проверьте список доступных устройств:

    $ pw-record --list-targets

    Available targets ("*" denotes default): 62
    	58: description="Built-in Audio" prio=1872
    	60: description="Built-in Audio" prio=2000
    *	62: description="Built-in Audio (Loopback PCM)" prio=1984

Другой вариант решения, предложенный в баг-трекере — добавить микрофон вручную. Сперва убедитесь, что ALSA видит микрофон.

    $ arecord -l

    **** List of CAPTURE Hardware Devices ****
    card номер_карты: имя_карты, device номер_устройства: имя_устройства
      ...

Выберите свой микрофон из списка, а для дальнейшего тестирования микрофона выполните следующие команды.

    $ arecord --duration=5 --format=dat --device=hw:номер_карты,номер_устройства test-mic.wav # запись с микрофона
    $ aplay test-mic.wav # воспроизведение записи

Если `arecord` успешно записывает микрофон, но PipeWire его не видит, попробуйте добавить файл настроек для ручного добавления микрофона.

    /etc/pipewire/pipewire.conf.d/microphone.conf (или ~/.config/pipewire/pipewire.conf.d/microphone.conf)

    context.objects = [
        { factory = adapter
            args = {
                factory.name           = api.alsa.pcm.source
                node.name              = "microphone"
                node.description       = "Undetected Microphone"
                media.class            = "Audio/Source"
                api.alsa.path          = "hw:номер_карты,номер_устройства"
            }
        }
    ]

Перезапустите PipeWire для применения изменений.

#### Звук не переключается автоматически при подключении нового устройства

Чтобы автоматически переключаться на вновь подключенные устройства, раскомментируйте следующую строку (выделена жирным):

    /usr/share/pipewire/pipewire-pulse.conf (или добавьте в ~/.config/pipewire/pipewire.conf)

    ...
    context.exec = [
        { path = "pactl"        args = "load-module module-always-sink" }
        { path = "pactl"        args = "load-module module-switch-on-connect" }
        #{ path = "/usr/bin/sh"  args = "~/.config/pipewire/default.pw" }
    ]
    ...

Перезапустите пользовательские юниты `pipewire.service` и `pipewire-pulse.service` для применения изменений.

#### Звук не переключается автоматически на наушники Bluetooth

Выполните `pactl load-module module-switch-on-connect` и настройте среду рабочего стола на автоматический запуск этой команды при входе в систему. Возможно, вам потребуется выполнить `wpctl set-default <id>`. Найти `<id>` можно в выводе команды `wpctl status`. Смотрите wireplumber issue #89 для более подробной информации.

#### Нет звука после подключения устройства Bluetooth

По состоянию на 2020-12-07, если у вас нет звука после подключения Bluetooth устройства, вам скорее всего потребуется переключить стандартный аудиопоток или перенаправить его к требуемому. Воспользуйтесь `pactl list sinks` для просмотра доступных потоков и `pactl set-default-sink` для смены стандартного потока на bluetooth устройство. Можно автоматизировать через udev, используя данный скрипт как пример.

Обсуждение данной проблемы можно посмотреть здесь. По словам автора скрипта, профиль гарнитуры (HSP) все еще может иметь проблемы.

#### Маленькая громкость

После замены PulseAudio на Pipewire громкость была как задумано, но после перезагрузки звук невыносимо тихий.

Откройте `alsamixer`, нажимайте `F6` для выбора нужной звуковой карты и удостоверьтесь, что уровень громкости стоит на 100%. `alsactl` должен сохранить настройки после перезагрузки.

#### Увеличение RLIMIT_MEMLOCK

    Dec 13 11:11:11 HOST pipewire-pulse[99999]: Failed to mlock memory 0x7f4f659d8000 32832: This is not a problem but for best performance, consider increasing RLIMIT_MEMLOCK

Установите realtime-privileges и добавьте пользователя в группу `realtime`.

Также, увеличение memlock с 64кБ до 128кБ должно хватить для решение проблемы. Если вы запускаете `pipewire-pulse` через systemd/User (Русский), допишите:

    имя_пользователя	soft	memlock	64
    имя_пользователя	hard	memlock	128

в `/etc/security/limits.d/username.conf`

#### Изменение частоты дискретизации

По умолчанию PipeWire глобально устанавливает частоту дискретизации равную 48КГц. Если вы хотите изменить ее (например если ваш ЦАП поддерживает более высокое значение), можно прописать своё значение по умолчанию:

    /etc/pipewire/pipewire.conf (или ~/.config/pipewire/pipewire.conf)

    ...
    context.properties = {
        ...
        default.clock.rate          = частота_дискретизации'
        ...

#### Изменение разрешённых частот дискретизации

PipeWire также может динамически изменять выходную частоту дискретизации, поддерживаемую вашим ЦАП. Частота дискретизации соответствует частоте дискретизации воспроизводимого аудиопотока.

    /etc/pipewire/pipewire.conf (или ~/.config/pipewire/pipewire.conf)

    ...
    context.properties = {
        ...
        default.clock.allowed-rates = [ частота_1 частота_2 частота_3 ... ]
        ...

например, `[ 44100 48000 88200 96000 ]`. Поддерживаемые значения должны быть описаны в инструкции к вашему ЦАП.

По словам разработчика，PipeWire допускает до 16 различных частот дискретизации и переключается по возможности. Это означает, что с приведёнными выше настройками передискретизация не производится, если используемая в аудиопотоке частота поддерживается устройством.

Чтобы проверить, с какой выходной частотой дискретизации и форматом дискретизации данные отправляются на ЦАП (возможно, вам понадобится изменить цифры):

    $ cat /proc/asound/card0/pcm0p/sub0/hw_params

Чтобы проверить, какая частота дискретизации используется на входе, измените `pcm0p` на `pcm0c`. (`c` означает «capture» — захват, `p` означает «playback» — воспроизведение).

#### Качество звука (качество передискретизации)

Если вы использовали PulseAudio с `resample-method = speex-float-10` или `soxr-vhq`, то вам стоит раскомментировать и изменить строку `resample.quality = 4` на `10` или максимальное `15` в блоке `stream.properties` в файлах `/etc/pipewire/client.conf` и `/etc/pipewire/pipewire-pulse.conf`. (скопируйте их из `/usr/share/pipewire/`, если они не существуют). Не забудьте перезапустить пользовательские юниты `pipewire.service` и `pipewire-pulse.socket` (никогда не забывайте про перезапуск `pipewire-pulse.socket`, если хотите применить изменения настроек).

Разница в качестве между `10` и `15` незначительна, но разница в загрузке процессора составляет 2-3 раза. А разница в задержке между `4`, `10`, `15` ещё никем не исследована. Использование `resample.quality = 15` на 44100→48000 Гц на Ryzen 2600 приводит к тому, что процессы `pipewire` или `pipewire-pulse` нагружают одно ядро CPU на 4.0%.

Вы можете сравнить ресемплеры здесь: https://src.infinitewave.ca/ (не обращайте внимания на всё, что выше 18 КГц и более 120 дБ). speex указан как "Xiph.org Speex".

PipeWire использует свой собственный алгоритм передискретизации под названием Spa. Как и в случае `sox` и Speex `speexenc`, алгоритм PipeWire доступен в виде автономной версии: `spa-resample`. Использование:

    $ spa-resample -q 15 -f s24 -r 48000 input16bit44100orAnythingElse.wav output24bit48000hz.wav

Вероятно, можно как-то использовать другие ресемплеры, создав свой собственный выход. Или просто использовать плагин в проигрывателе (например, в Qmmp есть плагин SoX).

#### Внешняя звуковая карта не включается после переподключения

Проверьте `~/.config/pipewire-media-session/default-profile`. Если присутствуют значения с стандартным профилем "off", удалите их. Если же это не поможет, удалите все файлы из `~/.config/pipewire/media-session.d/` и перезапустите пользовательскую службу `pipewire.service`.

#### Нет звука или pactl info показывает Failure: Connection refused

Эта ошибка говорит о том, что приложение не может присоединиться к службе PipeWire-Pulse. Убедитесь, что `/etc/pipewire/pipewire-pulse.conf` существует и файл не пустой, и перезапустите пользовательскую службу `pipewire-pulse.service`.

Если этот способ не исправит ошибку, запустите `strace -f -o /tmp/pipe.txt pactl info` для дебага и используйте `/tmp/pipe.txt` для помощи в IRC чате #pipewire или списках рассылки.

#### Низкое качество звука через Bluetooth

В случае, если звук через Bluetooth заикается, проверьте статус пользовательского юнита `pipewire.service`. Если у вас есть ошибки по типу:

    Feb 17 18:23:01 HOST pipewire[249297]: (bluez_input.18:54:CF:04:00:56.a2dp-sink-60) client too slow! rate:512/48000 pos:370688 status:triggered

проверьте используемый кодек командой `pactl list sinks` и попробуйте поменять его изменением `bluez5.codecs` на один из следующих: `sbc aac ldac aptx aptx_hd`. Также можно попробовать включить поддержку mSBC (исправляет микрофон на Sony 1000XM3, то есть Headphones WH-1000XM3 и Earbuds WF-1000XM3), и кодек SBC-XQ.

Если используется pipewire-media-session:

    /etc/pipewire/media-session.d/bluez-monitor.conf (или ~/.config/pipewire/media-session.d/bluez-monitor.conf)

    ...
    properties = {
      ...
      bluez5.enable-msbc = true
      bluez5.enable-sbc-xq = true
      bluez5.codecs = [sbc sbc_xq]
    ...

Если используется wireplumber:

    /etc/wireplumber/bluetooth.lua.d/51-bluez-config.lua (или ~/.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]",
    }

Перезапустите пользовательскую службу `pipewire.service` для применения изменений.

#### Заметная задержка звука при воспроизведении

Обычно это происходит после отключения узла в период неактивности.

Если вы используете pipewire-media-session, отключить это можно путём редактирования одного из файлов `/etc/pipewire/media-session.d/*-monitor.conf` в зависимости от того, где происходит задержка, заменив значение `session.suspend-timeout-seconds` на 0 для отключения или поэкспериментировав с другими значениями.

Либо же закомментируйте строку `suspend-node` в файле `/etc/pipewire/media-session.d/media-session.conf`.

Перезапустите службы `pipewire` и `pipewire-pulse` для применения изменений, или перезагрузитесь.

Если вы используете wireplumber, создайте новый файл для переопределения настроек по умолчанию:

    ~/.config/wireplumber/main.lua.d/51-disable-suspension.lua
    (или /etc/wireplumber/main.lua.d/51-disable-suspension.lua)

    table.insert (alsa_monitor.rules, {
      matches = {
        {
          -- Соответствует всем источникам.
          { "node.name", "matches", "alsa_input.*" },
        },
        {
          -- Соответствует всем выводам.
          { "node.name", "matches", "alsa_output.*" },
        },
      },
      apply_properties = {
        ["session.suspend-timeout-seconds"] = 0,  -- 0 выключает приостановку
      },
    })

Вместо полного отключения приостановки можно задать желаемое количество секунд задержки перед приостановкой.

#### Пропадание звука при проигрывании других потоков

Обычно проблему можно диагностировать в журнале пользовательской службы `pipewire-pulse.service`, в котором могут обнаружиться такие строки:

    pipewire-pulse[21740]: pulse-server 0x56009b9d5de0: [Nightly] UNDERFLOW channel:0 offset:370676 underrun:940

Согласно официальному гайду PipeWire по решению проблем, для решения проблемы при использовании pipewire-media-session измените следующие настройки:

    /etc/pipewire/media-session.d/alsa-monitor.conf (или ~/.config/pipewire/media-session.d/alsa-monitor.conf

    api.alsa.headroom = 1024

При использовании wireplumber:

    /etc/wireplumber/main.lua.d/50-alsa-config.lua (или ~/.config/wireplumber/main.lua.d/50-alsa-config.lua)

    apply_properties = {
        ["api.alsa.headroom"] = 1024,
    },

Если звук заикается из-за блокировки страниц в ядре или создаваемых планировщиком задержек, смотрите Gaming#Tweaking kernel parameters for response time consistency.

#### Искажённый звук

- Для микрофонов, найдите проблемную звуковую карту в `alsamixer` и уменьшите уровень "Mic Boost" или "Internal Mic Boost".
- Попробуйте уменьшить частоту дискретизации до `44100` (44.1 кГц), как описано в разделе #Изменение частоты дискретизации.

#### Различные проблемы после простоя

Если звук пропал или исказился после пробуждения системы после сна, возможно потребуется реинициализировать ALSA:

    # alsactl init

#### Большая задержка при использовании USB ЦАП (например, ЦАП Schiit)

Изменение частоты дискретизации или формата может помочь уменьшить задержку с некоторыми ЦАП, такими как Schiit Hel 2.[8] Используя правила соответствия в pipewire-media-session, мы можем установить свойства для устройств.[9]

Скопируйте стандартный файл настроек `/usr/share/pipewire/media-session.d/alsa-monitor.conf` в `/etc/pipewire/media-session.d/` или `~/.config/pipewire/media-session.d/`. Затем добавьте примерно такой блок правил:

    /etc/pipewire/media-session.d/alsa-monitor.conf (или ~/.config/pipewire/media-session.d/alsa-monitor.conf)

    ...
    rules = {
        ...
        {
            matches = [
                {
                    node.name = "alsa_output.имя-узла"
                }
            ]
            actions = {
                update-props = {
                    audio.format = "S24_3LE"
                    audio.rate = 96000
                    # Удваивайте это значение, пока не возникнут проблемы
                    api.alsa.period-size = 128
    ...

Узнать `alsa_output.имя-узла` можно с помощью `pw-top`.

Ваш ЦАП может поддерживать другой формат или частоту дискретизации. Можно проверить, что поддерживает ЦАП, через ALSA:

Сначала узнайте номер карты вашего ЦАП:

    $ aplay -l

    ...
    card 3: S2 [Schiit Hel 2], device 0: USB Audio [USB Audio]
      Subdevices: 0/1
      Subdevice #0: subdevice #0
    ...

В данном примере это карта 3. Получите все поддерживаемые частоты дискретизации и форматы:

    $ cat /proc/asound/cardX/streamX

    ...
    Playback:
      ...
      Interface 1
        Altset 1
        Format: S16_LE
        Channels: 2
        Endpoint: 0x05 (5 OUT) (ASYNC)
        Rates: 44100, 48000, 88200, 96000, 176400, 192000, 352800, 384000
        Data packet interval: 125 us
        Bits: 16
        ...
      Interface 1
        Altset 2
        Format: S24_3LE
        Channels: 2
        Endpoint: 0x05 (5 OUT) (ASYNC)
        Rates: 44100, 48000, 88200, 96000, 176400, 192000, 352800, 384000
        Data packet interval: 125 us
        Bits: 24
        ...
      Interface 1
        Altset 3
        Format: S32_LE
        Channels: 2
        Endpoint: 0x05 (5 OUT) (ASYNC)
        Rates: 44100, 48000, 88200, 96000, 176400, 192000, 352800, 384000
        Data packet interval: 125 us
        Bits: 32
        ...
    ...

В данном случае случае `S16_LE, S24_3LE, S32_LE` — это поддерживаемые форматы, а `44100, 48000, 88200, 96000, 176400, 192000, 352800, 384000` — поддерживаемые частоты дискретизации для всех форматов.

#### Нет звука от USB ЦАП до 30% громкости

Некоторые USB ЦАП не выдают звук, если громкость ниже определённой [10]. Обычно это около 25-30%, что приводит к некомфортному начальному уровню громкости и невозможности поддерживать низкий уровень громкости. Решением является игнорирование аппаратного управления громкостью путём установки `["api.alsa.soft-mixer"]` в `true`.

Если используется wireplumber, можно обновить конфигурацию `/usr/share/wireplumber/main.lua.d/50-alsa-config.lua`, добавив туда фрагмент с помощью `table.insert`:

    ~/.config/wireplumber/main.lua.d/51-volume-fix.lua

    table.insert (alsa_monitor.rules, {
        matches = {
          {
            -- Это правило охватывает все карты.
            { "device.name", "matches", "alsa_card.*" },
          },
        },
        -- Применение свойств в найденным объектам.
        apply_properties = {
          -- Не использовать аппаратный микшер для управления громкостью.
          -- Использовать только программную громкость. Микшер по-прежнему
          -- используется для отключения неиспользуемых путей в зависимости
          -- от выбранного порта.
          ["api.alsa.soft-mixer"] = true,
        }
      })

Затем перезапустите pipewire. Установите мастер-громкость в `alsamixer`, а затем сохраните настройки с помощью `# alsactl store`. Теперь микшер громкости должен работать без проблем.

#### Аудио в режиме реального времени не работает

Если в статусе пользовательского юнита `pipewire.service` есть ошибка `RTKit error: org.freedesktop.DBus.Error.AccessDenied`, это означает, что демон pipewire не получил приоритет реального времени. Смотрите [11] для более подробной информации.

#### Одновременный вывод на несколько выходов на одной звуковой карте

Создайте копию файла `/usr/share/alsa-card-profile/mixer/profile-sets/default.conf`, чтобы изменения были постоянными. В нём мы определим профиль, объединяющий два стандартных отображения для аналогового и HDMI выводов.

    /usr/share/alsa-card-profile/mixer/profile-sets/multiple.conf

    [General]
    auto-profiles = no

    [Mapping analog-stereo]
    device-strings = front:%f
    channel-map = left,right
    paths-output = analog-output analog-output-lineout analog-output-speaker analog-output-headphones analog-output-headphones-2
    paths-input = analog-input-front-mic analog-input-rear-mic analog-input-internal-mic analog-input-dock-mic analog-input analog-input-mic analog-input-linein analog-input-aux analog-input-video analog-input-tvtuner analog-input-fm analog-input-mic-line analog-input-headphone-mic analog-input-headset-mic
    priority = 15

    [Mapping hdmi-stereo]
    description = Digital Stereo (HDMI)
    device-strings = hdmi:%f
    paths-output = hdmi-output-0
    channel-map = left,right
    priority = 9
    direction = output

    [Profile multiple]
    description = Analog Stereo Duplex + Digital Stereo (HDMI) Output
    output-mappings = analog-stereo hdmi-stereo
    input-mappings = analog-stereo

Теперь настроим pipewire-media-session на использование нового профиля карты для нужных устройств. Идентификаторы можно узнать с помощью `$ pw-cli dump device`.

    /etc/pipewire/media-session.d/alsa-monitor.conf

    rules = [
        {
            matches = [ { alsa.card_name = "HDA Intel PCH" } ]
            actions = {
                update-props = {
                    api.alsa.use-acp = true
                    device.profile-set = "multiple.conf"
                    device.profile = "multiple"
                    api.acp.auto-profile = false
                    api.acp.auto-port = false
                }
            }
        }
    ]

#### Нет звуков уведомлений в Discord

Это может быть вызвано слишком низким значением min.quantum, попробуйте установить его на более чем 700. Можно сделать переопределение специально для Discord, добавив следующее правило в раздел pulse.rules в pipewire-pulse.conf.

    /etc/pipewire/pipewire-pulse.conf (или ~/.config/pipewire/pipewire-pulse.conf)

    ...
    pulse.rules = [
      ...
        {
            # Discord notification sounds fix
            matches = [ { application.process.binary = "Discord" } ]
            actions = {
                update-props = {
                    pulse.min.quantum      = 1024/48000     # 21ms
                }
            }
        }
    ...

### Видео

#### OBS ничего не показывает, даже если спрашивает окно/экран

Если вы уверены, что у вас установлен xdg-desktop-portal, а также xdg-desktop-portal-gtk или xdg-desktop-portal-kde, проверьте статус этих демонов.

В OBS, если всё работает, в стандартном выводе должно быть что-то такое:

    ...
    info: [pipewire] desktop selected, setting up screencast
    info: [pipewire] created stream 0x5632d7456850
    info: [pipewire] playing stream…

Для многомониторных установок пакет slurp позволит захватить все экраны.

## Смотрите также

- Wiki — PipeWire вики на Freedesktop GitLab
- Pipewire Update Blog Post — Пост в блоге от января 2018 с описанием состояния разработки на тот момент
- PipeWire Late Summer Update 2020 — Пост в блоге от сентября 2020

Category:

- Multimedia (Русский)