Elmord's Magic Valley

Computers, languages, and computer languages. Às vezes em Português, sometimes in English.

Posts com a tag: audio

Fixing audio device priorities in PulseAudio

2023-10-31 16:45 +0000. Tags: comp, unix, audio, in-english

Ever since I started using my current laptop (a ThinkPad E14 Gen 4, currently running Debian 12), I have had the following issue: when I connect headphones to the laptop, the audio goes to the headphones as expected, but when I disconnect the headphones, the audio goes to the HDMI output instead of going back to the laptop speakers. As it happens, my external monitor (an Eizo FlexScan EV2360) has audio output, but it’s pretty low-quality and I don’t use it. But PulseAudio (or is it ALSA?) assigns higher priority to the HDMI outputs, so as soon as the headphones are disconnected, it looks for the available device with the highest priority and picks the HDMI one. You can see the priority of each audio sink (output) by using pactl:

$ pactl list sinks | grep priority:
        [Out] HDMI3: HDMI / DisplayPort 3 Output (type: HDMI, priority: 700, not available)
        [Out] HDMI2: HDMI / DisplayPort 2 Output (type: HDMI, priority: 600, not available)
        [Out] HDMI1: HDMI / DisplayPort 1 Output (type: HDMI, priority: 500, available)
        [Out] Speaker: Speaker (type: Speaker, priority: 100, availability unknown)
        [Out] Headphones: Headphones (type: Headphones, priority: 200, not available)

In this case, the HDMI1 output is available and has priority 500, whereas the speakers have priority 100.

The solution is to change the HDMI priorities. The problem is where to set this. In my particular case, this was set in /usr/share/alsa/ucm2/Intel/sof-hda-dsp/Hdmi.conf (included from /usr/share/alsa/ucm2/Intel/sof-hda-dsp/Hdmi.conf), which looks like this:

# Use case Configuration for sof-hda-dsp

Include.hdmi.File "/codecs/hda/hdmi.conf"

If.hdmi1 {
    Condition { Type AlwaysTrue }
    True.Macro.hdmi1.HDMI {
        Number 1
        Device 3
        Priority 500
    }
}

If.hdmi2 {
    Condition { Type AlwaysTrue }
    True.Macro.hdmi1.HDMI {
        Number 2
        Device 4
        Priority 600
    }
}

If.hdmi3 {
    Condition { Type AlwaysTrue }
    True.Macro.hdmi1.HDMI {
        Number 3
        Device 5
        Priority 700
    }
}

I just changed the values 500, 600, 700 manually to 50, 60, 70 in this file. This is not a very good solution because this file belongs to the alsa-ucm-conf package and will get overridden whenever I upgrade it, but since this is Debian stable, I don’t have to worry about this any time soon. There is probably a better way to override these values, but I don’t know enough about either ALSA or PulseAudio (and I’m not particularly keen on learning more, unless my fellow readers know and want to leave a helpful comment), so this will have to do for now.

* * *

Another recurring issue is getting Bluetooth headphones to become the selected default device when they are connected. It seems that Bluetooth devices get created dynamically with a bunch of hardcoded priorities (and worse, sometimes I get a device with priority 40 and sometimes 0, I don’t know why). But it also seems that the priorities just don’t have any effect on the selection of the Bluetooth device. I was having a curious issue where some programs would pick the headphones and some wouldn’t, and the default device would remain unchanged (which among other things meant that my multimedia keys set the volume of the wrong device). What seems to be going on is that PulseAudio remembered the associations of certain programs (e.g., VLC) with the headphones, but only for those programs where I had at some point manually changed the output sink manually via pavucontrol. The solution here was two-step:

  1. In /etc/pulse/default.pa, replace the line that says:

    load-module module-stream-restore

    with:

    load-module module-stream-restore restore_device=false

    This will make PulseAudio not try to remember associations between specific programs and devices. From now on, all programs get the default sources/sinks when they connect to PulseAudio.

  2. Set the default sink manually to the Bluetooth headphones. Use pactl list sinks to figure out the sink name:

    $ pactl list sinks  | grep Name:
            Name: alsa_output.pci-0000_00_1f.3-platform-skl_hda_dsp_generic.HiFi__hw_sofhdadsp_5__sink
            Name: alsa_output.pci-0000_00_1f.3-platform-skl_hda_dsp_generic.HiFi__hw_sofhdadsp_4__sink
            Name: alsa_output.pci-0000_00_1f.3-platform-skl_hda_dsp_generic.HiFi__hw_sofhdadsp_3__sink
            Name: alsa_output.pci-0000_00_1f.3-platform-skl_hda_dsp_generic.HiFi__hw_sofhdadsp__sink
            Name: bluez_sink.C8_7B_23_9F_B3_21.a2dp_sink

    Then set it (replacing with the appropriate device name):

    pactl set-default-sink bluez_sink.C8_7B_23_9F_B3_21.a2dp_sink

