Jąkanie zlewu PulseAudio

12

Zainstalowałem Raspbian na moim Pi i skonfigurowałem zlew PulseAudio z zamiarem przesyłania strumieniowego całego dźwięku z mojego pulpitu do Pi, napędzając głośniki.

Postępowałem zgodnie z tym ładnym opisem: http://www.raspberrypi.org/phpBB3/viewtopic.php?f=38&t=11124

Początkowo wydawało się, że działa bez problemu. Jednak dźwięk wysyłany z pulpitu ciągle się zacina na Pi, tak jakby istniały ciągłe niedopełnienia bufora, a pomiędzy nimi brakowało tylko kilku próbek.

Cały dzień szukałem przyczyny, ale bezskutecznie. Podstawowa konfiguracja to:

  • przewodowe połączenie LAN
  • najnowsze Raspbian pi (26 września 2013) z najnowszymi aktualizacjami oprogramowania
  • PulseAudio 2.0 po obu stronach (komputer Ubuntu)
  • Odtwarzanie przez mplayer, totem, ffplay
  • transmisja sieciowa przez moduł-natywny-protokół-tcp

Oto, co próbowałem:

  • Odtwarzanie dźwięku bezpośrednio na Pi działa idealnie.
  • Przesyłanie strumieniowe do innych komputerów (stacjonarnych) działa dobrze.
  • Wysyłanie dźwięku za pomocą bezpośredniego połączenia (określając $ PULSE_SERVER) działa całkiem dobrze przy bardzo niewielkim jąkaniu, ale nadal jest podatne na problem-2 (patrz poniżej)
  • Wysyłanie dźwięku za pośrednictwem pulpitu Tunelowanie PulseAudio zapewnia ciągłe jąkanie
  • Zwiększenie priorytetów / planowania w czasie rzeczywistym ... nie pomogło
  • Naprawienie częstotliwości próbkowania do 48 kHz ... nie pomogło
  • Ustawienie algorytmu ponownego próbkowania na „trywialny” ... nie pomogło
  • Dostosowanie domyślnych fragmentów / rozmiaru fragmentów ... nie pomogło
  • Nie mogę znaleźć żadnych oznak problemu w dziennikach PulseAudio (pokazanych od momentu rozpoczęcia odtwarzania):

    D: [alsa-sink] protocol-native.c: Requesting rewind due to end of underrun.
    D: [alsa-sink] sink-input.c: Requesting rewind due to uncorking
    D: [pulseaudio] sink.c: Suspend cause of sink alsa_output.platform-bcm2835_AUD0.0.analog-stereo is 0x0000, resuming
    I: [alsa-sink] alsa-sink.c: Trying resume...
    I: [alsa-sink] alsa-util.c: cannot disable ALSA period wakeups
    D: [alsa-sink] alsa-util.c: Maximum hw buffer size is 341 ms
    D: [alsa-sink] alsa-util.c: Set buffer size first (to 16384 samples),  period size second (to 16384 samples).
    I: [alsa-sink] alsa-util.c: ALSA period wakeups were not disabled
    D: [alsa-sink] alsa-sink.c: Latency set to 25.00ms
    D: [alsa-sink] alsa-sink.c: hwbuf_unused=60736
    D: [alsa-sink] alsa-sink.c: setting avail_min=15665
    I: [alsa-sink] alsa-sink.c: Time scheduling watermark is 15.00ms
    I: [alsa-sink] alsa-sink.c: Resumed successfully...
    I: [alsa-sink] alsa-sink.c: Starting playback.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [pulseaudio] module-suspend-on-idle.c: Sink alsa_output.platform-bcm2835_AUD0.0.analog-stereo becomes busy.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] alsa-sink.c: Cutting sleep time for the initial iterations by half.
    D: [alsa-sink] ratelimit.c: 115 events suppressed
    D: [alsa-sink] alsa-sink.c: Wakeup from ALSA!
    ... no more output, but stuttering continues ...
    

Problem 2: jak powiedziano powyżej, mogę uzyskać całkiem niezły dźwięk z bezpośrednim połączeniem. Jednak po kilku przeskokach w strumieniu (przy użyciu mplayera) serwer PulseAudio zawiesza się i nie odtwarza żadnego dźwięku. Czasami można go przywrócić, uruchamiając ponownie mplayera. Czasami zawiesza się tak źle, że należy ponownie uruchomić PulseAudio. Czasami nawet zawiesza się, gdy zmieniam tylko poziom głośności.

