<p>Most (all ?) audio encoders are single-threaded and afaict, all encoding will occur in the main thread.</p>

<p>Maybe worth filing a feature request at trac.ffmpeg.org</p>

CC BY-SA 4.0
2018-08-26T18:32:27.500Z
I have already developed a wrapper running an `ffmpeg` instance for each stream and then `mkvmerge`'ing them together. Thanks for your help anyway.
hedgar2017
CC BY-SA 4.0
2018-08-26T17:42:01.767Z
2018-08-26T17:42:01.767Z
Gyan
<p>Is there a way of forcing ffmpeg to encode each audio stream in a different thread?</p>

<pre><code>ffmpeg
    -i audio1.ac3 -c:a libopus
    -i audio2.ac3 -c:a libopus
    -i audio3.ac3 -c:a libopus
    output.mkv
</code></pre>

<p>I mean only ffmpeg's own instruments, without multiple processes and other OS features.</p>

<p>Normally, there is only one core saturated, so encoding a file with many audio streams is very long.</p>

<p>Exact command:</p>

<pre><code>ffmpeg -loglevel verbose
    -i 'Ярость (Fury).mkv'
    -i 'Fury (2014) [Ukr &amp; Eng, Sub Eng] BDRip-AVC [Hurtom &amp; HELLYWOOD].mkv'
    -threads 0 -max_muxing_queue_size 65536 -avoid_negative_ts 1 -metadata title=2014.Fury.BDRip.HEVC.1080p
    -map 0:0 -c:v copy -metadata:s:v:0 title=2014.Fury.BDRip.HEVC.1080p -disposition:v:0 +default-forced
    -map 0:2 -c:a libopus -application audio -vbr on -packet_loss 0 -frame_duration 20 -mapping_family 255 -compression_level 10 -metadata:s:a:0 language=eng -metadata:s:a:0 title=Original -disposition:a:0 +default-forced
    -map 1:1 -c:a libopus -application audio -vbr on -packet_loss 0 -frame_duration 20 -mapping_family 255 -compression_level 10 -metadata:s:a:1 language=ukr -disposition:a:1 -default-forced
    -map 0:1 -c:a libopus -application audio -vbr on -packet_loss 0 -frame_duration 20 -mapping_family 255 -compression_level 10 -metadata:s:a:2 language=rus -metadata:s:a:2 title=Dub -disposition:a:2 -default-forced
    -map 0:10 -c:s copy -metadata:s:s:0 language=eng -metadata:s:s:0 title=Original -disposition:s:0 -default-forced
    -f matroska ./2014.Fury.BDRip.HEVC.1080p.mkv
</code></pre>

<p>Log:</p>

<pre><code>... inputs ...
Stream mapping:
  Stream #0:0 -&gt; #0:0 (copy)
  Stream #0:2 -&gt; #0:1 (dts (dca) -&gt; opus (libopus))
  Stream #1:1 -&gt; #0:2 (ac3 (native) -&gt; opus (libopus))
  Stream #0:1 -&gt; #0:3 (ac3 (native) -&gt; opus (libopus))
  Stream #0:10 -&gt; #0:4 (copy)
