]> granicus.if.org Git - handbrake/commitdiff
contrib: Add opus audio encoder.
authorJohn Stebbins <jstebbins.hb@gmail.com>
Mon, 18 Jul 2016 20:42:25 +0000 (13:42 -0700)
committerBradley Sepos <bradley@bradleysepos.com>
Fri, 2 Sep 2016 07:33:06 +0000 (03:33 -0400)
Remove:
hb_audio_samplerate_get_best()

Add:
hb_audio_samplerate_is_supported()
hb_audio_samplerate_find_closest()
hb_audio_samplerate_get_sr_shift()

13 files changed:
contrib/ffmpeg/module.defs
contrib/libopus/module.defs [new file with mode: 0644]
contrib/libopus/module.rules [new file with mode: 0644]
gtk/configure.ac
gtk/src/hb-backend.c
libhb/common.c
libhb/common.h
libhb/encavcodecaudio.c
libhb/module.defs
libhb/muxavformat.c
libhb/work.c
make/include/main.defs
test/module.defs

index dfd6ec9b16c2670942e81a74105ba87024eb0107..655df0651d928f86ad27a9c0615ddfeb45b3dc9e 100644 (file)
@@ -1,4 +1,4 @@
-__deps__ := YASM BZIP2 ZLIB FDKAAC LIBVPX LAME
+__deps__ := YASM BZIP2 ZLIB FDKAAC LIBVPX LAME LIBOPUS
 ifeq (1-mingw,$(BUILD.cross)-$(BUILD.system))
 __deps__ += PTHREADW32
 endif
@@ -43,6 +43,8 @@ FFMPEG.CONFIGURE.extra = \
     --enable-encoder=mpeg2video \
     --enable-encoder=mpeg4 \
     --enable-encoder=libmp3lame \
+    --enable-libopus \
+    --enable-encoder=libopus \
     --enable-libvpx \
     --enable-encoder=libvpx_vp8 \
     --disable-decoder=libvpx_vp8 \
diff --git a/contrib/libopus/module.defs b/contrib/libopus/module.defs
new file mode 100644 (file)
index 0000000..7292f70
--- /dev/null
@@ -0,0 +1,11 @@
+$(eval $(call import.MODULE.defs,LIBOPUS,libopus))
+$(eval $(call import.CONTRIB.defs,LIBOPUS))
+
+LIBOPUS.FETCH.url = http://download.handbrake.fr/contrib/opus-1.1.3.tar.gz
+LIBOPUS.FETCH.url += http://downloads.xiph.org/releases/opus/opus-1.1.3.tar.gz
+LIBOPUS.FETCH.md5 = 32bbb6b557fe1b6066adc0ae1f08b629
+
+LIBOPUS.CONFIGURE.shared = --enable-shared=no
+LIBOPUS.CONFIGURE.extra = --disable-doc --disable-extra-programs
+
+LIBOPUS.CONFIGURE.bootstrap = rm -fr aclocal.m4 autom4te.cache configure; autoreconf -I m4 -fiv;
diff --git a/contrib/libopus/module.rules b/contrib/libopus/module.rules
new file mode 100644 (file)
index 0000000..3493eaf
--- /dev/null
@@ -0,0 +1,2 @@
+$(eval $(call import.MODULE.rules,LIBOPUS))
+$(eval $(call import.CONTRIB.rules,LIBOPUS))
index 3b690b21febe07170a773b8f0f00fb7f2d7e00b6..4c75f4a90857b1fc2ba6a65abd21606e482cb16e 100644 (file)
@@ -164,7 +164,7 @@ PKG_CHECK_MODULES(GHB, [$GHB_PACKAGES])
 
 GHB_CFLAGS="$HBINC $GHB_CFLAGS"
 