The result of this is that PulseAudio will remember the headphones as the default sink device when they are present, but will revert to the built-in sound card when not.

I still don’t know why this works even though the Bluetooth device’s priority is lower than the built-in sound card. (There is a PulseAudio module called module-switch-on-connect that provides behavior like this, but it is not enabled on my system, and it does not show up as loaded in the pactl list output.) But It Works For Me™.

Comentários / Comments

Gravando áudio e eliminando ruído com o SoX

2013-04-26 19:52 -0300. Tags: comp, unix, audio, mundane, em-portugues

O SoX (SOund eXchange; pacotes sox e libsox-fmt-all no Debian) é uma biblioteca e um programa de linha de comando que permitem converter entre diversos formatos de arquivo de áudio, opcionalmente aplicando filtros. A sintaxe básica do comando sox é:

sox [opções-globais]
    [opções-de-formato] entrada1
    [[opções-de-formato] entrada2 ...]
    [opções-de-formato] saída
    [filtros ...]

Por exemplo, para gravar do microfone (usando ALSA) em um arquivo WAV:

sox -t alsa default -t wav blabla.wav

(Use Control-C para terminar a gravação. Tecnicamente o -t wav pode ser omitido, já que o sox é capaz de deduzir o formato do arquivo pela extensão.)

Um par de filtros particularmente interessante é o noiseprof/noisered, que permitem eliminar ou reduzir ruído constante de fundo. Isso é feito em duas etapas. Primeiro, executa-se o sox com o filtro noiseprof [profile.txt] sobre uma "amostra de silêncio", i.e., um trecho de áudio que consista apenas do ruído de fundo, de maneira a produzir um profile de ruído. Você pode capturar o "silêncio" do microfone ou de algum outro arquivo que consista apenas de silêncio (a opção --null pode ser usada no lugar do arquivo de saída, já que estamos interessados apenas no profile de ruído):

sox -t alsa default --null noiseprof profile.txt

sox algum-arquivo-que-consista-apenas-de-silêncio.wav --null noiseprof profile.txt

Alternativamente, você pode selecionar um trecho de um arquivo com o filtro trim início [duração] e usá-lo como fonte de silêncio:

# Seleciona o intervalo de de 1s até 2.5s. Aqui usamos '-t alsa default' como
# saída para podermos ouvir se o trecho selecionado de fato corresponde a "silêncio".

sox entrada.wav -t alsa default trim 1 1.5 noiseprof profile.txt

Se o nome do arquivo de profile for omitido, o sox escreve o profile na stdout.

Gerado o profile de ruído, podemos usar o filtro noisered [profile.txt [quantidade]] para remover o ruído do arquivo completo. quantidade é um número entre 0 e 1 indicando a quantidade de ruído que deve ser removida. Quanto maior o número, mais ruído será removido – e mais não-ruído também. Experimente com números pequenos (e.g., 0, 0.05, 0.1, etc.) primeiro.

sox entrada.wav saída.wav noisered profile.txt 0.05

Se você tem um microfone problemático, você pode querer guardar o arquivo de profile para usos futuros (assumindo que o padrão de ruído produzido seja sempre o mesmo).

Se o arquivo de entrada para o noisered não for especificado ou for -, o sox lê o profile da stdin. Assim, você pode combinar o profiling e a redução em um pipeline:

sox entrada.wav --null trim 0 1 noiseprof | sox entrada.wav saída.wav noisered - 0.05

Para mais informações, consulte a manpage do sox.

2 comentários / comments

Main menu

Recent posts

Recent comments

Tags

em-portugues (213) comp (148) prog (71) in-english (62) life (49) unix (38) pldesign (37) lang (32) random (28) about (28) mind (26) lisp (25) fenius (22) mundane (22) web (20) ramble (18) img (13) rant (12) hel (12) scheme (10) privacy (10) freedom (8) esperanto (7) music (7) lash (7) bash (7) academia (7) copyright (7) home (6) mestrado (6) shell (6) android (5) conlang (5) misc (5) emacs (5) latex (4) editor (4) etymology (4) php (4) worldly (4) book (4) politics (4) network (3) c (3) tour-de-scheme (3) security (3) kbd (3) film (3) wrong (3) cook (2) treta (2) poem (2) physics (2) x11 (2) audio (2) comic (2) lows (2) llvm (2) wm (2) philosophy (2) perl (1) wayland (1) ai (1) german (1) en-esperanto (1) golang (1) translation (1) kindle (1) pointless (1) old-chinese (1)

Elsewhere

Quod vide


Copyright © 2010-2024 Vítor De Araújo
O conteúdo deste blog, a menos que de outra forma especificado, pode ser utilizado segundo os termos da licença Creative Commons Attribution-NonCommercial-ShareAlike 4.0 International.

Powered by Blognir.