Press [q] to stop, [?] for help
[graph_2_in_0_1 @ 0000019ca2cb29c0] tb:1/48000 samplefmt:fltp samplerate:48000 chlayout:0x60f
[format_out_0_3 @ 0000019ca2cb20c0] auto-inserting filter 'auto_resampler_0' between the filter 'Parsed_anull_0' and the filter 'format_out_0_3'
[auto_resampler_0 @ 0000019ca2cb27c0] ch:6 chl:5.1(side) fmt:fltp r:48000Hz -&gt; ch:6 chl:5.1(side) fmt:flt r:48000Hz
[libopus @ 0000019ca2c9f3c0] No bit rate set. Defaulting to 384000 bps.
[graph_0_in_0_2 @ 0000019ca2cb1ac0] tb:1/48000 samplefmt:fltp samplerate:48000 chlayout:0x60f
[format_out_0_1 @ 0000019ca2cb1bc0] auto-inserting filter 'auto_resampler_0' between the filter 'Parsed_anull_0' and the filter 'format_out_0_1'
[auto_resampler_0 @ 0000019ca2cb14c0] ch:6 chl:5.1(side) fmt:fltp r:48000Hz -&gt; ch:6 chl:5.1(side) fmt:flt r:48000Hz
[libopus @ 0000019ca292c980] No bit rate set. Defaulting to 384000 bps.
[graph_1_in_1_1 @ 0000019ca2cb2bc0] tb:1/48000 samplefmt:fltp samplerate:48000 chlayout:0x60f
[format_out_0_2 @ 0000019ca2cb26c0] auto-inserting filter 'auto_resampler_0' between the filter 'Parsed_anull_0' and the filter 'format_out_0_2'
[auto_resampler_0 @ 0000019ca2cb0dc0] ch:6 chl:5.1(side) fmt:fltp r:48000Hz -&gt; ch:6 chl:5.1(side) fmt:flt r:48000Hz
[libopus @ 0000019ca292e980] No bit rate set. Defaulting to 384000 bps.
Output #0, matroska, to './2014.Fury.BDRip.HEVC.1080p.mkv':
  Metadata:
    DATE_RELEASED   : 2014
    title           : 2014.Fury.BDRip.HEVC.1080p
    Released by     : Buba5473 for NNM-Club
    Copyright       : Encoded by Goor80
    encoder         : Lavf58.12.100
    Chapter #0:0: start 0.000000, end 478.228000
    Metadata:
      title           : Chapter 01
    ... chapters ...
    Stream #0:0: Video: hevc (Main 10), 1 reference frame, yuv420p10le(tv), 1920x800 (0x0) [SAR 1:1 DAR 12:5], q=2-31, 23.98 fps, 23.98 tbr, 1k tbn, 1k tbc (default)
    Stream #0:1(eng): Audio: opus (libopus) ([255][255][255][255] / 0xFFFFFFFF), 48000 Hz, 5.1(side), flt, delay 312, 384 kb/s (default)
    Stream #0:2(ukr): Audio: opus (libopus) ([255][255][255][255] / 0xFFFFFFFF), 48000 Hz, 5.1(side), flt, delay 312, 384 kb/s
    Stream #0:3(rus): Audio: opus (libopus) ([255][255][255][255] / 0xFFFFFFFF), 48000 Hz, 5.1(side), flt, delay 312, 384 kb/s
    Stream #0:4(eng): Subtitle: subrip
[matroska @ 0000019ca2d17f00] Starting new cluster due to timestamp=6175.5kbits/s speed=10.2x
[matroska @ 0000019ca2d17f00] Starting new cluster due to timestamp=7530.8kbits/s speed=8.74x
[matroska @ 0000019ca2d17f00] Starting new cluster due to timestamp=7955.1kbits/s speed=9.02x
frame=156607 fps=205 q=-1.0 size= 8321971kB time=01:48:51.85 bitrate=10437.1kbits/s speed=8.55x
... not finished yet ...
</code></pre>

<p>fps is always around 3000/number_of_audio_channels, meaning all audio transcoding is done with the only thread.</p>

CC BY-SA 4.0
2018-05-30T15:54:37.070Z
Is that your exact command?
Gyan
CC BY-SA 4.0
2018-05-30T17:28:35.397Z
No, I removed unrelated options and details for better readability. I have tried to play with `-threads`, but this option is only about per-stream multithreading.
hedgar2017
CC BY-SA 4.0
2018-05-30T17:37:18.467Z
Share your exact command and log.
Gyan
CC BY-SA 4.0
2018-05-30T17:45:15.283Z
Posted the exact command and log above.
hedgar2017
CC BY-SA 4.0
2018-08-17T13:41:43.693Z
`fps=205` only represents turnover of video frames.
Gyan
CC BY-SA 4.0
2018-08-23T08:35:28.897Z
I know, it is just a hint. Only one core is saturated no matter how many stream I encode.
hedgar2017
CC BY-SA 4.0
2018-08-24T05:28:30.507Z
I checked and don't think this is possible. Audio encoders are single-threaded and ffmpeg manages encoder frame dispatch in its main thread.
Gyan
CC BY-SA 4.0
2018-08-25T10:42:12.450Z
Ok. Put it into an answer and I'll give you the bounty.
hedgar2017
<ffmpeg><transcoding>
Transcode each stream in a different thread with ffmpeg
hedgar2017
# Transcode each stream in a different thread with ffmpeg