-HB_LIBS="-lhandbrake -lavresample -lavformat -lavcodec -lavfilter -lavutil -ldvdnav -ldvdread -lmp3lame -lvorbis -lvorbisenc -logg -lsamplerate -lx264 -lswscale -ltheoraenc -ltheoradec -lvpx -lz -lbz2 -lbluray -lass -lfontconfig -lfreetype -lxml2 -ljansson"
+HB_LIBS="-lhandbrake -lavresample -lavformat -lavcodec -lavfilter -lavutil -ldvdnav -ldvdread -lmp3lame -lvorbis -lvorbisenc -logg -lsamplerate -lx264 -lswscale -ltheoraenc -ltheoradec -lvpx -lz -lbz2 -lbluray -lass -lfontconfig -lfreetype -lxml2 -ljansson -lopus"
 
 case $host in
   *-*-mingw*)
index 5feababa5138939ad1a3ed8f3435121bcc4eb244..1df18e7031596795a00e1b12bef2430f5762cf8b 100644 (file)
@@ -1011,20 +1011,7 @@ lookup_param_option(const hb_filter_param_t *param, const GhbValue *gval)
 gint
 ghb_find_closest_audio_samplerate(gint irate)
 {
-    gint result;
-    const hb_rate_t *rate;
-
-    result = 0;
-    for (rate = hb_audio_samplerate_get_next(NULL); rate != NULL;
-         rate = hb_audio_samplerate_get_next(rate))
-    {
-        if (irate <= rate->rate)
-        {
-            result = rate->rate;
-            break;
-        }
-    }
-    return result;
+    return hb_audio_samplerate_find_closest(irate, HB_ACODEC_INVALID);
 }
 
 const iso639_lang_t* ghb_iso639_lookup_by_int(int idx)
index c75e4e564e7a678c0fcbcbe73d47af96f445ac8e..50b596a987593934aa46e30f75fc37a9d5b1fdc3 100644 (file)
@@ -31,6 +31,8 @@
 #include <windows.h>
 #endif
 
+static int mixdown_get_opus_coupled_stream_count(int mixdown);
+
 /**********************************************************************
  * Global variables
  *********************************************************************/
@@ -63,6 +65,7 @@ enum
     HB_GID_ACODEC_MP3_PASS,
     HB_GID_ACODEC_TRUEHD_PASS,
     HB_GID_ACODEC_VORBIS,
+    HB_GID_ACODEC_OPUS,
     HB_GID_MUX_MKV,
     HB_GID_MUX_MP4,
 };
@@ -324,6 +327,7 @@ hb_encoder_internal_t hb_audio_encoders[]  =
     { { "FLAC 16-bit",        "flac16",     "FLAC 16-bit (libavcodec)",    HB_ACODEC_FFFLAC,                      HB_MUX_MASK_MKV, }, NULL, 1, HB_GID_ACODEC_FLAC,       },
     { { "FLAC 24-bit",        "flac24",     "FLAC 24-bit (libavcodec)",    HB_ACODEC_FFFLAC24,                    HB_MUX_MASK_MKV, }, NULL, 1, HB_GID_ACODEC_FLAC,       },
     { { "FLAC Passthru",      "copy:flac",  "FLAC Passthru",               HB_ACODEC_FLAC_PASS,                   HB_MUX_MASK_MKV, }, NULL, 1, HB_GID_ACODEC_FLAC_PASS,  },
+    { { "Opus",               "opus",     "Opus (libopus)",                HB_ACODEC_OPUS,                        HB_MUX_MASK_MKV, }, NULL, 1, HB_GID_ACODEC_OPUS,     },
     { { "Auto Passthru",      "copy",       "Auto Passthru",               HB_ACODEC_AUTO_PASS,   HB_MUX_MASK_MP4|HB_MUX_MASK_MKV, }, NULL, 1, HB_GID_ACODEC_AUTO_PASS,  },
 };
 int hb_audio_encoders_count = sizeof(hb_audio_encoders) / sizeof(hb_audio_encoders[0]);
@@ -361,6 +365,9 @@ static int hb_audio_encoder_is_enabled(int encoder)
         case HB_ACODEC_FFFLAC24:
             return avcodec_find_encoder(AV_CODEC_ID_FLAC) != NULL;
 
