Pourquoi l'utilisation de H264 dans les pipelines émetteur / récepteur introduit retard tout simplement énorme?

StackOverflow https://stackoverflow.com/questions/2893407

Question

Lorsque je tente de créer pipeline que les utilisations H264 à la vidéo d'émission, je reçois un certain retard énorme, jusqu'à 10 secondes à la vidéo de transmission de ma machine à ... ma machine! Ceci est inacceptable pour mes objectifs et je voudrais consulter StackOverflow sur ce que je (ou quelqu'un d'autre) ne va pas.

Je pris les pipelines de la page de documentation gstrtpbin et les légèrement modifiés pour utiliser Speex:

Ce pipeline est l'expéditeur:     #! / Bin / sh

gst-launch -v gstrtpbin name=rtpbin \
        v4l2src ! ffmpegcolorspace ! ffenc_h263 ! rtph263ppay ! rtpbin.send_rtp_sink_0 \
                  rtpbin.send_rtp_src_0 ! udpsink host=127.0.0.1 port=5000                            \
                  rtpbin.send_rtcp_src_0 ! udpsink host=127.0.0.1 port=5001 sync=false async=false    \
                  udpsrc port=5005 ! rtpbin.recv_rtcp_sink_0                           \
        pulsesrc ! audioconvert ! audioresample  ! audio/x-raw-int,rate=16000 !    \
                  speexenc bitrate=16000 ! rtpspeexpay ! rtpbin.send_rtp_sink_1                   \
                  rtpbin.send_rtp_src_1 ! udpsink host=127.0.0.1 port=5002                            \
                  rtpbin.send_rtcp_src_1 ! udpsink host=127.0.0.1 port=5003 sync=false async=false    \
                  udpsrc port=5007 ! rtpbin.recv_rtcp_sink_1

pipeline récepteur:

! / Bin / sh

gst-launch -v\
    gstrtpbin name=rtpbin                                          \
    udpsrc caps="application/x-rtp,media=(string)video, clock-rate=(int)90000, encoding-name=(string)H263-1998" \
            port=5000 ! rtpbin.recv_rtp_sink_0                                \
        rtpbin. ! rtph263pdepay ! ffdec_h263 ! xvimagesink                    \
     udpsrc port=5001 ! rtpbin.recv_rtcp_sink_0                               \
     rtpbin.send_rtcp_src_0 ! udpsink port=5005 sync=false async=false        \
    udpsrc caps="application/x-rtp,media=(string)audio, clock-rate=(int)16000, encoding-name=(string)SPEEX, encoding-params=(string)1, payload=(int)110" \
            port=5002 ! rtpbin.recv_rtp_sink_1                                \
        rtpbin. ! rtpspeexdepay ! speexdec ! audioresample ! audioconvert ! alsasink \
     udpsrc port=5003 ! rtpbin.recv_rtcp_sink_1                               \
     rtpbin.send_rtcp_src_1 ! udpsink host=127.0.0.1 port=5007 sync=false async=false

Ces pipelines, une combinaison de H263 et Speex, assez de travail de fin. Je mes doigts près de claquer la caméra et micropohne et je vois son mouvement et entendre en même temps.

Alors j'ai changé les pipelines à utiliser H264 le long du chemin vidéo.

L'expéditeur devient:     #! / Bin / sh

gst-launch -v gstrtpbin name=rtpbin \
        v4l2src ! ffmpegcolorspace ! x264enc bitrate=300 ! rtph264pay ! rtpbin.send_rtp_sink_0 \
                  rtpbin.send_rtp_src_0 ! udpsink host=127.0.0.1 port=5000                            \
                  rtpbin.send_rtcp_src_0 ! udpsink host=127.0.0.1 port=5001 sync=false async=false    \
                  udpsrc port=5005 ! rtpbin.recv_rtcp_sink_0                           \
        pulsesrc ! audioconvert ! audioresample  ! audio/x-raw-int,rate=16000 !    \
                  speexenc bitrate=16000 ! rtpspeexpay ! rtpbin.send_rtp_sink_1                   \
                  rtpbin.send_rtp_src_1 ! udpsink host=127.0.0.1 port=5002                            \
                  rtpbin.send_rtcp_src_1 ! udpsink host=127.0.0.1 port=5003 sync=false async=false    \
                  udpsrc port=5007 ! rtpbin.recv_rtcp_sink_1