(Asked by: username_0 on 2018-05-30)

Is there a way of forcing ffmpeg to encode each audio stream in a different thread?
ffmpeg
    -i audio1.ac3 -c:a libopus
    -i audio2.ac3 -c:a libopus
    -i audio3.ac3 -c:a libopus
    output.mkv

I mean only ffmpeg's own instruments, without multiple processes and other OS features.
Normally, there is only one core saturated, so encoding a file with many audio streams is very long.
Exact command:
ffmpeg -loglevel verbose
    -i 'Ярость (Fury).mkv'
    -i 'Fury (2014) [Ukr & Eng, Sub Eng] BDRip-AVC [Hurtom & HELLYWOOD].mkv'
    -threads 0 -max_muxing_queue_size 65536 -avoid_negative_ts 1 -metadata title=2014.Fury.BDRip.HEVC.1080p
    -map 0:0 -c:v copy -metadata:s:v:0 title=2014.Fury.BDRip.HEVC.1080p -disposition:v:0 +default-forced
    -map 0:2 -c:a libopus -application audio -vbr on -packet_loss 0 -frame_duration 20 -mapping_family 255 -compression_level 10 -metadata:s:a:0 language=eng -metadata:s:a:0 title=Original -disposition:a:0 +default-forced
    -map 1:1 -c:a libopus -application audio -vbr on -packet_loss 0 -frame_duration 20 -mapping_family 255 -compression_level 10 -metadata:s:a:1 language=ukr -disposition:a:1 -default-forced
    -map 0:1 -c:a libopus -application audio -vbr on -packet_loss 0 -frame_duration 20 -mapping_family 255 -compression_level 10 -metadata:s:a:2 language=rus -metadata:s:a:2 title=Dub -disposition:a:2 -default-forced
    -map 0:10 -c:s copy -metadata:s:s:0 language=eng -metadata:s:s:0 title=Original -disposition:s:0 -default-forced
    -f matroska ./2014.Fury.BDRip.HEVC.1080p.mkv

Log:
... inputs ...
Stream mapping:
  Stream #0:0 -> #0:0 (copy)
  Stream #0:2 -> #0:1 (dts (dca) -> opus (libopus))
  Stream #1:1 -> #0:2 (ac3 (native) -> opus (libopus))
  Stream #0:1 -> #0:3 (ac3 (native) -> opus (libopus))
  Stream #0:10 -> #0:4 (copy)