+        case HB_ACODEC_OPUS:
+            return avcodec_find_encoder(AV_CODEC_ID_OPUS) != NULL;
+
         // the following encoders are always enabled
         case HB_ACODEC_LAME:
         case HB_ACODEC_VORBIS:
@@ -742,56 +749,56 @@ int hb_video_framerate_get_close(hb_rational_t *framerate, double thresh)
     return result;
 }
 
-int hb_audio_samplerate_get_best(uint32_t codec, int samplerate, int *sr_shift)
+int hb_audio_samplerate_is_supported(int samplerate, uint32_t codec)
 {
-    int best_samplerate;
-    if (samplerate < 32000 && (codec == HB_ACODEC_AC3    ||
-                               codec == HB_ACODEC_FFEAC3 ||
-                               codec == HB_ACODEC_CA_HAAC))
-    {
-        // ca_haac can't do samplerates < 32 kHz
-        // libav's E-AC-3 encoder can't do samplerates < 32 kHz
-        // AC-3 < 32 kHz suffers from poor hardware compatibility
-        best_samplerate = 32000;
-    }
-    else if (samplerate < 16000 && codec == HB_ACODEC_FDK_HAAC)
-    {
-        // fdk_haac can't do samplerates < 16 kHz
-        best_samplerate = 16000;
-    }
-    else
+    switch (codec)
     {
-        best_samplerate                   = hb_audio_rates_first_item->rate;
-        const hb_rate_t *audio_samplerate = NULL;
-        while ((audio_samplerate = hb_audio_samplerate_get_next(audio_samplerate)) != NULL)
-        {
-            if (samplerate == audio_samplerate->rate)
-            {
-                // valid samplerate
-                best_samplerate = audio_samplerate->rate;
-                break;
-            }
-            if (samplerate > audio_samplerate->rate)
+        case HB_ACODEC_AC3:
+        case HB_ACODEC_FFEAC3:
+        case HB_ACODEC_CA_HAAC:
+            // ca_haac can't do samplerates < 32 kHz
+            // libav's E-AC-3 encoder can't do samplerates < 32 kHz
+            // AC-3 < 32 kHz suffers from poor hardware compatibility
+            if (samplerate < 32000)
+                return 0;
+            else
+                return 1;
+        case HB_ACODEC_FDK_HAAC:
+            // fdk_haac can't do samplerates < 16 kHz
+            if (samplerate < 16000)
+                return 0;
+             else
+                return 1;
+        case HB_ACODEC_OPUS:
+            switch (samplerate)
             {
-                // samplerates are sanitized downwards
-                best_samplerate = audio_samplerate->rate;
+                // Opus only supports samplerates 8kHz, 12kHz, 16kHz,
+                // 24kHz, 48kHz
+                case 8000:
+                case 12000:
+                case 16000:
+                case 24000:
+                case 48000:
+                    return 1;
+                default:
+                    return 0;
             }
-        }
-    }
-    if (sr_shift != NULL)
-    {
-        /* sr_shift: 0 -> 48000, 44100, 32000 Hz
-         *           1 -> 24000, 22050, 16000 Hz
-         *           2 -> 12000, 11025,  8000 Hz
-         *
-         * also, since samplerates are sanitized downwards:
-         *
-         * (samplerate < 32000) implies (samplerate <= 24000)
-         */
-        *sr_shift = ((best_samplerate < 16000) ? 2 :
-                     (best_samplerate < 32000) ? 1 : 0);
+        default:
+            return 1;
     }
-    return best_samplerate;
+}
+
+int hb_audio_samplerate_get_sr_shift(int samplerate)
+{
+    /* sr_shift: 0 -> 48000, 44100, 32000 Hz
+     *           1 -> 24000, 22050, 16000 Hz
+     *           2 -> 12000, 11025,  8000 Hz
+     *
+     * also, since samplerates are sanitized downwards:
+     *
+     * (samplerate < 32000) implies (samplerate <= 24000)
+     */
+    return ((samplerate < 16000) ? 2 : (samplerate < 32000) ? 1 : 0);
 }
 
 int hb_audio_samplerate_get_from_name(const char *name)