Według dokumentów PulseAudio zaletą bezpośredniego połączenia nad tunelowanym połączeniem jest lepsza kontrola buforowania, co wydaje się wskazywać, dlaczego otrzymuję dobry dźwięk z bezpośrednim połączeniem: http://www.freedesktop.org/wiki/Software / PulseAudio / Documentation / User / Network /

Nie mam już pomysłów. Co może powodować jąkanie i problem 2? Doceniony zostanie również pomysł, jak kontynuować debugowanie.

farindk
źródło
Jak bezpośrednio odtworzyłeś dźwięk? Nie miałem problemów z odtwarzaniem, ale paplay jąka się i echa strasznie.
John La Rooy
Użyłem mplayera, totemu, madplay, ... Ale fakt, że różni gracze zachowują się inaczej, potwierdza moje przypuszczenie, że to problem oprogramowania z buforowaniem danych. Niektórzy gracze wypychają więcej danych w czasie rzeczywistym niż inni.
farindk
Mam problem z odtwarzaniem fal sinusoidalnych . Myślę, że muszę to rozwiązać, zanim spróbuję przesyłać strumieniowo przez sieć LAN.
John La Rooy

Odpowiedzi:

6

tsched_buffer_sizei tsched_buffer_watermarkbyły ustawienia, które sprawiły, że to działało dla mnie.

Uruchamiam PulseAudio jako instancję systemu, więc konfiguracja jest włączona /etc/pulse/system.pa. Jeśli zamiast tego używasz instancji sesji, konfiguracja będzie dostępna /etc/pulse/default.pa.

To jest domyślne:

### Automatically load driver modules depending on the hardware available
.ifexists module-udev-detect.so
load-module module-udev-detect
.else
### Use the static hardware detection module (for systems that lack udev/hal  support)
load-module module-detect
.endif

Zastąpiłem to: (tzn. Skomentowałem)

### Automatically load driver modules depending on the hardware available
.ifexists module-udev-detect.so
#load-module module-udev-detect
.else
### Use the static hardware detection module (for systems that lack udev/hal  support)
#load-module module-detect
.endif

Następnie dodałem następujący wiersz:

load-module module-alsa-card device_id=0 tsched=true tsched_buffer_size=1048576 tsched_buffer_watermark=262144

Zobacz http://www.freedesktop.org/wiki/Software/PulseAudio/Documentation/User/Modules/#index6h3

Phil
źródło
Słuszna uwaga. Próbowałem, ale to nie pomogło. Nawet przy znacznie większych rozmiarach buforów. Wysyłanie dźwięku przez bezpośrednie połączenie poprzez ustawienie PULSE_SERVER na Pi daje czysty dźwięk, ale sama zmiana głośności ostatecznie zawiesi połączenie. Dźwięk przez tunelowanie nadal powoduje jąkanie. Domyślam się, że to naprawdę problem z PulseAudio, ponieważ przy tak dużych rozmiarach buforów (użyłem 4 MB), należy zauważyć, że dźwięk jest dekodowany znacznie wcześniej na początku pliku. Ale to nie jest. Więc musi być coś spowalniającego napełnianie.
farindk,
Występują takie same problemy. W moim szczególnym przypadku PULSE_SERVER + mplayer działa jak urok, podczas gdy PULSE_SERVER + clementine (który, jak sądzę, używa gstreamera) jąka się strasznie. Masz pojęcie, co różni się między nimi?
Jonathan Protzenko
@Protzenko: Domyślam się, że nie patrząc na żadne źródło, mplayer może przesyłać dane do momentu zablokowania PulseAudio, podczas gdy gstreamer może wysyłać dane taktowane referencjami w czasie rzeczywistym. Oznaczałoby to, że bufory są znacznie bardziej zapełnione w pierwszym przypadku, a zatem występuje większe opóźnienie.
farindk
Widzę ten sam problem PULSE_SERVER + ffmpeg grzywna, PULSE_SERVER + migawki mpd i ukryte
niedomówienia
3

Najważniejsze jest to, że musisz użyć module-tunnel-sink-new, ale musisz również wprowadzić kilka innych zmian, aby uzyskać bezproblemowy dźwięk sieciowy na Raspberry Pi 1.

  1. Uruchom pulseaudio na Raspberry Pi z priorytetem w czasie rzeczywistym:
pulseaudio --start --high-priority=yes --realtime=yes