Press [q] to stop, [?] for help
[graph_2_in_0_1 @ 0000019ca2cb29c0] tb:1/48000 samplefmt:fltp samplerate:48000 chlayout:0x60f
[format_out_0_3 @ 0000019ca2cb20c0] auto-inserting filter 'auto_resampler_0' between the filter 'Parsed_anull_0' and the filter 'format_out_0_3'
[auto_resampler_0 @ 0000019ca2cb27c0] ch:6 chl:5.1(side) fmt:fltp r:48000Hz -> ch:6 chl:5.1(side) fmt:flt r:48000Hz
[libopus @ 0000019ca2c9f3c0] No bit rate set. Defaulting to 384000 bps.
[graph_0_in_0_2 @ 0000019ca2cb1ac0] tb:1/48000 samplefmt:fltp samplerate:48000 chlayout:0x60f
[format_out_0_1 @ 0000019ca2cb1bc0] auto-inserting filter 'auto_resampler_0' between the filter 'Parsed_anull_0' and the filter 'format_out_0_1'
[auto_resampler_0 @ 0000019ca2cb14c0] ch:6 chl:5.1(side) fmt:fltp r:48000Hz -> ch:6 chl:5.1(side) fmt:flt r:48000Hz
[libopus @ 0000019ca292c980] No bit rate set. Defaulting to 384000 bps.
[graph_1_in_1_1 @ 0000019ca2cb2bc0] tb:1/48000 samplefmt:fltp samplerate:48000 chlayout:0x60f
[format_out_0_2 @ 0000019ca2cb26c0] auto-inserting filter 'auto_resampler_0' between the filter 'Parsed_anull_0' and the filter 'format_out_0_2'
[auto_resampler_0 @ 0000019ca2cb0dc0] ch:6 chl:5.1(side) fmt:fltp r:48000Hz -> ch:6 chl:5.1(side) fmt:flt r:48000Hz
[libopus @ 0000019ca292e980] No bit rate set. Defaulting to 384000 bps.
Output #0, matroska, to './2014.Fury.BDRip.HEVC.1080p.mkv':
  Metadata:
    DATE_RELEASED   : 2014
    title           : 2014.Fury.BDRip.HEVC.1080p
    Released by     : Buba5473 for NNM-Club
    Copyright       : Encoded by Goor80
    encoder         : Lavf58.12.100
    Chapter #0:0: start 0.000000, end 478.228000
    Metadata:
      title           : Chapter 01
    ... chapters ...
    Stream #0:0: Video: hevc (Main 10), 1 reference frame, yuv420p10le(tv), 1920x800 (0x0) [SAR 1:1 DAR 12:5], q=2-31, 23.98 fps, 23.98 tbr, 1k tbn, 1k tbc (default)
    Stream #0:1(eng): Audio: opus (libopus) ([255][255][255][255] / 0xFFFFFFFF), 48000 Hz, 5.1(side), flt, delay 312, 384 kb/s (default)
    Stream #0:2(ukr): Audio: opus (libopus) ([255][255][255][255] / 0xFFFFFFFF), 48000 Hz, 5.1(side), flt, delay 312, 384 kb/s
    Stream #0:3(rus): Audio: opus (libopus) ([255][255][255][255] / 0xFFFFFFFF), 48000 Hz, 5.1(side), flt, delay 312, 384 kb/s
    Stream #0:4(eng): Subtitle: subrip
[matroska @ 0000019ca2d17f00] Starting new cluster due to timestamp=6175.5kbits/s speed=10.2x
[matroska @ 0000019ca2d17f00] Starting new cluster due to timestamp=7530.8kbits/s speed=8.74x
[matroska @ 0000019ca2d17f00] Starting new cluster due to timestamp=7955.1kbits/s speed=9.02x
frame=156607 fps=205 q=-1.0 size= 8321971kB time=01:48:51.85 bitrate=10437.1kbits/s speed=8.55x
... not finished yet ...

fps is always around 3000/number_of_audio_channels, meaning all audio transcoding is done with the only thread.

**Tags:** ffmpeg, transcoding

> **Comments:**
> **username_1**: Is that your exact command?  
> **username_0**: No, I removed unrelated options and details for better readability. I have tried to play with `-threads`, but this option is only about per-stream multithreading.  
> **username_1**: Share your exact command and log.  
> **username_0**: Posted the exact command and log above.  
> **username_1**: `fps=205` only represents turnover of video frames.  
> **username_0**: I know, it is just a hint. Only one core is saturated no matter how many stream I encode.  
> **username_1**: I checked and don't think this is possible. Audio encoders are single-threaded and ffmpeg manages encoder frame dispatch in its main thread.  
> **username_0**: Ok. Put it into an answer and I'll give you the bounty.  

---

## 1 answers

### Answer by username_1 on 2018-08-26. Score: 1 | Accepted answer

Most (all ?) audio encoders are single-threaded and afaict, all encoding will occur in the main thread.

Maybe worth filing a feature request at trac.ffmpeg.org

> **Comments:**
> **username_0**: I have already developed a wrapper running an `ffmpeg` instance for each stream and then `mkvmerge`'ing them together. Thanks for your help anyway.  

---