@@ -813,7 +820,7 @@ int hb_audio_samplerate_get_from_name(const char *name)
     if (i >= hb_audio_rates_first_item->rate &&
         i <= hb_audio_rates_last_item ->rate)
     {
-        return hb_audio_samplerate_get_best(0, i, NULL);
+        return hb_audio_samplerate_find_closest(i, HB_ACODEC_INVALID);
     }
 
 fail:
@@ -848,6 +855,44 @@ const hb_rate_t* hb_audio_samplerate_get_next(const hb_rate_t *last)
     return ((hb_rate_internal_t*)last)->next;
 }
 
+const hb_rate_t* hb_audio_samplerate_get_next_for_codec(const hb_rate_t *last,
+                                                        uint32_t codec)
+{
+    while ((last = hb_audio_samplerate_get_next(last)) != NULL)
+        if (hb_audio_samplerate_is_supported(last->rate, codec))
+            return last;
+
+    // None found or end of list
+    return NULL;
+}
+
+int hb_audio_samplerate_find_closest(int samplerate, uint32_t codec)
+{
+    const hb_rate_t * rate, * prev, * next;
+
+    rate = prev = next = hb_audio_samplerate_get_next_for_codec(NULL, codec);
+    while (rate != NULL && next->rate < samplerate)
+    {
+        rate = hb_audio_samplerate_get_next_for_codec(rate, codec);
+        if (rate != NULL)
+        {
+            prev = next;
+            next = rate;
+        }
+    }
+
+    int delta_prev = samplerate - prev->rate;
+    int delta_next = next->rate - samplerate;
+    if (delta_prev <= delta_next)
+    {
+        return prev->rate;
+    }
+    else
+    {
+        return next->rate;
+    }
+}
+
 // Given an input bitrate, find closest match in the set of allowed bitrates
 static int hb_audio_bitrate_find_closest(int bitrate)
 {
@@ -894,11 +939,11 @@ int hb_audio_bitrate_get_default(uint32_t codec, int samplerate, int mixdown)
     if ((codec & HB_ACODEC_PASS_FLAG) || !(codec & HB_ACODEC_MASK))
         goto fail;
 
-    int bitrate, nchannels, sr_shift;
+    int bitrate, nchannels, nlfe, sr_shift;
     /* full-bandwidth channels, sr_shift */
-    nchannels = (hb_mixdown_get_discrete_channel_count(mixdown) -
-                 hb_mixdown_get_low_freq_channel_count(mixdown));
-    hb_audio_samplerate_get_best(codec, samplerate, &sr_shift);
+    nlfe      = hb_mixdown_get_low_freq_channel_count(mixdown);
+    nchannels = hb_mixdown_get_discrete_channel_count(mixdown) - nlfe;
+    sr_shift  = hb_audio_samplerate_get_sr_shift(samplerate);
 
     switch (codec)
     {
@@ -924,6 +969,14 @@ int hb_audio_bitrate_get_default(uint32_t codec, int samplerate, int mixdown)
             bitrate = nchannels * 32;
             break;
 
+        case HB_ACODEC_OPUS:
+        {
+            int coupled = mixdown_get_opus_coupled_stream_count(mixdown);
+            int uncoupled = nchannels + nlfe - 2 * coupled;
+
+            bitrate = coupled * 96 + uncoupled * 64;
+        } break;
+
         default:
             bitrate = nchannels * 80;
             break;
@@ -1070,7 +1123,8 @@ void hb_audio_bitrate_get_limits(uint32_t codec, int samplerate, int mixdown,
 
     /* samplerate, sr_shift */
     int sr_shift;
-    samplerate = hb_audio_samplerate_get_best(codec, samplerate, &sr_shift);
+    samplerate = hb_audio_samplerate_find_closest(samplerate, codec);
+    sr_shift = hb_audio_samplerate_get_sr_shift(samplerate);
 
     /* LFE, full-bandwidth channels */
     int lfe_count, nchannels;
@@ -1174,6 +1228,11 @@ void hb_audio_bitrate_get_limits(uint32_t codec, int samplerate, int mixdown,
                                                ( 50 * (samplerate >= 44100)));
             break;
 
+        case HB_ACODEC_OPUS:
+            *low  = (nchannels + lfe_count) * 6;
+            *high = (nchannels + lfe_count) * 256;
+            break;
+
         // Bitrates don't apply to passthrough audio, but may apply if we
         // fall back to an encoder when the source can't be passed through.
         default:
@@ -1473,6 +1532,13 @@ void hb_audio_quality_get_limits(uint32_t codec, float *low, float *high,
             *high        = 127.;
             break;
 
+        case HB_ACODEC_OPUS:
+            *direction   = 0;
+            *granularity = 1.;
+            *low         = 0.;
+            *high        = 10.;
+            break;
+
         default:
             *direction   = 0;
             *granularity = 1.;
@@ -1513,6 +1579,9 @@ float hb_audio_quality_get_default(uint32_t codec)
         case HB_ACODEC_CA_AAC:
             return 91.;
 
+        case HB_ACODEC_OPUS:
+            return 10.;
+
         default:
             return HB_INVALID_AUDIO_QUALITY;
     }
@@ -1658,6 +1727,34 @@ const hb_dither_t* hb_audio_dither_get_next(const hb_dither_t *last)
     return ((hb_dither_internal_t*)last)->next;
 }
 
+static int mixdown_get_opus_coupled_stream_count(int mixdown)
+{
+    switch (mixdown)
+    {
+        case HB_AMIXDOWN_7POINT1:
+        case HB_AMIXDOWN_6POINT1:
+            return 3;
+
+        case HB_AMIXDOWN_5POINT1:
+            return 2;
+
+        case HB_AMIXDOWN_MONO:
+        case HB_AMIXDOWN_LEFT:
+        case HB_AMIXDOWN_RIGHT:
+            return 0;
+
+        case HB_AMIXDOWN_NONE:
+        case HB_INVALID_AMIXDOWN:
+        case HB_AMIXDOWN_5_2_LFE:
+            // The 5F/2R/LFE configuration is currently not supported by Opus,
+            // so don't set coupled streams.
+            return 0;
+
+        default:
+            return 1;
+    }
+}
+
 int hb_mixdown_is_supported(int mixdown, uint32_t codec, uint64_t layout)
 {
     return (hb_mixdown_has_codec_support(mixdown, codec) &&
@@ -1679,6 +1776,7 @@ int hb_mixdown_has_codec_support(int mixdown, uint32_t codec)
         case HB_ACODEC_VORBIS:
         case HB_ACODEC_FFFLAC:
         case HB_ACODEC_FFFLAC24:
+        case HB_ACODEC_OPUS:
             return (mixdown <= HB_AMIXDOWN_7POINT1);
 
         case HB_ACODEC_LAME:
@@ -1831,6 +1929,7 @@ int hb_mixdown_get_default(uint32_t codec, uint64_t layout)
         // the FLAC encoder defaults to the best mixdown up to 7.1
         case HB_ACODEC_FFFLAC:
         case HB_ACODEC_FFFLAC24:
+        case HB_ACODEC_OPUS:
             mixdown = HB_AMIXDOWN_7POINT1;
             break;
 
@@ -2289,9 +2388,8 @@ void hb_autopassthru_apply_settings(hb_job_t *job)
                 if (audio->config.out.samplerate <= 0)
                     audio->config.out.samplerate = audio->config.in.samplerate;
                 audio->config.out.samplerate =
-                    hb_audio_samplerate_get_best(audio->config.out.codec,
-                                                 audio->config.out.samplerate,
-                                                 NULL);
+                    hb_audio_samplerate_find_closest(
+                        audio->config.out.samplerate, audio->config.out.codec);
                 int quality_not_allowed =
                     hb_audio_quality_get_default(audio->config.out.codec)
                             == HB_INVALID_AUDIO_QUALITY;
index 92cc1dadf0fe8cb71d7d109c48ecf3d276ec2a78..ae05f2726a14b6f9264e9d3a9fcd8aecd3129277 100644 (file)
@@ -341,10 +341,16 @@ const hb_rate_t* hb_video_framerate_get_next(const hb_rate_t *last);
 int              hb_video_framerate_get_close(hb_rational_t *framerate,
                                               double thresh);
 
-int              hb_audio_samplerate_get_best(uint32_t codec, int samplerate, int *sr_shift);
+int              hb_audio_samplerate_is_supported(int samplerate,
+                                                  uint32_t codec);
+int              hb_audio_samplerate_find_closest(int samplerate,
+                                                  uint32_t codec);
+int              hb_audio_samplerate_get_sr_shift(int samplerate);
 int              hb_audio_samplerate_get_from_name(const char *name);
 const char*      hb_audio_samplerate_get_name(int samplerate);
 const hb_rate_t* hb_audio_samplerate_get_next(const hb_rate_t *last);
+const hb_rate_t* hb_audio_samplerate_get_next_for_codec(const hb_rate_t *last,
+                                                        uint32_t codec);
 
 int              hb_audio_bitrate_get_best(uint32_t codec, int bitrate, int samplerate, int mixdown);
 int              hb_audio_bitrate_get_default(uint32_t codec, int samplerate, int mixdown);
@@ -659,7 +665,7 @@ struct hb_job_s
 /* Audio starts here */
 /* Audio Codecs: Update win/CS/HandBrake.Interop/HandBrakeInterop/HbLib/NativeConstants.cs when changing these consts */
 #define HB_ACODEC_INVALID   0x00000000
-#define HB_ACODEC_MASK      0x03FFFF00
+#define HB_ACODEC_MASK      0x07FFFF00
 #define HB_ACODEC_LAME      0x00000200
 #define HB_ACODEC_VORBIS    0x00000400
 #define HB_ACODEC_AC3       0x00000800
@@ -677,7 +683,8 @@ struct hb_job_s
 #define HB_ACODEC_FDK_HAAC  0x00800000
 #define HB_ACODEC_FFEAC3    0x01000000
 #define HB_ACODEC_FFTRUEHD  0x02000000
-#define HB_ACODEC_FF_MASK   0x03FF2800
+#define HB_ACODEC_OPUS      0x04000000
+#define HB_ACODEC_FF_MASK   0x07FF2800
 #define HB_ACODEC_PASS_FLAG 0x40000000
 #define HB_ACODEC_PASS_MASK   (HB_ACODEC_AC3 | HB_ACODEC_DCA | HB_ACODEC_DCA_HD | HB_ACODEC_FFAAC | HB_ACODEC_FFEAC3 | HB_ACODEC_FFFLAC | HB_ACODEC_MP3 | HB_ACODEC_FFTRUEHD)
 #define HB_ACODEC_AUTO_PASS   (HB_ACODEC_PASS_FLAG | HB_ACODEC_PASS_MASK)
index 544ee385aa2c31d42e95a2c5bbbddd725c584300..73d44a25ccd461d5b359256c8558e930790dc664 100644 (file)
@@ -125,6 +125,10 @@ static int encavcodecaInit(hb_work_object_t *w, hb_job_t *job)
             codec_name = "libmp3lame";
             break;
 
+        case HB_ACODEC_OPUS:
+            codec_name = "libopus";
+            break;
+
         default:
             hb_error("encavcodecaInit: unsupported codec (0x%x)",
                      audio->config.out.codec);
index ca80e56fa0de0d960075e706f73bcf21c944bb50..8ea828bfa34af791a091b72f5f9afa81a79c57dc 100644 (file)
@@ -1,7 +1,7 @@
 __deps__ := A52DEC BZIP2 LIBVPX FFMPEG FONTCONFIG FREETYPE LAME LIBASS LIBDCA \
     LIBDVDREAD LIBDVDNAV LIBICONV LIBSAMPLERATE LIBTHEORA LIBVORBIS LIBOGG \
     LIBXML2 PTHREADW32 X264 X265 ZLIB LIBBLURAY FDKAAC LIBMFX LIBGNURX JANSSON \
-    HARFBUZZ
+    HARFBUZZ LIBOPUS
 
 $(eval $(call import.MODULE.defs,LIBHB,libhb,$(__deps__)))
 $(eval $(call import.GCC,LIBHB))
@@ -124,7 +124,7 @@ LIBHB.lib = $(LIBHB.build/)hb.lib
 LIBHB.dll.libs = $(foreach n, \
         ass avcodec avformat avfilter avutil avresample dvdnav dvdread fontconfig \
         freetype mp3lame samplerate swscale vpx theora vorbis vorbisenc ogg \
-        x264 xml2 bluray jansson harfbuzz, \
+        x264 xml2 bluray jansson harfbuzz opus, \
         $(CONTRIB.build/)lib/lib$(n).a )
 
 ifeq (1,$(FEATURE.fdk_aac))
index b7533d4dc19ab3085b46dacaede4ce7ca3212cae..47762721c531a999d71756756f5490a1292e04dd 100644 (file)
@@ -485,6 +485,23 @@ static int avformatInit( hb_mux_object_t * m )
                     size += ogg_headers[jj]->bytes;
                 }
             } break;
+            case HB_ACODEC_OPUS:
+                track->st->codec->codec_id = AV_CODEC_ID_OPUS;
+
+                if (audio->priv.config.extradata.length)
+                {
+                    priv_size = audio->priv.config.extradata.length;
+                    priv_data = av_malloc(priv_size + FF_INPUT_BUFFER_PADDING_SIZE);
+                    if (priv_data == NULL)
+                    {
+                        hb_error("OPUS extradata: malloc failure");
+                        goto error;
+                    }
+                    memcpy(priv_data,
+                           audio->priv.config.extradata.bytes,
+                           audio->priv.config.extradata.length);
+                }
+                break;
             case HB_ACODEC_FFFLAC:
             case HB_ACODEC_FFFLAC24:
                 track->st->codec->codec_id = AV_CODEC_ID_FLAC;
index afb8663945a0b9af7362e0326bdab01f22c7dfb7..a2290cc8b0830a006efa60a199d2a7eb8b20bf6f 100644 (file)
@@ -967,9 +967,8 @@ static int sanitize_audio(hb_job_t *job)
             audio->config.out.samplerate = audio->config.in.samplerate;
         }
         best_samplerate =
-            hb_audio_samplerate_get_best(audio->config.out.codec,
-                                         audio->config.out.samplerate,
-                                         NULL);
+            hb_audio_samplerate_find_closest(audio->config.out.samplerate,
+                                             audio->config.out.codec);
         if (best_samplerate != audio->config.out.samplerate)
         {
             hb_log("work: sanitizing track %d unsupported samplerate %d Hz to %s kHz",
index b952279087d1d13a67fad49319c8c78dfb06b419..e7f3a0980a1682ecb83d62d01acc0d7a0ab0a483 100644 (file)
@@ -50,6 +50,7 @@ ifneq (,$(filter $(BUILD.system),darwin cygwin mingw))
     MODULES += contrib/libass
     MODULES += contrib/libogg
     MODULES += contrib/libvorbis
+    MODULES += contrib/libopus
     MODULES += contrib/libtheora
     MODULES += contrib/libsamplerate
     MODULES += contrib/lame
index 904a2e0f5004ae58eeed12d53054d2cee31ae0e4..3750d6efddc75627dbe2a8bf701dc3676def96b8 100644 (file)
@@ -17,7 +17,7 @@ TEST.GCC.l = \
         ass avresample avformat avcodec avfilter avutil mp3lame dvdnav \
         dvdread fontconfig fribidi \
         samplerate swscale vpx theoraenc theoradec vorbis vorbisenc ogg x264 \
-        bluray freetype xml2 bz2 z jansson harfbuzz
+        bluray freetype xml2 bz2 z jansson harfbuzz opus
 
 ifeq (1,$(FEATURE.qsv))
     TEST.GCC.D += USE_QSV HAVE_THREADS=1