Użyjmy terminu nadawca, aby wskazać komputer, który wysyła strumień do twojego malinowego pi.

  1. Ustaw default-fragmentsi default-fragment-size-msecna daemon.confco nadawcy do tych wartości:
default-fragments = 8
default-fragment-size-msec = 12
  1. Użyj module-tunnel-sink-new, wydając to polecenie u nadawcy (zakładając, że nazwa hosta twojego malinowego pi to RP1 i masz mDNS pracujący w twojej sieci lokalnej. W przeciwnym razie, po prostu użyj adresu IP twojego malinowego pi).
pactl load-module module-tunnel-sink-new server=RP1.local

Dzięki tym ustawieniom otrzymuję dźwięk bez zacinania się od raspberrypi 1 przez sieć bezprzewodową działającą z prędkością 54 Mb / s (w mojej konfiguracji nadawca używa sieci Ethernet, a RP1 używa sieci WLAN). W rzeczywistości działa nawet wtedy, gdy zarówno nadawca, jak i raspberrypi używają wlan, przynajmniej jeśli nie ma innych urządzeń w sieci bezprzewodowej.

Hans Ekbrand
źródło
Jak dotąd działa świetnie. Odkryłem, że dla mojego Pi3 (z nieco nowszym debianem / oprogramowaniem) musiałem zmienić coś innego, aby można było wybrać ustawienia „fragmentów domyślnych”. (mianowicie coś ustawienia tsched=0, patrz wiki.archlinux.org/index.php/PulseAudio/… )
rien333
Jeśli nadal występuje jąkanie, arch wiki zaleca również przejście na protokół przesyłania strumieniowego rtp
rien333
1

sprawdziłeś tę stronę:

http://manpages.ubuntu.com/manpages/lucid/man5/pulse-daemon.conf.5.html

DOMYŚLNE USTAWIENIA FRAGMENTU

   Some hardware drivers  require  the  hardware  playback  buffer  to  be
   subdivided  into  several  fragments.  It  is  possible to change these
   buffer metrics for machines with high  scheduling  latencies.  Not  all
   possible  values  that  may  be  configured  here  are available in all
   hardware. The driver will to find the nearest setting supported. Modern
   drivers that support timer-based scheduling ignore these options.

   default-fragments= The default number of fragments. Defaults to 4.

   default-fragment-size-msec=The  duration of a single fragment. Defaults
   to 25ms (i.e. the total buffer is thus 100ms long).
Alter Schwede
źródło
Tak, próbowałem tego, ale to nie pomogło. Jak wspomniałem, odtwarzanie dźwięku na samym urządzeniu działa dobrze. Zakładam, że jest to problem protokołu sieciowego z tunelowaniem PulseAudio. Nawet protokół bezpośredniego połączenia działa dobrze. Teraz zmieniłem na prosty sprzęt do przesyłania strumieniowego Bluetooth, który jest niezawodny i używa RPi do innych celów.
farindk
1

Aby pozbyć się jąkania lub problemów z przekroczeniem limitu czasu, spróbuj obniżyć wersję oprogramowania sprzętowego:

sudo rpi-update eeb2e51c3e08cd5efa4246aa8dc54a09b25ada12
użytkownik13034
źródło
1
OSTRZEŻENIE Bądź świadomy tego, co rpi-updatew ten sposób może zrobić z twoim systemem.
earthmeLon
@earthmeLon możesz przynajmniej podać referencje lub spróbować poinformować nas, co rpi-updatew ten sposób może zrobić z naszymi systemami ...
user11171
Pamiętaj, aby zapoznać się z instrukcją i zrobić kilka badań, aby zrozumieć, w jaki sposób wpływa to na system i wszelkie potencjalne zagrożenia.
earthmeLon
0

Zrozumiałem, że ten problem może być związany z wersją jądra. Po aktualizacji z 3.6.11 do 3.12.0 ciągle otrzymywałem te błędy. Powrót do wersji 3.6.11 rozwiązał dla mnie problem.

Manuel Faux
źródło
0

Czytałem tę stronę kilka razy ... Byłem również sfrustrowany jąkaniem się kombinacji RaspberryPi-pulseaudio-network. Szukałem jeszcze trochę i znalazłem stronę, na której znalazłem część rozwiązania:

=> Wyłącz moduł suspend-on-idle w default.pa (lub system.pa).

Oto jąkanie zniknęło!

Teraz jedynym problemem jest to, że po pewnym czasie (10 do 20 sekund) odtwarzanie się zawiesza: - /

Jakieś sugestie?

Jørn Christensen
źródło