Et le récepteur devient:     #! / Bin / sh

gst-launch -v\
    gstrtpbin name=rtpbin                                          \
    udpsrc caps="application/x-rtp,media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264" \
            port=5000 ! rtpbin.recv_rtp_sink_0                                \
        rtpbin. ! rtph264depay ! ffdec_h264 ! xvimagesink                    \
     udpsrc port=5001 ! rtpbin.recv_rtcp_sink_0                               \
     rtpbin.send_rtcp_src_0 ! udpsink port=5005 sync=false async=false        \
    udpsrc caps="application/x-rtp,media=(string)audio, clock-rate=(int)16000, encoding-name=(string)SPEEX, encoding-params=(string)1, payload=(int)110" \
            port=5002 ! rtpbin.recv_rtp_sink_1                                \
        rtpbin. ! rtpspeexdepay ! speexdec ! audioresample ! audioconvert ! alsasink \
     udpsrc port=5003 ! rtpbin.recv_rtcp_sink_1                               \
     rtpbin.send_rtcp_src_1 ! udpsink host=127.0.0.1 port=5007 sync=false async=false

est ce qui se passe sous Ubuntu 10.04. Je ne l'ai pas remarqué ces retards énormes sur Ubuntu 9.04 -. Les retards qu'il y avait dans la gamme 2-3 secondes, AFAIR

Était-ce utile?

La solution

Avec l'aide de la présélection "Sharktooth" en # x264 sur Freenode, je trouve que la version git des supports gst-plugins-laid "zéro latence".

http://cgit.freedesktop.org/gstreamer/gst-plugins-ugly

Je peaufiné votre exemple ensemble « x264enc pass = qual quantificateur = 20 = ZeroLatency air », et le temps d'attente semble rester à 0,7 - 0,9 secondes. Je ne peux pas comprendre comment l'obtenir plus bas.

Autres conseils

Quelque chose là-bas est mise en mémoire tampon, très probablement l'encodeur. Plus les données qu'il doit travailler avec la compression plus efficace, il peut atteindre. Je ne suis pas au courant de ce codeur, mais il est généralement un réglage de la quantité de mémoire tampon.

x264 par défaut tampons d'entrée pour avoir plus de données à travailler. L'augmentation du délai d'Ubuntu 10.04 est le plus probablement parce qu'il était coincé à une ancienne version de x264, avant l'introduction de --mbtree et --rc-préanalyse.

Cette page de Mewiki vous pouvez voir comment calculer le temps d'attente, en nombre de cadres, et ce qui suit, sur ce que vous devez d'abord désactiver pour réduire le temps d'attente:

  

La réduction de la latence x264 est possible, mais réduit la qualité. Si vous voulez pas de latence, réglez --tune ZeroLatency. Si vous pouvez gérer une petite latence (moins de 1 seconde), il est accordage vaut bien les options pour permettre cela. Voici une série d'étapes que vous pouvez suivre pour réduire progressivement la latence. Arrêtez lorsque votre temps d'attente est assez faible:

     
      
  1. commencant par défaut
  2.   
  3. kill-préanalyse
  4.   
  5. Chute-rc Lookahead pas moins de ~ 10
  6.   
  7. fils tomber à une valeur inférieure (c.-à-dire 6 au lieu de 12)
  8.   
  9. Utilisez des fils coupé en tranches
  10.   
  11. Désactiver rc-préanalyse
  12.   
  13. Désactiver b-frames
  14.   
  15. Maintenant, vous êtes --tune ZeroLatency
  16.   

Alors, vous devriez d'abord essayer d'ajouter quelque chose à votre commande en ligne comme

synchronisation = 0 préanalyse, rc = 10-préanalyse (je ne suis pas sûr de la mise en forme de la ligne de commande dans l'application)

Cela devrait se raser la plupart du temps d'attente, à un faible coût d'efficacité de compression. Si vous avez plusieurs noyaux (un quadcore avec HT, par exemple), il peut aussi être le numéro vaut do 4., à un coût peu de vitesse.

TUNE = ZeroLatency, selon Sharktooth conseils, si cela ne suffit pas encore.

En savoir plus sur le sujet: http://x264dev.multimedia.cx/archives/249

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top