Re: [libav-devel] [PATCH 07/12] lavfi: Add some common code for OpenCL filtering

2017-06-28 Thread Jun Zhao


On 2017/6/28 5:50, Mark Thompson wrote:
> ---
>  libavfilter/Makefile |   6 +
>  libavfilter/opencl.c | 285 
> +++
>  libavfilter/opencl.h |  74 +++
>  libavfilter/opencl/rgbyuv.cl | 117 ++
>  libavfilter/opencl_source.h  |  24 
>  tools/cl2c   |  20 +++
>  6 files changed, 526 insertions(+)

I guess we can give a general Colour Space Conversions solution based on 
OpenCL, now
I can think some case can't support in this patch. :) e,g:

- YUV422 <-> 420P
- 10bits <-> 8bits
...

>  create mode 100644 libavfilter/opencl.c
>  create mode 100644 libavfilter/opencl.h
>  create mode 100644 libavfilter/opencl/rgbyuv.cl
>  create mode 100644 libavfilter/opencl_source.h
>  create mode 100755 tools/cl2c
> 
> diff --git a/libavfilter/Makefile b/libavfilter/Makefile
> index 348ad9211..1370ef04b 100644
> --- a/libavfilter/Makefile
> +++ b/libavfilter/Makefile
> @@ -106,3 +106,9 @@ OBJS-$(CONFIG_TESTSRC_FILTER)+= 
> vsrc_testsrc.o
>  
>  TOOLS = graph2dot
>  TESTPROGS = filtfmts
> +
> +OPENCL = $(subst $(SRC_PATH)/,,$(wildcard 
> $(SRC_PATH)/libavfilter/opencl/*.cl))
> +.SECONDARY: $(OPENCL:.cl=.c)
> +libavfilter/opencl/%.c: TAG = OPENCL
> +libavfilter/opencl/%.c: $(SRC_PATH)/libavfilter/opencl/%.cl
> + $(M)$(SRC_PATH)/tools/cl2c $< $@
> diff --git a/libavfilter/opencl.c b/libavfilter/opencl.c
> new file mode 100644
> index 0..f7b3f1818
> --- /dev/null
> +++ b/libavfilter/opencl.c
> @@ -0,0 +1,285 @@
> +/*
> + * This file is part of Libav.
> + *
> + * Libav is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU Lesser General Public
> + * License as published by the Free Software Foundation; either
> + * version 2.1 of the License, or (at your option) any later version.
> + *
> + * Libav is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> + * Lesser General Public License for more details.
> + *
> + * You should have received a copy of the GNU Lesser General Public
> + * License along with Libav; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 
> USA
> + */
> +
> +#include 
> +#include 
> +
> +#include "libavutil/hwcontext.h"
> +#include "libavutil/hwcontext_opencl.h"
> +#include "libavutil/mem.h"
> +
> +#include "avfilter.h"
> +#include "formats.h"
> +#include "opencl.h"
> +
> +int ff_opencl_filter_query_formats(AVFilterContext *avctx)
> +{
> +const static enum AVPixelFormat formats[] = {
> +AV_PIX_FMT_OPENCL,
> +AV_PIX_FMT_NONE,
> +};
> +int i;
> +
> +for (i = 0; i < avctx->nb_inputs; i++) {
> +ff_formats_ref(ff_make_format_list(formats),
> +   >inputs[i]->out_formats);
> +}
> +
> +for (i = 0; i < avctx->nb_outputs; i++) {
> +ff_formats_ref(ff_make_format_list(formats),
> +   >outputs[i]->in_formats);
> +}
> +
> +return 0;
> +}
> +
> +int ff_opencl_filter_config_input(AVFilterLink *inlink)
> +{
> +AVFilterContext   *avctx = inlink->dst;
> +OpenCLFilterContext *ctx = avctx->priv;
> +AVHWFramesContext *input_frames;
> +
> +if (!inlink->hw_frames_ctx) {
> +av_log(avctx, AV_LOG_ERROR, "OpenCL filtering requires a "
> +   "hardware frames context on the input.\n");
> +return AVERROR(EINVAL);
> +}
> +
> +// Extract the device and default output format from the first input.
> +if (avctx->inputs[0] != inlink)
> +return 0;
> +
> +input_frames = (AVHWFramesContext*)inlink->hw_frames_ctx->data;
> +
> +if (input_frames->format != AV_PIX_FMT_OPENCL)
> +return AVERROR(EINVAL);
> +
> +ctx->device_ref = av_buffer_ref(input_frames->device_ref);
> +if (!ctx->device_ref)
> +return AVERROR(ENOMEM);
> +ctx->device = input_frames->device_ctx;
> +ctx->hwctx  = ctx->device->hwctx;
> +
> +// Default output parameters match input parameters.
> +if (ctx->output_format == AV_PIX_FMT_NONE)
> +ctx->output_format = input_frames->sw_format;
> +if (!ctx->output_width)
> +ctx->output_width  = inlink->w;
> +if (!ctx->output_height)
> +ctx->output_height = inlink->h;
> +
> +return 0;
> +}
> +
> +int ff_opencl_filter_config_output(AVFilterLink *outlink)
> +{
> +AVFilterContext   *avctx = outlink->src;
> +OpenCLFilterContext *ctx = avctx->priv;
> +AVBufferRef   *output_frames_ref = NULL;
> +AVHWFramesContext *output_frames;
> +int err;
> +
> +av_buffer_unref(>hw_frames_ctx);
> +
> +output_frames_ref = av_hwframe_ctx_alloc(ctx->device_ref);
> +if (!output_frames_ref) {
> +err = AVERROR(ENOMEM);
> +goto fail;
> +}
> +output_frames = 

[libav-devel] [PATCH 24/25] fate: Add ambisonic tests

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 tests/fate/mov.mak| 3 +++
 tests/fate/opus.mak   | 5 +
 tests/ref/fate/mov-ambisonic  | 1 +
 tests/ref/fate/opus-ambisonic | 1 +
 4 files changed, 10 insertions(+)
 create mode 100644 tests/ref/fate/mov-ambisonic
 create mode 100644 tests/ref/fate/opus-ambisonic

diff --git a/tests/fate/mov.mak b/tests/fate/mov.mak
index 9d64fd3a4a..00b447505b 100644
--- a/tests/fate/mov.mak
+++ b/tests/fate/mov.mak
@@ -1,3 +1,6 @@
+FATE_MOV += fate-mov-ambisonic
+fate-mov-ambisonic: CMD = probestream layout 
$(TARGET_SAMPLES)/mov/ambisonic.mp4
+
 FATE_MOV += fate-mov-dar
 fate-mov-dar: CMD = probestream display_aspect_ratio 
$(TARGET_SAMPLES)/mov/displaymatrix.mov
 
diff --git a/tests/fate/opus.mak b/tests/fate/opus.mak
index 161a94f472..2c80de8308 100644
--- a/tests/fate/opus.mak
+++ b/tests/fate/opus.mak
@@ -32,6 +32,11 @@ $(FATE_OPUS): FUZZ = 3
 $(FATE_OPUS_CELT): CMP = oneoff
 $(FATE_OPUS_CELT): FUZZ = 6
 
+# ambisonic does not change coding, only introduces a new map type
+# so a simple probe test should be enough
+FATE_OPUS += fate-opus-ambisonic
+fate-opus-ambisonic: CMD = probestream layout 
$(TARGET_SAMPLES)/opus/11ch-different-talkers.mka
+
 FATE_SAMPLES_AVCONV-$(call DEMDEC, MATROSKA, OPUS) += $(FATE_OPUS)
 fate-opus-celt: $(FATE_OPUS_CELT)
 fate-opus-hybrid: $(FATE_OPUS_HYBRID)
diff --git a/tests/ref/fate/mov-ambisonic b/tests/ref/fate/mov-ambisonic
new file mode 100644
index 00..3ee612c13a
--- /dev/null
+++ b/tests/ref/fate/mov-ambisonic
@@ -0,0 +1 @@
+ambisonic channels 4 order 1
diff --git a/tests/ref/fate/opus-ambisonic b/tests/ref/fate/opus-ambisonic
new file mode 100644
index 00..14f69e13e1
--- /dev/null
+++ b/tests/ref/fate/opus-ambisonic
@@ -0,0 +1 @@
+ambisonic channels 9 order 2|stereo
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 21/25] mov: Implement spatial audio support

2017-06-28 Thread Vittorio Giovara
As defined by Google's Spatial Audio RFC.

Signed-off-by: Vittorio Giovara 
---
 libavformat/mov.c | 98 +++
 1 file changed, 98 insertions(+)

diff --git a/libavformat/mov.c b/libavformat/mov.c
index c90b5fa108..48fd865411 100644
--- a/libavformat/mov.c
+++ b/libavformat/mov.c
@@ -3459,6 +3459,102 @@ static int mov_read_uuid(MOVContext *c, AVIOContext 
*pb, MOVAtom atom)
 return 0;
 }
 
+static int mov_read_SA3D(MOVContext *c, AVIOContext *pb, MOVAtom atom)
+{
+AVStream *st;
+MOVStreamContext *sc;
+int i, version, type;
+int ambisonic_order, channel_order, normalization, channel_count;
+
+if (c->fc->nb_streams < 1)
+return 0;
+
+st = c->fc->streams[c->fc->nb_streams - 1];
+sc = st->priv_data;
+
+if (atom.size < 16) {
+av_log(c->fc, AV_LOG_ERROR, "SA3D audio box too small\n");
+return AVERROR_INVALIDDATA;
+}
+
+version = avio_r8(pb);
+if (version) {
+av_log(c->fc, AV_LOG_WARNING, "Unsupported SA3D box version %d\n", 
version);
+return 0;
+}
+
+type = avio_r8(pb);
+if (type) {
+av_log(c->fc, AV_LOG_WARNING,
+   "Unsupported ambisonic type %d\n", type);
+return 0;
+}
+
+ambisonic_order = avio_rb32(pb);
+
+channel_order = avio_r8(pb);
+if (channel_order) {
+av_log(c->fc, AV_LOG_WARNING,
+   "Unsupported channel_order %d\n", channel_order);
+return 0;
+}
+
+normalization = avio_r8(pb);
+if (normalization) {
+av_log(c->fc, AV_LOG_WARNING,
+   "Unsupported normalization %d\n", normalization);
+return 0;
+}
+
+channel_count = avio_rb32(pb);
+if (ambisonic_order != sqrt(channel_count) - 1) {
+av_log(c->fc, AV_LOG_ERROR,
+   "Invalid number of channels (%d / %d)\n",
+   channel_count, ambisonic_order);
+return 0;
+}
+
+for (i = 0; i < channel_count; i++) {
+if (i != avio_rb32(pb)) {
+av_log(c->fc, AV_LOG_WARNING,
+   "Ambisonic channel reordering is not supported\n");
+return 0;
+}
+}
+
+av_channel_layout_uninit(>codecpar->ch_layout);
+st->codecpar->ch_layout.order = AV_CHANNEL_ORDER_AMBISONIC;
+st->codecpar->ch_layout.nb_channels = channel_count;
+
+return 0;
+}
+
+static int mov_read_SAND(MOVContext *c, AVIOContext *pb, MOVAtom atom)
+{
+AVStream *st;
+int version;
+
+if (c->fc->nb_streams < 1)
+return 0;
+
+st = c->fc->streams[c->fc->nb_streams - 1];
+
+if (atom.size < 5) {
+av_log(c->fc, AV_LOG_ERROR, "Empty SAND audio box\n");
+return AVERROR_INVALIDDATA;
+}
+
+version = avio_r8(pb);
+if (version) {
+av_log(c->fc, AV_LOG_WARNING, "Unsupported SAND box version %d\n", 
version);
+return 0;
+}
+
+st->disposition |= AV_DISPOSITION_NON_DIEGETIC;
+
+return 0;
+}
+
 static const MOVParseTableEntry mov_default_parse_table[] = {
 { MKTAG('a','v','s','s'), mov_read_extradata },
 { MKTAG('c','h','p','l'), mov_read_chpl },
@@ -3523,6 +3619,8 @@ static const MOVParseTableEntry mov_default_parse_table[] 
= {
 { MKTAG('s','t','3','d'), mov_read_st3d }, /* stereoscopic 3D video box */
 { MKTAG('s','v','3','d'), mov_read_sv3d }, /* spherical video box */
 { MKTAG('u','u','i','d'), mov_read_uuid }, /* universal unique identifier */
+{ MKTAG('S','A','3','D'), mov_read_SA3D }, /* ambisonic audio box */
+{ MKTAG('S','A','N','D'), mov_read_SAND }, /* non diegetic audio box */
 { MKTAG('-','-','-','-'), mov_read_custom },
 { 0, NULL }
 };
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 05/25] avtools: Use the new channel layout API in AVFrame

2017-06-28 Thread Vittorio Giovara
---
 avtools/avconv.c| 2 +-
 avtools/avconv_filter.c | 2 +-
 avtools/avplay.c| 4 ++--
 3 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/avtools/avconv.c b/avtools/avconv.c
index 8dd11bb5fc..42cbfef592 100644
--- a/avtools/avconv.c
+++ b/avtools/avconv.c
@@ -1209,7 +1209,7 @@ static int ifilter_send_frame(InputFilter *ifilter, 
AVFrame *frame)
 switch (ifilter->ist->st->codecpar->codec_type) {
 case AVMEDIA_TYPE_AUDIO:
 need_reinit |= ifilter->sample_rate!= frame->sample_rate ||
-   ifilter->channel_layout != frame->channel_layout;
+   ifilter->channel_layout != frame->ch_layout.u.mask;
 break;
 case AVMEDIA_TYPE_VIDEO:
 need_reinit |= ifilter->width  != frame->width ||
diff --git a/avtools/avconv_filter.c b/avtools/avconv_filter.c
index 884478da27..e719c06658 100644
--- a/avtools/avconv_filter.c
+++ b/avtools/avconv_filter.c
@@ -798,7 +798,7 @@ int ifilter_parameters_from_frame(InputFilter *ifilter, 
const AVFrame *frame)
 ifilter->sample_aspect_ratio = frame->sample_aspect_ratio;
 
 ifilter->sample_rate = frame->sample_rate;
-ifilter->channel_layout  = frame->channel_layout;
+ifilter->channel_layout  = frame->ch_layout.u.mask;
 
 if (frame->hw_frames_ctx) {
 ifilter->hw_frames_ctx = av_buffer_ref(frame->hw_frames_ctx);
diff --git a/avtools/avplay.c b/avtools/avplay.c
index b6dbc52cf7..6cc63258fc 100644
--- a/avtools/avplay.c
+++ b/avtools/avplay.c
@@ -1837,11 +1837,11 @@ static int audio_decode_frame(PlayerState *is, double 
*pts_ptr)
is->frame->format, 1);
 
 audio_resample = is->frame->format != is->sdl_sample_fmt   
  ||
- is->frame->channel_layout != 
is->sdl_channel_layout ||
+ is->frame->ch_layout.u.mask != 
is->sdl_channel_layout ||
  is->frame->sample_rate!= is->sdl_sample_rate;
 
 resample_changed = is->frame->format != 
is->resample_sample_fmt ||
-   is->frame->channel_layout != 
is->resample_channel_layout ||
+   is->frame->ch_layout.u.mask != 
is->resample_channel_layout ||
is->frame->sample_rate!= 
is->resample_sample_rate;
 
 if ((!is->avr && audio_resample) || resample_changed) {
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 23/25] avprobe: Print the channel layout string

2017-06-28 Thread Vittorio Giovara
---
 avtools/avprobe.c | 4 
 1 file changed, 4 insertions(+)

diff --git a/avtools/avprobe.c b/avtools/avprobe.c
index 7eab2573eb..9d7eecabb9 100644
--- a/avtools/avprobe.c
+++ b/avtools/avprobe.c
@@ -667,6 +667,7 @@ static void show_stream(InputFile *ifile, InputStream *ist)
 AVRational display_aspect_ratio, *sar = NULL;
 const AVPixFmtDescriptor *desc;
 const char *val;
+char *chlstr;
 
 probe_object_header("stream");
 
@@ -757,6 +758,9 @@ static void show_stream(InputFile *ifile, InputStream *ist)
par->sample_rate,
unit_hertz_str));
 probe_int("channels", par->ch_layout.nb_channels);
+chlstr = av_channel_layout_describe(>ch_layout);
+probe_str("layout", chlstr);
+av_free(chlstr);
 probe_int("bits_per_sample",
   av_get_bits_per_sample(par->codec_id));
 break;
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 22/25] aac: Allow pass-through transcoding of ambisonic audio

2017-06-28 Thread Vittorio Giovara
The defacto mov standard mandates support for PCM and AAC: only the
latter decoder overrides the channel layout passed by the container,
so let this happen only when the layout order is native (or unspecified).

On the encoding side, until full ambisonic channel layout conversion
is implemented, add a temporary layout to allow pass-through transcoding
of files tagged with this specification.

Signed-off-by: Vittorio Giovara 
---
 libavcodec/aacdec.c| 13 -
 libavcodec/libfdk-aacdec.c |  6 --
 libavcodec/libfdk-aacenc.c |  3 ++-
 3 files changed, 14 insertions(+), 8 deletions(-)

diff --git a/libavcodec/aacdec.c b/libavcodec/aacdec.c
index ab184b8634..33b6e3a40a 100644
--- a/libavcodec/aacdec.c
+++ b/libavcodec/aacdec.c
@@ -494,11 +494,14 @@ FF_ENABLE_DEPRECATION_WARNINGS
 }
 }
 
-av_channel_layout_uninit(>oc[1].ch_layout);
-av_channel_layout_from_mask(>oc[1].ch_layout, layout);
-ret = av_channel_layout_copy(>ch_layout, >oc[1].ch_layout);
-if (ret < 0)
-return ret;
+if (avctx->ch_layout.order == AV_CHANNEL_ORDER_NATIVE ||
+avctx->ch_layout.order == AV_CHANNEL_ORDER_UNSPEC) {
+av_channel_layout_uninit(>oc[1].ch_layout);
+av_channel_layout_from_mask(>oc[1].ch_layout, layout);
+ret = av_channel_layout_copy(>ch_layout, >oc[1].ch_layout);
+if (ret < 0)
+return ret;
+}
 #if FF_API_OLD_CHANNEL_LAYOUT
 FF_DISABLE_DEPRECATION_WARNINGS
 avctx->channels   = avctx->ch_layout.nb_channels;
diff --git a/libavcodec/libfdk-aacdec.c b/libavcodec/libfdk-aacdec.c
index 6a77e90392..a8eeb6a1c9 100644
--- a/libavcodec/libfdk-aacdec.c
+++ b/libavcodec/libfdk-aacdec.c
@@ -184,8 +184,10 @@ static int get_stream_info(AVCodecContext *avctx)
 }
 }
 
