Changes between Version 10 and Version 11 of FAQ

Oct 7, 2007 7:59:15 AM (11 years ago)

About latency


  • FAQ

    v10 v11  
    143143On typical PC, normally it's the sound device and jitter buffer that contribute the most latency, so this article will try to present how to optimize these settings. Codec latency is determined by the codec algorithm and its {{{ptime}}}, but normally it shouldn't add too much latency; maybe around 20 to 30 ms. The default resampling algorithm in PJMEDIA adds about 5 ms latency. I have no idea about AEC latency. Network latency, well, we can't do anything about it. 
     145==== Choosing lower audio frame length ==== 
     147Ticket #393 (release 0.7.1) added a new media setting {{{pjsua_media_config.audio_frame_ptime}}}, or in older PJSUA-LIB, this setting is hard-coded in {{{PTIME}}} macro in {{{pjsua_media.c}}}. This setting specifies the length of audio frame in milliseconds, to be set to both the sound device and to the conference bridge. 
     149The previous default value is 20 milliseconds, while the default value is now set to 10 milliseconds. Changing this value from 20 to 10 milliseconds will reduce sound device latency by about 100 milliseconds and end-to-end audio latency by about 200 milliseconds. 
     151==== Choose PJMEDIA_SOUND_BUFFER_COUNT carefully ==== 
     153The {{{PJMEDIA_SOUND_BUFFER_COUNT}}} in {{{pjmedia/config.h}}} specifies the number of audio frames in the conference bridge buffer. Larger number is better for sound stability and to accommodate sound devices that are unable to send frames in timely manner, however it would probably cause more audio delay. 
     155The default value was 16, and this has been changed to 6 by ticket #394 (release 0.7.1). 
     157==== Optimizing Sound Device Latency ==== 
     159On Windows with !PortAudio backend (the default sound driver backend), with the default setting !DirectSound does have lower latency than WMME, but !DirectSound has more erratic timing. This bad timing causes additional delay in the processing of packets in the jitter buffer; there can be up to 150ms delay between packet arrival time and the time when the frame is actually picked up from the jitter buffer, regardless of jitter buffer setting. 
     161Release 0.7.1 has been tuned to provide better latency, with providing these settings: 
     162 - ticket #384 gives the ability for application to choose !DirectSound over WMME. Default is no 
     163 - ticket #395 adds a configuration to control the maximum buffer latency for WMME, with default value is 60 (milliseconds). For similar setting for !DirectSound, application needs to set {{{PA_MIN_LATENCY_MSEC}}} environment variable. 
     165With default WMME backend and 60 milliseconds buffering, application should have much better latency than with using !DirectSound. 
    145167==== Optimizing Jitter Buffer Latency ==== 
    149171 - '''jb_max_pre''' - Jitter buffer maximum prefetch delay in msec. With the default settings, it will use the hard-coded value in {{{stream.c}}}, that is '''240''' ms. 
    150172 - '''jb_max''' - Set maximum delay that can be accomodated by the jitter buffer msec. The default value is also hard-coded  in {{{stream.c}}}, that is '''360''' ms. 
    152 You can tweak these jitter buffer settings according to your latency requirement. But please remember that the jitter buffer is not only used to accommodate network jitter, but also the jitter in the transmission by the sender. PJMEDIA for example, uses the sound device clock to drive its RTP transmission, and depending on the sound device clock accuracy, it may not [#tx-timing transmit RTP packets in timely manner], thus this needs to be accommodated by the receiver's jitter buffer. 
    154 ==== Optimizing Sound Device Latency ==== 
    156 The default sound device back-end in PJMEDIA is [ PortAudio]. !PortAudio itself supports several types of host APIs, depending on the platform: 
    157  - On Windows, it supports both !DirectSound and WMME. 
    158  - On Linux, it supports both ALSA and OSS. 
    159  - On MacOS X, it supports !CoreAudio 
    160  - etc. 
    162 On Windows, !DirectSound will have much better latency than WMME, so try to use !DirectSound device if possible. Unfortunately, with PJSIP version 0.7.0, WMME will be used by default. But this subsequently has been fixed with ticket #384, so version later than 0.7.0 will use !DirectSound if it is available (on Windows, that is). 
    164 !PortAudio !DirectSound has the default buffering latency set to '''120''' ms. This can be overridden by application, by setting {{{PA_MIN_LATENCY_MSEC}}} environment variable. 
    166 We can measure the sound device end-to-end latency using ''pjsua'', by doing this experimentation: 
    167  1. For this experiment, it's important to use speaker rather than headset, since we want the speaker signal to be captured by the microphone. 
    168  1. Run ''pjsua'' with this command line arguments: 
    169 {{{ 
    170   pjsua_vc6 --ec-tail 0 --rec-file latency.wav 
    171 }}} 
    172  1. On ''pjsua'' menu, loop-back the microphone to the speaker, and record the microphone signal: 
    173 {{{ 
    174  >>> cc 0 0 
    175  >>> cc 0 1 
    176 }}} 
    177  1. Then tap on the microphone. You should hear it being played to the speaker too. 
    178  1. Quit the application: 
    179 {{{ 
    180  >>> q 
    181 }}} 
    183 Using WAV file waveform display, open {{{latency.wav}}} and measure the delay between the ''tap'' being captured by microphone and its echoed signal. This is the overall (microphone and speaker) delay of the sound device. 
    185 On my system, an IBM X23 laptop running Windows 2000 Professional, !PortAudio !DirectSound with default settings has about 320 ms latency. Setting {{{PA_MIN_LATENCY_MSEC}}} environment variable to 20 ms will result in reduction of the latency to about 220 ms, which is consistent with the setting. 
    187 With WMME backend, the overall latency is about 464 ms, using default settings. It seems that !PortAudio sets the buffering latency to 200 ms for both input and output, in {{{paDevInfo->defaultLowInputLatency}}}. Unfortunately I don't know how to override this setting in application (setting {{{PA_MIN_LATENCY_MSEC}}} environment variable doesn't seem to change the latency). But if you want to change this setting, you can change PJMEDIA's {{{pasound.c}}} and hard-code {{{inputParam.suggestedLatency}}} and {{{outputParam.suggestedLatency}}} to your requirement (for example, {{{0.020}}}). I have experimented with setting these to {{{0.020}}}, and it reduced the latency to about 254 ms. 
    189 Your mileage may vary, of course. 
    191174=== How to run PJSUA without sound device? === #no-snd-dev