-av_channel_layout_uninit(>ch_layout);
-av_channel_layout_from_mask(>ch_layout, ch_layout);
+if (avctx->ch_layout.order == AV_CHANNEL_ORDER_NATIVE) {
+av_channel_layout_uninit(>ch_layout);
+av_channel_layout_from_mask(>ch_layout, ch_layout);
+}
 if (!ch_error && avctx->ch_layout.nb_channels != info->numChannels) {
 av_log(avctx, AV_LOG_WARNING, "unsupported channel configuration\n");
 ch_error = 1;
diff --git a/libavcodec/libfdk-aacenc.c b/libavcodec/libfdk-aacenc.c
index f92c14d65f..ec29e1c6ad 100644
--- a/libavcodec/libfdk-aacenc.c
+++ b/libavcodec/libfdk-aacenc.c
@@ -410,7 +410,7 @@ static const uint64_t aac_channel_layout[] = {
 };
 #endif /* FF_API_OLD_CHANNEL_LAYOUT */
 
-static const AVChannelLayout aac_ch_layouts[16] = {
+static const AVChannelLayout aac_ch_layouts[17] = {
 AV_CHANNEL_LAYOUT_MONO,
 AV_CHANNEL_LAYOUT_STEREO,
 AV_CHANNEL_LAYOUT_SURROUND,
@@ -421,6 +421,7 @@ static const AVChannelLayout aac_ch_layouts[16] = {
 AV_CHANNEL_LAYOUT_7POINT1_WIDE_BACK,
 AV_CHANNEL_LAYOUT_7POINT1,
 #endif
+AV_CHANNEL_LAYOUT_AMBISONIC_FIRST_ORDER,
 { 0 },
 };
 
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 20/25] lavf: Add non diegetic stream disposition flag

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavformat/avformat.h | 6 ++
 libavformat/dump.c | 2 ++
 2 files changed, 8 insertions(+)

diff --git a/libavformat/avformat.h b/libavformat/avformat.h
index 1bf66b15d1..47f7a445dd 100644
--- a/libavformat/avformat.h
+++ b/libavformat/avformat.h
@@ -673,6 +673,12 @@ typedef struct AVIndexEntry {
  * It can also be accessed at any time in AVStream.attached_pic.
  */
 #define AV_DISPOSITION_ATTACHED_PIC  0x0400
+/**
+ * The stream is intended to be mixed with a spatial audio track. For example,
+ * it could be used for narration or stereo music, and may remain unchanged by
+ * listener head rotation.
+ */
+#define AV_DISPOSITION_NON_DIEGETIC 0x1000
 
 typedef struct AVStreamInternal AVStreamInternal;
 
diff --git a/libavformat/dump.c b/libavformat/dump.c
index e1f6848547..b29f0ad834 100644
--- a/libavformat/dump.c
+++ b/libavformat/dump.c
@@ -482,6 +482,8 @@ static void dump_stream_format(AVFormatContext *ic, int i,
 av_log(NULL, AV_LOG_INFO, " (visual impaired)");
 if (st->disposition & AV_DISPOSITION_CLEAN_EFFECTS)
 av_log(NULL, AV_LOG_INFO, " (clean effects)");
+if (st->disposition & AV_DISPOSITION_NON_DIEGETIC)
+av_log(NULL, AV_LOG_INFO, " (non diegetic)");
 av_log(NULL, AV_LOG_INFO, "\n");
 
 dump_metadata(NULL, st->metadata, "");
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 25/25] Bump library versions, update Changelog and APIchanges

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 Changelog  |  1 +
 doc/APIchanges | 22 ++
 2 files changed, 23 insertions(+)

diff --git a/Changelog b/Changelog
index e44df54c93..ecff7d0a2b 100644
--- a/Changelog
+++ b/Changelog
@@ -16,6 +16,7 @@ version :
 - FM Screen Capture Codec decoder
 - ClearVideo decoder (I-frames only)
 - support for decoding through D3D11VA in avconv
+- Opus and MP4/MOV ambisonic detection
 
 
 version 12:
diff --git a/doc/APIchanges b/doc/APIchanges
index 0f7c839573..50cf0eba12 100644
--- a/doc/APIchanges
+++ b/doc/APIchanges
@@ -13,6 +13,28 @@ libavutil: 2017-03-23
 
 API changes, most recent first:
 
+20xx-xx-xx - lavu 56.xx.0 lavr 4.xx.0 lavfi 7.xx.0 lavc 58.xx.0 lavf 58.xx.0
+  xxx - Introduce AVChannelLayout and related API: use AVChannel and
+AVChannelOrder to describe a layout, deprecate old functions
+operating on channels and channel_layout fields.
+  xxx - Allow a new AVOption type AV_OPT_TYPE_CHANNEL_LAYOUT, with
+av_opt_set_channel_layout(), and av_opt_get_channel_layout().
+  xxx - Add AVFrame.ch_layout, deprecate channel_layout field.
+  xxx - Add avresample_build_matrix2(), in_ch_layout and out_ch_layout
+options to libavresample, deprecate avresample_build_matrix(), and
+in_channel_layout, out_channel_layout options.
+  xxx - Add AVFilterLink.ch_layout, deprecates channel_layout field.
+  xxx - Add AVBufferSrcParameters.ch_layout, deprecate channel_layout 
field.
+  xxx - Add AVCodecParameters.ch_layout, deprecate channel_layout and
+channels fields.
+  xxx - Add AVCodecContext.ch_layout, deprecate channel_layout and channels
+fields (and options), and replace request_channel_layout with a
+codec private option.
+  xxx - Support Ambisonic ordering in AVChannelLayout with
+AV_CHANNEL_ORDER_AMBISONIC and av_channel_layout_ambisonic() 
helper.
+  xxx - Add AV_DISPOSITION_NON_DIEGETIC flag for detecting streams that
+can be mixed with spatial audio.
+
 2017-xx-xx - xxx - lavc 58.4.0 - avcodec.h
   DXVA2 and D3D11 hardware accelerated decoding now supports the new hwaccel 
API,
   which can create the decoder context and allocate hardware frame 
automatically.
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 12/25] lavc: switch to the new channel layout API

2017-06-28 Thread Vittorio Giovara
Since the request_channel_layout is used only by a handful of codecs,
move the option to codec private contexts.
---
 libavcodec/avcodec.h   |  31 +
 libavcodec/decode.c|  49 +-
 libavcodec/encode.c|   9 ++-
 libavcodec/internal.h  |   2 +
 libavcodec/options_table.h |   5 ++
 libavcodec/utils.c | 162 +
 libavformat/utils.c|  26 +++-
 7 files changed, 220 insertions(+), 64 deletions(-)

diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h
index bc7097c7bd..b0eac85f72 100644
--- a/libavcodec/avcodec.h
+++ b/libavcodec/avcodec.h
@@ -1834,7 +1834,13 @@ typedef struct AVCodecContext {
 
 /* audio only */
 int sample_rate; ///< samples per second
+#if FF_API_OLD_CHANNEL_LAYOUT
+/**
+ * @deprecated use ch_layout.nb_channels
+ */
+attribute_deprecated
 int channels;///< number of audio channels
+#endif
 
 /**
  * audio sample format
@@ -1879,19 +1885,25 @@ typedef struct AVCodecContext {
  */
 int cutoff;
 
+#if FF_API_OLD_CHANNEL_LAYOUT
 /**
  * Audio channel layout.
  * - encoding: set by user.
  * - decoding: set by libavcodec.
+ *   @deprecated use ch_layout
  */
+attribute_deprecated
 uint64_t channel_layout;
 
 /**
  * Request decoder to use this channel layout if it can (0 for default)
  * - encoding: unused
  * - decoding: Set by user.
+ *   @deprecated use "downmix" codec private option
  */
+attribute_deprecated
 uint64_t request_channel_layout;
+#endif
 
 /**
  * Type of service that the audio stream conveys.
@@ -2730,6 +2742,14 @@ typedef struct AVCodecContext {
  * AVCodecContext.get_format callback)
  */
 int hwaccel_flags;
+
+/**
+ * Audio channel layout.
+ * - encoding: must be set by the caller, to one of AVCodec.ch_layouts.
+ * - decoding: may be set by the caller if known e.g. from the container.
+ * The decoder can then override during decoding as needed.
+ */
+AVChannelLayout ch_layout;
 } AVCodecContext;
 
 /**
@@ -2771,10 +2791,21 @@ typedef struct AVCodec {
 const enum AVPixelFormat *pix_fmts; ///< array of supported pixel 
formats, or NULL if unknown, array is terminated by -1
 const int *supported_samplerates;   ///< array of supported audio 
samplerates, or NULL if unknown, array is terminated by 0
 const enum AVSampleFormat *sample_fmts; ///< array of supported sample 
formats, or NULL if unknown, array is terminated by -1
+#if FF_API_OLD_CHANNEL_LAYOUT
+/**
+ * @deprecated use ch_layouts instead
+ */
+attribute_deprecated
 const uint64_t *channel_layouts; ///< array of support channel 
layouts, or NULL if unknown. array is terminated by 0
+#endif
 const AVClass *priv_class;  ///< AVClass for the private 
context
 const AVProfile *profiles;  ///< array of recognized profiles, 
or NULL if unknown, array is terminated by {FF_PROFILE_UNKNOWN}
 
+/**
+ * Array of supported channel layouts, terminated with a zeroed layout.
+ */
+const AVChannelLayout *ch_layouts;
+
 /*
  * No fields below this line are part of the public API. They
  * may not be used outside of libavcodec and can be changed and
diff --git a/libavcodec/decode.c b/libavcodec/decode.c
index b0d6b9fb33..c4bcfb95df 100644
--- a/libavcodec/decode.c
+++ b/libavcodec/decode.c
@@ -1131,27 +1131,42 @@ int ff_get_buffer(AVCodecContext *avctx, AVFrame 
*frame, int flags)
 frame->sample_rate= avctx->sample_rate;
 if (frame->format < 0)
 frame->format = avctx->sample_fmt;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+if (avctx->ch_layout.order == AV_CHANNEL_ORDER_NATIVE ||
+avctx->ch_layout.order == AV_CHANNEL_ORDER_UNSPEC) {
+if (!frame->ch_layout.nb_channels && (avctx->channel_layout || 
avctx->channels)) {
+if (avctx->channel_layout)
+av_channel_layout_from_mask(>ch_layout, 
avctx->channel_layout);
+else
+av_channel_layout_default(>ch_layout, 
avctx->channels);
+}
+}
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 if (!frame->ch_layout.nb_channels) {
-if (avctx->channel_layout)
-av_channel_layout_from_mask(>ch_layout, 
avctx->channel_layout);
-else
-av_channel_layout_default(>ch_layout, avctx->channels);
+ret = av_channel_layout_copy(>ch_layout, >ch_layout);
+if (ret < 0)
+return ret;
 }
 #if FF_API_OLD_CHANNEL_LAYOUT
 FF_DISABLE_DEPRECATION_WARNINGS
-/* set the deprecated channel_layout field for callers
- * that didn't update to the new API yet */
-if 

[libav-devel] [PATCH 16/25] tools, examples changes for the new channel layout API

2017-06-28 Thread Vittorio Giovara
This patch contains the following commits:

avplay: Support the new channel layout API

avconv: Support the new channel layout API

tools: Update to the new channel layout API

examples: Update to the new channel layout API
---
 avtools/avconv.c | 30 +++---
 avtools/avconv.h |  8 +++
 avtools/avconv_filter.c  | 44 ++
 avtools/avconv_opt.c | 48 --
 avtools/avplay.c | 50 +++-
 avtools/cmdutils.c   | 15 +++--
 avtools/cmdutils.h   |  8 ---
 doc/examples/decode_audio.c  |  2 +-
 doc/examples/encode_audio.c  | 36 ++-
 doc/examples/filter_audio.c  | 11 +-
 doc/examples/output.c| 30 ++
 doc/examples/transcode_aac.c | 29 +++--
 tools/graph2dot.c|  7 +++
 tools/ismindex.c |  2 +-
 tools/sidxindex.c|  2 +-
 15 files changed, 185 insertions(+), 137 deletions(-)

diff --git a/avtools/avconv.c b/avtools/avconv.c
index a1427e0cb4..904ea82de8 100644
--- a/avtools/avconv.c
+++ b/avtools/avconv.c
@@ -163,7 +163,7 @@ static void avconv_cleanup(int ret)
 for (j = 0; j < fg->nb_outputs; j++) {
 av_freep(>outputs[j]->name);
 av_freep(>outputs[j]->formats);
-av_freep(>outputs[j]->channel_layouts);
+av_freep(>outputs[j]->ch_layouts);
 av_freep(>outputs[j]->sample_rates);
 av_freep(>outputs[j]);
 }
@@ -1209,7 +1209,8 @@ static int ifilter_send_frame(InputFilter *ifilter, 
AVFrame *frame)
 switch (ifilter->ist->st->codecpar->codec_type) {
 case AVMEDIA_TYPE_AUDIO:
 need_reinit |= ifilter->sample_rate!= frame->sample_rate ||
-   ifilter->channel_layout != frame->ch_layout.u.mask;
+   av_channel_layout_compare(>ch_layout,
+ >ch_layout);
 break;
 case AVMEDIA_TYPE_VIDEO:
 need_reinit |= ifilter->width  != frame->width ||
@@ -1322,24 +1323,6 @@ static int decode(AVCodecContext *avctx, AVFrame *frame, 
int *got_frame, AVPacke
 return 0;
 }
 
-int guess_input_channel_layout(InputStream *ist)
-{
-AVCodecContext *dec = ist->dec_ctx;
-
-if (!dec->channel_layout) {
-char layout_name[256];
-
-dec->channel_layout = av_get_default_channel_layout(dec->channels);
-if (!dec->channel_layout)
-return 0;
-av_get_channel_layout_string(layout_name, sizeof(layout_name),
- dec->channels, dec->channel_layout);
-av_log(NULL, AV_LOG_WARNING, "Guessed Channel Layout for Input Stream "
-   "#%d.%d : %s\n", ist->file_index, ist->st->index, layout_name);
-}
-return 1;
-}
-
 static int decode_audio(InputStream *ist, AVPacket *pkt, int *got_output,
 int *decode_failed)
 {
@@ -1982,6 +1965,7 @@ static int init_output_stream_encode(OutputStream *ost)
 InputStream *ist = get_input_stream(ost);
 AVCodecContext *enc_ctx = ost->enc_ctx;
 AVCodecContext *dec_ctx = NULL;
+int ret;
 
 set_encoder_id(output_files[ost->file_index], ost);
 
@@ -1998,8 +1982,10 @@ static int init_output_stream_encode(OutputStream *ost)
 case AVMEDIA_TYPE_AUDIO:
 enc_ctx->sample_fmt = ost->filter->filter->inputs[0]->format;
 enc_ctx->sample_rate= ost->filter->filter->inputs[0]->sample_rate;
-enc_ctx->channel_layout = 
ost->filter->filter->inputs[0]->ch_layout.u.mask;
-enc_ctx->channels   = 
av_get_channel_layout_nb_channels(enc_ctx->channel_layout);
+ret = av_channel_layout_copy(_ctx->ch_layout,
+ 
>filter->filter->inputs[0]->ch_layout);
+if (ret < 0)
+return ret;
 enc_ctx->time_base  = (AVRational){ 1, enc_ctx->sample_rate };
 break;
 case AVMEDIA_TYPE_VIDEO:
diff --git a/avtools/avconv.h b/avtools/avconv.h
index 4c699333a5..2d3a77ba65 100644
--- a/avtools/avconv.h
+++ b/avtools/avconv.h
@@ -220,7 +220,7 @@ typedef struct InputFilter {
 AVRational sample_aspect_ratio;
 
 int sample_rate;
-uint64_t channel_layout;
+AVChannelLayout ch_layout;
 
 AVBufferRef *hw_frames_ctx;
 
@@ -242,11 +242,11 @@ typedef struct OutputFilter {
 AVRational frame_rate;
 int format;
 int sample_rate;
-uint64_t channel_layout;
+AVChannelLayout ch_layout;
 
 // those are only set if no format is specified and the encoder gives us 
multiple options
 int *formats;
-uint64_t *channel_layouts;
+AVChannelLayout *ch_layouts;
 int *sample_rates;
 } OutputFilter;
 
@@ -499,8 +499,6 @@ void opt_output_file(void *optctx, const char *filename);
 
 void assert_avoptions(AVDictionary *m);
 
-int 

[libav-devel] [PATCH 09/25] lavfi: Port filter negotiation to use the new channel layout API

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavfilter/af_aformat.c  |  30 +---
 libavfilter/af_channelmap.c   |   2 +-
 libavfilter/af_channelsplit.c |   6 ++-
 libavfilter/af_join.c |   2 +-
 libavfilter/avfiltergraph.c   | 109 +++---
 libavfilter/buffersrc.c   |   2 +-
 libavfilter/formats.c |  45 +++--
 libavfilter/formats.h |   4 +-
 8 files changed, 153 insertions(+), 47 deletions(-)

diff --git a/libavfilter/af_aformat.c b/libavfilter/af_aformat.c
index c5aa4f7148..259ece4c0b 100644
--- a/libavfilter/af_aformat.c
+++ b/libavfilter/af_aformat.c
@@ -94,11 +94,29 @@ static int get_sample_rate(const char *samplerate)
 return FFMAX(ret, 0);
 }
 
-static int get_channel_layout(const char *channel_layout)
+static int parse_channel_layout_string(AVFilterContext *ctx)
 {
-AVChannelLayout ch_layout = {0};
-av_channel_layout_from_string(_layout, channel_layout);
-return ch_layout.u.mask;
+AFormatContext *s = ctx->priv;
+char *next, *cur = s->channel_layouts_str, sep = '|';
+int ret;
+
+while (cur) {
+AVChannelLayout fmt = {0};
+next = strchr(cur, sep);
+if (next)
+*next++ = 0;
+
+ret = av_channel_layout_from_string(, cur);
+if (ret < 0) {
+av_log(ctx, AV_LOG_ERROR, "Error parsing channel layout: %s.\n", 
cur);\
+return ret;
+}
+ff_add_channel_layout(>channel_layouts, );
+
+cur = next;
+}
+
+return 0;
 }
 
 static av_cold int init(AVFilterContext *ctx)
@@ -109,10 +127,8 @@ static av_cold int init(AVFilterContext *ctx)
   ff_add_format, av_get_sample_fmt, AV_SAMPLE_FMT_NONE, 
"sample format");
 PARSE_FORMATS(s->sample_rates_str, int, s->sample_rates, ff_add_format,
   get_sample_rate, 0, "sample rate");
-PARSE_FORMATS(s->channel_layouts_str, uint64_t, s->channel_layouts,
-  ff_add_channel_layout, get_channel_layout, 0, "channel 
layout");
 
-return 0;
+return parse_channel_layout_string(ctx);
 }
 
 static int query_formats(AVFilterContext *ctx)
diff --git a/libavfilter/af_channelmap.c b/libavfilter/af_channelmap.c
index 939f056d6f..54ff146c5b 100644
--- a/libavfilter/af_channelmap.c
+++ b/libavfilter/af_channelmap.c
@@ -296,7 +296,7 @@ static int channelmap_query_formats(AVFilterContext *ctx)
 ChannelMapContext *s = ctx->priv;
 AVFilterChannelLayouts *channel_layouts = NULL;
 
-ff_add_channel_layout(_layouts, s->ch_layout.u.mask);
+ff_add_channel_layout(_layouts, >ch_layout);
 
 ff_set_common_formats(ctx, ff_planar_sample_fmts());
 ff_set_common_samplerates(ctx, ff_all_samplerates());
diff --git a/libavfilter/af_channelsplit.c b/libavfilter/af_channelsplit.c
index 41b3051c8c..b13919cdf0 100644
--- a/libavfilter/af_channelsplit.c
+++ b/libavfilter/af_channelsplit.c
@@ -85,16 +85,18 @@ static int query_formats(AVFilterContext *ctx)
 ff_set_common_formats(ctx, ff_planar_sample_fmts());
 ff_set_common_samplerates(ctx, ff_all_samplerates());
 
-ff_add_channel_layout(_layouts, s->ch_layout.u.mask);
+ff_add_channel_layout(_layouts, >ch_layout);
 ff_channel_layouts_ref(in_layouts, >inputs[0]->out_channel_layouts);
 
 for (i = 0; i < ctx->nb_outputs; i++) {
 AVFilterChannelLayouts *out_layouts = NULL;
+AVChannelLayout tmp = {0};
 int ret = av_channel_layout_get_channel(>ch_layout, i);
 if (ret < 0)
 return ret;
 
-ff_add_channel_layout(_layouts, 1ULL << ret);
+av_channel_layout_from_mask(, 1ULL << ret);
+ff_add_channel_layout(_layouts, );
 ff_channel_layouts_ref(out_layouts, 
>outputs[i]->in_channel_layouts);
 }
 
diff --git a/libavfilter/af_join.c b/libavfilter/af_join.c
index 6c000b9257..70dc2d00d7 100644
--- a/libavfilter/af_join.c
+++ b/libavfilter/af_join.c
@@ -234,7 +234,7 @@ static int join_query_formats(AVFilterContext *ctx)
 AVFilterChannelLayouts *layouts = NULL;
 int i;
 
-ff_add_channel_layout(, s->ch_layout.u.mask);
+ff_add_channel_layout(, >ch_layout);
 ff_channel_layouts_ref(layouts, >outputs[0]->in_channel_layouts);
 
 for (i = 0; i < ctx->nb_inputs; i++)
diff --git a/libavfilter/avfiltergraph.c b/libavfilter/avfiltergraph.c
index c72016d2c8..936a791175 100644
--- a/libavfilter/avfiltergraph.c
+++ b/libavfilter/avfiltergraph.c
@@ -374,6 +374,8 @@ static int query_formats(AVFilterGraph *graph, AVClass 
*log_ctx)
 
 static int pick_format(AVFilterLink *link)
 {
+int ret;
+
 if (!link || !link->in_formats)
 return 0;
 
@@ -399,11 +401,15 @@ static int pick_format(AVFilterLink *link)
 link->in_channel_layouts->nb_channel_layouts = 1;
 #if FF_API_OLD_CHANNEL_LAYOUT
 FF_DISABLE_DEPRECATION_WARNINGS
-link->channel_layout = link->in_channel_layouts->channel_layouts[0];
+if 

[libav-devel] [PATCH 17/25] channel_layout: Add Ambisonic components and channel order

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavutil/channel_layout.c | 86 --
 libavutil/channel_layout.h | 33 ++
 2 files changed, 116 insertions(+), 3 deletions(-)

diff --git a/libavutil/channel_layout.c b/libavutil/channel_layout.c
index 285997446d..d4791a9b61 100644
--- a/libavutil/channel_layout.c
+++ b/libavutil/channel_layout.c
@@ -260,7 +260,7 @@ void av_channel_layout_from_mask(AVChannelLayout 
*channel_layout,
 int av_channel_layout_from_string(AVChannelLayout *channel_layout,
   const char *str)
 {
-int i, channels;
+int i, channels, order;
 const char *dup = str;
 uint64_t mask = 0;
 
@@ -309,6 +309,44 @@ int av_channel_layout_from_string(AVChannelLayout 
*channel_layout,
 return 0;
 }
 
+/* ambisonic */
+if (sscanf(str, "ambisonic channels %d order %d", , ) == 2) 
{
+AVChannelLayout extra = {0};
+int harmonics = 0;
+
+// handle nondiegetic channels or half-sphere harmonics
+dup = str;
+while (*dup) {
+char *chname = av_get_token(, "|");
+if (!chname)
+return AVERROR(ENOMEM);
+if (*dup)
+dup++; // skip separator
+
+// no extra channel found
+if (!strcmp(chname, str))
+break;
+
+if (av_channel_from_string(chname) == AV_CHAN_AMBISONIC)
+harmonics++;
+else {
+char *nondiegetic = strstr(str, chname);
+int ret = av_channel_layout_from_string(, nondiegetic);
+// no other channels allowed after nondiegetic
+av_free(chname);
+if (ret < 0)
+return ret;
+break;
+}
+av_free(chname);
+}
+
+channel_layout->nb_channels = channels + harmonics + extra.nb_channels;
+channel_layout->u.mask = extra.u.mask;
+
+return 0;
+}
+
 return AVERROR_INVALIDDATA;
 }
 
@@ -361,6 +399,35 @@ char *av_channel_layout_describe(const AVChannelLayout 
*channel_layout)
 }
 return ret;
 }
+case AV_CHANNEL_ORDER_AMBISONIC: {
+char buf[64];
+int order = floor(sqrt(channel_layout->nb_channels)) - 1;
+int channels = (order + 1) * (order + 1);
+
+snprintf(buf, sizeof(buf), "ambisonic channels %d order %d",
+ channels, order);
+
+// handle nondiegetic channels or half-sphere harmonics
+for (i = channels; i < channel_layout->nb_channels; i++) {
+enum AVChannel chan = 
av_channel_layout_get_channel(channel_layout, i);
+if (chan == AV_CHAN_AMBISONIC) {
+av_strlcat(buf, "|", sizeof(buf));
+av_strlcat(buf, av_channel_name(chan), sizeof(buf));
+}
+}
+if (channel_layout->u.mask) {
+AVChannelLayout extra = {0};
+char *chlstr;
+
+av_channel_layout_from_mask(, channel_layout->u.mask);
+chlstr = av_channel_layout_describe();
+av_strlcat(buf, "|", sizeof(buf));
+av_strlcat(buf, chlstr, sizeof(buf));
+av_free(chlstr);
+}
+
+return av_strdup(buf);
+}
 case AV_CHANNEL_ORDER_UNSPEC: {
 char buf[64];
 snprintf(buf, sizeof(buf), "%d channels", channel_layout->nb_channels);
@@ -381,6 +448,11 @@ int av_channel_layout_get_channel(const AVChannelLayout 
*channel_layout, int idx
 switch (channel_layout->order) {
 case AV_CHANNEL_ORDER_CUSTOM:
 return channel_layout->u.map[idx];
+case AV_CHANNEL_ORDER_AMBISONIC:
+idx -= channel_layout->nb_channels - 
av_popcount64(channel_layout->u.mask);
+if (idx < 0)
+return AV_CHAN_AMBISONIC;
+// fall-through
 case AV_CHANNEL_ORDER_NATIVE:
 for (i = 0; i < 64; i++) {
 if ((1ULL << i) & channel_layout->u.mask && !idx--)
@@ -394,7 +466,7 @@ int av_channel_layout_get_channel(const AVChannelLayout 
*channel_layout, int idx
 int av_channel_layout_channel_index(const AVChannelLayout *channel_layout,
 enum AVChannel channel)
 {
-int i;
+int i, off = 0;
 
 switch (channel_layout->order) {
 case AV_CHANNEL_ORDER_CUSTOM:
@@ -402,12 +474,17 @@ int av_channel_layout_channel_index(const AVChannelLayout 
*channel_layout,
 if (channel_layout->u.map[i] == channel)
 return i;
 return AVERROR(EINVAL);
+case AV_CHANNEL_ORDER_AMBISONIC:
+if (channel == AV_CHAN_AMBISONIC)
+return 0;
+off = channel_layout->nb_channels - 
av_popcount64(channel_layout->u.mask);
+// fall-through
 case AV_CHANNEL_ORDER_NATIVE: {
 uint64_t mask = channel_layout->u.mask;
 if (!(mask & (1ULL << channel)))
 return 

[libav-devel] [PATCH 19/25] opus: Implement mapping type 2 for Ambisonic support

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavcodec/opus.c | 36 
 1 file changed, 28 insertions(+), 8 deletions(-)

diff --git a/libavcodec/opus.c b/libavcodec/opus.c
index 308d104212..6aebb40155 100644
--- a/libavcodec/opus.c
+++ b/libavcodec/opus.c
@@ -347,7 +347,7 @@ av_cold int ff_opus_parse_extradata(AVCodecContext *avctx,
 streams= 1;
 stereo_streams = channels - 1;
 channel_map= default_channel_map;
-} else if (map_type == 1 || map_type == 255) {
+} else if (map_type == 1 || map_type == 2 || map_type == 255) {
 if (extradata_size < 21 + channels) {
 av_log(avctx, AV_LOG_ERROR, "Invalid extradata size: %d\n",
extradata_size);
@@ -363,6 +363,7 @@ av_cold int ff_opus_parse_extradata(AVCodecContext *avctx,
 return AVERROR_INVALIDDATA;
 }
 
+layout = 0;
 if (map_type == 1) {
 if (channels > 8) {
 av_log(avctx, AV_LOG_ERROR,
@@ -371,8 +372,24 @@ av_cold int ff_opus_parse_extradata(AVCodecContext *avctx,
 }
 layout = ff_vorbis_ch_layouts[channels - 1].u.mask;
 channel_reorder = channel_reorder_vorbis;
-} else
-layout = 0;
+} else if (map_type == 2) {
+int ambisonic_order = ff_sqrt(channels) - 1;
+int idx = (ambisonic_order + 1) * (ambisonic_order + 1);
+if (channels <= 227 && (channels == idx || channels == idx + 2)) {
+av_channel_layout_uninit(>ch_layout);
+avctx->ch_layout.order = AV_CHANNEL_ORDER_AMBISONIC;
+avctx->ch_layout.nb_channels = channels;
+
+/* ACN order, followed by two optional channels of 
non-diegetic stereo */
+if (idx != channels)
+avctx->ch_layout.u.mask = AV_CH_LAYOUT_STEREO;
+} else {
+av_log(avctx, AV_LOG_ERROR, "Channel map 2 is only valid for "
+   "channel counts equal to (n + 1)^2 + 2j for {n,j} >= 0 "
+   "(max 227 channels).\n");
+return AVERROR_INVALIDDATA;
+}
+}
 
 channel_map = extradata + 21;
 } else {
@@ -415,11 +432,14 @@ av_cold int ff_opus_parse_extradata(AVCodecContext *avctx,
 }
 }
 
-av_channel_layout_uninit(>ch_layout);
-if (layout)
-av_channel_layout_from_mask(>ch_layout, layout);
-else
-av_channel_layout_default(>ch_layout, channels);
+if (avctx->ch_layout.order == AV_CHANNEL_ORDER_NATIVE) {
+av_channel_layout_uninit(>ch_layout);
+if (layout)
+av_channel_layout_from_mask(>ch_layout, layout);
+else
+av_channel_layout_default(>ch_layout, channels);
+}
+
 s->nb_streams = streams;
 s->nb_stereo_streams  = stereo_streams;
 
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 04/25] avframe: switch to the new channel layout API

2017-06-28 Thread Vittorio Giovara
From: Anton Khirnov 

Signed-off-by: Vittorio Giovara 
---
 libavcodec/decode.c | 67 
 libavcodec/encode.c |  9 ++
 libavutil/frame.c   | 88 +++--
 libavutil/frame.h   | 12 +++-
 4 files changed, 146 insertions(+), 30 deletions(-)

diff --git a/libavcodec/decode.c b/libavcodec/decode.c
index a49cd77e51..b0d6b9fb33 100644
--- a/libavcodec/decode.c
+++ b/libavcodec/decode.c
@@ -132,7 +132,7 @@ static int unrefcount_frame(AVCodecInternal *avci, AVFrame 
*frame)
 memcpy(frame->data, avci->to_free->data, sizeof(frame->data));
 memcpy(frame->linesize, avci->to_free->linesize, sizeof(frame->linesize));
 if (avci->to_free->extended_data != avci->to_free->data) {
-int planes = 
av_get_channel_layout_nb_channels(avci->to_free->channel_layout);
+int planes = avci->to_free->ch_layout.nb_channels;
 int size   = planes * sizeof(*frame->extended_data);
 
 if (!size) {
@@ -153,9 +153,19 @@ static int unrefcount_frame(AVCodecInternal *avci, AVFrame 
*frame)
 frame->format = avci->to_free->format;
 frame->width  = avci->to_free->width;
 frame->height = avci->to_free->height;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 frame->channel_layout = avci->to_free->channel_layout;
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 frame->nb_samples = avci->to_free->nb_samples;
 
+ret = av_channel_layout_copy(>ch_layout, >to_free->ch_layout);
+if (ret < 0) {
+av_frame_unref(frame);
+return ret;
+}
+
 return 0;
 }
 
@@ -887,10 +897,20 @@ static int update_frame_pool(AVCodecContext *avctx, 
AVFrame *frame)
 break;
 }
 case AVMEDIA_TYPE_AUDIO: {
-int ch = av_get_channel_layout_nb_channels(frame->channel_layout);
+int ch = frame->ch_layout.nb_channels;
 int planar = av_sample_fmt_is_planar(frame->format);
 int planes = planar ? ch : 1;
 
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+if (!ch && frame->channel_layout) {
+av_channel_layout_from_mask(>ch_layout, 
frame->channel_layout);
+ch = frame->ch_layout.nb_channels;
+planes = planar ? ch : 1;
+}
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+
 if (pool->format == frame->format && pool->planes == planes &&
 pool->channels == ch && frame->nb_samples == pool->samples)
 return 0;
@@ -,28 +1131,35 @@ int ff_get_buffer(AVCodecContext *avctx, AVFrame 
*frame, int flags)
 frame->sample_rate= avctx->sample_rate;
 if (frame->format < 0)
 frame->format = avctx->sample_fmt;
+if (!frame->ch_layout.nb_channels) {
+if (avctx->channel_layout)
+av_channel_layout_from_mask(>ch_layout, 
avctx->channel_layout);
+else
+av_channel_layout_default(>ch_layout, avctx->channels);
+}
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+/* set the deprecated channel_layout field for callers
+ * that didn't update to the new API yet */
+if (frame->ch_layout.nb_channels > FF_SANE_NB_CHANNELS) {
+av_log(avctx, AV_LOG_ERROR, "Too many channels.\n");
+return AVERROR(EINVAL);
+}
 if (!frame->channel_layout) {
-if (avctx->channel_layout) {
- if (av_get_channel_layout_nb_channels(avctx->channel_layout) 
!=
- avctx->channels) {
- av_log(avctx, AV_LOG_ERROR, "Inconsistent channel "
-"configuration.\n");
- return AVERROR(EINVAL);
- }
-
-frame->channel_layout = avctx->channel_layout;
-} else {
-if (avctx->channels > FF_SANE_NB_CHANNELS) {
-av_log(avctx, AV_LOG_ERROR, "Too many channels: %d.\n",
-   avctx->channels);
-return AVERROR(ENOSYS);
-}
-
-frame->channel_layout = 
av_get_default_channel_layout(avctx->channels);
+if (frame->ch_layout.order == AV_CHANNEL_ORDER_NATIVE)
+frame->channel_layout = frame->ch_layout.u.mask;
+else {
+frame->channel_layout = 
av_get_default_channel_layout(frame->ch_layout.nb_channels);
 if (!frame->channel_layout)
-frame->channel_layout = (1ULL << avctx->channels) - 1;
+frame->channel_layout = (1ULL << 
frame->ch_layout.nb_channels) - 1;
 }
 }
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+if (!av_channel_layout_check(>ch_layout)) {
+av_log(avctx, AV_LOG_ERROR, "Invalid channel layout.\n");
+return AVERROR_INVALIDDATA;
+}
 

[libav-devel] [PATCH 06/25] lavr: switch to the new channel layout API

2017-06-28 Thread Vittorio Giovara
From: Anton Khirnov 

Signed-off-by: Vittorio Giovara 
---
 libavresample/audio_mix.c| 148 ++--
 libavresample/audio_mix_matrix.c | 477 ++-
 libavresample/avresample.h   |  42 +++-
 libavresample/internal.h |  10 +-
 libavresample/options.c  |   8 +
 libavresample/tests/avresample.c |  26 +--
 libavresample/utils.c| 127 +++
 7 files changed, 504 insertions(+), 334 deletions(-)

diff --git a/libavresample/audio_mix.c b/libavresample/audio_mix.c
index 89ecc6ba71..36dff2b979 100644
--- a/libavresample/audio_mix.c
+++ b/libavresample/audio_mix.c
@@ -20,6 +20,7 @@
 
 #include 
 
+#include "libavutil/channel_layout.h"
 #include "libavutil/common.h"
 #include "libavutil/libm.h"
 #include "libavutil/samplefmt.h"
@@ -34,10 +35,8 @@ struct AudioMix {
 AVAudioResampleContext *avr;
 enum AVSampleFormat fmt;
 enum AVMixCoeffType coeff_type;
-uint64_t in_layout;
-uint64_t out_layout;
-int in_channels;
-int out_channels;
+AVChannelLayout in_layout;
+AVChannelLayout out_layout;
 
 int ptr_align;
 int samples_align;
@@ -331,8 +330,8 @@ static av_cold int mix_function_init(AudioMix *am)
 if (!am->mix) {
 av_log(am->avr, AV_LOG_ERROR, "audio_mix: NO FUNCTION FOUND: [fmt=%s] "
"[c=%s] [%d to %d]\n", av_get_sample_fmt_name(am->fmt),
-   coeff_type_names[am->coeff_type], am->in_channels,
-   am->out_channels);
+   coeff_type_names[am->coeff_type], am->in_layout.nb_channels,
+   am->out_layout.nb_channels);
 return AVERROR_PATCHWELCOME;
 }
 return 0;
@@ -358,38 +357,42 @@ AudioMix *ff_audio_mix_alloc(AVAudioResampleContext *avr)
 
 am->fmt  = avr->internal_sample_fmt;
 am->coeff_type   = avr->mix_coeff_type;
-am->in_layout= avr->in_channel_layout;
-am->out_layout   = avr->out_channel_layout;
-am->in_channels  = avr->in_channels;
-am->out_channels = avr->out_channels;
+
+ret = av_channel_layout_copy(>in_layout, >in_ch_layout);
+if (ret < 0)
+goto error;
+ret = av_channel_layout_copy(>out_layout, >out_ch_layout);
+if (ret < 0)
+goto error;
 
 /* build matrix if the user did not already set one */
 if (avr->mix_matrix) {
-ret = ff_audio_mix_set_matrix(am, avr->mix_matrix, avr->in_channels);
+ret = ff_audio_mix_set_matrix(am, avr->mix_matrix, 
avr->in_ch_layout.nb_channels);
 if (ret < 0)
 goto error;
 av_freep(>mix_matrix);
 } else {
-double *matrix_dbl = av_mallocz(avr->out_channels * avr->in_channels *
+double *matrix_dbl = av_mallocz(avr->out_ch_layout.nb_channels *
+avr->in_ch_layout.nb_channels *
 sizeof(*matrix_dbl));
 if (!matrix_dbl)
 goto error;
 
-ret = avresample_build_matrix(avr->in_channel_layout,
-  avr->out_channel_layout,
-  avr->center_mix_level,
-  avr->surround_mix_level,
-  avr->lfe_mix_level,
-  avr->normalize_mix_level,
-  matrix_dbl,
-  avr->in_channels,
-  avr->matrix_encoding);
+ret = avresample_build_matrix2(>in_ch_layout,
+   >out_ch_layout,
+   avr->center_mix_level,
+   avr->surround_mix_level,
+   avr->lfe_mix_level,
+   avr->normalize_mix_level,
+   matrix_dbl,
+   avr->in_ch_layout.nb_channels,
+   avr->matrix_encoding);
 if (ret < 0) {
 av_free(matrix_dbl);
 goto error;
 }
 
-ret = ff_audio_mix_set_matrix(am, matrix_dbl, avr->in_channels);
+ret = ff_audio_mix_set_matrix(am, matrix_dbl, 
avr->in_ch_layout.nb_channels);
 if (ret < 0) {
 av_log(avr, AV_LOG_ERROR, "error setting mix matrix\n");
 av_free(matrix_dbl);
@@ -402,7 +405,7 @@ AudioMix *ff_audio_mix_alloc(AVAudioResampleContext *avr)
 return am;
 
 error:
-av_free(am);
+ff_audio_mix_free();
 return NULL;
 }
 
@@ -422,11 +425,16 @@ void ff_audio_mix_free(AudioMix **am_p)
 memset(am->matrix_q15, 0, sizeof(am->matrix_q15));
 memset(am->matrix_flt, 0, sizeof(am->matrix_flt));
 
+av_channel_layout_uninit(>in_layout);
+av_channel_layout_uninit(>out_layout);
+
 av_freep(am_p);
 }
 
 int ff_audio_mix(AudioMix *am, AudioData *src)
 {
+int 

[libav-devel] [PATCH 18/25] lavr: Only let pass-through ambisonic channel layouts

2017-06-28 Thread Vittorio Giovara
Resampling or conversion to/from ambisonic audio are currently
unsupported features.

Signed-off-by: Vittorio Giovara 
---
 libavresample/utils.c | 8 
 1 file changed, 8 insertions(+)

diff --git a/libavresample/utils.c b/libavresample/utils.c
index 15c827efbe..af2b9dbf2d 100644
--- a/libavresample/utils.c
+++ b/libavresample/utils.c
@@ -70,6 +70,14 @@ int avresample_open(AVAudioResampleContext *avr)
 av_channel_layout_default(>out_ch_layout, 
avr->out_ch_layout.nb_channels);
 }
 
+if (( avr->in_ch_layout.order == AV_CHANNEL_ORDER_AMBISONIC ||
+ avr->out_ch_layout.order == AV_CHANNEL_ORDER_AMBISONIC) &&
+av_channel_layout_compare(>in_ch_layout, >out_ch_layout)) {
+av_log(avr, AV_LOG_ERROR,
+   "Resampling to/from ambisonic channel layouts is not 
supported.\n");
+return AVERROR(ENOSYS);
+}
+
 /* set channel mixing parameters */
 #if FF_API_OLD_CHANNEL_LAYOUT
 if (avr->in_channel_layout) {
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 13/25] aac: convert to new channel layout API

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavcodec/aac.h|  7 +++--
 libavcodec/aac_ac3_parser.c |  9 --
 libavcodec/aaccoder.c   |  2 +-
 libavcodec/aacdec.c | 76 ++---
 libavcodec/aacdectab.h  | 16 ++
 libavcodec/aacenc.c |  2 +-
 libavcodec/aacpsy.c | 10 +++---
 7 files changed, 99 insertions(+), 23 deletions(-)

diff --git a/libavcodec/aac.h b/libavcodec/aac.h
index fed6bf4214..b72af09ca0 100644
--- a/libavcodec/aac.h
+++ b/libavcodec/aac.h
@@ -30,6 +30,7 @@
 #ifndef AVCODEC_AAC_H
 #define AVCODEC_AAC_H
 
+#include "libavutil/channel_layout.h"
 #include "libavutil/float_dsp.h"
 #include "avcodec.h"
 #include "imdct15.h"
@@ -116,8 +117,7 @@ typedef struct OutputConfiguration {
 MPEG4AudioConfig m4ac;
 uint8_t layout_map[MAX_ELEM_ID*4][3];
 int layout_map_tags;
-int channels;
-uint64_t channel_layout;
+AVChannelLayout ch_layout;
 enum OCStatus status;
 } OutputConfiguration;
 
@@ -260,6 +260,7 @@ typedef struct ChannelElement {
  * main AAC context
  */
 typedef struct AACContext {
+const AVClass *class;
 AVCodecContext *avctx;
 AVFrame *frame;
 
@@ -306,6 +307,8 @@ typedef struct AACContext {
 DECLARE_ALIGNED(32, float, temp)[128];
 
 OutputConfiguration oc[2];
+
+AVChannelLayout downmix_layout;
 } AACContext;
 
 #endif /* AVCODEC_AAC_H */
diff --git a/libavcodec/aac_ac3_parser.c b/libavcodec/aac_ac3_parser.c
index a754f4a957..17e88435f8 100644
--- a/libavcodec/aac_ac3_parser.c
+++ b/libavcodec/aac_ac3_parser.c
@@ -82,8 +82,13 @@ get_next:
seconds is still correct (as is the number of bits in the frame). */
 if (avctx->codec_id != AV_CODEC_ID_AAC) {
 avctx->sample_rate = s->sample_rate;
-avctx->channels = s->channels;
-avctx->channel_layout = s->channel_layout;
+
+av_channel_layout_uninit(>ch_layout);
+if (s->channel_layout)
+av_channel_layout_from_mask(>ch_layout, s->channel_layout);
+else
+av_channel_layout_default(>ch_layout, s->channels);
+
 s1->duration = s->samples;
 avctx->audio_service_type = s->service_type;
 }
diff --git a/libavcodec/aaccoder.c b/libavcodec/aaccoder.c
index a654844cd0..ec936d89ad 100644
--- a/libavcodec/aaccoder.c
+++ b/libavcodec/aaccoder.c
@@ -710,7 +710,7 @@ static void search_for_quantizers_twoloop(AVCodecContext 
*avctx,
   const float lambda)
 {
 int start = 0, i, w, w2, g;
-int destbits = avctx->bit_rate * 1024.0 / avctx->sample_rate / 
avctx->channels * (lambda / 120.f);
+int destbits = avctx->bit_rate * 1024.0 / avctx->sample_rate / 
avctx->ch_layout.nb_channels * (lambda / 120.f);
 float dists[128] = { 0 }, uplims[128];
 float maxvals[128];
 int fflag, minscaler;
diff --git a/libavcodec/aacdec.c b/libavcodec/aacdec.c
index e436b4f2f7..ab184b8634 100644
--- a/libavcodec/aacdec.c
+++ b/libavcodec/aacdec.c
@@ -81,6 +81,7 @@
  */
 
 #include "libavutil/float_dsp.h"
+#include "libavutil/opt.h"
 #include "avcodec.h"
 #include "internal.h"
 #include "get_bits.h"
@@ -193,7 +194,7 @@ static int frame_configure_elements(AVCodecContext *avctx)
 }
 
 /* map output channel pointers to AVFrame data */
-for (ch = 0; ch < avctx->channels; ch++) {
+for (ch = 0; ch < avctx->ch_layout.nb_channels; ch++) {
 if (ac->output_element[ch])
 ac->output_element[ch]->ret = (float 
*)ac->frame->extended_data[ch];
 }
@@ -432,8 +433,7 @@ static void push_output_configuration(AACContext *ac) {
 static void pop_output_configuration(AACContext *ac) {
 if (ac->oc[1].status != OC_LOCKED && ac->oc[0].status != OC_NONE) {
 ac->oc[1] = ac->oc[0];
-ac->avctx->channels = ac->oc[1].channels;
-ac->avctx->channel_layout = ac->oc[1].channel_layout;
+av_channel_layout_copy(>avctx->ch_layout, >oc[1].ch_layout);
 }
 }
 
@@ -464,7 +464,15 @@ static int output_configure(AACContext *ac,
 }
 // Try to sniff a reasonable channel order, otherwise output the
 // channels in the order the PCE declared them.
-if (avctx->request_channel_layout != AV_CH_LAYOUT_NATIVE)
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+if (avctx->request_channel_layout) {
+av_channel_layout_uninit(>downmix_layout);
+av_channel_layout_from_mask(>downmix_layout, 
avctx->request_channel_layout);
+}
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+if (ac->downmix_layout.order == AV_CHANNEL_ORDER_NATIVE)
 layout = sniff_channel_order(layout_map, tags);
 for (i = 0; i < tags; i++) {
 int type = layout_map[i][0];
@@ -486,8 +494,18 @@ static int output_configure(AACContext *ac,
 }
 }
 
-avctx->channel_layout = ac->oc[1].channel_layout = layout;
-avctx->channels   = ac->oc[1].channels   = channels;
+

[libav-devel] [PATCH 14/25] ac3: convert to new channel layout API

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavcodec/ac3dec.c   | 49 +---
 libavcodec/ac3dec.h   |  2 ++
 libavcodec/ac3enc.c   | 83 ---
 libavcodec/ac3enc.h   |  4 ++-
 libavcodec/ac3enc_fixed.c |  5 +++
 libavcodec/ac3enc_float.c |  5 +++
 libavcodec/eac3enc.c  |  5 +++
 tests/fate/ac3.mak| 12 +++
 8 files changed, 128 insertions(+), 37 deletions(-)

diff --git a/libavcodec/ac3dec.c b/libavcodec/ac3dec.c
index 4be0f1f411..3d3414f7d7 100644
--- a/libavcodec/ac3dec.c
+++ b/libavcodec/ac3dec.c
@@ -172,6 +172,8 @@ static av_cold void ac3_tables_init(void)
 static av_cold int ac3_decode_init(AVCodecContext *avctx)
 {
 AC3DecodeContext *s = avctx->priv_data;
+static AVChannelLayout mono   = (AVChannelLayout)AV_CHANNEL_LAYOUT_MONO;
+static AVChannelLayout stereo = (AVChannelLayout)AV_CHANNEL_LAYOUT_STEREO;
 int i;
 
 s->avctx = avctx;
@@ -190,12 +192,23 @@ static av_cold int ac3_decode_init(AVCodecContext *avctx)
 avctx->sample_fmt = AV_SAMPLE_FMT_FLTP;
 
 /* allow downmixing to stereo or mono */
-if (avctx->channels > 1 &&
-avctx->request_channel_layout == AV_CH_LAYOUT_MONO)
-avctx->channels = 1;
-else if (avctx->channels > 2 &&
- avctx->request_channel_layout == AV_CH_LAYOUT_STEREO)
-avctx->channels = 2;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+if (avctx->request_channel_layout) {
+av_channel_layout_uninit(>downmix_layout);
+av_channel_layout_from_mask(>downmix_layout, 
avctx->request_channel_layout);
+}
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+if (avctx->ch_layout.nb_channels > 1 &&
+!av_channel_layout_compare(>downmix_layout, )) {
+av_channel_layout_uninit(>ch_layout);
+avctx->ch_layout = (AVChannelLayout)AV_CHANNEL_LAYOUT_MONO;
+} else if (avctx->ch_layout.nb_channels > 2 &&
+ !av_channel_layout_compare(>downmix_layout, )) {
+av_channel_layout_uninit(>ch_layout);
+avctx->ch_layout = (AVChannelLayout)AV_CHANNEL_LAYOUT_STEREO;
+}
 s->downmixed = 1;
 
 for (i = 0; i < AC3_MAX_CHANNELS; i++) {
@@ -1364,6 +1377,7 @@ static int ac3_decode_frame(AVCodecContext * avctx, void 
*data,
 const float *output[AC3_MAX_CHANNELS];
 enum AVMatrixEncoding matrix_encoding;
 AVDownmixInfo *downmix_info;
+uint64_t mask;
 
 /* copy input buffer to decoder context to avoid reading past the end
of the buffer, which can be caused by a damaged input stream. */
@@ -1440,16 +1454,19 @@ static int ac3_decode_frame(AVCodecContext * avctx, 
void *data,
 
 /* channel config */
 if (!err || (s->channels && s->out_channels != s->channels)) {
+static AVChannelLayout mono   = 
(AVChannelLayout)AV_CHANNEL_LAYOUT_MONO;
+static AVChannelLayout stereo = 
(AVChannelLayout)AV_CHANNEL_LAYOUT_STEREO;
+
 s->out_channels = s->channels;
 s->output_mode  = s->channel_mode;
 if (s->lfe_on)
 s->output_mode |= AC3_OUTPUT_LFEON;
 if (s->channels > 1 &&
-avctx->request_channel_layout == AV_CH_LAYOUT_MONO) {
+!av_channel_layout_compare(>downmix_layout, )) {
 s->out_channels = 1;
 s->output_mode  = AC3_CHMODE_MONO;
 } else if (s->channels > 2 &&
-   avctx->request_channel_layout == AV_CH_LAYOUT_STEREO) {
+   !av_channel_layout_compare(>downmix_layout, )) {
 s->out_channels = 2;
 s->output_mode  = AC3_CHMODE_STEREO;
 }
@@ -1466,10 +1483,19 @@ static int ac3_decode_frame(AVCodecContext * avctx, 
void *data,
 av_log(avctx, AV_LOG_ERROR, "unable to determine channel mode\n");
 return AVERROR_INVALIDDATA;
 }
-avctx->channels = s->out_channels;
-avctx->channel_layout = avpriv_ac3_channel_layout_tab[s->output_mode & 
~AC3_OUTPUT_LFEON];
+
+mask = avpriv_ac3_channel_layout_tab[s->output_mode & ~AC3_OUTPUT_LFEON];
 if (s->output_mode & AC3_OUTPUT_LFEON)
-avctx->channel_layout |= AV_CH_LOW_FREQUENCY;
+mask |= AV_CH_LOW_FREQUENCY;
+
+av_channel_layout_uninit(>ch_layout);
+av_channel_layout_from_mask(>ch_layout, mask);
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+avctx->channels = avctx->ch_layout.nb_channels;
+avctx->channel_layout = avctx->ch_layout.u.mask;
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 
 /* set audio service type based on bitstream mode for AC-3 */
 avctx->audio_service_type = s->bitstream_mode;
@@ -1588,6 +1614,7 @@ static av_cold int ac3_decode_end(AVCodecContext *avctx)
 #define PAR (AV_OPT_FLAG_DECODING_PARAM | AV_OPT_FLAG_AUDIO_PARAM)
 static const AVOption options[] = {
 { "drc_scale", "percentage of dynamic range compression to apply", 
OFFSET(drc_scale), AV_OPT_TYPE_FLOAT, {.dbl = 1.0}, 0.0, 6.0, PAR },
+{ "downmix", "Request 

[libav-devel] [PATCH 03/25] lavc: deprecate channel count/layout changing side data

2017-06-28 Thread Vittorio Giovara
From: Anton Khirnov 

They are incompatible with the new channel layout scheme and no decoder
uses them.

Signed-off-by: Vittorio Giovara 
---
 libavcodec/avcodec.h | 5 +
 libavcodec/decode.c  | 4 
 libavformat/dump.c   | 9 -
 libavformat/utils.c  | 9 +
 4 files changed, 26 insertions(+), 1 deletion(-)

diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h
index 162f1abe4b..4089c08a24 100644
--- a/libavcodec/avcodec.h
+++ b/libavcodec/avcodec.h
@@ -1165,8 +1165,13 @@ typedef struct AVPacket {
 #define AV_PKT_FLAG_CORRUPT 0x0002 ///< The packet content is corrupted
 
 enum AVSideDataParamChangeFlags {
+#if FF_API_OLD_CHANNEL_LAYOUT
+/**
+ * @deprecated those are not used by any decoder
+ */
 AV_SIDE_DATA_PARAM_CHANGE_CHANNEL_COUNT  = 0x0001,
 AV_SIDE_DATA_PARAM_CHANGE_CHANNEL_LAYOUT = 0x0002,
+#endif
 AV_SIDE_DATA_PARAM_CHANGE_SAMPLE_RATE= 0x0004,
 AV_SIDE_DATA_PARAM_CHANGE_DIMENSIONS = 0x0008,
 };
diff --git a/libavcodec/decode.c b/libavcodec/decode.c
index 175a6fae4c..a49cd77e51 100644
--- a/libavcodec/decode.c
+++ b/libavcodec/decode.c
@@ -60,6 +60,8 @@ static int apply_param_change(AVCodecContext *avctx, AVPacket 
*avpkt)
 flags = bytestream_get_le32();
 size -= 4;
 
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 if (flags & AV_SIDE_DATA_PARAM_CHANGE_CHANNEL_COUNT) {
 if (size < 4)
 goto fail;
@@ -72,6 +74,8 @@ static int apply_param_change(AVCodecContext *avctx, AVPacket 
*avpkt)
 avctx->channel_layout = bytestream_get_le64();
 size -= 8;
 }
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 if (flags & AV_SIDE_DATA_PARAM_CHANGE_SAMPLE_RATE) {
 if (size < 4)
 goto fail;
diff --git a/libavformat/dump.c b/libavformat/dump.c
index 261e21efd3..e1f6848547 100644
--- a/libavformat/dump.c
+++ b/libavformat/dump.c
@@ -142,8 +142,11 @@ static void dump_paramchange(void *ctx, AVPacketSideData 
*sd)
 {
 int size = sd->size;
 const uint8_t *data = sd->data;
-uint32_t flags, channels, sample_rate, width, height;
+uint32_t flags, sample_rate, width, height;
+#if FF_API_OLD_CHANNEL_LAYOUT
+uint32_t channels;
 uint64_t layout;
+#endif
 
 if (!data || sd->size < 4)
 goto fail;
@@ -152,6 +155,8 @@ static void dump_paramchange(void *ctx, AVPacketSideData 
*sd)
 data += 4;
 size -= 4;
 
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 if (flags & AV_SIDE_DATA_PARAM_CHANGE_CHANNEL_COUNT) {
 if (size < 4)
 goto fail;
@@ -169,6 +174,8 @@ static void dump_paramchange(void *ctx, AVPacketSideData 
*sd)
 av_log(ctx, AV_LOG_INFO,
"channel layout: %s, ", av_get_channel_name(layout));
 }
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif /* FF_API_OLD_CHANNEL_LAYOUT */
 if (flags & AV_SIDE_DATA_PARAM_CHANGE_SAMPLE_RATE) {
 if (size < 4)
 goto fail;
diff --git a/libavformat/utils.c b/libavformat/utils.c
index eaba473914..c8bb04aa70 100644
--- a/libavformat/utils.c
+++ b/libavformat/utils.c
@@ -3234,6 +3234,9 @@ int ff_add_param_change(AVPacket *pkt, int32_t channels,
 uint8_t *data;
 if (!pkt)
 return AVERROR(EINVAL);
+
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 if (channels) {
 size  += 4;
 flags |= AV_SIDE_DATA_PARAM_CHANGE_CHANNEL_COUNT;
@@ -3242,6 +3245,8 @@ int ff_add_param_change(AVPacket *pkt, int32_t channels,
 size  += 8;
 flags |= AV_SIDE_DATA_PARAM_CHANGE_CHANNEL_LAYOUT;
 }
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 if (sample_rate) {
 size  += 4;
 flags |= AV_SIDE_DATA_PARAM_CHANGE_SAMPLE_RATE;
@@ -3254,10 +3259,14 @@ int ff_add_param_change(AVPacket *pkt, int32_t channels,
 if (!data)
 return AVERROR(ENOMEM);
 bytestream_put_le32(, flags);
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 if (channels)
 bytestream_put_le32(, channels);
 if (channel_layout)
 bytestream_put_le64(, channel_layout);
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 if (sample_rate)
 bytestream_put_le32(, sample_rate);
 if (width || height) {
-- 
2.13.1

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

[libav-devel] [PATCH 10/25] avcodecpar: switch to the new channel layout API

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavcodec/avcodec.h  | 11 +++
 libavcodec/utils.c| 31 +++
 libavformat/audiointerleave.c |  2 +-
 libavformat/mux.c |  2 +-
 4 files changed, 40 insertions(+), 6 deletions(-)

diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h
index 4089c08a24..bc7097c7bd 100644
--- a/libavcodec/avcodec.h
+++ b/libavcodec/avcodec.h
@@ -3202,16 +3202,22 @@ typedef struct AVCodecParameters {
 enum AVColorSpace  color_space;
 enum AVChromaLocation  chroma_location;
 
+#if FF_API_OLD_CHANNEL_LAYOUT
 /**
  * Audio only. The channel layout bitmask. May be 0 if the channel layout 
is
  * unknown or unspecified, otherwise the number of bits set must be equal 
to
  * the channels field.
+ * @deprecated use ch_layout
  */
+attribute_deprecated
 uint64_t channel_layout;
 /**
  * Audio only. The number of audio channels.
+ * @deprecated use ch_layout.nb_channels
  */
+attribute_deprecated
 int  channels;
+#endif
 /**
  * Audio only. The number of audio samples per second.
  */
@@ -3238,6 +3244,11 @@ typedef struct AVCodecParameters {
  * audio without any trailing padding.
  */
 int trailing_padding;
+
+/**
+ * Audio only. The channel layout and number of channels.
+ */
+AVChannelLayout ch_layout;
 } AVCodecParameters;
 
 /**
diff --git a/libavcodec/utils.c b/libavcodec/utils.c
index bc421f67f8..f8ae415d52 100644
--- a/libavcodec/utils.c
+++ b/libavcodec/utils.c
@@ -1300,8 +1300,15 @@ int av_get_audio_frame_duration(AVCodecContext *avctx, 
int frame_bytes)
 
 int av_get_audio_frame_duration2(AVCodecParameters *par, int frame_bytes)
 {
+int channels = par->ch_layout.nb_channels;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+if (!channels)
+channels = par->channels;
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
 return get_audio_frame_duration(par->codec_id, par->sample_rate,
-par->channels, par->block_align,
+channels, par->block_align,
 par->codec_tag, par->bits_per_coded_sample,
 frame_bytes);
 }
@@ -1588,7 +1595,7 @@ int avcodec_parameters_copy(AVCodecParameters *dst, const 
AVCodecParameters *src
 dst->extradata_size = src->extradata_size;
 }
 
-return 0;
+return av_channel_layout_copy(>ch_layout, >ch_layout);
 }
 
 int avcodec_parameters_from_context(AVCodecParameters *par,
@@ -1620,8 +1627,16 @@ int avcodec_parameters_from_context(AVCodecParameters 
*par,
 break;
 case AVMEDIA_TYPE_AUDIO:
 par->format  = codec->sample_fmt;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 par->channel_layout  = codec->channel_layout;
 par->channels= codec->channels;
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+if (codec->channel_layout)
+av_channel_layout_from_mask(>ch_layout, 
codec->channel_layout);
+else
+av_channel_layout_default(>ch_layout, codec->channels);
 par->sample_rate = codec->sample_rate;
 par->block_align = codec->block_align;
 par->initial_padding = codec->initial_padding;
@@ -1666,8 +1681,16 @@ int avcodec_parameters_to_context(AVCodecContext *codec,
 break;
 case AVMEDIA_TYPE_AUDIO:
 codec->sample_fmt  = par->format;
-codec->channel_layout  = par->channel_layout;
-codec->channels= par->channels;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+codec->channel_layout = par->channel_layout;
+codec->channels   = par->channels;
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+if (par->ch_layout.u.mask)
+codec->channel_layout = par->ch_layout.u.mask;
+if (par->ch_layout.nb_channels)
+codec->channels = par->ch_layout.nb_channels;
 codec->sample_rate = par->sample_rate;
 codec->block_align = par->block_align;
 codec->initial_padding = par->initial_padding;
diff --git a/libavformat/audiointerleave.c b/libavformat/audiointerleave.c
index aa379f675e..4923c55b35 100644
--- a/libavformat/audiointerleave.c
+++ b/libavformat/audiointerleave.c
@@ -52,7 +52,7 @@ int ff_audio_interleave_init(AVFormatContext *s,
 AudioInterleaveContext *aic = st->priv_data;
 
 if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO) {
-aic->sample_size = (st->codecpar->channels *
+aic->sample_size = (st->codecpar->ch_layout.nb_channels *
 
av_get_bits_per_sample(st->codecpar->codec_id)) / 8;
 if (!aic->sample_size) {
 av_log(s, AV_LOG_ERROR, "could not compute sample size\n");
diff --git a/libavformat/mux.c b/libavformat/mux.c

[libav-devel] [PATCH 08/25] libavfilter changes for the new channel layout API

2017-06-28 Thread Vittorio Giovara
This patch contains the following commits:

avtools: Use the new channel layout API in libavfilter

af_aformat: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_amix: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_ashowinfo: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_asyncts: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_atrim: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_channelmap: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_channelsplit: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_compand: convert to new channel layout API

Signed-off-by: Vittorio Giovara 

af_hdcd: convert to new channel layout API

af_join: convert to new channel layout API

af_resample: convert to new channel layout API

af_volume: convert to new channel layout
---
 avtools/avconv.c  |  2 +-
 avtools/avconv_filter.c   |  4 +-
 libavfilter/af_aformat.c  | 10 -
 libavfilter/af_amix.c | 11 --
 libavfilter/af_ashowinfo.c| 12 +++---
 libavfilter/af_asyncts.c  |  6 +--
 libavfilter/af_channelmap.c   | 92 ---
 libavfilter/af_channelsplit.c | 38 +-
 libavfilter/af_compand.c  |  8 ++--
 libavfilter/af_hdcd.c |  2 +-
 libavfilter/af_join.c | 84 ++-
 libavfilter/af_resample.c | 33 +---
 libavfilter/af_volume.c   |  2 +-
 libavfilter/trim.c|  3 +-
 14 files changed, 163 insertions(+), 144 deletions(-)

diff --git a/avtools/avconv.c b/avtools/avconv.c
index 42cbfef592..a1427e0cb4 100644
--- a/avtools/avconv.c
+++ b/avtools/avconv.c
@@ -1998,7 +1998,7 @@ static int init_output_stream_encode(OutputStream *ost)
 case AVMEDIA_TYPE_AUDIO:
 enc_ctx->sample_fmt = ost->filter->filter->inputs[0]->format;
 enc_ctx->sample_rate= ost->filter->filter->inputs[0]->sample_rate;
-enc_ctx->channel_layout = 
ost->filter->filter->inputs[0]->channel_layout;
+enc_ctx->channel_layout = 
ost->filter->filter->inputs[0]->ch_layout.u.mask;
 enc_ctx->channels   = 
av_get_channel_layout_nb_channels(enc_ctx->channel_layout);
 enc_ctx->time_base  = (AVRational){ 1, enc_ctx->sample_rate };
 break;
diff --git a/avtools/avconv_filter.c b/avtools/avconv_filter.c
index e719c06658..7df64c647a 100644
--- a/avtools/avconv_filter.c
+++ b/avtools/avconv_filter.c
@@ -591,7 +591,7 @@ static int configure_input_audio_filter(FilterGraph *fg, 
InputFilter *ifilter,
 par->time_base  = (AVRational){ 1, ifilter->sample_rate };
 par->sample_rate= ifilter->sample_rate;
 par->format = ifilter->format;
-par->channel_layout = ifilter->channel_layout;
+av_channel_layout_from_mask(>ch_layout, ifilter->channel_layout);
 
 ret = av_buffersrc_parameters_set(ifilter->filter, par);
 av_freep();
@@ -758,7 +758,7 @@ int configure_filtergraph(FilterGraph *fg)
 ofilter->height = link->h;
 
 ofilter->sample_rate= link->sample_rate;
-ofilter->channel_layout = link->channel_layout;
+ofilter->channel_layout = link->ch_layout.u.mask;
 }
 
 for (i = 0; i < fg->nb_inputs; i++) {
diff --git a/libavfilter/af_aformat.c b/libavfilter/af_aformat.c
index f0746737dc..c5aa4f7148 100644
--- a/libavfilter/af_aformat.c
+++ b/libavfilter/af_aformat.c
@@ -94,6 +94,13 @@ static int get_sample_rate(const char *samplerate)
 return FFMAX(ret, 0);
 }
 
+static int get_channel_layout(const char *channel_layout)
+{
+AVChannelLayout ch_layout = {0};
+av_channel_layout_from_string(_layout, channel_layout);
+return ch_layout.u.mask;
+}
+
 static av_cold int init(AVFilterContext *ctx)
 {
 AFormatContext *s = ctx->priv;
@@ -103,8 +110,7 @@ static av_cold int init(AVFilterContext *ctx)
 PARSE_FORMATS(s->sample_rates_str, int, s->sample_rates, ff_add_format,
   get_sample_rate, 0, "sample rate");
 PARSE_FORMATS(s->channel_layouts_str, uint64_t, s->channel_layouts,
-  ff_add_channel_layout, av_get_channel_layout, 0,
-  "channel layout");
+  ff_add_channel_layout, get_channel_layout, 0, "channel 
layout");
 
 return 0;
 }
diff --git a/libavfilter/af_amix.c b/libavfilter/af_amix.c
index bfba1504ea..a35e04530f 100644
--- a/libavfilter/af_amix.c
+++ b/libavfilter/af_amix.c
@@ -226,7 +226,7 @@ static int config_output(AVFilterLink *outlink)
 AVFilterContext *ctx = outlink->src;
 MixContext *s  = ctx->priv;
 int i;
-char buf[64];
+char *chlstr;
 
 s->planar  = 

[libav-devel] [PATCH 07/25] lavfi, buffersrc: switch to the new channel layout API

2017-06-28 Thread Vittorio Giovara
Signed-off-by: Vittorio Giovara 
---
 libavfilter/audio.c | 17 +--
 libavfilter/avfilter.c  |  9 
 libavfilter/avfilter.h  | 13 ++-
 libavfilter/avfiltergraph.c | 35 +++---
 libavfilter/buffersink.c|  2 +-
 libavfilter/buffersrc.c | 53 -
 libavfilter/buffersrc.h | 12 +-
 libavfilter/fifo.c  |  7 +++---
 8 files changed, 106 insertions(+), 42 deletions(-)

diff --git a/libavfilter/audio.c b/libavfilter/audio.c
index 5fe9da95c3..afd8bdc169 100644
--- a/libavfilter/audio.c
+++ b/libavfilter/audio.c
@@ -31,7 +31,7 @@ AVFrame *ff_null_get_audio_buffer(AVFilterLink *link, int 
nb_samples)
 AVFrame *ff_default_get_audio_buffer(AVFilterLink *link, int nb_samples)
 {
 AVFrame *frame = av_frame_alloc();
-int channels = av_get_channel_layout_nb_channels(link->channel_layout);
+int channels = link->ch_layout.nb_channels;
 int ret;
 
 if (!frame)
@@ -39,7 +39,20 @@ AVFrame *ff_default_get_audio_buffer(AVFilterLink *link, int 
nb_samples)
 
 frame->nb_samples = nb_samples;
 frame->format = link->format;
-frame->channel_layout = link->channel_layout;
+
+ret = av_channel_layout_copy(>ch_layout, >ch_layout);
+if (ret < 0) {
+av_frame_free();
+return NULL;
+}
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
+if (link->ch_layout.order == AV_CHANNEL_ORDER_NATIVE ||
+link->ch_layout.order == AV_CHANNEL_ORDER_UNSPEC)
+frame->channel_layout = link->channel_layout;
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+
 frame->sample_rate= link->sample_rate;
 ret = av_frame_get_buffer(frame, 0);
 if (ret < 0) {
diff --git a/libavfilter/avfilter.c b/libavfilter/avfilter.c
index 83c1a7c20d..f2adefff3d 100644
--- a/libavfilter/avfilter.c
+++ b/libavfilter/avfilter.c
@@ -247,16 +247,15 @@ void ff_dlog_link(void *ctx, AVFilterLink *link, int end)
 link->dst ? link->dst->filter->name : "",
 end ? "\n" : "");
 } else {
-char buf[128];
-av_get_channel_layout_string(buf, sizeof(buf), -1, 
link->channel_layout);
-
+char *chlstr = av_channel_layout_describe(>ch_layout);
 av_log(ctx, AV_LOG_TRACE,
 "link[%p r:%d cl:%s fmt:%-16s %-16s->%-16s]%s",
-link, link->sample_rate, buf,
+link, link->sample_rate, chlstr,
 av_get_sample_fmt_name(link->format),
 link->src ? link->src->filter->name : "",
 link->dst ? link->dst->filter->name : "",
 end ? "\n" : "");
+av_free(chlstr);
 }
 }
 
@@ -683,7 +682,7 @@ int ff_filter_frame(AVFilterLink *link, AVFrame *frame)
 case AVMEDIA_TYPE_AUDIO:
 av_samples_copy(out->extended_data, frame->extended_data,
 0, 0, frame->nb_samples,
-
av_get_channel_layout_nb_channels(frame->channel_layout),
+frame->ch_layout.nb_channels,
 frame->format);
 break;
 default:
diff --git a/libavfilter/avfilter.h b/libavfilter/avfilter.h
index 6df69dbbbf..5d5edf0ed3 100644
--- a/libavfilter/avfilter.h
+++ b/libavfilter/avfilter.h
@@ -36,6 +36,7 @@
 #include "libavutil/attributes.h"
 #include "libavutil/avutil.h"
 #include "libavutil/buffer.h"
+#include "libavutil/channel_layout.h"
 #include "libavutil/frame.h"
 #include "libavutil/log.h"
 #include "libavutil/samplefmt.h"
@@ -334,7 +335,12 @@ struct AVFilterLink {
 int h;  ///< agreed upon image height
 AVRational sample_aspect_ratio; ///< agreed upon sample aspect ratio
 /* These two parameters apply only to audio */
-uint64_t channel_layout;///< channel layout of current buffer (see 
libavutil/channel_layout.h)
+#if FF_API_OLD_CHANNEL_LAYOUT
+/**
+ * @deprecated use ch_layout instead
+ */
+attribute_deprecated uint64_t channel_layout;
+#endif
 int sample_rate;///< samples per second
 
 int format; ///< agreed upon media format
@@ -405,6 +411,11 @@ struct AVFilterLink {
  * AVHWFramesContext describing the frames.
  */
 AVBufferRef *hw_frames_ctx;
+
+/**
+ * Channel layout of current buffer.
+ */
+AVChannelLayout ch_layout;
 };
 
 /**
diff --git a/libavfilter/avfiltergraph.c b/libavfilter/avfiltergraph.c
index a0f797e283..c72016d2c8 100644
--- a/libavfilter/avfiltergraph.c
+++ b/libavfilter/avfiltergraph.c
@@ -397,7 +397,13 @@ static int pick_format(AVFilterLink *link)
 return AVERROR(EINVAL);
 }
 link->in_channel_layouts->nb_channel_layouts = 1;
+#if FF_API_OLD_CHANNEL_LAYOUT
+FF_DISABLE_DEPRECATION_WARNINGS
 link->channel_layout = link->in_channel_layouts->channel_layouts[0];
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
+ 

[libav-devel] [PATCH 01/25] Add a new channel layout API

2017-06-28 Thread Vittorio Giovara
From: Anton Khirnov 

The new API is more extensible and allows for custom layouts.
More accurate information is exported, eg for decoders that do not
set a channel layout, lavc will not make one up for them.

Deprecate the old API working with just uint64_t bitmasks.

Expanded and completed by Vittorio Giovara .
Signed-off-by: Vittorio Giovara 
---
 libavutil/channel_layout.c | 387 +
 libavutil/channel_layout.h | 362 +++---
 libavutil/version.h|   3 +
 3 files changed, 662 insertions(+), 90 deletions(-)

diff --git a/libavutil/channel_layout.c b/libavutil/channel_layout.c
index 41340ecdb6..285997446d 100644
--- a/libavutil/channel_layout.c
+++ b/libavutil/channel_layout.c
@@ -31,77 +31,90 @@
 #include "common.h"
 
 static const char * const channel_names[] = {
-[0]  = "FL",/* front left */
-[1]  = "FR",/* front right */
-[2]  = "FC",/* front center */
-[3]  = "LFE",   /* low frequency */
-[4]  = "BL",/* back left */
-[5]  = "BR",/* back right */
-[6]  = "FLC",   /* front left-of-center  */
-[7]  = "FRC",   /* front right-of-center */
-[8]  = "BC",/* back-center */
-[9]  = "SL",/* side left */
-[10] = "SR",/* side right */
-[11] = "TC",/* top center */
-[12] = "TFL",   /* top front left */
-[13] = "TFC",   /* top front center */
-[14] = "TFR",   /* top front right */
-[15] = "TBL",   /* top back left */
-[16] = "TBC",   /* top back center */
-[17] = "TBR",   /* top back right */
-[29] = "DL",/* downmix left */
-[30] = "DR",/* downmix right */
-[31] = "WL",/* wide left */
-[32] = "WR",/* wide right */
-[33] = "SDL",   /* surround direct left */
-[34] = "SDR",   /* surround direct right */
-[35] = "LFE2",  /* low frequency 2 */
+[AV_CHAN_FRONT_LEFT  ] = "FL",
+[AV_CHAN_FRONT_RIGHT ] = "FR",
+[AV_CHAN_FRONT_CENTER] = "FC",
+[AV_CHAN_LOW_FREQUENCY   ] = "LFE",
+[AV_CHAN_BACK_LEFT   ] = "BL",
+[AV_CHAN_BACK_RIGHT  ] = "BR",
+[AV_CHAN_FRONT_LEFT_OF_CENTER] = "FLC",
+[AV_CHAN_FRONT_RIGHT_OF_CENTER   ] = "FRC",
+[AV_CHAN_BACK_CENTER ] = "BC",
+[AV_CHAN_SIDE_LEFT   ] = "SL",
+[AV_CHAN_SIDE_RIGHT  ] = "SR",
+[AV_CHAN_TOP_CENTER  ] = "TC",
+[AV_CHAN_TOP_FRONT_LEFT  ] = "TFL",
+[AV_CHAN_TOP_FRONT_CENTER] = "TFC",
+[AV_CHAN_TOP_FRONT_RIGHT ] = "TFR",
+[AV_CHAN_TOP_BACK_LEFT   ] = "TBL",
+[AV_CHAN_TOP_BACK_CENTER ] = "TBC",
+[AV_CHAN_TOP_BACK_RIGHT  ] = "TBR",
+[AV_CHAN_STEREO_LEFT ] = "DL",
+[AV_CHAN_STEREO_RIGHT] = "DR",
+[AV_CHAN_WIDE_LEFT   ] = "WL",
+[AV_CHAN_WIDE_RIGHT  ] = "WR",
+[AV_CHAN_SURROUND_DIRECT_LEFT] = "SDL",
+[AV_CHAN_SURROUND_DIRECT_RIGHT   ] = "SDR",
+[AV_CHAN_LOW_FREQUENCY_2 ] = "LFE2",
+[AV_CHAN_SILENCE ] = "PAD",
 };
 
-static const char *get_channel_name(int channel_id)
+const char *av_channel_name(enum AVChannel channel_id)
 {
-if (channel_id < 0 || channel_id >= FF_ARRAY_ELEMS(channel_names))
-return NULL;
+if ((unsigned) channel_id >= FF_ARRAY_ELEMS(channel_names))
+return "?";
 return channel_names[channel_id];
 }
 
+int av_channel_from_string(const char *str)
+{
+int i;
+for (i = 0; i < FF_ARRAY_ELEMS(channel_names); i++) {
+if (channel_names[i] && !strcmp(str, channel_names[i])) {
+return i;
+}
+}
+return AVERROR(EINVAL);
+}
+
 static const struct {
 const char *name;
-int nb_channels;
-uint64_t layout;
+AVChannelLayout layout;
 } channel_layout_map[] = {
-{ "mono",1,  AV_CH_LAYOUT_MONO },
-{ "stereo",  2,  AV_CH_LAYOUT_STEREO },
-{ "stereo",  2,  AV_CH_LAYOUT_STEREO_DOWNMIX },
-{ "2.1", 3,  AV_CH_LAYOUT_2POINT1 },
-{ "3.0", 3,  AV_CH_LAYOUT_SURROUND },
-{ "3.0(back)",   3,  AV_CH_LAYOUT_2_1 },
-{ "3.1", 4,  AV_CH_LAYOUT_3POINT1 },
-{ "4.0", 4,  AV_CH_LAYOUT_4POINT0 },
-{ "quad",4,  AV_CH_LAYOUT_QUAD },
-{ "quad(side)",  4,  AV_CH_LAYOUT_2_2 },
-{ "4.1", 5,  AV_CH_LAYOUT_4POINT1 },
-{ "5.0", 5,  AV_CH_LAYOUT_5POINT0 },
-{ "5.0", 5,  AV_CH_LAYOUT_5POINT0_BACK },
-{ "5.1", 6,  AV_CH_LAYOUT_5POINT1 },
-{ "5.1", 6,  AV_CH_LAYOUT_5POINT1_BACK },
-{ "6.0", 6,  AV_CH_LAYOUT_6POINT0 },
-{ "6.0(front)",  6,  AV_CH_LAYOUT_6POINT0_FRONT },
-{ "hexagonal",   6,  

[libav-devel] [PATCH 00/25] New channel API, review compatibility

2017-06-28 Thread Vittorio Giovara
Hello,
it has brought to my attention that reviewing 200 patches is not
desirable, and following the reviewers' suggestions, I squashed the
more mundane replacement patches across the codebase, and left the
more important or complex ones separate to simplify review.

Some of the single patches at the beginning have already been published
and reviewed, added for completeness.

Cheers,
Vittorio

Anton Khirnov (5):
  Add a new channel layout API
  lavu: support AVChannelLayout AVOptions
  lavc: deprecate channel count/layout changing side data
  avframe: switch to the new channel layout API
  lavr: switch to the new channel layout API

Vittorio Giovara (20):
  avtools: Use the new channel layout API in AVFrame
  lavfi, buffersrc: switch to the new channel layout API
  libavfilter changes for the new channel layout API
  lavfi: Port filter negotiation to use the new channel layout API
  avcodecpar: switch to the new channel layout API
  libavformat changes for the new channel layout API
  lavc: switch to the new channel layout API
  aac: convert to new channel layout API
  ac3: convert to new channel layout API
  libavcodec changes for the the new channel layout API
  tools, examples changes for the new channel layout API
  channel_layout: Add Ambisonic components and channel order
  lavr: Only let pass-through ambisonic channel layouts
  opus: Implement mapping type 2 for Ambisonic support
  lavf: Add non diegetic stream disposition flag
  mov: Implement spatial audio support
  aac: Allow pass-through transcoding of ambisonic audio
  avprobe: Print the channel layout string
  fate: Add ambisonic tests
  Bump library versions, update Changelog and APIchanges

 Changelog  |   1 +
 avtools/avconv.c   |  30 +--
 avtools/avconv.h   |   8 +-
 avtools/avconv_filter.c|  44 +++-
 avtools/avconv_opt.c   |  52 ++--
 avtools/avplay.c   |  52 ++--
 avtools/avprobe.c  |   6 +-
 avtools/cmdutils.c |  17 +-
 avtools/cmdutils.h |   8 -
 doc/APIchanges |  22 ++
 doc/examples/decode_audio.c|   2 +-
 doc/examples/encode_audio.c|  36 +--
 doc/examples/filter_audio.c|  11 +-
 doc/examples/output.c  |  30 ++-
 doc/examples/transcode_aac.c   |  29 ++-
 libavcodec/8svx.c  |  15 +-
 libavcodec/aac.h   |   7 +-
 libavcodec/aac_ac3_parser.c|   9 +-
 libavcodec/aaccoder.c  |   2 +-
 libavcodec/aacdec.c|  79 +-
 libavcodec/aacdectab.h |  16 ++
 libavcodec/aacenc.c|   2 +-
 libavcodec/aacpsy.c|  10 +-
 libavcodec/ac3dec.c|  49 +++-
 libavcodec/ac3dec.h|   2 +
 libavcodec/ac3enc.c|  83 +--
 libavcodec/ac3enc.h|   4 +-
 libavcodec/ac3enc_fixed.c  |   5 +
 libavcodec/ac3enc_float.c  |   5 +
 libavcodec/adpcm.c |  57 ++---
 libavcodec/adpcmenc.c  |  92 +++
 libavcodec/adx.c   |  16 +-
 libavcodec/adxdec.c|   6 +-
 libavcodec/adxenc.c|  11 +-
 libavcodec/alac.c  |  18 +-
 libavcodec/alac_data.c |  12 +
 libavcodec/alac_data.h |   6 +
 libavcodec/alacenc.c   |  20 +-
 libavcodec/alsdec.c|  65 ++---
 libavcodec/amrnbdec.c  |   6 +-
 libavcodec/amrwbdec.c  |   6 +-
 libavcodec/apedec.c|   9 +-
 libavcodec/atrac1.c|  10 +-
 libavcodec/atrac3.c|  26 +-
 libavcodec/atrac3plusdec.c |  25 +-
 libavcodec/avcodec.h   |  47 
 libavcodec/binkaudio.c |  17 +-
 libavcodec/bmvaudio.c  |   4 +-
 libavcodec/cngdec.c|   3 +-
 libavcodec/cngenc.c|   6 +-
 libavcodec/cook.c  |  22 +-
 libavcodec/cook_parser.c   |   4 +-
 libavcodec/dca.h   |   2 +
 libavcodec/dca_xll.c   |   6 +-
 libavcodec/dcadec.c|  54 +++--
 libavcodec/decode.c|  88 +--
 libavcodec/dpcm.c  |  14 +-
 libavcodec/dsicinaudio.c   |   4 +-
 libavcodec/dss_sp.c|   4 +-
 libavcodec/eac3enc.c   |   5 +
 libavcodec/encode.c|  18 +-
 libavcodec/flac.c  |  37 +--
 libavcodec/flac.h  |   2 +-
 libavcodec/flac_parser.c   |   7 +-
 libavcodec/flacdec.c   |  10 +-
 libavcodec/flacenc.c   |   2 +-
 libavcodec/g722dec.c   |   4 +-
 libavcodec/g722enc.c   |   8 +-
 libavcodec/g723_1dec.c |   4 +-
 libavcodec/g723_1enc.c |   8 +-
 libavcodec/g726.c  |   6 +-
 libavcodec/gsmdec.c|   4 +-
 libavcodec/imc.c

[libav-devel] [PATCH 02/25] lavu: support AVChannelLayout AVOptions

2017-06-28 Thread Vittorio Giovara
From: Anton Khirnov 

Signed-off-by: Vittorio Giovara 
---
 libavutil/opt.c | 47 +++
 libavutil/opt.h | 10 ++
 2 files changed, 57 insertions(+)

diff --git a/libavutil/opt.c b/libavutil/opt.c
index 44d6299117..698f6e97e0 100644
--- a/libavutil/opt.c
+++ b/libavutil/opt.c
@@ -242,6 +242,14 @@ static int set_string_number(void *obj, void *target_obj, 
const AVOption *o, con
 }
 }
 
+static int set_string_channel_layout(void *obj, const AVOption *o,
+ const char *val, void *dst)
+{
+AVChannelLayout *channel_layout = dst;
+av_channel_layout_uninit(channel_layout);
+return av_channel_layout_from_string(channel_layout, val);
+}
+
 int av_opt_set(void *obj, const char *name, const char *val, int search_flags)
 {
 void *dst, *target_obj;
@@ -264,6 +272,8 @@ int av_opt_set(void *obj, const char *name, const char 
*val, int search_flags)
 case AV_OPT_TYPE_DOUBLE:
 case AV_OPT_TYPE_RATIONAL:
 return set_string_number(obj, target_obj, o, val, dst);
+case AV_OPT_TYPE_CHANNEL_LAYOUT:
+return set_string_channel_layout(obj, o, val, dst);
 }
 
 av_log(obj, AV_LOG_ERROR, "Invalid option type.\n");
@@ -365,6 +375,22 @@ int av_opt_set_dict_val(void *obj, const char *name, const 
AVDictionary *val,
 return 0;
 }
 
+int av_opt_set_channel_layout(void *obj, const char *name,
+  const AVChannelLayout *channel_layout,
+  int search_flags)
+{
+void *target_obj;
+const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, 
_obj);
+AVChannelLayout *dst;
+
+if (!o || !target_obj)
+return AVERROR_OPTION_NOT_FOUND;
+
+dst = (AVChannelLayout*)((uint8_t*)target_obj + o->offset);
+
+return av_channel_layout_copy(dst, channel_layout);
+}
+
 int av_opt_get(void *obj, const char *name, int search_flags, uint8_t 
**out_val)
 {
 void *dst, *target_obj;
@@ -414,6 +440,9 @@ int av_opt_get(void *obj, const char *name, int 
search_flags, uint8_t **out_val)
 for (i = 0; i < len; i++)
 snprintf(*out_val + i * 2, 3, "%02X", bin[i]);
 return 0;
+case AV_OPT_TYPE_CHANNEL_LAYOUT:
+*out_val = av_channel_layout_describe(dst);
+return *out_val ? 0 : AVERROR(EINVAL);
 default:
 return AVERROR(EINVAL);
 }
@@ -499,6 +528,20 @@ int av_opt_get_dict_val(void *obj, const char *name, int 
search_flags, AVDiction
 return 0;
 }
 
+int av_opt_get_channel_layout(void *obj, const char *name, int search_flags,
+  AVChannelLayout *channel_layout)
+{
+void *dst, *target_obj;
+const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, 
_obj);
+
+if (!o || !target_obj)
+return AVERROR_OPTION_NOT_FOUND;
+
+dst = ((uint8_t*)target_obj) + o->offset;
+
+return av_channel_layout_copy(channel_layout, dst);
+}
+
 int av_opt_flag_is_set(void *obj, const char *field_name, const char 
*flag_name)
 {
 const AVOption *field = av_opt_find(obj, field_name, NULL, 0, 0);
@@ -561,6 +604,9 @@ static void opt_list(void *obj, void *av_log_obj, const 
char *unit,
 case AV_OPT_TYPE_BINARY:
 av_log(av_log_obj, AV_LOG_INFO, "%-7s ", "");
 break;
+case AV_OPT_TYPE_CHANNEL_LAYOUT:
+av_log(av_log_obj, AV_LOG_INFO, "%-7s", "");
+break;
 case AV_OPT_TYPE_CONST:
 default:
 av_log(av_log_obj, AV_LOG_INFO, "%-7s ", "");
@@ -626,6 +672,7 @@ void av_opt_set_defaults(void *s)
 }
 break;
 case AV_OPT_TYPE_STRING:
+case AV_OPT_TYPE_CHANNEL_LAYOUT:
 av_opt_set(s, opt->name, opt->default_val.str, 0);
 break;
 case AV_OPT_TYPE_BINARY:
diff --git a/libavutil/opt.h b/libavutil/opt.h
index b68a396da7..a30c53b0ab 100644
--- a/libavutil/opt.h
+++ b/libavutil/opt.h
@@ -29,6 +29,7 @@
 
 #include "rational.h"
 #include "avutil.h"
+#include "channel_layout.h"
 #include "dict.h"
 #include "log.h"
 
@@ -225,6 +226,11 @@ enum AVOptionType{
 AV_OPT_TYPE_RATIONAL,
 AV_OPT_TYPE_BINARY,  ///< offset must point to a pointer immediately 
followed by an int for the length
 AV_OPT_TYPE_DICT,
+/**
+ * The offset point to an AVChannelLayout, the default is .str, which gets
+ * passed to av_channel_layout_from_string().
+ */
+AV_OPT_TYPE_CHANNEL_LAYOUT,
 AV_OPT_TYPE_CONST = 128,
 };
 
@@ -499,6 +505,8 @@ int av_opt_set_bin (void *obj, const char *name, const 
uint8_t *val, int siz
  * caller still owns val is and responsible for freeing it.
  */
 int av_opt_set_dict_val(void *obj, const char *name, const AVDictionary *val, 
int search_flags);
+int av_opt_set_channel_layout(void *obj, const char *name,
+  const AVChannelLayout *channel_layout, int 
search_flags);
 /**
  * @}
  */
@@ -528,6 

Re: [libav-devel] [libav-commits] dvbsubdec: Fixed segfault when decoding subtitles

2017-06-28 Thread Diego Biurrun
On Wed, Jun 28, 2017 at 04:14:23PM +0200, Lorenz Brun  wrote:
> Module: libav
> Branch: master
> Commit: 1cfd566324f4a9be066ea400685b81c0695e64d9
> 
> Author:Lorenz Brun 
> Committer: Vittorio Giovara 
> Date:  Fri Oct 21 22:51:37 2016 +0200
> 
> dvbsubdec: Fixed segfault when decoding subtitles
> 
> This fixes a segfault (originally found in Movian, but traced to libav)
> when decoding subtitles because only an array of rects is allocated,
> but not the actual structs it contains. The issue was probably
> introduced in commit 2383323 where the loop to allocate the rects in
> the array was thrown away.
> 
> Signed-off-by: Vittorio Giovara 

Will port this to v12 tomorrow.

Diego
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH] lavu: Add DRM hwcontext

2017-06-28 Thread Mark Thompson
On 28/06/17 16:24, Rémi Denis-Courmont wrote:
> Le sunnuntaina 18. kesäkuuta 2017, 19.08.02 EEST Mark Thompson a écrit :
>> ---
>> The intent of this is to have a common structure which can be used in all
>> cases where DRM objects need to be shared between components.  It would be
>> helpful if anyone familiar with specific drivers or use-cases could ensure
>> that the structure (see the hwcontext_drm.h header) is sufficiently general
>> to cover them - we would like this to the one answer and never require any
>> more formats in future.
> 
> AFAIU, the main point of using DRM directly is abstraction from the windowing 
> system. So the dependency on Xf68 looks very suspicious. It should work with 
> X11, with Wayland, with plain KMS or even with just a render node (e.g. 
> transcoding).
> 
> I suspect that this may be tying X11-DRI and kernel DRM too tightly.

There is no X11 dependency; the libdrm header has xf86 in the name for 
hysterical raisins.



___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 02/12] lavu: OpenCL hwcontext implementation

2017-06-28 Thread Mark Thompson
On 28/06/17 15:03, wm4 wrote:
> On Wed, 28 Jun 2017 13:36:30 +0100
> Mark Thompson  wrote:
> 
>> On 28/06/17 12:03, wm4 wrote:
>>> On Tue, 27 Jun 2017 22:50:44 +0100
>>> Mark Thompson  wrote:
>>>   
 ---
  configure  |5 +-
  doc/APIchanges |4 +
  libavutil/Makefile |2 +
  libavutil/hwcontext.c  |4 +
  libavutil/hwcontext.h  |1 +
  libavutil/hwcontext_internal.h |1 +
  libavutil/hwcontext_opencl.c   | 1303 
 
  libavutil/hwcontext_opencl.h   |   96 +++
  libavutil/version.h|4 +-
  9 files changed, 1417 insertions(+), 3 deletions(-)
  create mode 100644 libavutil/hwcontext_opencl.c
  create mode 100644 libavutil/hwcontext_opencl.h
 ...
 +/**
 + * OpenCL frame descriptor for pool allocation.
 + *
 + * In user-allocated pools, AVHWFramesContext.pool must return 
 AVBufferRefs
 + * with the data pointer pointing at an object of this type describing the
 + * planes of the frame.
 + */
 +typedef struct AVOpenCLFrameDescriptor {
 +/**
 + * Number of planes in the frame.
 + */
 +int nb_planes;
 +/**
 + * OpenCL image2d objects for each plane of the frame.
 + */
 +cl_mem planes[AV_NUM_DATA_POINTERS];
 +} AVOpenCLFrameDescriptor;  
>>>
>>> Not sure if this should have more metadata about the formats?  
>>
>> I'm not sure what other metadata you want here?  This structure is used as 
>> the buffer reference, and also then also to carry the objects for some 
>> mapping cases where that is useful.  It doesn't actually end up in the frame 
>> itself.
> 
> Well, the semantics of those are bound to sw_format, but in the end
> it's all a bit obscure, undocumented, and hidden in the source code.
> 
 +
 +/**
 + * OpenCL device details.
 + *
 + * Allocated as AVHWDeviceContext.hwctx
 + */
 +typedef struct AVOpenCLDeviceContext {
 +/**
 + * The primary device ID of the device.  If multiple OpenCL devices
 + * are associated with the context then this is the one which will
 + * be used for all operations internal to Libav.
 + */
 +cl_device_id device_id;
 +/**
 + * The OpenCL context which will contain all operations and frames on
 + * this device.
 + */
 +cl_context context;
 +/**
 + * The default command queue for this device, which will be used by 
 all
 + * frames contexts which do not have their own command queue.  If not
 + * intialised by the user, a default queue will be created on the
 + * primary device.
 + */
 +cl_command_queue command_queue;
 +} AVOpenCLDeviceContext;  
>>>
>>> Is the default queue also set on the public struct if created by Libav?  
>>
>> Not currently - it stays internal so that it is clear where all of the 
>> references to it are.
>>
>> It could be put here with suitable documentation if you want?
> 
> Sure. Should the command queue be accessible to API users? If not, why
> can the API user _set_ it?

The API user can set it in order to be able to enforce operation ordering in 
the way they want.  Since the API isn't exposing any event interface, you need 
some way to be sure that dependent events (such as writing the contents of the 
frame you are about to download) have completed.  Controlling the command queue 
the transfer is executed on allows you to set such dependencies externally, 
with barriers on a common queue or by enqueuing a wait for events on another 
queue.

You can also do everything synchronously (always call clFinish() to make sure 
kernels have finished running) - then none of that is needed and you don't have 
to touch any of this.

(I have thoughts of allowing the opposite case as well, so that transfer 
operations don't need to wait for completion internally.  It would require 
adding a new flag something like AV_HWFRAME_TRANSFER_ASYNCHRONOUS, though, so I 
haven't yet pursued it.)

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 12/12] test-only: Create D3D11 textures with D3D11_RESOURCE_MISC_SHARED

2017-06-28 Thread Mark Thompson
On 28/06/17 15:06, wm4 wrote:
> On Wed, 28 Jun 2017 13:51:26 +0100
> Mark Thompson  wrote:
> 
>> On 28/06/17 12:13, wm4 wrote:
>>> On Tue, 27 Jun 2017 22:50:54 +0100
>>> Mark Thompson  wrote:
>>>   
 ---
  libavutil/hwcontext_d3d11va.c | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)

 diff --git a/libavutil/hwcontext_d3d11va.c b/libavutil/hwcontext_d3d11va.c
 index 75f78d866..543f90d6c 100644
 --- a/libavutil/hwcontext_d3d11va.c
 +++ b/libavutil/hwcontext_d3d11va.c
 @@ -227,7 +227,7 @@ static int d3d11va_frames_init(AVHWFramesContext *ctx)
  .ArraySize  = ctx->initial_pool_size,
  .Usage  = D3D11_USAGE_DEFAULT,
  .BindFlags  = hwctx->BindFlags,
 -.MiscFlags  = hwctx->MiscFlags,
 +.MiscFlags  = hwctx->MiscFlags | D3D11_RESOURCE_MISC_SHARED,
  };
  
  if (hwctx->texture) {  
>>>
>>> So what does test-only mean?  
>>
>> "I'm not going to apply this hack, but it's useful for testing other stuff 
>> in the series"
> 
> Doesn't this imply it's somehow needed to use that other stuff?

If you use avconv, then yes with the current code.  That doesn't mean we should 
be making a library change like this now - some future magic negotiation stuff 
might be able to tell you that this flag needs to be set, and if you make your 
own D3D11 textures then you can supply whatever flags you like.

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 12/12] test-only: Create D3D11 textures with D3D11_RESOURCE_MISC_SHARED

2017-06-28 Thread wm4
On Wed, 28 Jun 2017 13:51:26 +0100
Mark Thompson  wrote:

> On 28/06/17 12:13, wm4 wrote:
> > On Tue, 27 Jun 2017 22:50:54 +0100
> > Mark Thompson  wrote:
> >   
> >> ---
> >>  libavutil/hwcontext_d3d11va.c | 2 +-
> >>  1 file changed, 1 insertion(+), 1 deletion(-)
> >>
> >> diff --git a/libavutil/hwcontext_d3d11va.c b/libavutil/hwcontext_d3d11va.c
> >> index 75f78d866..543f90d6c 100644
> >> --- a/libavutil/hwcontext_d3d11va.c
> >> +++ b/libavutil/hwcontext_d3d11va.c
> >> @@ -227,7 +227,7 @@ static int d3d11va_frames_init(AVHWFramesContext *ctx)
> >>  .ArraySize  = ctx->initial_pool_size,
> >>  .Usage  = D3D11_USAGE_DEFAULT,
> >>  .BindFlags  = hwctx->BindFlags,
> >> -.MiscFlags  = hwctx->MiscFlags,
> >> +.MiscFlags  = hwctx->MiscFlags | D3D11_RESOURCE_MISC_SHARED,
> >>  };
> >>  
> >>  if (hwctx->texture) {  
> > 
> > So what does test-only mean?  
> 
> "I'm not going to apply this hack, but it's useful for testing other stuff in 
> the series"

Doesn't this imply it's somehow needed to use that other stuff?
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 03/12] hwcontext_opencl: VAAPI to OpenCL mapping for Intel i965+beignet

2017-06-28 Thread wm4
On Wed, 28 Jun 2017 13:49:28 +0100
Mark Thompson  wrote:

> On 28/06/17 12:09, wm4 wrote:
> > On Tue, 27 Jun 2017 22:50:45 +0100
> > Mark Thompson  wrote:
> >   
> >> Supports all surface formats in common between the two.
> >> ---
> >>  configure  |   6 +
> >>  libavutil/hwcontext_internal.h |   3 +
> >>  libavutil/hwcontext_opencl.c   | 298 
> >> +
> >>  libavutil/hwcontext_vaapi.c|   9 ++
> >>  4 files changed, 316 insertions(+)
> >>  
> > 
> > Can't say much except:
> > 1. It looks like we'll have NxM mapping implementation, and I question
> >whether they really should exist as ifdef mess in the individual
> >hwcontext impls, instead of a more structured approach (like one
> >soruce file per N-M mapping).  
> 
> I don't think we actually will have that many.  OpenCL looks nasty here 
> because it's a common leaf node which a lot of other things can map to, but 
> that isn't true for most others.
> 
> > 2. ff_vaapi_fourcc_from_pix_fmt() is also funny - sure that we
> >shouldn't have a more general public format mapping API like I
> >suggested once with a patch?  
> 
> That would be nice.  Would you like to resurrect that patch?

Depends on elenril, I guess.
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 02/12] lavu: OpenCL hwcontext implementation

2017-06-28 Thread wm4
On Wed, 28 Jun 2017 13:36:30 +0100
Mark Thompson  wrote:

> On 28/06/17 12:03, wm4 wrote:
> > On Tue, 27 Jun 2017 22:50:44 +0100
> > Mark Thompson  wrote:
> >   
> >> ---
> >>  configure  |5 +-
> >>  doc/APIchanges |4 +
> >>  libavutil/Makefile |2 +
> >>  libavutil/hwcontext.c  |4 +
> >>  libavutil/hwcontext.h  |1 +
> >>  libavutil/hwcontext_internal.h |1 +
> >>  libavutil/hwcontext_opencl.c   | 1303 
> >> 
> >>  libavutil/hwcontext_opencl.h   |   96 +++
> >>  libavutil/version.h|4 +-
> >>  9 files changed, 1417 insertions(+), 3 deletions(-)
> >>  create mode 100644 libavutil/hwcontext_opencl.c
> >>  create mode 100644 libavutil/hwcontext_opencl.h
> >> ...
> >> +/**
> >> + * OpenCL frame descriptor for pool allocation.
> >> + *
> >> + * In user-allocated pools, AVHWFramesContext.pool must return 
> >> AVBufferRefs
> >> + * with the data pointer pointing at an object of this type describing the
> >> + * planes of the frame.
> >> + */
> >> +typedef struct AVOpenCLFrameDescriptor {
> >> +/**
> >> + * Number of planes in the frame.
> >> + */
> >> +int nb_planes;
> >> +/**
> >> + * OpenCL image2d objects for each plane of the frame.
> >> + */
> >> +cl_mem planes[AV_NUM_DATA_POINTERS];
> >> +} AVOpenCLFrameDescriptor;  
> > 
> > Not sure if this should have more metadata about the formats?  
> 
> I'm not sure what other metadata you want here?  This structure is used as 
> the buffer reference, and also then also to carry the objects for some 
> mapping cases where that is useful.  It doesn't actually end up in the frame 
> itself.

Well, the semantics of those are bound to sw_format, but in the end
it's all a bit obscure, undocumented, and hidden in the source code.

> >> +
> >> +/**
> >> + * OpenCL device details.
> >> + *
> >> + * Allocated as AVHWDeviceContext.hwctx
> >> + */
> >> +typedef struct AVOpenCLDeviceContext {
> >> +/**
> >> + * The primary device ID of the device.  If multiple OpenCL devices
> >> + * are associated with the context then this is the one which will
> >> + * be used for all operations internal to Libav.
> >> + */
> >> +cl_device_id device_id;
> >> +/**
> >> + * The OpenCL context which will contain all operations and frames on
> >> + * this device.
> >> + */
> >> +cl_context context;
> >> +/**
> >> + * The default command queue for this device, which will be used by 
> >> all
> >> + * frames contexts which do not have their own command queue.  If not
> >> + * intialised by the user, a default queue will be created on the
> >> + * primary device.
> >> + */
> >> +cl_command_queue command_queue;
> >> +} AVOpenCLDeviceContext;  
> > 
> > Is the default queue also set on the public struct if created by Libav?  
> 
> Not currently - it stays internal so that it is clear where all of the 
> references to it are.
> 
> It could be put here with suitable documentation if you want?

Sure. Should the command queue be accessible to API users? If not, why
can the API user _set_ it?
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH] hevc: Add support for alternative transfer characterics SEI

2017-06-28 Thread Luca Barbato
On 6/13/17 8:54 PM, Vittorio Giovara wrote:
> The use of this SEI is for backward compatibility in HLG HDR systems:
> older devices that cannot interpret the "arib-std-b67" transfer will
> get the compatible transfer (usually bt709 or bt2020) from the VUI,
> while newer devices that can interpret HDR will read the SEI and use
> its value instead.
> 
> Signed-off-by: Vittorio Giovara 
> ---
> Expanded commit log and better validated the SEI contents.
> Vittorio
> 
>  libavcodec/hevc_sei.c | 9 +
>  libavcodec/hevc_sei.h | 7 +++
>  libavcodec/hevcdec.c  | 6 ++
>  3 files changed, 22 insertions(+)
> 
> diff --git a/libavcodec/hevc_sei.c b/libavcodec/hevc_sei.c
> index 153d211b4b..0a5d4440bf 100644
> --- a/libavcodec/hevc_sei.c
> +++ b/libavcodec/hevc_sei.c
> @@ -86,6 +86,13 @@ static int 
> decode_nal_sei_display_orientation(HEVCSEIDisplayOrientation *s, GetB
>  return 0;
>  }
>  
> +static int decode_nal_sei_alternative_transfer(HEVCSEIAlternativeTransfer 
> *s, GetBitContext *gb)
> +{
> +s->present = 1;
> +s->preferred_transfer_characteristics = get_bits(gb, 8);
> +return 0;
> +}
> +
>  static int decode_nal_sei_prefix(GetBitContext *gb, void *logctx, HEVCSEI *s,
>   int type, int size)
>  {
> @@ -96,6 +103,8 @@ static int decode_nal_sei_prefix(GetBitContext *gb, void 
> *logctx, HEVCSEI *s,
>  return decode_nal_sei_frame_packing_arrangement(>frame_packing, 
> gb);
>  case HEVC_SEI_TYPE_DISPLAY_ORIENTATION:
>  return decode_nal_sei_display_orientation(>display_orientation, 
> gb);
> +case HEVC_SEI_TYPE_ALTERNATIVE_TRANSFER_CHARACTERISTICS:
> +return decode_nal_sei_alternative_transfer(>alternative_transfer, 
> gb);
>  default:
>  av_log(logctx, AV_LOG_DEBUG, "Skipped PREFIX SEI %d\n", type);
>  skip_bits_long(gb, 8 * size);
> diff --git a/libavcodec/hevc_sei.h b/libavcodec/hevc_sei.h
> index b699fef45d..e4aeac1fbe 100644
> --- a/libavcodec/hevc_sei.h
> +++ b/libavcodec/hevc_sei.h
> @@ -54,6 +54,7 @@ typedef enum {
>  HEVC_SEI_TYPE_REGION_REFRESH_INFO  = 134,
>  HEVC_SEI_TYPE_MASTERING_DISPLAY_INFO   = 137,
>  HEVC_SEI_TYPE_CONTENT_LIGHT_LEVEL_INFO = 144,
> +HEVC_SEI_TYPE_ALTERNATIVE_TRANSFER_CHARACTERISTICS = 147,
>  } HEVC_SEI_Type;
>  
>  typedef struct HEVCSEIPictureHash {
> @@ -74,10 +75,16 @@ typedef struct HEVCSEIDisplayOrientation {
>  int hflip, vflip;
>  } HEVCSEIDisplayOrientation;
>  
> +typedef struct HEVCSEIAlternativeTransfer {
> +int present;
> +int preferred_transfer_characteristics;
> +} HEVCSEIAlternativeTransfer;
> +
>  typedef struct HEVCSEI {
>  HEVCSEIPictureHash picture_hash;
>  HEVCSEIFramePacking frame_packing;
>  HEVCSEIDisplayOrientation display_orientation;
> +HEVCSEIAlternativeTransfer alternative_transfer;
>  } HEVCSEI;
>  
>  int ff_hevc_decode_nal_sei(GetBitContext *gb, void *logctx, HEVCSEI *s,
> diff --git a/libavcodec/hevcdec.c b/libavcodec/hevcdec.c
> index 7a9182af9b..ac0b1a3c1d 100644
> --- a/libavcodec/hevcdec.c
> +++ b/libavcodec/hevcdec.c
> @@ -2407,6 +2407,12 @@ static int set_side_data(HEVCContext *s)
> s->sei.display_orientation.vflip);
>  }
>  
> +if (s->sei.alternative_transfer.present &&
> +
> av_color_transfer_name(s->sei.alternative_transfer.preferred_transfer_characteristics)
>  &&
> +s->sei.alternative_transfer.preferred_transfer_characteristics != 
> AVCOL_TRC_UNSPECIFIED) {
> +s->avctx->color_trc = 
> s->sei.alternative_transfer.preferred_transfer_characteristics;
> +}
> +
>  return 0;
>  }
>  
> 

Still ok.

lu
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 12/12] test-only: Create D3D11 textures with D3D11_RESOURCE_MISC_SHARED

2017-06-28 Thread Mark Thompson
On 28/06/17 12:13, wm4 wrote:
> On Tue, 27 Jun 2017 22:50:54 +0100
> Mark Thompson  wrote:
> 
>> ---
>>  libavutil/hwcontext_d3d11va.c | 2 +-
>>  1 file changed, 1 insertion(+), 1 deletion(-)
>>
>> diff --git a/libavutil/hwcontext_d3d11va.c b/libavutil/hwcontext_d3d11va.c
>> index 75f78d866..543f90d6c 100644
>> --- a/libavutil/hwcontext_d3d11va.c
>> +++ b/libavutil/hwcontext_d3d11va.c
>> @@ -227,7 +227,7 @@ static int d3d11va_frames_init(AVHWFramesContext *ctx)
>>  .ArraySize  = ctx->initial_pool_size,
>>  .Usage  = D3D11_USAGE_DEFAULT,
>>  .BindFlags  = hwctx->BindFlags,
>> -.MiscFlags  = hwctx->MiscFlags,
>> +.MiscFlags  = hwctx->MiscFlags | D3D11_RESOURCE_MISC_SHARED,
>>  };
>>  
>>  if (hwctx->texture) {
> 
> So what does test-only mean?

"I'm not going to apply this hack, but it's useful for testing other stuff in 
the series"

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 03/12] hwcontext_opencl: VAAPI to OpenCL mapping for Intel i965+beignet

2017-06-28 Thread Mark Thompson
On 28/06/17 12:09, wm4 wrote:
> On Tue, 27 Jun 2017 22:50:45 +0100
> Mark Thompson  wrote:
> 
>> Supports all surface formats in common between the two.
>> ---
>>  configure  |   6 +
>>  libavutil/hwcontext_internal.h |   3 +
>>  libavutil/hwcontext_opencl.c   | 298 
>> +
>>  libavutil/hwcontext_vaapi.c|   9 ++
>>  4 files changed, 316 insertions(+)
>>
> 
> Can't say much except:
> 1. It looks like we'll have NxM mapping implementation, and I question
>whether they really should exist as ifdef mess in the individual
>hwcontext impls, instead of a more structured approach (like one
>soruce file per N-M mapping).

I don't think we actually will have that many.  OpenCL looks nasty here because 
it's a common leaf node which a lot of other things can map to, but that isn't 
true for most others.

> 2. ff_vaapi_fourcc_from_pix_fmt() is also funny - sure that we
>shouldn't have a more general public format mapping API like I
>suggested once with a patch?

That would be nice.  Would you like to resurrect that patch?

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 02/12] lavu: OpenCL hwcontext implementation

2017-06-28 Thread Mark Thompson
On 28/06/17 12:03, wm4 wrote:
> On Tue, 27 Jun 2017 22:50:44 +0100
> Mark Thompson  wrote:
> 
>> ---
>>  configure  |5 +-
>>  doc/APIchanges |4 +
>>  libavutil/Makefile |2 +
>>  libavutil/hwcontext.c  |4 +
>>  libavutil/hwcontext.h  |1 +
>>  libavutil/hwcontext_internal.h |1 +
>>  libavutil/hwcontext_opencl.c   | 1303 
>> 
>>  libavutil/hwcontext_opencl.h   |   96 +++
>>  libavutil/version.h|4 +-
>>  9 files changed, 1417 insertions(+), 3 deletions(-)
>>  create mode 100644 libavutil/hwcontext_opencl.c
>>  create mode 100644 libavutil/hwcontext_opencl.h
>> ...
>> +/**
>> + * OpenCL frame descriptor for pool allocation.
>> + *
>> + * In user-allocated pools, AVHWFramesContext.pool must return AVBufferRefs
>> + * with the data pointer pointing at an object of this type describing the
>> + * planes of the frame.
>> + */
>> +typedef struct AVOpenCLFrameDescriptor {
>> +/**
>> + * Number of planes in the frame.
>> + */
>> +int nb_planes;
>> +/**
>> + * OpenCL image2d objects for each plane of the frame.
>> + */
>> +cl_mem planes[AV_NUM_DATA_POINTERS];
>> +} AVOpenCLFrameDescriptor;
> 
> Not sure if this should have more metadata about the formats?

I'm not sure what other metadata you want here?  This structure is used as the 
buffer reference, and also then also to carry the objects for some mapping 
cases where that is useful.  It doesn't actually end up in the frame itself.

>> +
>> +/**
>> + * OpenCL device details.
>> + *
>> + * Allocated as AVHWDeviceContext.hwctx
>> + */
>> +typedef struct AVOpenCLDeviceContext {
>> +/**
>> + * The primary device ID of the device.  If multiple OpenCL devices
>> + * are associated with the context then this is the one which will
>> + * be used for all operations internal to Libav.
>> + */
>> +cl_device_id device_id;
>> +/**
>> + * The OpenCL context which will contain all operations and frames on
>> + * this device.
>> + */
>> +cl_context context;
>> +/**
>> + * The default command queue for this device, which will be used by all
>> + * frames contexts which do not have their own command queue.  If not
>> + * intialised by the user, a default queue will be created on the
>> + * primary device.
>> + */
>> +cl_command_queue command_queue;
>> +} AVOpenCLDeviceContext;
> 
> Is the default queue also set on the public struct if created by Libav?

Not currently - it stays internal so that it is clear where all of the 
references to it are.

It could be put here with suitable documentation if you want?

>> +
>> +/**
>> + * OpenCL-specific data associated with a frame pool.
>> + *
>> + * Allocated as AVHWFramesContext.hwctx.
>> + */
>> +typedef struct AVOpenCLFramesContext {
>> +/**
>> + * The command queue used for internal asynchronous operations on this
>> + * device (av_hwframe_transfer_data(), av_hwframe_map()).
>> + *
>> + * If this is not set, the command queue from the associated device is
>> + * used instead.
>> + */
>> +cl_command_queue command_queue;
>> +} AVOpenCLFramesContext;
> 
> Same question.

Same answer.

Thanks,

- Mark

___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 10/12] vf_hwmap: Pass mapping mode when deriving frames context on an existing device

2017-06-28 Thread Luca Barbato
On 6/27/17 11:50 PM, Mark Thompson wrote:
> To match creation on a newly-derived device.  (This was missed earlier
> because the mode is only used in some cases.)
> ---
>  libavfilter/vf_hwmap.c | 3 ++-
>  1 file changed, 2 insertions(+), 1 deletion(-)
> 
> diff --git a/libavfilter/vf_hwmap.c b/libavfilter/vf_hwmap.c
> index b28cb2145..3a3a502b7 100644
> --- a/libavfilter/vf_hwmap.c
> +++ b/libavfilter/vf_hwmap.c
> @@ -110,7 +110,8 @@ static int hwmap_config_output(AVFilterLink *outlink)
>  err = av_hwframe_ctx_create_derived(>hwframes_ref,
>  outlink->format,
>  device,
> -inlink->hw_frames_ctx, 0);
> +inlink->hw_frames_ctx,
> +ctx->mode);
>  if (err < 0) {
>  av_log(avctx, AV_LOG_ERROR, "Failed to create derived "
> "frames context: %d.\n", err);
> 

Seems good to go before the rest.
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 12/12] test-only: Create D3D11 textures with D3D11_RESOURCE_MISC_SHARED

2017-06-28 Thread wm4
On Tue, 27 Jun 2017 22:50:54 +0100
Mark Thompson  wrote:

> ---
>  libavutil/hwcontext_d3d11va.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> diff --git a/libavutil/hwcontext_d3d11va.c b/libavutil/hwcontext_d3d11va.c
> index 75f78d866..543f90d6c 100644
> --- a/libavutil/hwcontext_d3d11va.c
> +++ b/libavutil/hwcontext_d3d11va.c
> @@ -227,7 +227,7 @@ static int d3d11va_frames_init(AVHWFramesContext *ctx)
>  .ArraySize  = ctx->initial_pool_size,
>  .Usage  = D3D11_USAGE_DEFAULT,
>  .BindFlags  = hwctx->BindFlags,
> -.MiscFlags  = hwctx->MiscFlags,
> +.MiscFlags  = hwctx->MiscFlags | D3D11_RESOURCE_MISC_SHARED,
>  };
>  
>  if (hwctx->texture) {

So what does test-only mean?
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 07/12] lavfi: Add some common code for OpenCL filtering

2017-06-28 Thread wm4
On Tue, 27 Jun 2017 22:50:49 +0100
Mark Thompson  wrote:

> ---
>  libavfilter/Makefile |   6 +
>  libavfilter/opencl.c | 285 
> +++
>  libavfilter/opencl.h |  74 +++
>  libavfilter/opencl/rgbyuv.cl | 117 ++
>  libavfilter/opencl_source.h  |  24 
>  tools/cl2c   |  20 +++
>  6 files changed, 526 insertions(+)
>  create mode 100644 libavfilter/opencl.c
>  create mode 100644 libavfilter/opencl.h
>  create mode 100644 libavfilter/opencl/rgbyuv.cl
>  create mode 100644 libavfilter/opencl_source.h
>  create mode 100755 tools/cl2c
> 
> diff --git a/libavfilter/Makefile b/libavfilter/Makefile
> index 348ad9211..1370ef04b 100644
> --- a/libavfilter/Makefile
> +++ b/libavfilter/Makefile
> @@ -106,3 +106,9 @@ OBJS-$(CONFIG_TESTSRC_FILTER)+= 
> vsrc_testsrc.o
>  
>  TOOLS = graph2dot
>  TESTPROGS = filtfmts
> +
> +OPENCL = $(subst $(SRC_PATH)/,,$(wildcard 
> $(SRC_PATH)/libavfilter/opencl/*.cl))
> +.SECONDARY: $(OPENCL:.cl=.c)
> +libavfilter/opencl/%.c: TAG = OPENCL
> +libavfilter/opencl/%.c: $(SRC_PATH)/libavfilter/opencl/%.cl
> + $(M)$(SRC_PATH)/tools/cl2c $< $@
> diff --git a/libavfilter/opencl.c b/libavfilter/opencl.c
> new file mode 100644
> index 0..f7b3f1818
> --- /dev/null
> +++ b/libavfilter/opencl.c
> @@ -0,0 +1,285 @@
> +/*
> + * This file is part of Libav.
> + *
> + * Libav is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU Lesser General Public
> + * License as published by the Free Software Foundation; either
> + * version 2.1 of the License, or (at your option) any later version.
> + *
> + * Libav is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> + * Lesser General Public License for more details.
> + *
> + * You should have received a copy of the GNU Lesser General Public
> + * License along with Libav; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 
> USA
> + */
> +
> +#include 
> +#include 
> +
> +#include "libavutil/hwcontext.h"
> +#include "libavutil/hwcontext_opencl.h"
> +#include "libavutil/mem.h"
> +
> +#include "avfilter.h"
> +#include "formats.h"
> +#include "opencl.h"
> +
> +int ff_opencl_filter_query_formats(AVFilterContext *avctx)
> +{
> +const static enum AVPixelFormat formats[] = {
> +AV_PIX_FMT_OPENCL,
> +AV_PIX_FMT_NONE,
> +};
> +int i;
> +
> +for (i = 0; i < avctx->nb_inputs; i++) {
> +ff_formats_ref(ff_make_format_list(formats),
> +   >inputs[i]->out_formats);
> +}
> +
> +for (i = 0; i < avctx->nb_outputs; i++) {
> +ff_formats_ref(ff_make_format_list(formats),
> +   >outputs[i]->in_formats);
> +}
> +
> +return 0;
> +}
> +
> +int ff_opencl_filter_config_input(AVFilterLink *inlink)
> +{
> +AVFilterContext   *avctx = inlink->dst;
> +OpenCLFilterContext *ctx = avctx->priv;
> +AVHWFramesContext *input_frames;
> +
> +if (!inlink->hw_frames_ctx) {
> +av_log(avctx, AV_LOG_ERROR, "OpenCL filtering requires a "
> +   "hardware frames context on the input.\n");
> +return AVERROR(EINVAL);
> +}
> +
> +// Extract the device and default output format from the first input.
> +if (avctx->inputs[0] != inlink)
> +return 0;
> +
> +input_frames = (AVHWFramesContext*)inlink->hw_frames_ctx->data;
> +
> +if (input_frames->format != AV_PIX_FMT_OPENCL)
> +return AVERROR(EINVAL);
> +
> +ctx->device_ref = av_buffer_ref(input_frames->device_ref);
> +if (!ctx->device_ref)
> +return AVERROR(ENOMEM);
> +ctx->device = input_frames->device_ctx;
> +ctx->hwctx  = ctx->device->hwctx;
> +
> +// Default output parameters match input parameters.
> +if (ctx->output_format == AV_PIX_FMT_NONE)
> +ctx->output_format = input_frames->sw_format;
> +if (!ctx->output_width)
> +ctx->output_width  = inlink->w;
> +if (!ctx->output_height)
> +ctx->output_height = inlink->h;
> +
> +return 0;
> +}
> +
> +int ff_opencl_filter_config_output(AVFilterLink *outlink)
> +{
> +AVFilterContext   *avctx = outlink->src;
> +OpenCLFilterContext *ctx = avctx->priv;
> +AVBufferRef   *output_frames_ref = NULL;
> +AVHWFramesContext *output_frames;
> +int err;
> +
> +av_buffer_unref(>hw_frames_ctx);
> +
> +output_frames_ref = av_hwframe_ctx_alloc(ctx->device_ref);
> +if (!output_frames_ref) {
> +err = AVERROR(ENOMEM);
> +goto fail;
> +}
> +output_frames = (AVHWFramesContext*)output_frames_ref->data;
> +
> +output_frames->format= AV_PIX_FMT_OPENCL;
> +output_frames->sw_format = ctx->output_format;
> +output_frames->width = 

Re: [libav-devel] [PATCH 03/12] hwcontext_opencl: VAAPI to OpenCL mapping for Intel i965+beignet

2017-06-28 Thread wm4
On Tue, 27 Jun 2017 22:50:45 +0100
Mark Thompson  wrote:

> Supports all surface formats in common between the two.
> ---
>  configure  |   6 +
>  libavutil/hwcontext_internal.h |   3 +
>  libavutil/hwcontext_opencl.c   | 298 
> +
>  libavutil/hwcontext_vaapi.c|   9 ++
>  4 files changed, 316 insertions(+)
> 

Can't say much except:
1. It looks like we'll have NxM mapping implementation, and I question
   whether they really should exist as ifdef mess in the individual
   hwcontext impls, instead of a more structured approach (like one
   soruce file per N-M mapping).
2. ff_vaapi_fourcc_from_pix_fmt() is also funny - sure that we
   shouldn't have a more general public format mapping API like I
   suggested once with a patch?
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH 02/12] lavu: OpenCL hwcontext implementation

2017-06-28 Thread wm4
On Tue, 27 Jun 2017 22:50:44 +0100
Mark Thompson  wrote:

> ---
>  configure  |5 +-
>  doc/APIchanges |4 +
>  libavutil/Makefile |2 +
>  libavutil/hwcontext.c  |4 +
>  libavutil/hwcontext.h  |1 +
>  libavutil/hwcontext_internal.h |1 +
>  libavutil/hwcontext_opencl.c   | 1303 
> 
>  libavutil/hwcontext_opencl.h   |   96 +++
>  libavutil/version.h|4 +-
>  9 files changed, 1417 insertions(+), 3 deletions(-)
>  create mode 100644 libavutil/hwcontext_opencl.c
>  create mode 100644 libavutil/hwcontext_opencl.h


> +static int opencl_get_plane_format(enum AVPixelFormat pixfmt,
> +   int plane, int width, int height,
> +   cl_image_format *image_format,
> +   cl_image_desc *image_desc)
> +{
> +const AVPixFmtDescriptor *desc;
> +const AVComponentDescriptor *comp;
> +int channels = 0, order = 0, depth = 0, step = 0;
> +int wsub, hsub, alpha;
> +int c;
> +
> +if (plane >= AV_NUM_DATA_POINTERS)
> +return AVERROR(ENOENT);
> +
> +desc = av_pix_fmt_desc_get(pixfmt);
> +
> +// Only normal images are allowed.
> +if (desc->flags & (AV_PIX_FMT_FLAG_BITSTREAM |
> +   AV_PIX_FMT_FLAG_HWACCEL   |
> +   AV_PIX_FMT_FLAG_PAL))
> +return AVERROR(EINVAL);
> +
> +wsub = 1 << desc->log2_chroma_w;
> +hsub = 1 << desc->log2_chroma_h;
> +// Subsampled components must be exact.
> +if (width & wsub - 1 || height & hsub - 1)
> +return AVERROR(EINVAL);
> +
> +for (c = 0; c < desc->nb_components; c++) {
> +comp = >comp[c];
> +if (comp->plane != plane)
> +continue;
> +// The step size must be a power of two.
> +if (comp->step != 1 && comp->step != 2 &&
> +comp->step != 4 && comp->step != 8)
> +return AVERROR(EINVAL);
> +// The bits in each component must be packed in the
> +// most-significant-bits of the relevant bytes.
> +if (comp->shift + comp->depth != 8 &&
> +comp->shift + comp->depth != 16)
> +return AVERROR(EINVAL);
> +// The depth must not vary between components.
> +if (depth && comp->depth != depth)
> +return AVERROR(EINVAL);
> +// If a single data element crosses multiple bytes then
> +// it must match the native endianness.
> +if (comp->depth > 8 &&
> +HAVE_BIGENDIAN == !(desc->flags & AV_PIX_FMT_FLAG_BE))
> +return AVERROR(EINVAL);
> +// A single data element must not contain multiple samples
> +// from the same component.
> +if (step && comp->step != step)
> +return AVERROR(EINVAL);
> +order = order * 10 + c + 1;
> +depth = comp->depth;
> +step  = comp->step;
> +alpha = (desc->flags & AV_PIX_FMT_FLAG_ALPHA &&
> + c == desc->nb_components - 1);
> +++channels;
> +}
> +if (channels == 0)
> +return AVERROR(ENOENT);
> +
> +memset(image_format, 0, sizeof(*image_format));
> +memset(image_desc,   0, sizeof(*image_desc));
> +image_desc->image_type = CL_MEM_OBJECT_IMAGE2D;
> +
> +if (plane == 0 || alpha) {
> +image_desc->image_width = width;
> +image_desc->image_height= height;
> +image_desc->image_row_pitch = step * width;
> +} else {
> +image_desc->image_width = width  / wsub;
> +image_desc->image_height= height / hsub;
> +image_desc->image_row_pitch = step * width / wsub;
> +}
> +
> +if (depth <= 8) {
> +image_format->image_channel_data_type = CL_UNORM_INT8;
> +} else {
> +if (depth <= 16)
> +image_format->image_channel_data_type = CL_UNORM_INT16;
> +else
> +return AVERROR(EINVAL);
> +}
> +
> +#define CHANNEL_ORDER(order, type) \
> +case order: image_format->image_channel_order = type; break;
> +switch (order) {
> +CHANNEL_ORDER(1,CL_R);
> +CHANNEL_ORDER(2,CL_R);
> +CHANNEL_ORDER(3,CL_R);
> +CHANNEL_ORDER(4,CL_R);
> +CHANNEL_ORDER(12,   CL_RG);
> +CHANNEL_ORDER(23,   CL_RG);
> +CHANNEL_ORDER(1234, CL_RGBA);
> +CHANNEL_ORDER(3214, CL_BGRA);
> +CHANNEL_ORDER(4123, CL_ARGB);
> +#ifdef CL_ABGR
> +CHANNEL_ORDER(4321, CL_ABGR);
> +#endif
> +default:
> +return AVERROR(EINVAL);
> +}
> +#undef CHANNEL_ORDER
> +
> +return 0;
> +}

I suggest we make a generic helper for this.  I "often" need to know
about component order and whether formats are byte-aligned too. The
pixdesc struct is so generic yet insufficient that this can be quite
tricky and complex.


> +/**
> + * OpenCL frame descriptor for pool allocation.
> + 

Re: [libav-devel] [PATCH] lavu: Add DRM hwcontext

2017-06-28 Thread wm4
On Wed, 28 Jun 2017 11:37:57 +0200
Luca Barbato  wrote:

> On 6/28/17 11:36 AM, wm4 wrote:
> > Or maybe we should get back to your old nested arrays, but I'm worried
> > about excessive memory usage.  
> 
> The alternative is malloc it with all the usability issues around it =/

Or maybe limit them to 4 or whatever. Maybe I'm overthinking and
overcomplicating this.
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH] lavu: Add DRM hwcontext

2017-06-28 Thread Luca Barbato
On 6/28/17 11:36 AM, wm4 wrote:
> Or maybe we should get back to your old nested arrays, but I'm worried
> about excessive memory usage.

The alternative is malloc it with all the usability issues around it =/

lu
___
libav-devel mailing list
libav-devel@libav.org
https://lists.libav.org/mailman/listinfo/libav-devel

Re: [libav-devel] [PATCH] lavu: Add DRM hwcontext

2017-06-28 Thread wm4
On Sun, 18 Jun 2017 19:08:02 +0100
Mark Thompson  wrote:

> ---
> The intent of this is to have a common structure which can be used in all 
> cases where DRM objects need to be shared between components.  It would be 
> helpful if anyone familiar with specific drivers or use-cases could ensure 
> that the structure (see the hwcontext_drm.h header) is sufficiently general 
> to cover them - we would like this to the one answer and never require any 
> more formats in future.
> 
> Also unclear about how the libdrm dependency should actually be included.  
> Alot of this (including the header) doesn't actually require it, and it 
> wouldn't be difficult to make it a build-time-only dependency by replacing a 
> few calls with ioctls().
> 
> (See  
> for more context.)
> 
> 
>  configure  |   5 +-
>  libavutil/Makefile |   1 +
>  libavutil/hwcontext.c  |   4 +
>  libavutil/hwcontext.h  |   1 +
>  libavutil/hwcontext_drm.c  | 281 
> +
>  libavutil/hwcontext_drm.h  | 145 +
>  libavutil/hwcontext_internal.h |   1 +
>  libavutil/pixdesc.c|   4 +
>  libavutil/pixfmt.h |   6 +
>  9 files changed, 447 insertions(+), 1 deletion(-)
>  create mode 100644 libavutil/hwcontext_drm.c
>  create mode 100644 libavutil/hwcontext_drm.h
> 
> diff --git a/configure b/configure
> index fd879bc9d..12d831995 100755
> --- a/configure
> +++ b/configure
> @@ -190,6 +190,7 @@ External library support:
>--enable-avisynth  video frameserver
>--enable-avxsynth  Linux version of AviSynth
>--enable-bzlib bzip2 compression [autodetect]
> +  --enable-drm   DRM buffer sharing
>--enable-frei0rvideo filtering plugins
>--enable-gnutlscrypto
>--enable-libbs2b   Bauer stereophonic-to-binaural DSP
> @@ -1303,6 +1304,7 @@ EXTERNAL_LIBRARY_LIST="
>  $EXTERNAL_LIBRARY_VERSION3_LIST
>  avisynth
>  avxsynth
> +drm
>  frei0r
>  gnutls
>  libbs2b
> @@ -2547,7 +2549,7 @@ avdevice_extralibs="libm_extralibs"
>  avformat_extralibs="libm_extralibs"
>  avfilter_extralibs="pthreads_extralibs libm_extralibs"
>  avresample_extralibs="libm_extralibs"
> -avutil_extralibs="clock_gettime_extralibs cuda_extralibs libm_extralibs 
> libmfx_extralibs nanosleep_extralibs pthreads_extralibs user32_extralibs 
> vaapi_extralibs vaapi_drm_extralibs vaapi_x11_extralibs vdpau_x11_extralibs 
> wincrypt_extralibs"
> +avutil_extralibs="clock_gettime_extralibs cuda_extralibs libdrm_extralibs 
> libm_extralibs libmfx_extralibs nanosleep_extralibs pthreads_extralibs 
> user32_extralibs vaapi_extralibs vaapi_drm_extralibs vaapi_x11_extralibs 
> vdpau_x11_extralibs wincrypt_extralibs"
>  swscale_extralibs="libm_extralibs"
>  
>  # programs
> @@ -4734,6 +4736,7 @@ done
>  enabled avisynth  && require_header avisynth/avisynth_c.h
>  enabled avxsynth  && require_header avxsynth/avxsynth_c.h
>  enabled cuda  && require cuda cuda.h cuInit -lcuda
> +enabled drm   && require_pkg_config libdrm libdrm xf86drm.h 
> drmGetVersion
>  enabled frei0r&& require_header frei0r.h
>  enabled gnutls&& require_pkg_config gnutls gnutls 
> gnutls/gnutls.h gnutls_global_init
>  enabled libbs2b   && require_pkg_config libbs2b libbs2b bs2b.h 
> bs2b_open
> diff --git a/libavutil/Makefile b/libavutil/Makefile
> index 6fb24db67..9493a0059 100644
> --- a/libavutil/Makefile
> +++ b/libavutil/Makefile
> @@ -114,6 +114,7 @@ OBJS = adler32.o  
>   \
>  
>  OBJS-$(CONFIG_CUDA) += hwcontext_cuda.o
>  OBJS-$(CONFIG_D3D11VA)  += hwcontext_d3d11va.o
> +OBJS-$(CONFIG_DRM)  += hwcontext_drm.o
>  OBJS-$(CONFIG_DXVA2)+= hwcontext_dxva2.o
>  OBJS-$(CONFIG_LIBMFX)   += hwcontext_qsv.o
>  OBJS-$(CONFIG_LZO)  += lzo.o
> diff --git a/libavutil/hwcontext.c b/libavutil/hwcontext.c
> index 6dc95bba1..e0febaf26 100644
> --- a/libavutil/hwcontext.c
> +++ b/libavutil/hwcontext.c
> @@ -35,6 +35,9 @@ static const HWContextType * const hw_table[] = {
>  #if CONFIG_D3D11VA
>  _hwcontext_type_d3d11va,
>  #endif
> +#if CONFIG_DRM
> +_hwcontext_type_drm,
> +#endif
>  #if CONFIG_DXVA2
>  _hwcontext_type_dxva2,
>  #endif
> @@ -52,6 +55,7 @@ static const HWContextType * const hw_table[] = {
>  
>  static const char *const hw_type_names[] = {
>  [AV_HWDEVICE_TYPE_CUDA]   = "cuda",
> +[AV_HWDEVICE_TYPE_DRM]= "drm",
>  [AV_HWDEVICE_TYPE_DXVA2]  = "dxva2",
>  [AV_HWDEVICE_TYPE_D3D11VA] = "d3d11va",
>  [AV_HWDEVICE_TYPE_QSV]= "qsv",
> diff --git a/libavutil/hwcontext.h b/libavutil/hwcontext.h
> index 203ea510e..a48b2e53c 100644
> ---