From 48c43e5b7fa311b98574184207bc22c3de78ddc4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Olivier=20Cr=C3=AAte?= Date: Wed, 5 Jul 2023 18:46:25 -0600 Subject: [PATCH] gst-omx: Retire the whole package The OpenMAX standard is long dead and even the Raspberry Pi OS no longer supports it. Part-of: --- .gitignore | 2 - .gitlab-ci.yml | 5 - ci/docker/fedora/prepare.sh | 1 - ci/fuzzing/build-oss-fuzz.sh | 1 - ci/meson/gst-werror.ini | 3 - gst-env.py | 4 - meson.build | 1 - meson_options.txt | 1 - scripts/gen-changelog.py | 1 - scripts/meson.build | 1 - scripts/move_mrs_to_monorepo.py | 2 - .../gst-devtools/scripts/gen-changelog.py | 1 - .../hardware-accelerated-video-decoding.md | 8 - subprojects/gst-docs/scripts/gen-changelog.py | 1 - .../scripts/gen-changelog.py | 1 - .../gst-libav/scripts/gen-changelog.py | 1 - subprojects/gst-omx/.gitignore | 3 - subprojects/gst-omx/AUTHORS | 2 - subprojects/gst-omx/COPYING | 502 -- subprojects/gst-omx/NEWS | 1239 ----- subprojects/gst-omx/README | 17 - subprojects/gst-omx/RELEASE | 104 - .../gst-omx/config/bellagio/gstomx.conf | 60 - .../gst-omx/config/bellagio/meson.build | 1 - subprojects/gst-omx/config/meson.build | 21 - subprojects/gst-omx/config/rpi/gstomx.conf | 102 - subprojects/gst-omx/config/rpi/meson.build | 1 - .../gst-omx/config/tizonia/gstomx.conf.in | 49 - .../gst-omx/config/tizonia/meson.build | 5 - .../config/zynqultrascaleplus/gstomx.conf | 35 - .../config/zynqultrascaleplus/meson.build | 1 - .../gst-omx/docs/gst_plugins_cache.json | 13 - subprojects/gst-omx/docs/index.md | 3 - subprojects/gst-omx/docs/meson.build | 69 - subprojects/gst-omx/docs/sitemap.txt | 1 - .../examples/egl/cube_texture_and_coords.h | 100 - subprojects/gst-omx/examples/egl/meson.build | 31 - subprojects/gst-omx/examples/egl/testegl.c | 1611 ------- subprojects/gst-omx/examples/meson.build | 7 - subprojects/gst-omx/gst-omx.doap | 412 -- subprojects/gst-omx/meson.build | 430 -- subprojects/gst-omx/meson_options.txt | 14 - subprojects/gst-omx/omx/gstomx.c | 4179 ----------------- subprojects/gst-omx/omx/gstomx.h | 493 -- subprojects/gst-omx/omx/gstomxaacdec.c | 296 -- subprojects/gst-omx/omx/gstomxaacdec.h | 60 - subprojects/gst-omx/omx/gstomxaacenc.c | 511 -- subprojects/gst-omx/omx/gstomxaacenc.h | 65 - subprojects/gst-omx/omx/gstomxallocator.c | 554 --- subprojects/gst-omx/omx/gstomxallocator.h | 114 - subprojects/gst-omx/omx/gstomxamrdec.c | 220 - subprojects/gst-omx/omx/gstomxamrdec.h | 61 - .../gst-omx/omx/gstomxanalogaudiosink.c | 64 - .../gst-omx/omx/gstomxanalogaudiosink.h | 61 - subprojects/gst-omx/omx/gstomxaudiodec.c | 1404 ------ subprojects/gst-omx/omx/gstomxaudiodec.h | 100 - subprojects/gst-omx/omx/gstomxaudioenc.c | 1181 ----- subprojects/gst-omx/omx/gstomxaudioenc.h | 87 - subprojects/gst-omx/omx/gstomxaudiosink.c | 1228 ----- subprojects/gst-omx/omx/gstomxaudiosink.h | 103 - subprojects/gst-omx/omx/gstomxbufferpool.c | 674 --- subprojects/gst-omx/omx/gstomxbufferpool.h | 101 - subprojects/gst-omx/omx/gstomxh263dec.c | 99 - subprojects/gst-omx/omx/gstomxh263dec.h | 60 - subprojects/gst-omx/omx/gstomxh263enc.c | 302 -- subprojects/gst-omx/omx/gstomxh263enc.h | 60 - subprojects/gst-omx/omx/gstomxh264dec.c | 216 - subprojects/gst-omx/omx/gstomxh264dec.h | 60 - subprojects/gst-omx/omx/gstomxh264enc.c | 894 ---- subprojects/gst-omx/omx/gstomxh264enc.h | 73 - subprojects/gst-omx/omx/gstomxh264utils.c | 131 - subprojects/gst-omx/omx/gstomxh264utils.h | 36 - subprojects/gst-omx/omx/gstomxh265dec.c | 224 - subprojects/gst-omx/omx/gstomxh265dec.h | 61 - subprojects/gst-omx/omx/gstomxh265enc.c | 748 --- subprojects/gst-omx/omx/gstomxh265enc.h | 72 - subprojects/gst-omx/omx/gstomxh265utils.c | 138 - subprojects/gst-omx/omx/gstomxh265utils.h | 37 - subprojects/gst-omx/omx/gstomxhdmiaudiosink.c | 66 - subprojects/gst-omx/omx/gstomxhdmiaudiosink.h | 61 - subprojects/gst-omx/omx/gstomxmjpegdec.c | 98 - subprojects/gst-omx/omx/gstomxmjpegdec.h | 60 - subprojects/gst-omx/omx/gstomxmp3dec.c | 246 - subprojects/gst-omx/omx/gstomxmp3dec.h | 60 - subprojects/gst-omx/omx/gstomxmp3enc.c | 278 -- subprojects/gst-omx/omx/gstomxmp3enc.h | 65 - subprojects/gst-omx/omx/gstomxmpeg2videodec.c | 101 - subprojects/gst-omx/omx/gstomxmpeg2videodec.h | 59 - subprojects/gst-omx/omx/gstomxmpeg4videodec.c | 102 - subprojects/gst-omx/omx/gstomxmpeg4videodec.h | 60 - subprojects/gst-omx/omx/gstomxmpeg4videoenc.c | 336 -- subprojects/gst-omx/omx/gstomxmpeg4videoenc.h | 60 - subprojects/gst-omx/omx/gstomxtheoradec.c | 157 - subprojects/gst-omx/omx/gstomxtheoradec.h | 61 - subprojects/gst-omx/omx/gstomxvideo.c | 356 -- subprojects/gst-omx/omx/gstomxvideo.h | 74 - subprojects/gst-omx/omx/gstomxvideodec.c | 3524 -------------- subprojects/gst-omx/omx/gstomxvideodec.h | 119 - subprojects/gst-omx/omx/gstomxvideoenc.c | 3732 --------------- subprojects/gst-omx/omx/gstomxvideoenc.h | 133 - subprojects/gst-omx/omx/gstomxvp8dec.c | 99 - subprojects/gst-omx/omx/gstomxvp8dec.h | 60 - subprojects/gst-omx/omx/gstomxwmvdec.c | 98 - subprojects/gst-omx/omx/gstomxwmvdec.h | 60 - subprojects/gst-omx/omx/meson.build | 63 - subprojects/gst-omx/omx/openmax/OMX_Audio.h | 1311 ------ .../gst-omx/omx/openmax/OMX_Component.h | 579 --- .../gst-omx/omx/openmax/OMX_ComponentExt.h | 61 - .../gst-omx/omx/openmax/OMX_ContentPipe.h | 195 - subprojects/gst-omx/omx/openmax/OMX_Core.h | 1431 ------ subprojects/gst-omx/omx/openmax/OMX_CoreExt.h | 73 - .../gst-omx/omx/openmax/OMX_IVCommon.h | 920 ---- subprojects/gst-omx/omx/openmax/OMX_Image.h | 328 -- subprojects/gst-omx/omx/openmax/OMX_Index.h | 258 - .../gst-omx/omx/openmax/OMX_IndexExt.h | 87 - subprojects/gst-omx/omx/openmax/OMX_Other.h | 337 -- subprojects/gst-omx/omx/openmax/OMX_Types.h | 359 -- subprojects/gst-omx/omx/openmax/OMX_Video.h | 1060 ----- .../gst-omx/omx/openmax/OMX_VideoExt.h | 69 - .../extract-release-date-from-doap-file.py | 45 - subprojects/gst-omx/scripts/gen-changelog.py | 240 - .../gst-omx/tests/check/generic/states.c | 225 - subprojects/gst-omx/tests/check/meson.build | 56 - subprojects/gst-omx/tests/meson.build | 8 - subprojects/gst-omx/tools/listcomponents.c | 169 - subprojects/gst-omx/tools/meson.build | 27 - .../gst-plugins-bad/scripts/gen-changelog.py | 1 - .../gst-plugins-base/scripts/gen-changelog.py | 1 - .../gst-plugins-good/scripts/gen-changelog.py | 1 - .../gst-plugins-ugly/scripts/gen-changelog.py | 1 - .../gst-python/scripts/gen-changelog.py | 1 - .../gst-rtsp-server/scripts/gen-changelog.py | 1 - .../gstreamer-sharp/scripts/gen-changelog.py | 1 - .../gstreamer-vaapi/scripts/gen-changelog.py | 1 - .../gstreamer/scripts/gen-changelog.py | 1 - subprojects/gstreamer/scripts/git-version.sh | 1 - 136 files changed, 37670 deletions(-) delete mode 100644 subprojects/gst-omx/.gitignore delete mode 100644 subprojects/gst-omx/AUTHORS delete mode 100644 subprojects/gst-omx/COPYING delete mode 100644 subprojects/gst-omx/NEWS delete mode 100644 subprojects/gst-omx/README delete mode 100644 subprojects/gst-omx/RELEASE delete mode 100644 subprojects/gst-omx/config/bellagio/gstomx.conf delete mode 100644 subprojects/gst-omx/config/bellagio/meson.build delete mode 100644 subprojects/gst-omx/config/meson.build delete mode 100644 subprojects/gst-omx/config/rpi/gstomx.conf delete mode 100644 subprojects/gst-omx/config/rpi/meson.build delete mode 100644 subprojects/gst-omx/config/tizonia/gstomx.conf.in delete mode 100644 subprojects/gst-omx/config/tizonia/meson.build delete mode 100644 subprojects/gst-omx/config/zynqultrascaleplus/gstomx.conf delete mode 100644 subprojects/gst-omx/config/zynqultrascaleplus/meson.build delete mode 100644 subprojects/gst-omx/docs/gst_plugins_cache.json delete mode 100644 subprojects/gst-omx/docs/index.md delete mode 100644 subprojects/gst-omx/docs/meson.build delete mode 100644 subprojects/gst-omx/docs/sitemap.txt delete mode 100644 subprojects/gst-omx/examples/egl/cube_texture_and_coords.h delete mode 100644 subprojects/gst-omx/examples/egl/meson.build delete mode 100644 subprojects/gst-omx/examples/egl/testegl.c delete mode 100644 subprojects/gst-omx/examples/meson.build delete mode 100644 subprojects/gst-omx/gst-omx.doap delete mode 100644 subprojects/gst-omx/meson.build delete mode 100644 subprojects/gst-omx/meson_options.txt delete mode 100644 subprojects/gst-omx/omx/gstomx.c delete mode 100644 subprojects/gst-omx/omx/gstomx.h delete mode 100644 subprojects/gst-omx/omx/gstomxaacdec.c delete mode 100644 subprojects/gst-omx/omx/gstomxaacdec.h delete mode 100644 subprojects/gst-omx/omx/gstomxaacenc.c delete mode 100644 subprojects/gst-omx/omx/gstomxaacenc.h delete mode 100644 subprojects/gst-omx/omx/gstomxallocator.c delete mode 100644 subprojects/gst-omx/omx/gstomxallocator.h delete mode 100644 subprojects/gst-omx/omx/gstomxamrdec.c delete mode 100644 subprojects/gst-omx/omx/gstomxamrdec.h delete mode 100644 subprojects/gst-omx/omx/gstomxanalogaudiosink.c delete mode 100644 subprojects/gst-omx/omx/gstomxanalogaudiosink.h delete mode 100644 subprojects/gst-omx/omx/gstomxaudiodec.c delete mode 100644 subprojects/gst-omx/omx/gstomxaudiodec.h delete mode 100644 subprojects/gst-omx/omx/gstomxaudioenc.c delete mode 100644 subprojects/gst-omx/omx/gstomxaudioenc.h delete mode 100644 subprojects/gst-omx/omx/gstomxaudiosink.c delete mode 100644 subprojects/gst-omx/omx/gstomxaudiosink.h delete mode 100644 subprojects/gst-omx/omx/gstomxbufferpool.c delete mode 100644 subprojects/gst-omx/omx/gstomxbufferpool.h delete mode 100644 subprojects/gst-omx/omx/gstomxh263dec.c delete mode 100644 subprojects/gst-omx/omx/gstomxh263dec.h delete mode 100644 subprojects/gst-omx/omx/gstomxh263enc.c delete mode 100644 subprojects/gst-omx/omx/gstomxh263enc.h delete mode 100644 subprojects/gst-omx/omx/gstomxh264dec.c delete mode 100644 subprojects/gst-omx/omx/gstomxh264dec.h delete mode 100644 subprojects/gst-omx/omx/gstomxh264enc.c delete mode 100644 subprojects/gst-omx/omx/gstomxh264enc.h delete mode 100644 subprojects/gst-omx/omx/gstomxh264utils.c delete mode 100644 subprojects/gst-omx/omx/gstomxh264utils.h delete mode 100644 subprojects/gst-omx/omx/gstomxh265dec.c delete mode 100644 subprojects/gst-omx/omx/gstomxh265dec.h delete mode 100644 subprojects/gst-omx/omx/gstomxh265enc.c delete mode 100644 subprojects/gst-omx/omx/gstomxh265enc.h delete mode 100644 subprojects/gst-omx/omx/gstomxh265utils.c delete mode 100644 subprojects/gst-omx/omx/gstomxh265utils.h delete mode 100644 subprojects/gst-omx/omx/gstomxhdmiaudiosink.c delete mode 100644 subprojects/gst-omx/omx/gstomxhdmiaudiosink.h delete mode 100644 subprojects/gst-omx/omx/gstomxmjpegdec.c delete mode 100644 subprojects/gst-omx/omx/gstomxmjpegdec.h delete mode 100644 subprojects/gst-omx/omx/gstomxmp3dec.c delete mode 100644 subprojects/gst-omx/omx/gstomxmp3dec.h delete mode 100644 subprojects/gst-omx/omx/gstomxmp3enc.c delete mode 100644 subprojects/gst-omx/omx/gstomxmp3enc.h delete mode 100644 subprojects/gst-omx/omx/gstomxmpeg2videodec.c delete mode 100644 subprojects/gst-omx/omx/gstomxmpeg2videodec.h delete mode 100644 subprojects/gst-omx/omx/gstomxmpeg4videodec.c delete mode 100644 subprojects/gst-omx/omx/gstomxmpeg4videodec.h delete mode 100644 subprojects/gst-omx/omx/gstomxmpeg4videoenc.c delete mode 100644 subprojects/gst-omx/omx/gstomxmpeg4videoenc.h delete mode 100644 subprojects/gst-omx/omx/gstomxtheoradec.c delete mode 100644 subprojects/gst-omx/omx/gstomxtheoradec.h delete mode 100644 subprojects/gst-omx/omx/gstomxvideo.c delete mode 100644 subprojects/gst-omx/omx/gstomxvideo.h delete mode 100644 subprojects/gst-omx/omx/gstomxvideodec.c delete mode 100644 subprojects/gst-omx/omx/gstomxvideodec.h delete mode 100644 subprojects/gst-omx/omx/gstomxvideoenc.c delete mode 100644 subprojects/gst-omx/omx/gstomxvideoenc.h delete mode 100644 subprojects/gst-omx/omx/gstomxvp8dec.c delete mode 100644 subprojects/gst-omx/omx/gstomxvp8dec.h delete mode 100644 subprojects/gst-omx/omx/gstomxwmvdec.c delete mode 100644 subprojects/gst-omx/omx/gstomxwmvdec.h delete mode 100644 subprojects/gst-omx/omx/meson.build delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Audio.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Component.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_ComponentExt.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_ContentPipe.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Core.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_CoreExt.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_IVCommon.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Image.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Index.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_IndexExt.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Other.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Types.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_Video.h delete mode 100644 subprojects/gst-omx/omx/openmax/OMX_VideoExt.h delete mode 100755 subprojects/gst-omx/scripts/extract-release-date-from-doap-file.py delete mode 100755 subprojects/gst-omx/scripts/gen-changelog.py delete mode 100644 subprojects/gst-omx/tests/check/generic/states.c delete mode 100644 subprojects/gst-omx/tests/check/meson.build delete mode 100644 subprojects/gst-omx/tests/meson.build delete mode 100644 subprojects/gst-omx/tools/listcomponents.c delete mode 100644 subprojects/gst-omx/tools/meson.build diff --git a/.gitignore b/.gitignore index 008c714201..3f8e282ecd 100644 --- a/.gitignore +++ b/.gitignore @@ -22,7 +22,6 @@ prefix/ /gst-integration-testsuites /gst-editing-services /gstreamer-vaapi -/gst-omx /gstreamer-sharp /pygobject /gst-python @@ -47,7 +46,6 @@ subprojects/*/ !subprojects/gst-examples !subprojects/gst-integration-testsuites !subprojects/gst-libav -!subprojects/gst-omx !subprojects/gst-plugins-bad !subprojects/gst-plugins-base !subprojects/gst-plugins-good diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 09dcbf02b3..965300cf9e 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -61,8 +61,6 @@ variables: SIMPLE_BUILD: >- ${DEFAULT_MESON_ARGS} -Dsharp=enabled - -Domx=enabled - -Dgst-omx:target=generic -Ddoc=disabled workflow: @@ -287,7 +285,6 @@ commitlint: - subprojects/gst-editing-services/**/* - subprojects/gst-integration-testsuites/**/* - subprojects/gst-libav/**/* - - subprojects/gst-omx/**/* - subprojects/gst-plugins-bad/**/* - subprojects/gst-plugins-base/**/* - subprojects/gst-plugins-good/**/* @@ -598,7 +595,6 @@ integration testsuites fedora: variables: MESON_ARGS: >- ${SIMPLE_BUILD} - -Domx=disabled -Dsharp=disabled -Dvaapi=disabled -Dexamples=disabled @@ -845,7 +841,6 @@ build documentation: - subprojects/gst-devtools/**/* - subprojects/gst-editing-services/**/* - subprojects/gst-libav/**/* - - subprojects/gst-omx/**/* - subprojects/gst-plugins-bad/**/* - subprojects/gst-plugins-base/**/* - subprojects/gst-plugins-good/**/* diff --git a/ci/docker/fedora/prepare.sh b/ci/docker/fedora/prepare.sh index 716d1482b7..2be08aad89 100644 --- a/ci/docker/fedora/prepare.sh +++ b/ci/docker/fedora/prepare.sh @@ -105,7 +105,6 @@ dnf install -y \ valgrind \ vulkan \ vulkan-devel \ - mesa-omx-drivers \ mesa-libGL \ mesa-libGL-devel \ mesa-libGLU \ diff --git a/ci/fuzzing/build-oss-fuzz.sh b/ci/fuzzing/build-oss-fuzz.sh index 475f7c62ff..e155878a04 100755 --- a/ci/fuzzing/build-oss-fuzz.sh +++ b/ci/fuzzing/build-oss-fuzz.sh @@ -84,7 +84,6 @@ meson \ -Dbad=disabled \ -Dlibav=disabled \ -Dges=disabled \ - -Domx=disabled \ -Dvaapi=disabled \ -Dsharp=disabled \ -Drs=disabled \ diff --git a/ci/meson/gst-werror.ini b/ci/meson/gst-werror.ini index ebd9ca2e42..ab7e8cfcf0 100644 --- a/ci/meson/gst-werror.ini +++ b/ci/meson/gst-werror.ini @@ -28,9 +28,6 @@ werror = true [gst-docs:built-in options] werror = true -[gst-omx:built-in options] -werror = true - [gst-devtools:built-in options] werror = true diff --git a/gst-env.py b/gst-env.py index 2d4ae32a43..42e07ddd4b 100755 --- a/gst-env.py +++ b/gst-env.py @@ -453,10 +453,6 @@ def get_subprocess_env(options, gst_version): encoding_targets.add( os.path.abspath(os.path.join(os.path.dirname(path), '..'))) - if path.endswith('gstomx.conf'): - prepend_env_var(env, 'GST_OMX_CONFIG_DIR', os.path.dirname(path), - options.sysroot) - for p in sorted(presets): prepend_env_var(env, 'GST_PRESET_PATH', p, options.sysroot) diff --git a/meson.build b/meson.build index 32a31add67..125439ef5d 100644 --- a/meson.build +++ b/meson.build @@ -105,7 +105,6 @@ subprojects = [ ['gst-integration-testsuites', { 'option': get_option('devtools') }], ['gst-editing-services', { 'option': get_option('ges'), 'build-hotdoc': true}], ['gstreamer-vaapi', { 'option': get_option('vaapi'), 'build-hotdoc': true}], - ['gst-omx', { 'option': get_option('omx'), 'build-hotdoc': true}], ['gstreamer-sharp', { 'option': get_option('sharp') }], ['pygobject', { 'option': get_option('python'), 'match_gst_version': false, 'sysdep': 'pygobject-3.0', 'sysdep_version': '>= 3.8' }], ['gst-python', { 'option': get_option('python')}], diff --git a/meson_options.txt b/meson_options.txt index e5eeb4cb32..276e0e807f 100644 --- a/meson_options.txt +++ b/meson_options.txt @@ -8,7 +8,6 @@ option('devtools', type : 'feature', value : 'enabled') option('ges', type : 'feature', value : 'enabled') option('rtsp_server', type : 'feature', value : 'enabled') option('rs', type : 'feature', value : 'disabled') -option('omx', type : 'feature', value : 'disabled') option('vaapi', type : 'feature', value : 'disabled') option('gst-examples', type : 'feature', value : 'auto', description : 'Build gst-examples subproject') # Bindings diff --git a/scripts/gen-changelog.py b/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/scripts/gen-changelog.py +++ b/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/scripts/meson.build b/scripts/meson.build index 0554b17b6e..e053ff35e1 100644 --- a/scripts/meson.build +++ b/scripts/meson.build @@ -13,7 +13,6 @@ release_modules = [ 'gst-devtools', 'gst-python', 'gstreamer-vaapi', - 'gst-omx', 'gst-docs', 'gstreamer-sharp', ] diff --git a/scripts/move_mrs_to_monorepo.py b/scripts/move_mrs_to_monorepo.py index cdd343feae..fd0e0e9d36 100755 --- a/scripts/move_mrs_to_monorepo.py +++ b/scripts/move_mrs_to_monorepo.py @@ -101,7 +101,6 @@ GST_PROJECTS = [ 'gstreamer-vaapi', 'gstreamer-sharp', 'gst-python', - 'gst-omx', 'gst-editing-services', 'gst-devtools', 'gst-docs', @@ -120,7 +119,6 @@ GST_PROJECTS_ID = { 'gst-plugins-good': 1353, 'gst-plugins-base': 1352, 'gst-plugins-bad': 1351, - 'gst-omx': 1350, 'gst-libav': 1349, 'gst-integration-testsuites': 1348, 'gst-examples': 1347, diff --git a/subprojects/gst-devtools/scripts/gen-changelog.py b/subprojects/gst-devtools/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-devtools/scripts/gen-changelog.py +++ b/subprojects/gst-devtools/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-docs/markdown/tutorials/playback/hardware-accelerated-video-decoding.md b/subprojects/gst-docs/markdown/tutorials/playback/hardware-accelerated-video-decoding.md index 54c390a968..d76a2bdead 100644 --- a/subprojects/gst-docs/markdown/tutorials/playback/hardware-accelerated-video-decoding.md +++ b/subprojects/gst-docs/markdown/tutorials/playback/hardware-accelerated-video-decoding.md @@ -43,14 +43,6 @@ Technologies](http://en.wikipedia.org/wiki/Imagination_Technologies) or [S3 Graphics](http://en.wikipedia.org/wiki/S3_Graphics). Accessible to GStreamer through the [gstreamer-vaapi](https://gitlab.freedesktop.org/gstreamer/gstreamer/-/tree/main/subprojects/gstreamer-vaapi/) package. - - [OpenMAX](http://en.wikipedia.org/wiki/OpenMAX) (*Open Media -Acceleration*): Managed by the non-profit technology consortium [Khronos -Group](http://en.wikipedia.org/wiki/Khronos_Group "Khronos Group"), -it is a "royalty-free, cross-platform set of C-language programming -interfaces that provides abstractions for routines especially useful for -audio, video, and still images". Accessible to GStreamer through -the [gst-omx](http://git.freedesktop.org/gstreamer/gst-omx) plugin. - - [OVD](http://developer.amd.com/sdks/AMDAPPSDK/assets/OpenVideo_Decode_API.PDF) (*Open Video Decode*): Another API from [AMD Graphics](http://en.wikipedia.org/wiki/AMD_Graphics), designed to be a diff --git a/subprojects/gst-docs/scripts/gen-changelog.py b/subprojects/gst-docs/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-docs/scripts/gen-changelog.py +++ b/subprojects/gst-docs/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-editing-services/scripts/gen-changelog.py b/subprojects/gst-editing-services/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-editing-services/scripts/gen-changelog.py +++ b/subprojects/gst-editing-services/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-libav/scripts/gen-changelog.py b/subprojects/gst-libav/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-libav/scripts/gen-changelog.py +++ b/subprojects/gst-libav/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-omx/.gitignore b/subprojects/gst-omx/.gitignore deleted file mode 100644 index d4cb069593..0000000000 --- a/subprojects/gst-omx/.gitignore +++ /dev/null @@ -1,3 +0,0 @@ -*~ -*.bak -*.swp diff --git a/subprojects/gst-omx/AUTHORS b/subprojects/gst-omx/AUTHORS deleted file mode 100644 index 3d3e8d7e9c..0000000000 --- a/subprojects/gst-omx/AUTHORS +++ /dev/null @@ -1,2 +0,0 @@ -Sebastian Dröge - diff --git a/subprojects/gst-omx/COPYING b/subprojects/gst-omx/COPYING deleted file mode 100644 index 4362b49151..0000000000 --- a/subprojects/gst-omx/COPYING +++ /dev/null @@ -1,502 +0,0 @@ - GNU LESSER GENERAL PUBLIC LICENSE - Version 2.1, February 1999 - - Copyright (C) 1991, 1999 Free Software Foundation, Inc. - 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - Everyone is permitted to copy and distribute verbatim copies - of this license document, but changing it is not allowed. - -[This is the first released version of the Lesser GPL. It also counts - as the successor of the GNU Library Public License, version 2, hence - the version number 2.1.] - - Preamble - - The licenses for most software are designed to take away your -freedom to share and change it. By contrast, the GNU General Public -Licenses are intended to guarantee your freedom to share and change -free software--to make sure the software is free for all its users. - - This license, the Lesser General Public License, applies to some -specially designated software packages--typically libraries--of the -Free Software Foundation and other authors who decide to use it. You -can use it too, but we suggest you first think carefully about whether -this license or the ordinary General Public License is the better -strategy to use in any particular case, based on the explanations below. - - When we speak of free software, we are referring to freedom of use, -not price. Our General Public Licenses are designed to make sure that -you have the freedom to distribute copies of free software (and charge -for this service if you wish); that you receive source code or can get -it if you want it; that you can change the software and use pieces of -it in new free programs; and that you are informed that you can do -these things. - - To protect your rights, we need to make restrictions that forbid -distributors to deny you these rights or to ask you to surrender these -rights. These restrictions translate to certain responsibilities for -you if you distribute copies of the library or if you modify it. - - For example, if you distribute copies of the library, whether gratis -or for a fee, you must give the recipients all the rights that we gave -you. You must make sure that they, too, receive or can get the source -code. If you link other code with the library, you must provide -complete object files to the recipients, so that they can relink them -with the library after making changes to the library and recompiling -it. And you must show them these terms so they know their rights. - - We protect your rights with a two-step method: (1) we copyright the -library, and (2) we offer you this license, which gives you legal -permission to copy, distribute and/or modify the library. - - To protect each distributor, we want to make it very clear that -there is no warranty for the free library. Also, if the library is -modified by someone else and passed on, the recipients should know -that what they have is not the original version, so that the original -author's reputation will not be affected by problems that might be -introduced by others. - - Finally, software patents pose a constant threat to the existence of -any free program. We wish to make sure that a company cannot -effectively restrict the users of a free program by obtaining a -restrictive license from a patent holder. Therefore, we insist that -any patent license obtained for a version of the library must be -consistent with the full freedom of use specified in this license. - - Most GNU software, including some libraries, is covered by the -ordinary GNU General Public License. This license, the GNU Lesser -General Public License, applies to certain designated libraries, and -is quite different from the ordinary General Public License. We use -this license for certain libraries in order to permit linking those -libraries into non-free programs. - - When a program is linked with a library, whether statically or using -a shared library, the combination of the two is legally speaking a -combined work, a derivative of the original library. The ordinary -General Public License therefore permits such linking only if the -entire combination fits its criteria of freedom. The Lesser General -Public License permits more lax criteria for linking other code with -the library. - - We call this license the "Lesser" General Public License because it -does Less to protect the user's freedom than the ordinary General -Public License. It also provides other free software developers Less -of an advantage over competing non-free programs. These disadvantages -are the reason we use the ordinary General Public License for many -libraries. However, the Lesser license provides advantages in certain -special circumstances. - - For example, on rare occasions, there may be a special need to -encourage the widest possible use of a certain library, so that it becomes -a de-facto standard. To achieve this, non-free programs must be -allowed to use the library. A more frequent case is that a free -library does the same job as widely used non-free libraries. In this -case, there is little to gain by limiting the free library to free -software only, so we use the Lesser General Public License. - - In other cases, permission to use a particular library in non-free -programs enables a greater number of people to use a large body of -free software. For example, permission to use the GNU C Library in -non-free programs enables many more people to use the whole GNU -operating system, as well as its variant, the GNU/Linux operating -system. - - Although the Lesser General Public License is Less protective of the -users' freedom, it does ensure that the user of a program that is -linked with the Library has the freedom and the wherewithal to run -that program using a modified version of the Library. - - The precise terms and conditions for copying, distribution and -modification follow. Pay close attention to the difference between a -"work based on the library" and a "work that uses the library". The -former contains code derived from the library, whereas the latter must -be combined with the library in order to run. - - GNU LESSER GENERAL PUBLIC LICENSE - TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION - - 0. This License Agreement applies to any software library or other -program which contains a notice placed by the copyright holder or -other authorized party saying it may be distributed under the terms of -this Lesser General Public License (also called "this License"). -Each licensee is addressed as "you". - - A "library" means a collection of software functions and/or data -prepared so as to be conveniently linked with application programs -(which use some of those functions and data) to form executables. - - The "Library", below, refers to any such software library or work -which has been distributed under these terms. A "work based on the -Library" means either the Library or any derivative work under -copyright law: that is to say, a work containing the Library or a -portion of it, either verbatim or with modifications and/or translated -straightforwardly into another language. (Hereinafter, translation is -included without limitation in the term "modification".) - - "Source code" for a work means the preferred form of the work for -making modifications to it. For a library, complete source code means -all the source code for all modules it contains, plus any associated -interface definition files, plus the scripts used to control compilation -and installation of the library. - - Activities other than copying, distribution and modification are not -covered by this License; they are outside its scope. The act of -running a program using the Library is not restricted, and output from -such a program is covered only if its contents constitute a work based -on the Library (independent of the use of the Library in a tool for -writing it). Whether that is true depends on what the Library does -and what the program that uses the Library does. - - 1. You may copy and distribute verbatim copies of the Library's -complete source code as you receive it, in any medium, provided that -you conspicuously and appropriately publish on each copy an -appropriate copyright notice and disclaimer of warranty; keep intact -all the notices that refer to this License and to the absence of any -warranty; and distribute a copy of this License along with the -Library. - - You may charge a fee for the physical act of transferring a copy, -and you may at your option offer warranty protection in exchange for a -fee. - - 2. You may modify your copy or copies of the Library or any portion -of it, thus forming a work based on the Library, and copy and -distribute such modifications or work under the terms of Section 1 -above, provided that you also meet all of these conditions: - - a) The modified work must itself be a software library. - - b) You must cause the files modified to carry prominent notices - stating that you changed the files and the date of any change. - - c) You must cause the whole of the work to be licensed at no - charge to all third parties under the terms of this License. - - d) If a facility in the modified Library refers to a function or a - table of data to be supplied by an application program that uses - the facility, other than as an argument passed when the facility - is invoked, then you must make a good faith effort to ensure that, - in the event an application does not supply such function or - table, the facility still operates, and performs whatever part of - its purpose remains meaningful. - - (For example, a function in a library to compute square roots has - a purpose that is entirely well-defined independent of the - application. Therefore, Subsection 2d requires that any - application-supplied function or table used by this function must - be optional: if the application does not supply it, the square - root function must still compute square roots.) - -These requirements apply to the modified work as a whole. If -identifiable sections of that work are not derived from the Library, -and can be reasonably considered independent and separate works in -themselves, then this License, and its terms, do not apply to those -sections when you distribute them as separate works. But when you -distribute the same sections as part of a whole which is a work based -on the Library, the distribution of the whole must be on the terms of -this License, whose permissions for other licensees extend to the -entire whole, and thus to each and every part regardless of who wrote -it. - -Thus, it is not the intent of this section to claim rights or contest -your rights to work written entirely by you; rather, the intent is to -exercise the right to control the distribution of derivative or -collective works based on the Library. - -In addition, mere aggregation of another work not based on the Library -with the Library (or with a work based on the Library) on a volume of -a storage or distribution medium does not bring the other work under -the scope of this License. - - 3. You may opt to apply the terms of the ordinary GNU General Public -License instead of this License to a given copy of the Library. To do -this, you must alter all the notices that refer to this License, so -that they refer to the ordinary GNU General Public License, version 2, -instead of to this License. (If a newer version than version 2 of the -ordinary GNU General Public License has appeared, then you can specify -that version instead if you wish.) Do not make any other change in -these notices. - - Once this change is made in a given copy, it is irreversible for -that copy, so the ordinary GNU General Public License applies to all -subsequent copies and derivative works made from that copy. - - This option is useful when you wish to copy part of the code of -the Library into a program that is not a library. - - 4. You may copy and distribute the Library (or a portion or -derivative of it, under Section 2) in object code or executable form -under the terms of Sections 1 and 2 above provided that you accompany -it with the complete corresponding machine-readable source code, which -must be distributed under the terms of Sections 1 and 2 above on a -medium customarily used for software interchange. - - If distribution of object code is made by offering access to copy -from a designated place, then offering equivalent access to copy the -source code from the same place satisfies the requirement to -distribute the source code, even though third parties are not -compelled to copy the source along with the object code. - - 5. A program that contains no derivative of any portion of the -Library, but is designed to work with the Library by being compiled or -linked with it, is called a "work that uses the Library". Such a -work, in isolation, is not a derivative work of the Library, and -therefore falls outside the scope of this License. - - However, linking a "work that uses the Library" with the Library -creates an executable that is a derivative of the Library (because it -contains portions of the Library), rather than a "work that uses the -library". The executable is therefore covered by this License. -Section 6 states terms for distribution of such executables. - - When a "work that uses the Library" uses material from a header file -that is part of the Library, the object code for the work may be a -derivative work of the Library even though the source code is not. -Whether this is true is especially significant if the work can be -linked without the Library, or if the work is itself a library. The -threshold for this to be true is not precisely defined by law. - - If such an object file uses only numerical parameters, data -structure layouts and accessors, and small macros and small inline -functions (ten lines or less in length), then the use of the object -file is unrestricted, regardless of whether it is legally a derivative -work. (Executables containing this object code plus portions of the -Library will still fall under Section 6.) - - Otherwise, if the work is a derivative of the Library, you may -distribute the object code for the work under the terms of Section 6. -Any executables containing that work also fall under Section 6, -whether or not they are linked directly with the Library itself. - - 6. As an exception to the Sections above, you may also combine or -link a "work that uses the Library" with the Library to produce a -work containing portions of the Library, and distribute that work -under terms of your choice, provided that the terms permit -modification of the work for the customer's own use and reverse -engineering for debugging such modifications. - - You must give prominent notice with each copy of the work that the -Library is used in it and that the Library and its use are covered by -this License. You must supply a copy of this License. If the work -during execution displays copyright notices, you must include the -copyright notice for the Library among them, as well as a reference -directing the user to the copy of this License. Also, you must do one -of these things: - - a) Accompany the work with the complete corresponding - machine-readable source code for the Library including whatever - changes were used in the work (which must be distributed under - Sections 1 and 2 above); and, if the work is an executable linked - with the Library, with the complete machine-readable "work that - uses the Library", as object code and/or source code, so that the - user can modify the Library and then relink to produce a modified - executable containing the modified Library. (It is understood - that the user who changes the contents of definitions files in the - Library will not necessarily be able to recompile the application - to use the modified definitions.) - - b) Use a suitable shared library mechanism for linking with the - Library. A suitable mechanism is one that (1) uses at run time a - copy of the library already present on the user's computer system, - rather than copying library functions into the executable, and (2) - will operate properly with a modified version of the library, if - the user installs one, as long as the modified version is - interface-compatible with the version that the work was made with. - - c) Accompany the work with a written offer, valid for at - least three years, to give the same user the materials - specified in Subsection 6a, above, for a charge no more - than the cost of performing this distribution. - - d) If distribution of the work is made by offering access to copy - from a designated place, offer equivalent access to copy the above - specified materials from the same place. - - e) Verify that the user has already received a copy of these - materials or that you have already sent this user a copy. - - For an executable, the required form of the "work that uses the -Library" must include any data and utility programs needed for -reproducing the executable from it. However, as a special exception, -the materials to be distributed need not include anything that is -normally distributed (in either source or binary form) with the major -components (compiler, kernel, and so on) of the operating system on -which the executable runs, unless that component itself accompanies -the executable. - - It may happen that this requirement contradicts the license -restrictions of other proprietary libraries that do not normally -accompany the operating system. Such a contradiction means you cannot -use both them and the Library together in an executable that you -distribute. - - 7. You may place library facilities that are a work based on the -Library side-by-side in a single library together with other library -facilities not covered by this License, and distribute such a combined -library, provided that the separate distribution of the work based on -the Library and of the other library facilities is otherwise -permitted, and provided that you do these two things: - - a) Accompany the combined library with a copy of the same work - based on the Library, uncombined with any other library - facilities. This must be distributed under the terms of the - Sections above. - - b) Give prominent notice with the combined library of the fact - that part of it is a work based on the Library, and explaining - where to find the accompanying uncombined form of the same work. - - 8. You may not copy, modify, sublicense, link with, or distribute -the Library except as expressly provided under this License. Any -attempt otherwise to copy, modify, sublicense, link with, or -distribute the Library is void, and will automatically terminate your -rights under this License. However, parties who have received copies, -or rights, from you under this License will not have their licenses -terminated so long as such parties remain in full compliance. - - 9. You are not required to accept this License, since you have not -signed it. However, nothing else grants you permission to modify or -distribute the Library or its derivative works. These actions are -prohibited by law if you do not accept this License. Therefore, by -modifying or distributing the Library (or any work based on the -Library), you indicate your acceptance of this License to do so, and -all its terms and conditions for copying, distributing or modifying -the Library or works based on it. - - 10. Each time you redistribute the Library (or any work based on the -Library), the recipient automatically receives a license from the -original licensor to copy, distribute, link with or modify the Library -subject to these terms and conditions. You may not impose any further -restrictions on the recipients' exercise of the rights granted herein. -You are not responsible for enforcing compliance by third parties with -this License. - - 11. If, as a consequence of a court judgment or allegation of patent -infringement or for any other reason (not limited to patent issues), -conditions are imposed on you (whether by court order, agreement or -otherwise) that contradict the conditions of this License, they do not -excuse you from the conditions of this License. If you cannot -distribute so as to satisfy simultaneously your obligations under this -License and any other pertinent obligations, then as a consequence you -may not distribute the Library at all. For example, if a patent -license would not permit royalty-free redistribution of the Library by -all those who receive copies directly or indirectly through you, then -the only way you could satisfy both it and this License would be to -refrain entirely from distribution of the Library. - -If any portion of this section is held invalid or unenforceable under any -particular circumstance, the balance of the section is intended to apply, -and the section as a whole is intended to apply in other circumstances. - -It is not the purpose of this section to induce you to infringe any -patents or other property right claims or to contest validity of any -such claims; this section has the sole purpose of protecting the -integrity of the free software distribution system which is -implemented by public license practices. Many people have made -generous contributions to the wide range of software distributed -through that system in reliance on consistent application of that -system; it is up to the author/donor to decide if he or she is willing -to distribute software through any other system and a licensee cannot -impose that choice. - -This section is intended to make thoroughly clear what is believed to -be a consequence of the rest of this License. - - 12. If the distribution and/or use of the Library is restricted in -certain countries either by patents or by copyrighted interfaces, the -original copyright holder who places the Library under this License may add -an explicit geographical distribution limitation excluding those countries, -so that distribution is permitted only in or among countries not thus -excluded. In such case, this License incorporates the limitation as if -written in the body of this License. - - 13. The Free Software Foundation may publish revised and/or new -versions of the Lesser General Public License from time to time. -Such new versions will be similar in spirit to the present version, -but may differ in detail to address new problems or concerns. - -Each version is given a distinguishing version number. If the Library -specifies a version number of this License which applies to it and -"any later version", you have the option of following the terms and -conditions either of that version or of any later version published by -the Free Software Foundation. If the Library does not specify a -license version number, you may choose any version ever published by -the Free Software Foundation. - - 14. If you wish to incorporate parts of the Library into other free -programs whose distribution conditions are incompatible with these, -write to the author to ask for permission. For software which is -copyrighted by the Free Software Foundation, write to the Free -Software Foundation; we sometimes make exceptions for this. Our -decision will be guided by the two goals of preserving the free status -of all derivatives of our free software and of promoting the sharing -and reuse of software generally. - - NO WARRANTY - - 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO -WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. -EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR -OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY -KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE -IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR -PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE -LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME -THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. - - 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN -WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY -AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU -FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR -CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE -LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING -RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A -FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF -SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH -DAMAGES. - - END OF TERMS AND CONDITIONS - - How to Apply These Terms to Your New Libraries - - If you develop a new library, and you want it to be of the greatest -possible use to the public, we recommend making it free software that -everyone can redistribute and change. You can do so by permitting -redistribution under these terms (or, alternatively, under the terms of the -ordinary General Public License). - - To apply these terms, attach the following notices to the library. It is -safest to attach them to the start of each source file to most effectively -convey the exclusion of warranty; and each file should have at least the -"copyright" line and a pointer to where the full notice is found. - - - Copyright (C) - - This library 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. - - This library 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 this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - -Also add information on how to contact you by electronic and paper mail. - -You should also get your employer (if you work as a programmer) or your -school, if any, to sign a "copyright disclaimer" for the library, if -necessary. Here is a sample; alter the names: - - Yoyodyne, Inc., hereby disclaims all copyright interest in the - library `Frob' (a library for tweaking knobs) written by James Random Hacker. - - , 1 April 1990 - Ty Coon, President of Vice - -That's all there is to it! diff --git a/subprojects/gst-omx/NEWS b/subprojects/gst-omx/NEWS deleted file mode 100644 index 9802493d32..0000000000 --- a/subprojects/gst-omx/NEWS +++ /dev/null @@ -1,1239 +0,0 @@ -GStreamer 1.22 Release Notes - -GStreamer 1.22.0 was originally released on 23 January 2023. - -See https://gstreamer.freedesktop.org/releases/1.22/ for the latest -version of this document. - -Last updated: Monday 23 January 2023, 17:00 UTC (log) - -Introduction - -The GStreamer team is proud to announce a new major feature release in -the stable 1.x API series of your favourite cross-platform multimedia -framework! - -As always, this release is again packed with many new features, bug -fixes and other improvements. - -Highlights - -- AV1 video codec support improvements -- New HLS, DASH and Microsoft Smooth Streaming adaptive streaming - clients -- Qt6 support for rendering video inside a QML scene -- Minimal builds optimised for binary size, including only the - individual elements needed -- Playbin3, Decodebin3, UriDecodebin3, Parsebin enhancements and - stabilisation -- WebRTC simulcast support and support for Google Congestion Control -- WebRTC-based media server ingestion/egress (WHIP/WHEP) support -- New easy to use batteries-included WebRTC sender plugin -- Easy RTP sender timestamp reconstruction for RTP and RTSP -- ONVIF timed metadata support -- New fragmented MP4 muxer and non-fragmented MP4 muxer -- New plugins for Amazon AWS storage and audio transcription services -- New gtk4paintablesink and gtkwaylandsink renderers -- New videocolorscale element that can convert and scale in one go for - better performance -- High bit-depth video improvements -- Touchscreen event support in navigation API -- Rust plugins now shipped in macOS and Windows/MSVC binary packages -- H.264/H.265 timestamp correction elements for PTS/DTS reconstruction - before muxers -- Improved design for DMA buffer sharing and modifier handling for - hardware-accelerated video decoders/encoders/filters and - capturing/rendering on Linux -- Video4Linux2 hardware accelerated decoder improvements -- CUDA integration and Direct3D11 integration and plugin improvements -- New H.264 / AVC, H.265 / HEVC and AV1 hardware-accelerated video - encoders for AMD GPUs using the Advanced Media Framework (AMF) SDK -- applemedia: H.265 / HEVC video encoding + decoding support -- androidmedia: H.265 / HEVC video encoding support -- New “force-live” property for audiomixer, compositor, glvideomixer, - d3d11compositor etc. -- Lots of new plugins, features, performance improvements and bug - fixes - -Major new features and changes - -AV1 video codec support improvements - -AV1 is a royalty free next-generation video codec by AOMedia and a free -alternative to H.265/HEVC. - -While supported in earlier versions of GStreamer already, this release -saw a lot of improvements across the board: - -- Support for hardware encoding and decoding via VAAPI/VA, AMF, D3D11, - NVCODEC, QSV and Intel MediaSDK. Hardware codecs for AV1 are slowly - becoming available in embedded systems and desktop GPUs (AMD, Intel, - NVIDIA), and these can now be used via GStreamer. - -- New AV1 RTP payloader and depayloader elements. - -- New encoder settings in the AOM reference encoder-based av1enc - element. - -- Various improvements in the AV1 parser and in the MP4/Matroska/WebM - muxers/demuxers. - -- dav1d and rav1e based software decoder/encoder elements shipped as - part of the binaries. - -- AV1 parser improvements and various bugfixes all over the place. - -Touchscreen event support in Navigation API - -The Navigation API supports the sending of key press events and mouse -events through a GStreamer pipeline. Typically these will be picked up -by a video sink on which these events happen and then the event is -transmitted into the pipeline so it can be handled by elements inside -the pipeline if it wasn’t handled by the application. - -This has traditionally been used for DVD menu support, but can also be -used to forward such inputs to source elements that render a web page -using a browser engine such as WebKit or Chromium. - -This API has now gained support for touchscreen events, and this has -been implemented in various plugins such as the GTK, Qt, XV, and x11 -video sinks as well as the wpevideosrc element. - -GStreamer CUDA integration - -- New gst-cuda library -- integration with D3D11 and NVIDIA dGPU NVMM elements -- new cudaconvertscale element - -GStreamer Direct3D11 integration - -- New gst-d3d11 public library - - gst-d3d11 library is not integrated with GStreamer documentation - system yet. Please refer to the examples -- d3d11screencapture: Add Windows Graphics Capture API based capture - mode, including Win32 application window capturing -- d3d11videosink and d3d11convert can support flip/rotation and crop - meta -- d3d11videosink: New emit-present property and present signal so that - applications can overlay an image on Direct3D11 swapchain’s - backbuffer via Direct3D/Direct2D APIs. See also C++ and Rust - examples -- d3d11compositor supports YUV blending/composing without intermediate - RGB(A) conversion to improve performance -- Direct3D11 video decoders are promoted to GST_RANK_PRIMARY or - higher, except for the MPEG2 decoder - -H.264/H.265 timestamp correction elements - -- Muxers are often picky and need proper PTS/DTS timestamps set on the - input buffers, but that can be a problem if the encoded input media - stream comes from a source that doesn’t provide proper signalling of - DTS, such as is often the case for RTP, RTSP and WebRTC streams or - Matroska container files. Theoretically parsers should be able to - fix this up, but it would probably require fairly invasive changes - in the parsers, so two new elements h264timestamper and - h265timestamper bridge the gap in the meantime and can reconstruct - missing PTS/DTS. - -Easy sender timestamp reconstruction for RTP and RTSP - -- it was always possible to reconstruct and retrieve the original RTP - sender timestamps in GStreamer, but required a fair bit of - understanding of the internal mechanisms and the right property - configuration and clock setup. - -- rtspsrc and rtpjitterbuffer gained a new - “add-reference-timestamp-meta” property that if set puts the - original absolute reconstructed sender timestamps on the output - buffers via a meta. This is particularly useful if the sender is - synced to an NTP clock or PTP clock. The original sender timestamps - are either based on the RTCP NTP times, NTP RTP header extensions - (RFC6051) or RFC7273-style clock signalling. - -Qt6 support - -- new qml6glsink element for Qt6 similar to the existing Qt5 element. - Matching source and overlay elements will hopefully follow in the - near future. - -OpenGL + Video library enhancements - -- Support for new video formats (NV12_4L4, NV12_16L32S, NV12_8L128, - NV12_10BE_8L128) and dmabuf import in more formats (Y410, Y212_LE, - Y212_BE, Y210, NV21, NV61) - -- Improved support for tiled formats with arbitrary tile dimensions, - as needed by certain hardware decoders/encoders - -- glvideomixer: New “crop-left,”crop-right, “crop-top” and - “crop-bottom” pad properties for cropping inputs - -- OpenGL support for gst_video_sample_convert(): - - - Used for video snapshotting and thumbnailing, to convert buffers - retrieved from appsinks or sink “last-sample” properties in - JPG/PNG thumbnails. - - This function can now take samples and buffers backed by GL - textures as input and will automatically plug a gldownload - element in that case. - -High bit-depth support (10, 12, 16 bits per component value) improvements - -- compositor can now handle any supported input format and also mix - high-bitdepth (10-16 bit) formats (naively) - -- videoflip has gained support for higher bit depth formats. - -- vp9enc, vp9dec now support 12-bit formats and also 10-bit 4:4:4 - -WebRTC - -- Allow insertion of bandwidth estimation elements e.g. for Google - Congestion Control (GCC) support - -- Initial support for sending or receiving simulcast streams - -- Support for asynchronous host resolution for STUN/TURN servers - -- GstWebRTCICE was split into base classes and implementation to make - it possible to plug custom ICE implementations - -- webrtcsink: batteries-included WebRTC sender (Rust) - -- whipsink: WebRTC HTTP ingest (WHIP) to a MediaServer (Rust) - -- whepsrc: WebRTC HTTP egress (WHEP) from a MediaServer (Rust) - -- Many other improvements and bug fixes - -New HLS, DASH and MSS adaptive streaming clients - -A new set of “adaptive demuxers” to support HLS, DASH and MSS adaptive -streaming protocols has been added. They provide improved performance, -new features and better stream compatibility compared to the previous -elements. These new elements require a “streams-aware” pipeline such as -playbin3, uridecodebin3 or urisourcebin. - -The previous elements’ design prevented implementing several use-cases -and fixing long-standing issues. The new elements were re-designed from -scratch to tackle those: - -- Scheduling Only 3 threads are present, regardless of the number of - streams selected. One in charge of downloading fragments and - manifests, one in charge of outputting parsed data downstream, and - one in charge of scheduling. This improves performance, resource - usage and latency. - -- Better download control The elements now directly control the - scheduling and download of manifests and fragments using libsoup - directly instead of depending on external elements for downloading. - -- Stream selection, only the selected streams are downloaded. This - improves bandwith usage. Switching stream is done in such a way to - ensure there are no gaps, meaning the new stream will be switched to - only once enough data for it has been downloaded. - -- Internal parsing, the downloaded streams are parsed internally. This - allows the element to fully respect the various specifications and - offer accurate buffering, seeking and playback. This is especially - important for HLS streams which require parsing for proper - positioning of streams. - -- Buffering and adaptive rate switching, the new elements handle - buffering internally which allows them to have a more accurate - visibility of which bandwith variant to switch to. - -Playbin3, Decodebin3, UriDecodebin3, Parsebin improvements - -The “new” playback elements introduced in 1.18 (playbin3 and its various -components) have been refactored to allow more use-cases and improve -performance. They are no longer considered experimental, so applications -using the legacy playback elements (playbin and (uri)decodebin) can -migrate to the new components to benefit from these improvements. - -- Gapless The “gapless” feature allows files and streams to be - fetched, buffered and decoded in order to provide a “gapless” - output. This feature has been refactored extensively in the new - components: - - A single (uri)decodebin3 (and therefore a single set of - decoders) is used. This improves memory and cpu usage, since on - identical codecs a single decoder will be used. - - The “next” stream to play will be pre-rolled “just-in-time” - thanks to the buffering improvements in urisourcebin (see below) - - This feature is now handled at the uridecodebin3 level. - Applications that wish to have a “gapless” stream and process it - (instead of just outputting it, for example for transcoding, - retransmission, …) can now use uridecodebin3 directly. Note that - a streamsynchronizer element is required in that case. -- Buffering improvements The urisourcebin element is in charge of - fetching and (optionally) buffering/downloading the stream. It has - been extended and improved: - - When the parse-streams property is used (by default in - uridecodebin3 and playbin3), compatible streams will be demuxed - and parsed (via parsebin) and buffering will be done on the - elementary streams. This provides a more accurate handling of - buffering. Previously buffering was done on a best-effort basis - and was mostly wrong (i.e. downloading more than needed). - - Applications can use urisourcebin with this property as a - convenient way of getting elementary streams from a given URI. - - Elements can handle buffering themselves (such as the new - adaptive demuxers) by answering the GST_QUERY_BUFFERING query. - In that case urisourcebin will not handle it. -- Stream Selection Efficient stream selection was previously only - possible within decodebin3. The downside is that this meant that - upstream elements had to provide all the streams from which to chose - from, which is inefficient. With the addition of the - GST_QUERY_SELECTABLE query, this can now be handled by elements - upstream (i.e. sources) - - Elements that can handle stream selection internally (such as - the new adaptive demuxer elements) answer that query, and handle - the stream selection events themselves. - - In this case, decodebin3 will always process all streams that - are provided to it. -- Instant URI switching This new feature allows switching URIs - “instantly” in playbin3 (and uridecodebin3) without having to change - states. This mimics switching channels on a television. - - If compatible, decoders will be re-used, providing lower - latency/cpu/memory than by switching states. - - This is enabled by setting the instant-uri property to true, - setting the URI to switch to immediately, and then disabling the - instant-uri property again afterwards. -- playbin3, decodebin3, uridecodebin3, parsebin, and urisrc are no - longer experimental - - They were originally marked as ‘technology preview’ but have - since seen extensive usage in production settings, so are - considered ready for general use now. - -Fraunhofer AAC audio encoder HE-AAC and AAC-LD profile support - -- fdkaacenc: - - Support for encoding to HE-AACv1 and HE-AACv2 profile - - Support for encoding to AAC Low Delay (LD) profile - - Advanced bitrate control options via new “rate-control”, - “vbr-preset”, “peak-bitrate”, and “afterburner” properties - -RTP rapid synchronization support in the RTP stack (RFC6051) - -RTP provides several mechanisms how streams can be synchronized relative -to each other, and how absolute sender times for RTP packets can be -obtained. One of these mechanisms is via RTCP, which has the -disadvantage that the synchronization information is only distributed -out-of-band and usually some time after the start. - -GStreamer’s RTP stack, specifically the rtpbin, rtpsession and -rtpjitterbuffer elements, now also have support for retrieving and -sending the same synchronization information in-band via RTP header -extensions according to RFC6051 (Rapid Synchronisation of RTP Flows). -Only 64-bit timestamps are supported currently. - -This provides per packet synchronization information from the very -beginning of a stream and allows accurate inter-stream, and (depending -on setup) inter-device, synchronization at the receiver side. - -ONVIF XML Timed Metadata support - -The ONVIF standard implemented by various security cameras also -specifies a format for timed metadata that is transmitted together with -the audio/video streams, usually over RTSP. - -Support for this timed metadata is implemented in the MP4 demuxer now as -well as the new fragmented MP4 muxer and the new non-fragmented MP4 -muxer from the GStreamer Rust plugins. Additionally, the new onvif -plugin ‒ which is part of the GStreamer Rust plugins ‒ provides general -elements for handling the metadata and e.g. overlaying certain parts of -it over a video stream. - -As part of this support for absolute UTC times was also implemented -according to the requirements of the ONVIF standards in the -corresponding elements. - -MP3 gapless playback support - -While MP3 can probably considered a legacy format at this point, a new -feature was added with this release. - -When playing back plain MP3 files, i.e. outside a container format, -switches between files can now be completely gapless if the required -metadata is provided inside the file. There is no standardized metadata -for this, but the LAME MP3 encoder writes metadata that can be parsed by -the mpegaudioparse element now and forwarded to decoders for ensuring -removal of padding samples at the front and end of MP3 files. - -“force-live” property for audio + video aggregators - -This is a quality of life fix for playout and streaming applications -where it is common to have audio and video mixer elements that should -operate in live mode from the start and produce output continuously. - -Often one would start a pipeline without any inputs hooked up to these -mixers in the beginning, and up until now there was no way to easily -force these elements into live mode from the start. One would have to -add an initial live video or audio test source as dummy input to achieve -this. - -The new “force-live” property makes these audio and video aggregators -start in live mode without the need for any dummy inputs, which is -useful for scenarios where inputs are only added after starting the -pipeline. - -This new property should usually be used in connection with the -“min-upstream-latency” property, i.e. you should always set a non-0 -minimum upstream latency then. - -This is now supported in all GstAudioAggregator and GstVideoAggregator -subclasses such as audiomixer, audiointerleave, compositor, -glvideomixer, d3d11compositor, etc. - -New elements and plugins - -- new cudaconvertscale element that can convert and scale in one pass - -- new gtkwaylandsink element based on gtksink, but similar to - waylandsink and uses Wayland APIs directly instead of rendering with - Gtk/Cairo primitives. This approach is only compatible with Gtk3, - and like gtksink this element only supports Gtk3. - -- new h264timestamper and h265timestamper elements to reconstruct - missing pts/dts from inputs that might not provide them such as - e.g. RTP/RTSP/WebRTC inputs (see above) - -- mfaacdec, mfmp3dec: Windows MediaFoundation AAC and MP3 decoders - -- new msdkav1enc AV1 video encoder element - -- new nvcudah264enc, nvcudah265enc, nvd3d11h264enc, and nvd3d11h265enc - NVIDIA GPU encoder elements to support zero-copy encoding, via CUDA - and Direct3D11 APIs, respectively - -- new nvautogpuh264enc and nvautogpuh265enc NVIDIA GPU encoder - elements: The auto GPU elements will automatically select a target - GPU instance in case multiple NVIDIA desktop GPUs are present, also - taking into account the input memory. On Windows CUDA or Direct3D11 - mode will be determined by the elements automatically as well. Those - new elements are useful if target GPU and/or API mode (either CUDA - or Direct3D11 in case of Windows) is undeterminable from the encoder - point of view at the time when pipeline is configured, and therefore - lazy target GPU and/or API selection are required in order to avoid - unnecessary memory copy operations. - -- new nvav1dec AV1 NVIDIA desktop GPU decoder element - -- new qml6glsink element to render video with Qt6 - -- qsv: New Intel OneVPL/MediaSDK (a.k.a Intel Quick Sync) based - decoder and encoder elements, with gst-d3d11 (on Windows) and gst-va - (on Linux) integration - - - Support multi-GPU environment, for example, concurrent video - encoding using Intel iGPU and dGPU in a single pipeline - - H.264 / H.265 / VP9 and JPEG decoders - - H.264 / H.265 / VP9 / AV1 / JPEG encoders with dynamic encoding - bitrate update - - New plugin does not require external SDK for building on Windows - -- vulkanoverlaycompositor: new vulkan overlay compositor element to - overlay upstream GstVideoOverlayCompositonMeta onto the video - stream. - -- vulkanshaderspv: performs operations with SPIRV shaders in Vulkan - -- win32ipcvideosink, win32ipcvideosrc: new shared memory videosrc/sink - elements for Windows - -- wicjpegdec, wicpngdec: Windows Imaging Component (WIC) based JPEG - and PNG decoder elements. - -- Many exciting new Rust elements, see Rust section below - -New element features and additions - -- audioconvert: Dithering now uses a slightly slower, less biased PRNG - which results in better quality output. Also dithering can now be - enabled via the new “dithering-threshold” property for target bit - depths of more than 20 bits. - -- av1enc: Add “keyframe-max-dist” property for controlling max - distance between keyframes, as well as “enc-pass”, “keyframe-mode”, - “lag-in-frames” and “usage-profile” properties. - -- cccombiner: new “output-padding” property - -- decklink: Add support for 4k DCI, 8k/UHD2 and 8k DCI modes - -- dvbsubenc: Support for >SD resolutions is working correctly now. - -- fdkaacenc: Add HE-AAC / HE-AACv2 profile support - -- glvideomixer: New “crop-left,”crop-right, “crop-top” and - “crop-bottom” pad properties for cropping inputs - -- gssink: new ‘content-type’ property. Useful when one wants to upload - a video as video/mp4 instead of ’video/quicktime` for example. - -- jpegparse: Rewritten using the common parser library - -- msdk: - - - new msdkav1enc AV1 video encoder element - - msdk decoders: Add support for Scaler Format Converter (SFC) on - supported Intel platforms for hardware accelerated conversion - and scaling - - msdk encoders: support import of dmabuf, va memory and D3D11 - memory - - msdk encoders: add properties for low delay bitrate control and - max frame sizes for I/P frames - - msdkh264enc, msdkh265enc: more properties to control intra - refresh - - note that on systems with multi GPUs the Windows D3D11 - integration might only work reliably if the Intel GPU is the - primary GPU - -- mxfdemux: Add support for Canon XF-HEVC - -- openaptx: Support the freeaptx library - -- qroverlay: - - - new “qrcode-case-sensitive” property allows encoding case - sensitive strings like wifi SSIDs or passwords. - - added the ability to pick up data to render from an - upstream-provided custom GstQROverlay meta - -- qtdemux: Add support for ONVIF XML Timed MetaData and AVC-Intra - video - -- rfbsrc now supports the uri handler interface, so applications can - use RFB/VNC sources in uridecodebin(3) and playbin, with - e.g. rfb://:password@10.1.2.3:5903?shared=1 - -- rtponviftimestamp: Add support for using reference timestamps - -- rtpvp9depay now has the same keyframe-related properties as - rtpvp8depay and rtph264depay: “request-keyframe” and - “wait-for-keyframe” - -- rtspsrc: Various RTSP servers are using invalid URL operations for - constructing the control URL. Until GStreamer 1.16 these worked - correctly because GStreamer was just appending strings itself to - construct the control URL, but starting version 1.18 the correct URL - operations were used. With GStreamer 1.22, rtspsrc now first tries - with the correct control URL and if that fails it will retry with - the wrongly constructed control URL to restore support for such - servers. - -- rtspsrc and rtpjitterbuffer gained a new - “add-reference-timestamp-meta” property that makes them put the - unmodified original sender timestamp on output buffers for NTP or - PTP clock synced senders - -- srtsrc, srtsink: new “auto-reconnect” property to make it possible - to disable automatic reconnects (in caller mode) and make the - elements post an error immediately instead; also stats improvements - -- srtsrc: new “keep-listening” property to avoid EOS on disconnect and - keep the source running while it waits for a new connection. - -- videocodectestsink: added YUV 4:2:2 support - -- wasapi2src: Add support for process loopback capture - -- wpesrc: Add support for modifiers in key/touch/pointer events - -Plugin and library moves - -- The xingmux plugin has been moved from gst-plugins-ugly into - gst-plugins-good. - -- The various Windows directshow plugins in gst-plugins-bad have been - unified into a single directshow plugin. - -Plugin removals - -- The dxgiscreencapsrc element has been removed, use - d3d11screencapturesrc instead - -Miscellaneous API additions - -- GST_AUDIO_FORMAT_INFO_IS_VALID_RAW() and - GST_VIDEO_FORMAT_INFO_IS_VALID_RAW() can be used to check if a - GstAudioFormatInfo or GstVideoFormatInfo has been initialised to a - valid raw format. - -- Video SEI meta: new GstVideoSEIUserDataUnregisteredMeta to carry - H.264 and H.265 metadata from SEI User Data Unregistered messages. - -- vulkan: Expose gst_vulkan_result_to_string() - -Miscellaneous performance, latency and memory optimisations - -- liborc 0.4.33 adds support for aarch64 (64-bit ARM) architecture - (not enabled by default on Windows yet though) and improvements for - 32-bit ARM and should greatly enhance performance for certain - operations that use ORC. - -- as always there have been plenty of performance, latency and memory - optimisations all over the place. - -Miscellaneous other changes and enhancements - -- the audio/video decoder base classes will not consider decoding - errors a hard error by default anymore but will continue trying to - decode. Previously more than 10 consecutive errors were considered a - hard error but this caused various partially broken streams to fail. - The threshold is configurable via the “max-errors” property. - -- compatibility of the GStreamer PTP clock implementation with - different PTP server implementations was improved, and - synchronization is achieved successfully in various scenarios that - failed before. - -Tracing framework and debugging improvements - -New tracers - -- buffer-lateness: Records lateness of buffers and the reported - latency for each pad in a CSV file. Comes with a script for - visualisation. - -- pipeline-snapshot: Creates a .dot file of all pipelines in the - application whenever requested via SIGUSR1 (on UNIX systems) - -- queue-levels: Records queue levels for each queue in a CSV file. - Comes with a script for visualisation. - -Debug logging system improvements - -- new log macros GST_LOG_ID, GST_DEBUG_ID, GST_INFO_ID, - GST_WARNING_ID, GST_ERROR_ID, and GST_TRACE_ID allow passing a - string identifier instead of a GObject. This makes it easier to log - non-gobject-based items and also has performance benefits. - -Tools - -- gst-play-1.0 gained a --no-position command line option to suppress - position/duration queries, which can be useful to reduce debug log - noise. - -GStreamer FFMPEG wrapper - -- Fixed bitrate management and timestamp inaccuracies for video - encoders - -- Fix synchronization issues and errors created by the (wrong) - forwarding of upstream segment events by ffmpeg demuxers. - -- Clipping meta support for gapless mp3 playback - -GStreamer RTSP server - -- Add RFC5576 Source-specific media attribute to the SDP media for - signalling the CNAME - -- Add support for adjusting request response on pipeline errors - - - Give the application the possibility to adjust the error code - when responding to a request. For that purpose the pipeline’s - bus messages are emitted to subscribers through a - “handle-message” signal. The subscribers can then check those - messages for errors and adjust the response error code by - overriding the virtual method - GstRTSPClientClass::adjust_error_code(). - -- Add gst_rtsp_context_set_token() method to make it possible to set - the RTSPToken on some RTSPContext from bindings such as the Python - bindings. - -- rtspclientsink gained a “publish-clock-mode” property to configure - whether the pipeline clock should be published according to RFC7273 - (RTP Clock Source Signalling), similar to the same API on - GstRTSPMedia. - -GStreamer VA-API support - -- Development activity has shifted towards the new va plugin, with - gstreamer-vaapi now basically in maintenance-only mode. Most of the - below refers to the va plugin (not gstreamer-vaapi). - -- new gst-va library for GStreamer VA-API integration - -- vajpegdec: new JPEG decoder - -- vah264enc, vah265enc: new H.264/H.265 encoders - -- vah264lpenc, vah265lpenc: new low power mode encoders - -- vah265enc: Add extended formats support such as 10/12 bits, 4:2:2 - and 4:4:4 - -- Support encoder reconfiguration - -- vacompositor: Add new compositor element using the VA-API VPP - interface - -- vapostproc: - - - new “scale-method” property - - Process HDR caps if supported - - parse video orientation from tags - -- vaapipostproc: Enable the use of DMA-Buf import and export - (gstreamer-vaapi) - -GStreamer Video4Linux2 support - -- Added support for Mediatek Stateless CODEC (VP8, H.264, VP9) - -- Stateless H.264 interlaced decoder support - -- Stateless H.265 decoder support - -- Stateful decoder support for driver resolution change events - -- Stateful decoding support fixes for NXP/Amphion driver - -- Support for hardware crop in v4l2src - -- Conformance test improvement for stateful decoders - -- Fixes for Raspberry Pi CODEC - -GStreamer OMX - -- There were no changes in this module - -GStreamer Editing Services and NLE - -- Handle compositors that are bins around the actual compositor - implementation (like glvideomixers which wraps several elements) - -- Add a mode to disable timeline editing API so the user can be in - full control of its layout (meaning that the user is responsible for - ensuring its validity/coherency) - -- Add a new fade-in transition type - -- Add support for non-1/1 PAR source videos - -- Fix frame accuracy when working with very low framerate streams - -GStreamer validate - -- Clean up and stabilize API so we can now generate rust bindings - -- Enhance the appsrc-push action type allowing to find tune the - buffers more in details - -- Add an action type to verify currently configured pad caps - -- Add a way to run checks from any thread after executing a ‘wait’ - action. This is useful when waiting on a signal and want to check - the value of a property right when it is emited for example. - -GStreamer Python Bindings - -- Add a Gst.init_python() function to be called from plugins which - will initialise everything needed for the GStreamer Python bindings - but not call Gst.init() again since this will have been called - already. - -- Add support for the GstURIHandlerInterface that allows elements to - advertise what URI protocols they support. - -GStreamer C# Bindings - -- Fix AppSrc and AppSink constructors - -- The C# bindings have yet to be updated to include new 1.22 API, - which requires improvements in various places in the bindings / - binding generator stack. See issue #1718 in GitLab for more - information and to track progress. - -GStreamer Rust Bindings and Rust Plugins - -The GStreamer Rust bindings are released separately with a different -release cadence that’s tied to gtk-rs, but the latest release has -already been updated for the new GStreamer 1.22 API. Check the bindings -release notes for details of the changes since 0.18, which was released -around GStreamer 1.20. - -gst-plugins-rs, the module containing GStreamer plugins written in Rust, -has also seen lots of activity with many new elements and plugins. A -list of all Rust plugins and elements provided with the 0.9 release can -be found in the repository. - -- 33% of GStreamer commits are now in Rust (bindings + plugins), and - the Rust plugins module is also where most of the new plugins are - added these days. - -- The Rust plugins are now shipped as part of the Windows MSVC + macOS - binary packages. See below for the list of shipped plugins and the - status of Rust support in cerbero. - -- The Rust plugins are also part of the documentation on the GStreamer - website now. - -- Rust plugins can be used from any programming language. To the - outside they look just like a plugin written in C or C++. - -New Rust plugins and elements - -- rtpav1pay / rtpav1depay: RTP (de)payloader for the AV1 video codec -- gtk4paintablesink: a GTK4 video sink that provides a GdkPaintable - for rendering a video in any place inside a GTK UI. Supports - zero-copy rendering via OpenGL on Linux and macOS. -- ndi: source, sink and device provider for NewTek NDI protocol -- onvif: Various elements for parsing, RTP (de)payloading, overlaying - of ONVIF timed metadata. -- livesync: Element for converting a live stream into a continuous - stream without gaps and timestamp jumps while preserving live - latency requirements. -- raptorq: Encoder/decoder elements for the RaptorQ FEC mechanism that - can be used for RTP streams (RFC6330). - -WebRTC elements - -- webrtcsink: a WebRTC sink (batteries included WebRTC sender with - specific signalling) -- whipsink: WebRTC HTTP ingest (WHIP) to MediaServer -- whepsrc: WebRTC HTTP egress (WHEP) from MediaServer -- rtpgccbwe: RTP bandwidth estimator based on the Google Congestion - Control algorithm (GCC), used by webrtcsink - -Amazon AWS services - -- awss3src / awss3sink: A source and sink element to talk to the - Amazon S3 object storage system. -- awss3hlssink: A sink element to store HLS streams on Amazon S3. -- awstranscriber: an element wrapping the AWS Transcriber service. -- awstranscribeparse: an element parsing the packets of the AWS - Transcriber service. - -Video Effects (videofx) - -- roundedcorners: Element to make the corners of a video rounded via - the alpha channel. -- colordetect: A pass-through filter able to detect the dominant - color(s) on incoming frames, using color-thief. -- videocompare: Compare similarity of video frames. The element can - use different hashing algorithms like Blockhash, DSSIM, and others. - -New MP4 muxer + Fragmented MP4 muxer - -- fmp4mux: New fragmented MP4/ISOBMFF/CMAF muxer for generating - e.g. DASH/HLS media fragments. -- isomp4mux: New non-fragmented, normal MP4 muxer. - -Both plugins provides elements that replace the existing qtmux/mp4mux -element from gst-plugins-good. While not feature-equivalent yet, the new -codebase and using separate elements for the fragment and non-fragmented -case allows for easier extensability in the future. - -Cerbero Rust support - -- Starting this release, cerbero has support for building and shipping - Rust code on Linux, Windows (MSVC) and macOS. The Windows (MSVC) and - macOS binaries also ship the GStreamer Rust plugins in this release. - Only dynamic plugins are built and shipped currently. - -- Preliminary support for Android, iOS and Windows (MinGW) exists but - more work is needed. Check the tracker issue for more details about - future work. - -- The following plugins are included currently: audiofx, aws, cdg, - claxon, closedcaption, dav1d, fallbackswitch, ffv1, fmp4, gif, - hlssink3, hsv, json, livesync, lewton, mp4, ndi, onvif, rav1e, - regex, reqwest, raptorq, png, rtp, textahead, textwrap, threadshare, - togglerecord, tracers, uriplaylistbin, videofx, webrtc, webrtchttp. - -Build and Dependencies - -- meson 0.62 or newer is required - -- GLib >= 2.62 is now required (but GLib >= 2.64 is strongly - recommended) - -- libnice >= 0.1.21 is now required and contains important fixes for - GStreamer’s WebRTC stack. - -- liborc >= 0.4.33 is recommended for 64-bit ARM support and 32-bit - ARM improvements - -- onnx: OnnxRT >= 1.13.1 is now required - -- openaptx: can now be built against libfreeaptx - -- opencv: allow building against any 4.x version - -- shout: libshout >= 2.4.3 is now required - -- gstreamer-vaapi’s Meson build options have been switched from a - custom combo type (yes/no/auto) to the built-in Meson feature type - (enabled/disabled/auto) - -- The GStreamer Rust plugins module gst-plugins-rs is now considered - an essential part of the GStreamer plugin offering and packagers and - distributors are strongly encouraged to package and ship those - plugins alongside the existing plugin modules. - -- we now make use of Meson’s install tags feature which allows - selective installation of installl components and might be useful - for packagers. - -Monorepo build (gst-build) - -- new “orc-source” build option to allow build against a - system-installed liborc instead of forcing the use of orc as a - subproject. - -- GStreamer command line tools can now be linked to the gstreamer-full - library if it’s built - -Cerbero - -Cerbero is a meta build system used to build GStreamer plus dependencies -on platforms where dependencies are not readily available, such as -Windows, Android, iOS, and macOS. - -General improvements - -- Rust support was added for all support configurations, controlled by - the rust variant; see above for more details -- All pkgconfig files are now reliably relocatable without requiring - pkg-config --define-prefix. This also fixes statically linking with - GStreamer plugins using the corresponding pkgconfig files. -- New documentation on how to build a custom GStreamer repository - using Cerbero, please see the README -- HTTPS certificate checking is enabled for downloads on all platforms - now -- Fetching now automatically retries on error for robustness against - transient errors -- Support for building the new Qt6 plugin was added -- pkgconfig files for various recipes were fixed -- Several recipes were updated to newer versions -- New plugins: adaptivedemux2 aes codectimestamper dav1d -- New libraries: cuda webrtcnice - -macOS / iOS - -- Added support for running Cerbero on ARM64 macOS -- GStreamer.framework and all libraries in it are now relocatable, - which means they use LC_RPATH entries to find dependencies instead - of using an absolute path. If you link to GStreamer using the - pkgconfig files, no action is necessary. However, if you use the - framework directly or link to the libraries inside the framework by - hand, then you need to pass -Wl,-rpath, to the - linker. -- Apple bitcode support was dropped, since Apple has deprecated it -- macOS installer now correctly advertises support for both x86_64 and - arm64 -- macOS framework now ships the gst-rtsp-server-1.0 library -- Various fixes were made to make static linking to gstreamer - libraries and plugins work correctly on macOS -- When statically linking to the applemedia plugin using Xcode 13, you - will need to pass -fno-objc-msgsend-selector-stubs which works - around a backwards-incompatible change in Xcode 14. This is not - required for the rest of GStreamer at present, but will be in the - future. -- macOS installer now shows the GStreamer logo correctly - -Windows - -- MSVC is now required by default on Windows, and the Visual Studio - variant is enabled by default - - To build with MinGW, use the mingw variant -- Visual Studio props files were updated for newer Visual Studio - versions -- Visual Studio 2015 support was dropped -- MSYS2 is now supported as the base instead of MSYS. Please see the - README for more details. Some advantages include: - - Faster build times, since parallel make works - - Faster bootstrap, since some tools are provided by MSYS2 - - Other speed-ups due to using MSYS2 tools instead of MSYS -- Faster download by using powershell instead of hand-rolled Python - code -- Many recipes were ported from Autotools to Meson, speeding up the - build -- Universal Windows Platform is no longer supported, and binaries are - no longer shipped for it -- New documentation on how to force a specific Visual Studio - installation in Cerbero, please see the README -- New plugins: qsv wavpack directshow amfcodec wic win32ipc -- New libraries: d3d11 - -Windows MSI installer - -- Universal Windows Platform prebuilt binaries are no longer available - -Linux - -- Various fixes for RHEL/CentOS 7 support -- Added support for running on Linux ARM64 - -Android - -- Android support now requires Android API version 21 (Lollipop) -- Support for Android Gradle plugin 7.2 - -Platform-specific changes and improvements - -Android - -- Android SDK 21 is required now as minimum SDK version - -- androidmedia: Add H.265 / HEVC video encoder mapping - -- Implement JNI_OnLoad() to register static plugins etc. automatically - in case GStreamer is loaded from Java using System.loadLibrary(), - which is also useful for the gst-full deployment scenario. - -Apple macOS and iOS - -- The GLib version shipped with the GStreamer binaries does not - initialize an NSApp and does not run a NSRunLoop on the main thread - anymore. This was a custom GLib patch and caused it to behave - different from the GLib shipped by Homebrew or anybody else. - - The change was originally introduced because various macOS APIs - require a NSRunLoop to run on the main thread to function correctly - but as this change will never get merged into GLib and it was - reverted for 1.22. Applications that relied on this behaviour should - move to the new gst_macos_main() function, which also does not - require the usage of a GMainLoop. - - See e.g. gst-play.c for an example for the usage of - gst_macos_main(). - -- GStreamer.framework and all libraries in it are now relocatable, - which means they use LC_RPATH entries to find dependencies instead - of using an absolute path. If you link to GStreamer using the - pkgconfig files, no action is necessary. However, if you use the - framework directly or link to the libraries inside the framework by - hand, then you need to pass -Wl,-rpath, to the - linker. - -- avfvideosrc: Allow specifying crop coordinates during screen capture - -- vtenc, vtdec: H.265 / HEVC video encoding + decoding support - -- osxaudiosrc: Support a device as both input and output - - - osxaudiodeviceprovider now probes devices more than once to - determine if the device can function as both an input AND and - output device. Previously, if the device provider detected that - a device had any output capabilities, it was treated solely as - an Audio/Sink. This caused issues for devices that have both - input and output capabilities (for example, USB interfaces for - professional audio have both input and output channels). Such - devicesare now listed as both an Audio/Sink as well as an - Audio/Source. - -- osxaudio: support hidden devices on macOS - - - These are devices that will not be shown in the macOS UIs and - that cannot be retrieved without having the specific UID of the - hidden device. There are cases when you might want to have a - hidden device, for example when having a virtual speaker that - forwards the data to a virtual hidden input device from which - you can then grab the audio. The blackhole project supports - these hidden devices and this change provides a way that if the - device id is a hidden device it will use it instead of checkinf - the hardware list of devices to understand if the device is - valid. - -Windows - -- win32ipcvideosink, win32ipcvideosrc: new shared memory videosrc/sink - elements - -- wasapi2: Add support for process loopback capture for a specified - PID (requires Windows 11/Windows Server 2022) - -- The Windows universal UWP build is currently non-functional and will - need updating after the recent GLib upgrade. It is unclear if anyone - is using these binaries, so if you are please make yourself known. - -- wicjpegdec, wicpngdec: Windows Imaging Component (WIC) based JPEG - and PNG decoder elements. - -- mfaacdec, mfmp3dec: Windows MediaFoundation AAC and MP3 decoders - -- The uninstalled development environment supports PowerShell 7 now - -Linux - -- Improved design for DMA buffer sharing and modifier handling for - hardware-accelerated video decoders/encoders/filters and - capture/rendering on Linux and Linux-like system. - -- kmssink - - - new “fd” property which allows an application to provide their - own opened DRM device fd handle to kmssink. That way an - application can lease multiple fd’s from a DRM master to display - on different CRTC outputs at the same time with multiple kmssink - instances, for example. - - new “skip-vsync” property to achieve full framerate with legacy - emulation in drivers. - - HDR10 infoframe support - -- va plugin and gstreamer-vaapi improvements (see above) - -- waylandsink: Add “rotate-method” property and “render-rectangle” - property - -- new gtkwaylandsink element based on gtksink, but similar to - waylandsink and uses Wayland APIs directly instead of rendering with - Gtk/Cairo primitives. This approach is only compatible with Gtk3, - and like gtksink this element only supports Gtk3. - -Documentation improvements - -- The GStreamer Rust plugins are now included and documented in the - plugin documentation. - -Possibly Breaking Changes - -- the Opus audio RTP payloader and depayloader no longer accept the - lower case encoding-format=multiopus but instead produce and accept - only the upper case variant encoding-format=MULTIOPUS, since those - should always be upper case in GStreamer (caps fields are always - case sensitive). This should hopefully only affect applications - where RTP caps are set manually and multi-channel audio (>= 3 - channels) is used. - -- wpesrc: the URI handler protocols changed from wpe:// and web:// to - web+http://, web+https://, and web+file:// which means URIs are RFC - 3986 compliant and the source can simply strip the prefix from the - protocol. - -- The Windows screen capture element dxgiscreencapsrc has been - removed, please use d3d11screencapturesrc instead. - -- On Android the minimum supported Android API version is now version - 21 and has been increased from 16. - -- On macOS, the GLib version shipped with the GStreamer binaries will - no longer initialize an NSApp or run an NSRunLoop on the main - thread. See macOS/iOS section above for details. - -- decklink: The decklink plugin is now using the 12.2.2 version of the - SDK and will not work with drivers older than version 12. - -- On iOS Apple Bitcode support was removed from the binaries. This - feature is deprecated since XCode 14 and not used on the App Store - anymore. - -- The MP4/Matroska/WebM muxers now require the “stream-format” to be - provided as part of the AV1 caps as only the original “obu-stream” - format is supported in these containers and not the “annexb” format. - -Known Issues - -- The Windows UWP build in Cerbero needs fixing after the recent GLib - upgrade (see above) - -- The C# bindings have not been updated to include new 1.22 API yet - (see above) - -Statistics - -- 4072 commits - -- 2224 Merge Requests - -- 716 Issues - -- 200+ Contributors - -- ~33% of all commits and Merge Requests were in Rust modules - -- 4747 files changed - -- 469633 lines added - -- 209842 lines deleted - -- 259791 lines added (net) - -Contributors - -Ádám Balázs, Adam Doupe, Adrian Fiergolski, Adrian Perez de Castro, Alba -Mendez, Aleix Conchillo Flaqué, Aleksandr Slobodeniuk, Alicia Boya -García, Alireza Miryazdi, Andoni Morales Alastruey, Andrew Pritchard, -Arun Raghavan, A. Wilcox, Bastian Krause, Bastien Nocera, Benjamin -Gaignard, Bill Hofmann, Bo Elmgreen, Boyuan Zhang, Brad Hards, Branko -Subasic, Bruce Liang, Bunio FH, byran77, Camilo Celis Guzman, Carlos -Falgueras García, Carlos Rafael Giani, Célestin Marot, Christian Wick, -Christopher Obbard, Christoph Reiter, Chris Wiggins, Chun-wei Fan, Colin -Kinloch, Corentin Damman, Corentin Noël, Damian Hobson-Garcia, Daniel -Almeida, Daniel Morin, Daniel Stone, Daniels Umanovskis, Danny Smith, -David Svensson Fors, Devin Anderson, Diogo Goncalves, Dmitry Osipenko, -Dongil Park, Doug Nazar, Edward Hervey, ekwange, Eli Schwartz, Elliot -Chen, Enrique Ocaña González, Eric Knapp, Erwann Gouesbet, Evgeny -Pavlov, Fabian Orccon, Fabrice Fontaine, Fan F He, F. Duncanh, Filip -Hanes, Florian Zwoch, François Laignel, Fuga Kato, George Kiagiadakis, -Guillaume Desmottes, Gu Yanjie, Haihao Xiang, Haihua Hu, Havard Graff, -Heiko Becker, He Junyan, Henry Hoegelow, Hiero32, Hoonhee Lee, Hosang -Lee, Hou Qi, Hugo Svirak, Ignacio Casal Quinteiro, Ignazio Pillai, Igor -V. Kovalenko, Jacek Skiba, Jakub Adam, James Cowgill, James Hilliard, -Jan Alexander Steffens (heftig), Jan Lorenz, Jan Schmidt, Jianhui Dai, -jinsl00000, Johan Sternerup, Jonas Bonn, Jonas Danielsson, Jordan -Petridis, Joseph Donofry, Jose Quaresma, Julian Bouzas, Junsoo Park, -Justin Chadwell, Khem Raj, Krystian Wojtas, László Károlyi, Linus -Svensson, Loïc Le Page, Ludvig Rappe, Marc Leeman, Marek Olejnik, Marek -Vasut, Marijn Suijten, Mark Nauwelaerts, Martin Dørum, Martin Reboredo, -Mart Raudsepp, Mathieu Duponchelle, Matt Crane, Matthew Waters, Matthias -Clasen, Matthias Fuchs, Mengkejiergeli Ba, MGlolenstine, Michael Gruner, -Michiel Konstapel, Mikhail Fludkov, Ming Qian, Mingyang Ma, Myles -Inglis, Nicolas Dufresne, Nirbheek Chauhan, Olivier Crête, Pablo Marcos -Oltra, Patricia Muscalu, Patrick Griffis, Paweł Stawicki, Peter -Stensson, Philippe Normand, Philipp Zabel, Pierre Bourré, Piotr -Brzeziński, Rabindra Harlalka, Rafael Caricio, Rafael Sobral, Rafał -Dzięgiel, Raul Tambre, Robert Mader, Robert Rosengren, Rodrigo -Bernardes, Rouven Czerwinski, Ruben Gonzalez, Sam Van Den Berge, -Sanchayan Maity, Sangchul Lee, Sebastian Dröge, Sebastian Fricke, -Sebastian Groß, Sebastian Mueller, Sebastian Wick, Sergei Kovalev, -Seungha Yang, Seungmin Kim, sezanzeb, Sherrill Lin, Shingo Kitagawa, -Stéphane Cerveau, Talha Khan, Taruntej Kanakamalla, Thibault Saunier, -Tim Mooney, Tim-Philipp Müller, Tomasz Andrzejak, Tom Schuring, Tong Wu, -toor, Tristan Matthews, Tulio Beloqui, U. Artie Eoff, Víctor Manuel -Jáquez Leal, Vincent Cheah Beng Keat, Vivia Nikolaidou, Vivienne -Watermeier, WANG Xuerui, Wojciech Kapsa, Wonchul Lee, Wu Tong, Xabier -Rodriguez Calvar, Xavier Claessens, Yatin Mann, Yeongjin Jeong, Zebediah -Figura, Zhao Zhili, Zhiyuaniu, مهدي شينون (Mehdi Chinoune), - -… and many others who have contributed bug reports, translations, sent -suggestions or helped testing. - -Stable 1.22 branch - -After the 1.22.0 release there will be several 1.22.x bug-fix releases -which will contain bug fixes which have been deemed suitable for a -stable branch, but no new features or intrusive changes will be added to -a bug-fix release usually. The 1.22.x bug-fix releases will be made from -the git 1.22 branch, which will be a stable branch. - -1.22.0 - -1.22.0 was originally released on 23 January 2023. - -Schedule for 1.24 - -Our next major feature release will be 1.24, and 1.23 will be the -unstable development version leading up to the stable 1.24 release. The -development of 1.23/1.24 will happen in the git main branch of the -GStreamer mono repository. - -The plan for the 1.24 development cycle is yet to be confirmed. - -1.24 will be backwards-compatible to the stable 1.22, 1.20, 1.18, 1.16, -1.14, 1.12, 1.10, 1.8, 1.6, 1.4, 1.2 and 1.0 release series. - ------------------------------------------------------------------------- - -These release notes have been prepared by Tim-Philipp Müller with -contributions from Edward Hervey, Matthew Waters, Nicolas Dufresne, -Nirbheek Chauhan, Olivier Crête, Sebastian Dröge, Seungha Yang, and -Thibault Saunier. - -License: CC BY-SA 4.0 diff --git a/subprojects/gst-omx/README b/subprojects/gst-omx/README deleted file mode 100644 index 6e94c384c2..0000000000 --- a/subprojects/gst-omx/README +++ /dev/null @@ -1,17 +0,0 @@ -GStreamer OpenMAX IL wrapper plugin --------------------------- - - This plugin wraps available OpenMAX IL components and makes - them available as standard GStreamer elements. - -License: --------- - - This package and its contents are licensend under the GNU Lesser General -Public License (LGPL). - -Dependencies: -------------- - - * GStreamer core - * gst-plugins-base diff --git a/subprojects/gst-omx/RELEASE b/subprojects/gst-omx/RELEASE deleted file mode 100644 index 70a8db0777..0000000000 --- a/subprojects/gst-omx/RELEASE +++ /dev/null @@ -1,104 +0,0 @@ -This is GStreamer gst-omx 1.22.0. - -The GStreamer team is thrilled to announce a new major feature release -of your favourite cross-platform multimedia framework! - -As always, this release is again packed with new features, bug fixes and -other improvements. - -The 1.22 release series adds new features on top of the 1.20 series and is -part of the API and ABI-stable 1.x release series. - -Full release notes can be found at: - - https://gstreamer.freedesktop.org/releases/1.22/ - -Binaries for Android, iOS, Mac OS X and Windows will usually be provided -shortly after the release. - -This module will not be very useful by itself and should be used in conjunction -with other GStreamer modules for a complete multimedia experience. - - - gstreamer: provides the core GStreamer libraries and some generic plugins - - - gst-plugins-base: a basic set of well-supported plugins and additional - media-specific GStreamer helper libraries for audio, - video, rtsp, rtp, tags, OpenGL, etc. - - - gst-plugins-good: a set of well-supported plugins under our preferred - license - - - gst-plugins-ugly: a set of well-supported plugins which might pose - problems for distributors - - - gst-plugins-bad: a set of plugins of varying quality that have not made - their way into one of core/base/good/ugly yet, for one - reason or another. Many of these are are production quality - elements, but may still be missing documentation or unit - tests; others haven't passed the rigorous quality testing - we expect yet. - - - gst-libav: a set of codecs plugins based on the ffmpeg library. This is - where you can find audio and video decoders and encoders - for a wide variety of formats including H.264, AAC, etc. - - - gstreamer-vaapi: hardware-accelerated video decoding and encoding using - VA-API on Linux. Primarily for Intel graphics hardware. - - - gst-omx: hardware-accelerated video decoding and encoding, primarily for - embedded Linux systems that provide an OpenMax - implementation layer such as the Raspberry Pi. - - - gst-rtsp-server: library to serve files or streaming pipelines via RTSP - - - gst-editing-services: library an plugins for non-linear editing - - - gst-plugins-rs: an exciting collection of well-maintained plugins written - in the Rust programming language (usable from any language) - -==== Download ==== - -You can find source releases of gstreamer in the download -directory: https://gstreamer.freedesktop.org/src/gstreamer/ - -The git repository and details how to clone it can be found at -https://gitlab.freedesktop.org/gstreamer/gstreamer/ - -==== Homepage ==== - -The project's website is https://gstreamer.freedesktop.org/ - -==== Support and Bugs ==== - -We track bugs and feature requests in GitLab: - - https://gitlab.freedesktop.org/gstreamer/gstreamer/ - -Please submit patches via GitLab as well, in form of Merge Requests. See - - https://gstreamer.freedesktop.org/documentation/contribute/ - -for more details. - -For help and support, please subscribe to and send questions to the -gstreamer-devel mailing list (see below for details). - -There is also a #gstreamer IRC channel on the OFTC IRC network, which is -also bridged into the Matrix network. - -Please do not submit support requests in GitLab, we only use it -for bug tracking and merge requests review. - -==== Developers ==== - -The GStreamer source code repository can be found on GitLab on freedesktop.org: - - https://gitlab.freedesktop.org/gstreamer/gstreamer/ - -and can also be cloned from there and this is also where you can submit -Merge Requests or file issues for bugs or feature requests. - -Interested developers of the core library, plugins, and applications should -subscribe to the gstreamer-devel list: - - https://lists.freedesktop.org/mailman/listinfo/gstreamer-devel diff --git a/subprojects/gst-omx/config/bellagio/gstomx.conf b/subprojects/gst-omx/config/bellagio/gstomx.conf deleted file mode 100644 index 0e856bea86..0000000000 --- a/subprojects/gst-omx/config/bellagio/gstomx.conf +++ /dev/null @@ -1,60 +0,0 @@ -[omxmpeg4videodec] -type-name=GstOMXMPEG4VideoDec -core-name=/usr/local/lib/libomxil-bellagio.so.0 -component-name=OMX.st.video_decoder.mpeg4 -rank=257 -in-port-index=0 -out-port-index=1 -hacks=event-port-settings-changed-ndata-parameter-swap;event-port-settings-changed-port-0-to-1 - -[omxh264dec] -type-name=GstOMXH264Dec -core-name=/usr/local/lib/libomxil-bellagio.so.0 -component-name=OMX.st.video_decoder.avc -rank=257 -in-port-index=0 -out-port-index=1 -hacks=event-port-settings-changed-ndata-parameter-swap;event-port-settings-changed-port-0-to-1 - -[omxmpeg4videoenc] -type-name=GstOMXMPEG4VideoEnc -core-name=/usr/local/lib/libomxil-bellagio.so.0 -component-name=OMX.st.video_encoder.mpeg4 -rank=0 -in-port-index=0 -out-port-index=1 -hacks=event-port-settings-changed-ndata-parameter-swap;video-framerate-integer;syncframe-flag-not-used - -[omxaacenc] -type-name=GstOMXAACEnc -core-name=/usr/local/lib/libomxil-bellagio.so.0 -component-name=OMX.st.audio_encoder.aac -rank=0 -in-port-index=0 -out-port-index=1 -hacks=event-port-settings-changed-ndata-parameter-swap - -[omxmp3dec] -type-name=GstOMXMP3Dec -core-name=/usr/lib/libomxil-bellagio.so.0 -component-name=OMX.st.audio_decoder.mp3.mad -rank=0 -in-port-index=0 -out-port-index=1 -hacks=event-port-settings-changed-ndata-parameter-swap;no-component-role;no-disable-outport;drain-may-not-return - -[omxh264dec] -type-name=GstOMXH264Dec -core-name=/usr/lib/libomxil-bellagio.so.0 -component-name=OMX.mesa.video_decoder.avc -rank=0 -in-port-index=0 -out-port-index=1 - -[omxmpeg2dec] -type-name=GstOMXMPEG2VideoDec -core-name=/usr/lib/libomxil-bellagio.so.0 -component-name=OMX.mesa.video_decoder.mpeg2 -rank=0 -in-port-index=0 -out-port-index=1 diff --git a/subprojects/gst-omx/config/bellagio/meson.build b/subprojects/gst-omx/config/bellagio/meson.build deleted file mode 100644 index dc99c08bc1..0000000000 --- a/subprojects/gst-omx/config/bellagio/meson.build +++ /dev/null @@ -1 +0,0 @@ -install_data (['gstomx.conf'], install_dir : omx_conf_dir) diff --git a/subprojects/gst-omx/config/meson.build b/subprojects/gst-omx/config/meson.build deleted file mode 100644 index 94be8a669d..0000000000 --- a/subprojects/gst-omx/config/meson.build +++ /dev/null @@ -1,21 +0,0 @@ -if omx_target == 'rpi' - sub = 'rpi' -elif omx_target == 'bellagio' - sub = 'bellagio' -elif omx_target == 'zynqultrascaleplus' - sub = 'zynqultrascaleplus' -elif omx_target == 'tizonia' - sub = 'tizonia' -else - # No config file defined for the 'generic' target - sub = '' -endif - -if sub != '' - subdir (sub) - # Used by tests to load the proper conf file - omx_config_dir = join_paths (meson.current_source_dir(), sub) - meson.add_devenv({'GST_OMX_CONFIG_DIR': omx_config_dir}) -else - omx_config_dir = '' -endif diff --git a/subprojects/gst-omx/config/rpi/gstomx.conf b/subprojects/gst-omx/config/rpi/gstomx.conf deleted file mode 100644 index d3ea56a883..0000000000 --- a/subprojects/gst-omx/config/rpi/gstomx.conf +++ /dev/null @@ -1,102 +0,0 @@ -[omxmpeg2videodec] -type-name=GstOMXMPEG2VideoDec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role - -[omxmpeg4videodec] -type-name=GstOMXMPEG4VideoDec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role - -[omxh263dec] -type-name=GstOMXH263Dec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role - -[omxh264dec] -type-name=GstOMXH264Dec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role;signals-premature-eos - -[omxtheoradec] -type-name=GstOMXTheoraDec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role - -[omxvp8dec] -type-name=GstOMXVP8Dec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role - -[omxmjpegdec] -type-name=GstOMXMJPEGDec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role - -[omxvc1dec] -type-name=GstOMXWMVDec -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_decode -rank=257 -in-port-index=130 -out-port-index=131 -hacks=no-component-role -sink-template-caps=video/x-wmv,wmvversion=(int)3,format=(string){WMV3,WVC1},width=(int)[1,MAX],height=(int)[1,MAX] - -[omxh264enc] -type-name=GstOMXH264Enc -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.video_encode -rank=257 -in-port-index=200 -out-port-index=201 -hacks=no-component-role;no-component-reconfigure - -[omxanalogaudiosink] -type-name=GstOMXAnalogAudioSink -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.audio_render -rank=257 -in-port-index=100 -out-port-index=101 -hacks=no-component-role -sink-template-caps=audio/x-raw,format=(string){S16LE,S32LE},layout=(string)interleaved,rate=(int){8000,11025,16000,22050,24000,32000,44100,48000,88200,96000,176400,192000},channels=(int)[1,2] - -[omxhdmiaudiosink] -type-name=GstOMXHdmiAudioSink -core-name=/opt/vc/lib/libopenmaxil.so -component-name=OMX.broadcom.audio_render -rank=258 -in-port-index=100 -out-port-index=101 -hacks=no-component-role -sink-template-caps=audio/x-raw,format=(string){S16LE,S32LE},layout=(string)interleaved,rate=(int){8000,11025,16000,22050,24000,32000,44100,48000,88200,96000,176400,192000},channels=(int)[1,8];audio/x-ac3,framed=(boolean)true;audio/x-dts,framed=(boolean)true,block-size=(int){512,1024,2048} - diff --git a/subprojects/gst-omx/config/rpi/meson.build b/subprojects/gst-omx/config/rpi/meson.build deleted file mode 100644 index dc99c08bc1..0000000000 --- a/subprojects/gst-omx/config/rpi/meson.build +++ /dev/null @@ -1 +0,0 @@ -install_data (['gstomx.conf'], install_dir : omx_conf_dir) diff --git a/subprojects/gst-omx/config/tizonia/gstomx.conf.in b/subprojects/gst-omx/config/tizonia/gstomx.conf.in deleted file mode 100644 index 4f7fb2b74e..0000000000 --- a/subprojects/gst-omx/config/tizonia/gstomx.conf.in +++ /dev/null @@ -1,49 +0,0 @@ -[omxmp3dec] -type-name=GstOMXMP3Dec -core-name=@TIZONIA_LIBDIR@/libtizcore.so -component-name=OMX.Aratelia.audio_decoder.mp3 -rank=0 -in-port-index=0 -out-port-index=1 - -[omxmp3enc] -type-name=GstOMXMP3Enc -core-name=@TIZONIA_LIBDIR@/libtizcore.so -component-name=OMX.Aratelia.audio_encoder.mp3 -rank=0 -in-port-index=0 -out-port-index=1 - -[omxaacdec] -type-name=GstOMXAACDec -core-name=@TIZONIA_LIBDIR@/libtizcore.so -component-name=OMX.Aratelia.audio_decoder.aac -rank=0 -in-port-index=0 -out-port-index=1 - -[omxvp8dec] -type-name=GstOMXVP8Dec -core-name=@TIZONIA_LIBDIR@/libtizcore.so -component-name=OMX.Aratelia.video_decoder.vp8 -rank=0 -in-port-index=0 -out-port-index=1 - -[omxh264dec] -type-name=GstOMXH264Dec -core-name=@TIZONIA_LIBDIR@/libtizcore.so -component-name=OMX.mesa.video.all -component-role=video_decoder.avc -rank=0 -in-port-index=0 -out-port-index=1 - -[omxh264enc] -type-name=GstOMXH264Enc -core-name=@TIZONIA_LIBDIR@/libtizcore.so -component-name=OMX.mesa.video.all -component-role=video_encoder.avc -rank=0 -in-port-index=0 -out-port-index=1 diff --git a/subprojects/gst-omx/config/tizonia/meson.build b/subprojects/gst-omx/config/tizonia/meson.build deleted file mode 100644 index 86b191db79..0000000000 --- a/subprojects/gst-omx/config/tizonia/meson.build +++ /dev/null @@ -1,5 +0,0 @@ -tizonia_cdata = cdata -configure_file(input : 'gstomx.conf.in', - output : 'gstomx.conf', - configuration : tizonia_cdata, - install_dir : omx_conf_dir) diff --git a/subprojects/gst-omx/config/zynqultrascaleplus/gstomx.conf b/subprojects/gst-omx/config/zynqultrascaleplus/gstomx.conf deleted file mode 100644 index ca6f4412f0..0000000000 --- a/subprojects/gst-omx/config/zynqultrascaleplus/gstomx.conf +++ /dev/null @@ -1,35 +0,0 @@ -[omxh264enc] -type-name=GstOMXH264Enc -core-name=/usr/lib/libOMX.allegro.core.so.1 -component-name=OMX.allegro.h264.encoder -in-port-index=0 -out-port-index=1 -rank=257 -hacks=ensure-buffer-count-actual - -[omxh264dec] -type-name=GstOMXH264Dec -core-name=/usr/lib/libOMX.allegro.core.so.1 -component-name=OMX.allegro.h264.decoder -in-port-index=0 -out-port-index=1 -rank=257 -hacks=pass-profile-to-decoder;pass-color-format-to-decoder;ensure-buffer-count-actual - -[omxh265enc] -type-name=GstOMXH265Enc -core-name=/usr/lib/libOMX.allegro.core.so.1 -component-name=OMX.allegro.h265.encoder -in-port-index=0 -out-port-index=1 -rank=257 -hacks=ensure-buffer-count-actual - -[omxh265dec] -type-name=GstOMXH265Dec -core-name=/usr/lib/libOMX.allegro.core.so.1 -component-name=OMX.allegro.h265.decoder -in-port-index=0 -out-port-index=1 -rank=257 -hacks=pass-profile-to-decoder;pass-color-format-to-decoder;ensure-buffer-count-actual diff --git a/subprojects/gst-omx/config/zynqultrascaleplus/meson.build b/subprojects/gst-omx/config/zynqultrascaleplus/meson.build deleted file mode 100644 index dc99c08bc1..0000000000 --- a/subprojects/gst-omx/config/zynqultrascaleplus/meson.build +++ /dev/null @@ -1 +0,0 @@ -install_data (['gstomx.conf'], install_dir : omx_conf_dir) diff --git a/subprojects/gst-omx/docs/gst_plugins_cache.json b/subprojects/gst-omx/docs/gst_plugins_cache.json deleted file mode 100644 index 2fa2156c4c..0000000000 --- a/subprojects/gst-omx/docs/gst_plugins_cache.json +++ /dev/null @@ -1,13 +0,0 @@ -{ - "omx": { - "description": "GStreamer OpenMAX Plug-ins", - "elements": {}, - "filename": "gstomx", - "license": "LGPL", - "other-types": {}, - "package": "GStreamer OpenMAX Plug-ins", - "source": "gst-omx", - "tracers": {}, - "url": "Unknown package origin" - } -} \ No newline at end of file diff --git a/subprojects/gst-omx/docs/index.md b/subprojects/gst-omx/docs/index.md deleted file mode 100644 index b5d574b93f..0000000000 --- a/subprojects/gst-omx/docs/index.md +++ /dev/null @@ -1,3 +0,0 @@ ---- -short-description: GStreamer plugins from OpenMax -... \ No newline at end of file diff --git a/subprojects/gst-omx/docs/meson.build b/subprojects/gst-omx/docs/meson.build deleted file mode 100644 index a315f8732d..0000000000 --- a/subprojects/gst-omx/docs/meson.build +++ /dev/null @@ -1,69 +0,0 @@ -build_hotdoc = false - -if meson.is_cross_build() - if get_option('doc').enabled() - error('Documentation enabled but building the doc while cross building is not supported yet.') - endif - - message('Documentation not built as building the docmentation while cross building is not supported yet.') - subdir_done() -endif - -required_hotdoc_extensions = ['gst-extension'] -if gst_dep.type_name() == 'internal' - gst_proj = subproject('gstreamer') - plugins_cache_generator = gst_proj.get_variable('plugins_cache_generator') -else - required_hotdoc_extensions += ['gst-extension'] - plugins_cache_generator = find_program(join_paths(gst_dep.get_variable('libexecdir'), 'gstreamer-' + api_version, 'gst-plugins-doc-cache-generator'), - required: false) -endif - -plugins_cache = join_paths(meson.current_source_dir(), 'gst_plugins_cache.json') -if plugins_cache_generator.found() - gst_plugins_doc_dep = custom_target('omx-plugins-doc-cache', - command: [plugins_cache_generator, plugins_cache, '@OUTPUT@', '@INPUT@'], - input: plugins, - output: 'gst_plugins_cache.json', - ) -else - warning('GStreamer plugin inspector for documentation not found, can\'t update the cache') -endif - -hotdoc_p = find_program('hotdoc', required: get_option('doc')) -if not hotdoc_p.found() - message('Hotdoc not found, not building the documentation') - subdir_done() -endif - -build_hotdoc = true -hotdoc = import('hotdoc') -if not hotdoc.has_extensions(required_hotdoc_extensions) - if get_option('doc').enabled() - error('Documentation enabled but gi-extension missing') - endif - - message('@0@ extensions not found, not building documentation'.format(required_hotdoc_extensions)) - subdir_done() -endif - -message('Plugins: @0@'.format(plugins)) -if host_machine.system() == 'windows' - pathsep = ';' -else - pathsep = ':' -endif -cdir = meson.current_source_dir() -gst_plugins_doc = run_command( - plugins_cache_generator, - 'hotdoc-config', - '--builddir', meson.current_build_dir(), - '--project_version', api_version, - '--sitemap', cdir / 'sitemap.txt', - '--index', cdir / 'index.md', - '--gst_index', cdir / 'index.md', - '--gst_c_sources', cdir / '../gst/*/*.[ch]', - '--gst_cache_file', cdir / plugins_cache, - check: true, -).stdout().split(pathsep) - diff --git a/subprojects/gst-omx/docs/sitemap.txt b/subprojects/gst-omx/docs/sitemap.txt deleted file mode 100644 index 058a2713a4..0000000000 --- a/subprojects/gst-omx/docs/sitemap.txt +++ /dev/null @@ -1 +0,0 @@ -gst-index diff --git a/subprojects/gst-omx/examples/egl/cube_texture_and_coords.h b/subprojects/gst-omx/examples/egl/cube_texture_and_coords.h deleted file mode 100644 index 1832df3e9f..0000000000 --- a/subprojects/gst-omx/examples/egl/cube_texture_and_coords.h +++ /dev/null @@ -1,100 +0,0 @@ -/* -Copyright (c) 2012, Broadcom Europe Ltd -All rights reserved. - -Redistribution and use in source and binary forms, with or without -modification, are permitted provided that the following conditions are met: - * Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - * Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - * Neither the name of the copyright holder nor the - names of its contributors may be used to endorse or promote products - derived from this software without specific prior written permission. - -THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND -ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE -DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY -DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; -LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND -ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -*/ - -// Spatial coordinates for the cube - -static const GLfloat quadx[6*4*3] = { - /* FRONT */ - -1.f, -1.f, 1.f, - 1.f, -1.f, 1.f, - -1.f, 1.f, 1.f, - 1.f, 1.f, 1.f, - - /* BACK */ - -1.f, -1.f, -1.f, - -1.f, 1.f, -1.f, - 1.f, -1.f, -1.f, - 1.f, 1.f, -1.f, - - /* LEFT */ - -1.f, -1.f, 1.f, - -1.f, 1.f, 1.f, - -1.f, -1.f, -1.f, - -1.f, 1.f, -1.f, - - /* RIGHT */ - 1.f, -1.f, -1.f, - 1.f, 1.f, -1.f, - 1.f, -1.f, 1.f, - 1.f, 1.f, 1.f, - - /* TOP */ - -1.f, 1.f, 1.f, - 1.f, 1.f, 1.f, - -1.f, 1.f, -1.f, - 1.f, 1.f, -1.f, - - /* BOTTOM */ - -1.f, -1.f, 1.f, - -1.f, -1.f, -1.f, - 1.f, -1.f, 1.f, - 1.f, -1.f, -1.f, -}; - -/** Texture coordinates for the quad. */ -static const GLfloat texCoords[6 * 4 * 2] = { - 0.f, 0.f, - 1.f, 0.f, - 0.f, 1.f, - 1.f, 1.f, - - 0.f, 0.f, - 1.f, 0.f, - 0.f, 1.f, - 1.f, 1.f, - - 0.f, 0.f, - 1.f, 0.f, - 0.f, 1.f, - 1.f, 1.f, - - 0.f, 0.f, - 1.f, 0.f, - 0.f, 1.f, - 1.f, 1.f, - - 0.f, 0.f, - 1.f, 0.f, - 0.f, 1.f, - 1.f, 1.f, - - 0.f, 0.f, - 1.f, 0.f, - 0.f, 1.f, - 1.f, 1.f, -}; - diff --git a/subprojects/gst-omx/examples/egl/meson.build b/subprojects/gst-omx/examples/egl/meson.build deleted file mode 100644 index 5ba6fc43ea..0000000000 --- a/subprojects/gst-omx/examples/egl/meson.build +++ /dev/null @@ -1,31 +0,0 @@ -optional_deps = [] -if x11_dep.found() - optional_deps += x11_dep -endif - -if x11_dep.found() or omx_target == 'rpi' - egl_sources = ['testegl.c'] - - egl_dep = dependency('egl', required : false) - if not egl_dep.found() - egl_dep = cc.find_library ('EGL') - endif - - gles2_dep = dependency('glesv2', required : false) - if not gles2_dep.found() - gles2_dep = cc.find_library ('GLESv2') - endif - - if omx_target == 'rpi' - brcmegl_dep = dependency('brcmegl', required : true) - optional_deps += brcmegl_dep - endif - - executable ('testegl', - sources : egl_sources, - c_args : gst_omx_args, - include_directories : [configinc], - dependencies : [libm, gst_dep, gstvideo_dep, gstgl_dep, egl_dep, - gles2_dep] + optional_deps - ) -endif diff --git a/subprojects/gst-omx/examples/egl/testegl.c b/subprojects/gst-omx/examples/egl/testegl.c deleted file mode 100644 index b7e77450e8..0000000000 --- a/subprojects/gst-omx/examples/egl/testegl.c +++ /dev/null @@ -1,1611 +0,0 @@ -/* -Copyright (c) 2012, Broadcom Europe Ltd -Copyright (c) 2012, OtherCrashOverride -Copyright (C) 2013, Fluendo S.A. - @author: Josep Torra -Copyright (C) 2013, Video Experts Group LLC. - @author: Ilya Smelykh -Copyright (C) 2014 Julien Isorce -All rights reserved. - -Redistribution and use in source and binary forms, with or without -modification, are permitted provided that the following conditions are met: - * Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - * Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - * Neither the name of the copyright holder nor the - names of its contributors may be used to endorse or promote products - derived from this software without specific prior written permission. - -THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND -ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE -DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY -DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; -LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND -ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -*/ - -/* A rotating cube rendered with OpenGL|ES and video played using GStreamer on - * the cube faces. - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#if defined (USE_OMX_TARGET_RPI) && defined (__GNUC__) -#ifndef __VCCOREVER__ -#define __VCCOREVER__ 0x04000000 -#endif -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wredundant-decls" -#pragma GCC optimize ("gnu89-inline") -#endif - -#include -#include - -#include -#include -#include -#include -#include -#include - -#include - -#define GST_USE_UNSTABLE_API -#include -#include - -#if defined (USE_OMX_TARGET_RPI) -#include -#include -#elif defined(HAVE_X11) -#include -#include -#endif - -#if defined (USE_OMX_TARGET_RPI) && defined (__GNUC__) -#pragma GCC reset_options -#pragma GCC diagnostic pop -#endif - -#include "cube_texture_and_coords.h" - -#ifndef M_PI -#define M_PI 3.141592654 -#endif - -#define SYNC_BUFFERS TRUE - -#define TRACE_VC_MEMORY_ENABLED 0 - -#if defined (USE_OMX_TARGET_RPI) && TRACE_VC_MEMORY_ENABLED -#define TRACE_VC_MEMORY(str) \ - fprintf (stderr, "\n\n" str "\n"); \ - system ("vcdbg reloc >&2") - -#define TRACE_VC_MEMORY_DEFINE_ID(id) \ - static int id = 0 - -#define TRACE_VC_MEMORY_RESET_ID(id) \ - G_STMT_START { \ - id = 0; \ - } G_STMT_END - -#define TRACE_VC_MEMORY_ONCE_FOR_ID(str,id) \ - G_STMT_START { \ - if (id == 0) { \ - fprintf (stderr, "\n\n" str "\n"); \ - system ("vcdbg reloc >&2"); \ - id = 1; \ - } \ - } G_STMT_END - -#define TRACE_VC_MEMORY_ONCE(str,id) \ - G_STMT_START { \ - static int id = 0; \ - if (id == 0) { \ - fprintf (stderr, "\n\n" str "\n"); \ - system ("vcdbg reloc >&2"); \ - id = 1; \ - } \ - } G_STMT_END - -#else -#define TRACE_VC_MEMORY(str) while(0) -#define TRACE_VC_MEMORY_DEFINE_ID(id) -#define TRACE_VC_MEMORY_RESET_ID(id) while(0) -#define TRACE_VC_MEMORY_ONCE_FOR_ID(str,id) while(0) -#define TRACE_VC_MEMORY_ONCE(str,id) while(0) -#endif - -/* some helpers that we should provide in libgstgl */ - -typedef struct -{ - GLfloat m[4][4]; -} GstGLMatrix; - -static void -gst_gl_matrix_load_identity (GstGLMatrix * matrix) -{ - memset (matrix, 0x0, sizeof (GstGLMatrix)); - matrix->m[0][0] = 1.0f; - matrix->m[1][1] = 1.0f; - matrix->m[2][2] = 1.0f; - matrix->m[3][3] = 1.0f; -} - -static void -gst_gl_matrix_multiply (GstGLMatrix * matrix, GstGLMatrix * srcA, - GstGLMatrix * srcB) -{ - GstGLMatrix tmp; - int i; - - for (i = 0; i < 4; i++) { - tmp.m[i][0] = (srcA->m[i][0] * srcB->m[0][0]) + - (srcA->m[i][1] * srcB->m[1][0]) + - (srcA->m[i][2] * srcB->m[2][0]) + (srcA->m[i][3] * srcB->m[3][0]); - - tmp.m[i][1] = (srcA->m[i][0] * srcB->m[0][1]) + - (srcA->m[i][1] * srcB->m[1][1]) + - (srcA->m[i][2] * srcB->m[2][1]) + (srcA->m[i][3] * srcB->m[3][1]); - - tmp.m[i][2] = (srcA->m[i][0] * srcB->m[0][2]) + - (srcA->m[i][1] * srcB->m[1][2]) + - (srcA->m[i][2] * srcB->m[2][2]) + (srcA->m[i][3] * srcB->m[3][2]); - - tmp.m[i][3] = (srcA->m[i][0] * srcB->m[0][3]) + - (srcA->m[i][1] * srcB->m[1][3]) + - (srcA->m[i][2] * srcB->m[2][3]) + (srcA->m[i][3] * srcB->m[3][3]); - } - - memcpy (matrix, &tmp, sizeof (GstGLMatrix)); -} - -static void -gst_gl_matrix_translate (GstGLMatrix * matrix, GLfloat tx, GLfloat ty, - GLfloat tz) -{ - matrix->m[3][0] += - (matrix->m[0][0] * tx + matrix->m[1][0] * ty + matrix->m[2][0] * tz); - matrix->m[3][1] += - (matrix->m[0][1] * tx + matrix->m[1][1] * ty + matrix->m[2][1] * tz); - matrix->m[3][2] += - (matrix->m[0][2] * tx + matrix->m[1][2] * ty + matrix->m[2][2] * tz); - matrix->m[3][3] += - (matrix->m[0][3] * tx + matrix->m[1][3] * ty + matrix->m[2][3] * tz); -} - -static void -gst_gl_matrix_frustum (GstGLMatrix * matrix, GLfloat left, GLfloat right, - GLfloat bottom, GLfloat top, GLfloat nearZ, GLfloat farZ) -{ - GLfloat deltaX = right - left; - GLfloat deltaY = top - bottom; - GLfloat deltaZ = farZ - nearZ; - GstGLMatrix frust; - - if ((nearZ <= 0.0f) || (farZ <= 0.0f) || - (deltaX <= 0.0f) || (deltaY <= 0.0f) || (deltaZ <= 0.0f)) - return; - - frust.m[0][0] = 2.0f * nearZ / deltaX; - frust.m[0][1] = frust.m[0][2] = frust.m[0][3] = 0.0f; - - frust.m[1][1] = 2.0f * nearZ / deltaY; - frust.m[1][0] = frust.m[1][2] = frust.m[1][3] = 0.0f; - - frust.m[2][0] = (right + left) / deltaX; - frust.m[2][1] = (top + bottom) / deltaY; - frust.m[2][2] = -(nearZ + farZ) / deltaZ; - frust.m[2][3] = -1.0f; - - frust.m[3][2] = -2.0f * nearZ * farZ / deltaZ; - frust.m[3][0] = frust.m[3][1] = frust.m[3][3] = 0.0f; - - gst_gl_matrix_multiply (matrix, &frust, matrix); -} - -static void -gst_gl_matrix_perspective (GstGLMatrix * matrix, GLfloat fovy, GLfloat aspect, - GLfloat nearZ, GLfloat farZ) -{ - GLfloat frustumW, frustumH; - - frustumH = tanf (fovy / 360.0f * M_PI) * nearZ; - frustumW = frustumH * aspect; - - gst_gl_matrix_frustum (matrix, -frustumW, frustumW, -frustumH, frustumH, - nearZ, farZ); -} - -/* *INDENT-OFF* */ - -/* vertex source */ -static const gchar *cube_v_src = - "attribute vec4 a_position; \n" - "attribute vec2 a_texCoord; \n" - "uniform float u_rotx; \n" - "uniform float u_roty; \n" - "uniform float u_rotz; \n" - "uniform mat4 u_modelview; \n" - "uniform mat4 u_projection; \n" - "varying vec2 v_texCoord; \n" - "void main() \n" - "{ \n" - " float PI = 3.14159265; \n" - " float xrot = u_rotx*2.0*PI/360.0; \n" - " float yrot = u_roty*2.0*PI/360.0; \n" - " float zrot = u_rotz*2.0*PI/360.0; \n" - " mat4 matX = mat4 ( \n" - " 1.0, 0.0, 0.0, 0.0, \n" - " 0.0, cos(xrot), sin(xrot), 0.0, \n" - " 0.0, -sin(xrot), cos(xrot), 0.0, \n" - " 0.0, 0.0, 0.0, 1.0 ); \n" - " mat4 matY = mat4 ( \n" - " cos(yrot), 0.0, -sin(yrot), 0.0, \n" - " 0.0, 1.0, 0.0, 0.0, \n" - " sin(yrot), 0.0, cos(yrot), 0.0, \n" - " 0.0, 0.0, 0.0, 1.0 ); \n" - " mat4 matZ = mat4 ( \n" - " cos(zrot), sin(zrot), 0.0, 0.0, \n" - " -sin(zrot), cos(zrot), 0.0, 0.0, \n" - " 0.0, 0.0, 1.0, 0.0, \n" - " 0.0, 0.0, 0.0, 1.0 ); \n" - " gl_Position = u_projection * u_modelview * matZ * matY * matX * a_position;\n" - " v_texCoord = a_texCoord; \n" - "} \n"; - -/* fragment source */ -static const gchar *cube_f_src = - "precision mediump float; \n" - "varying vec2 v_texCoord; \n" - "uniform sampler2D s_texture; \n" - "void main() \n" - "{ \n" - " gl_FragColor = texture2D (s_texture, v_texCoord); \n" - "} \n"; -/* *INDENT-ON* */ - -typedef struct -{ -#if defined (USE_OMX_TARGET_RPI) - DISPMANX_DISPLAY_HANDLE_T dispman_display; - DISPMANX_ELEMENT_HANDLE_T dispman_element; -#endif - - uint32_t screen_width; - uint32_t screen_height; - gboolean animate; - - GstCaps *caps; - - /* OpenGL|ES objects */ - EGLDisplay display; - EGLSurface surface; - EGLContext context; - GLuint tex; - - GLint vshader; - GLint fshader; - GLint program; - - GLint u_modelviewmatrix; - GLint u_projectionmatrix; - GLint s_texture; - GLint u_rotx; - GLint u_roty; - GLint u_rotz; - - GstGLMatrix modelview; - GstGLMatrix projection; - GLfloat fov; - GLfloat aspect; - - /* model rotation vector and direction */ - GLfloat rot_angle_x_inc; - GLfloat rot_angle_y_inc; - GLfloat rot_angle_z_inc; - - /* current model rotation angles */ - GLfloat rot_angle_x; - GLfloat rot_angle_y; - GLfloat rot_angle_z; - - /* current distance from camera */ - GLfloat distance; - GLfloat distance_inc; - - /* GStreamer related resources */ - GstElement *pipeline; - GstElement *vsink; - GstGLDisplayEGL *gst_display; - GstGLContext *gl_context; - gboolean can_avoid_upload; - - /* Interthread comunication */ - GAsyncQueue *queue; - GMutex queue_lock; - GCond cond; - gboolean flushing; - GstMiniObject *popped_obj; - GstBuffer *current_buffer; - - /* GLib mainloop */ - GMainLoop *main_loop; - GstBuffer *last_buffer; - - /* Rendering thread state */ - gboolean running; - - /* number of rendered and dropped frames */ - guint64 rendered; - guint64 dropped; - -#if !defined (USE_OMX_TARGET_RPI) && defined(HAVE_X11) - Display *xdisplay; - Window xwindow; -#endif -} APP_STATE_T; - -static void init_ogl (APP_STATE_T * state); -static void init_model_proj (APP_STATE_T * state); -static void reset_model (APP_STATE_T * state); -static GLfloat inc_and_wrap_angle (GLfloat angle, GLfloat angle_inc); -static void redraw_scene (APP_STATE_T * state); -static void update_model (APP_STATE_T * state); -static void init_textures (APP_STATE_T * state, GstBuffer * buffer); -static APP_STATE_T _state, *state = &_state; -static gboolean queue_object (APP_STATE_T * state, GstMiniObject * obj, - gboolean synchronous); - -TRACE_VC_MEMORY_DEFINE_ID (gid0); -TRACE_VC_MEMORY_DEFINE_ID (gid1); -TRACE_VC_MEMORY_DEFINE_ID (gid2); - -typedef enum -{ - GST_PLAY_FLAG_VIDEO = (1 << 0), - GST_PLAY_FLAG_AUDIO = (1 << 1), - GST_PLAY_FLAG_TEXT = (1 << 2), - GST_PLAY_FLAG_VIS = (1 << 3), - GST_PLAY_FLAG_SOFT_VOLUME = (1 << 4), - GST_PLAY_FLAG_NATIVE_AUDIO = (1 << 5), - GST_PLAY_FLAG_NATIVE_VIDEO = (1 << 6), - GST_PLAY_FLAG_DOWNLOAD = (1 << 7), - GST_PLAY_FLAG_BUFFERING = (1 << 8), - GST_PLAY_FLAG_DEINTERLACE = (1 << 9), - GST_PLAY_FLAG_SOFT_COLORBALANCE = (1 << 10) -} GstPlayFlags; - -/*********************************************************** - * Name: init_ogl - * - * Arguments: - * APP_STATE_T *state - holds OGLES model info - * - * Description: Sets the display, OpenGL|ES context and screen stuff - * - * Returns: void - * - ***********************************************************/ -static void -init_ogl (APP_STATE_T * state) -{ -#if defined (USE_OMX_TARGET_RPI) - int32_t success = 0; -#else - gint screen_num = 0; - gulong black_pixel = 0; -#endif - EGLBoolean result; - EGLint num_config; - EGLNativeWindowType window_handle = (EGLNativeWindowType) 0; - -#if defined (USE_OMX_TARGET_RPI) - static EGL_DISPMANX_WINDOW_T nativewindow; - - DISPMANX_UPDATE_HANDLE_T dispman_update; - VC_RECT_T dst_rect; - VC_RECT_T src_rect; - - VC_DISPMANX_ALPHA_T alpha = { DISPMANX_FLAGS_ALPHA_FIXED_ALL_PIXELS, 255, 0 }; -#endif - - static const EGLint attribute_list[] = { - EGL_DEPTH_SIZE, 16, - EGL_SURFACE_TYPE, EGL_WINDOW_BIT, - EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, - EGL_NONE - }; - - static const EGLint context_attributes[] = { - EGL_CONTEXT_CLIENT_VERSION, 2, - EGL_NONE - }; - - EGLConfig config; - - /* get an EGL display connection */ - state->display = eglGetDisplay (EGL_DEFAULT_DISPLAY); - assert (state->display != EGL_NO_DISPLAY); - - /* initialize the EGL display connection */ - result = eglInitialize (state->display, NULL, NULL); - assert (EGL_FALSE != result); - -#if defined (USE_OMX_TARGET_RPI) - /* get an appropriate EGL frame buffer configuration - * this uses a BRCM extension that gets the closest match, rather - * than standard which returns anything that matches. */ - result = - eglSaneChooseConfigBRCM (state->display, attribute_list, &config, 1, - &num_config); - assert (EGL_FALSE != result); -#else - result = - eglChooseConfig (state->display, attribute_list, &config, 1, &num_config); -#endif - - /* create an EGL rendering context */ - state->context = - eglCreateContext (state->display, config, EGL_NO_CONTEXT, - context_attributes); - assert (state->context != EGL_NO_CONTEXT); - -#if defined (USE_OMX_TARGET_RPI) - /* create an EGL window surface */ - success = graphics_get_display_size (0 /* LCD */ , &state->screen_width, - &state->screen_height); - assert (success >= 0); - - dst_rect.x = 0; - dst_rect.y = 0; - dst_rect.width = state->screen_width; - dst_rect.height = state->screen_height; - - src_rect.x = 0; - src_rect.y = 0; - src_rect.width = state->screen_width << 16; - src_rect.height = state->screen_height << 16; - - state->dispman_display = vc_dispmanx_display_open (0 /* LCD */ ); - dispman_update = vc_dispmanx_update_start (0); - - state->dispman_element = - vc_dispmanx_element_add (dispman_update, state->dispman_display, - 0 /*layer */ , &dst_rect, 0 /*src */ , - &src_rect, DISPMANX_PROTECTION_NONE, &alpha, 0 /*clamp */ , - 0 /*transform */ ); - - nativewindow.element = state->dispman_element; - nativewindow.width = state->screen_width; - nativewindow.height = state->screen_height; - vc_dispmanx_update_submit_sync (dispman_update); - - window_handle = &nativewindow; -#elif defined(HAVE_X11) - state->screen_width = 1280; - state->screen_height = 720; - state->xdisplay = XOpenDisplay (NULL); - screen_num = DefaultScreen (state->xdisplay); - black_pixel = XBlackPixel (state->xdisplay, screen_num); - state->xwindow = XCreateSimpleWindow (state->xdisplay, - DefaultRootWindow (state->xdisplay), 0, 0, state->screen_width, - state->screen_height, 0, 0, black_pixel); - XSetWindowBackgroundPixmap (state->xdisplay, state->xwindow, None); - XMapRaised (state->xdisplay, state->xwindow); - XSync (state->xdisplay, FALSE); - window_handle = state->xwindow; -#endif - - state->surface = - eglCreateWindowSurface (state->display, config, window_handle, NULL); - assert (state->surface != EGL_NO_SURFACE); - - /* connect the context to the surface */ - result = - eglMakeCurrent (state->display, state->surface, state->surface, - state->context); - assert (EGL_FALSE != result); - - state->gst_display = gst_gl_display_egl_new_with_egl_display (state->display); - state->gl_context = - gst_gl_context_new_wrapped (GST_GL_DISPLAY (state->gst_display), - (guintptr) state->context, GST_GL_PLATFORM_EGL, GST_GL_API_GLES2); -} - -/*********************************************************** - * Name: init_model_proj - * - * Arguments: - * APP_STATE_T *state - holds OGLES model info - * - * Description: Sets the OpenGL|ES model to default values - * - * Returns: void - * - ***********************************************************/ -static void -init_model_proj (APP_STATE_T * state) -{ - GLint ret = 0; - - state->vshader = glCreateShader (GL_VERTEX_SHADER); - - glShaderSource (state->vshader, 1, &cube_v_src, NULL); - glCompileShader (state->vshader); - assert (glGetError () == GL_NO_ERROR); - - state->fshader = glCreateShader (GL_FRAGMENT_SHADER); - - glShaderSource (state->fshader, 1, &cube_f_src, NULL); - glCompileShader (state->fshader); - assert (glGetError () == GL_NO_ERROR); - - state->program = glCreateProgram (); - - glAttachShader (state->program, state->vshader); - glAttachShader (state->program, state->fshader); - - glBindAttribLocation (state->program, 0, "a_position"); - glBindAttribLocation (state->program, 1, "a_texCoord"); - - glLinkProgram (state->program); - - glGetProgramiv (state->program, GL_LINK_STATUS, &ret); - assert (ret == GL_TRUE); - - glUseProgram (state->program); - - state->u_rotx = glGetUniformLocation (state->program, "u_rotx"); - state->u_roty = glGetUniformLocation (state->program, "u_roty"); - state->u_rotz = glGetUniformLocation (state->program, "u_rotz"); - - state->u_modelviewmatrix = - glGetUniformLocation (state->program, "u_modelview"); - - state->u_projectionmatrix = - glGetUniformLocation (state->program, "u_projection"); - - state->s_texture = glGetUniformLocation (state->program, "s_texture"); - - glViewport (0, 0, (GLsizei) state->screen_width, - (GLsizei) state->screen_height); - - state->fov = 45.0f; - state->distance = 5.0f; - state->aspect = - (GLfloat) state->screen_width / (GLfloat) state->screen_height; - - gst_gl_matrix_load_identity (&state->projection); - gst_gl_matrix_perspective (&state->projection, state->fov, state->aspect, - 1.0f, 100.0f); - - gst_gl_matrix_load_identity (&state->modelview); - gst_gl_matrix_translate (&state->modelview, 0.0f, 0.0f, -state->distance); - - reset_model (state); -} - -/*********************************************************** - * Name: reset_model - * - * Arguments: - * APP_STATE_T *state - holds OGLES model info - * - * Description: Resets the Model projection and rotation direction - * - * Returns: void - * - ***********************************************************/ -static void -reset_model (APP_STATE_T * state) -{ - /* reset model rotation */ - state->rot_angle_x = 45.f; - state->rot_angle_y = 30.f; - state->rot_angle_z = 0.f; - state->rot_angle_x_inc = 0.5f; - state->rot_angle_y_inc = 0.5f; - state->rot_angle_z_inc = 0.f; -} - -/*********************************************************** - * Name: update_model - * - * Arguments: - * APP_STATE_T *state - holds OGLES model info - * - * Description: Updates model projection to current position/rotation - * - * Returns: void - * - ***********************************************************/ -static void -update_model (APP_STATE_T * state) -{ - if (state->animate) { - /* update position */ - state->rot_angle_x = - inc_and_wrap_angle (state->rot_angle_x, state->rot_angle_x_inc); - state->rot_angle_y = - inc_and_wrap_angle (state->rot_angle_y, state->rot_angle_y_inc); - state->rot_angle_z = - inc_and_wrap_angle (state->rot_angle_z, state->rot_angle_z_inc); - } -} - -/*********************************************************** - * Name: inc_and_wrap_angle - * - * Arguments: - * GLfloat angle current angle - * GLfloat angle_inc angle increment - * - * Description: Increments or decrements angle by angle_inc degrees - * Wraps to 0 at 360 deg. - * - * Returns: new value of angle - * - ***********************************************************/ -static GLfloat -inc_and_wrap_angle (GLfloat angle, GLfloat angle_inc) -{ - angle += angle_inc; - - if (angle >= 360.0) - angle -= 360.f; - else if (angle <= 0) - angle += 360.f; - - return angle; -} - -/*********************************************************** - * Name: redraw_scene - * - * Arguments: - * APP_STATE_T *state - holds OGLES model info - * - * Description: Draws the model and calls eglSwapBuffers - * to render to screen - * - * Returns: void - * - ***********************************************************/ -static void -redraw_scene (APP_STATE_T * state) -{ - glBindFramebuffer (GL_FRAMEBUFFER, 0); - - glEnable (GL_CULL_FACE); - glEnable (GL_DEPTH_TEST); - - /* Set background color and clear buffers */ - glClearColor (0.15f, 0.25f, 0.35f, 1.0f); - glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - - glUseProgram (state->program); - - glVertexAttribPointer (0, 3, GL_FLOAT, GL_FALSE, 0, quadx); - glVertexAttribPointer (1, 2, GL_FLOAT, GL_FALSE, 0, texCoords); - - glEnableVertexAttribArray (0); - glEnableVertexAttribArray (1); - - glActiveTexture (GL_TEXTURE0); - glBindTexture (GL_TEXTURE_2D, state->tex); - glUniform1i (state->s_texture, 0); - - glUniform1f (state->u_rotx, state->rot_angle_x); - glUniform1f (state->u_roty, state->rot_angle_y); - glUniform1f (state->u_rotz, state->rot_angle_z); - - glUniformMatrix4fv (state->u_modelviewmatrix, 1, GL_FALSE, - &state->modelview.m[0][0]); - - glUniformMatrix4fv (state->u_projectionmatrix, 1, GL_FALSE, - &state->projection.m[0][0]); - - /* draw first 4 vertices */ - glDrawArrays (GL_TRIANGLE_STRIP, 0, 4); - glDrawArrays (GL_TRIANGLE_STRIP, 4, 4); - glDrawArrays (GL_TRIANGLE_STRIP, 8, 4); - glDrawArrays (GL_TRIANGLE_STRIP, 12, 4); - glDrawArrays (GL_TRIANGLE_STRIP, 16, 4); - glDrawArrays (GL_TRIANGLE_STRIP, 20, 4); - - if (!eglSwapBuffers (state->display, state->surface)) { - g_main_loop_quit (state->main_loop); - return; - } - - glDisable (GL_DEPTH_TEST); - glDisable (GL_CULL_FACE); -} - -/*********************************************************** - * Name: init_textures - * - * Arguments: - * APP_STATE_T *state - holds OGLES model info - * - * Description: Initialise OGL|ES texture surfaces to use image - * buffers - * - * Returns: void - * - ***********************************************************/ -static void -init_textures (APP_STATE_T * state, GstBuffer * buffer) -{ - GstCapsFeatures *feature = gst_caps_get_features (state->caps, 0); - - if (gst_caps_features_contains (feature, "memory:GLMemory")) { - g_print ("Prepare texture for GLMemory\n"); - state->can_avoid_upload = TRUE; - state->tex = 0; - } else if (gst_caps_features_contains (feature, - "meta:GstVideoGLTextureUploadMeta")) { - GstVideoMeta *meta = NULL; - guint internal_format = - gst_gl_sized_gl_format_from_gl_format_type (state->gl_context, - GL_RGBA, GL_UNSIGNED_BYTE); - - g_print ("Prepare texture for GstVideoGLTextureUploadMeta\n"); - meta = gst_buffer_get_video_meta (buffer); - state->can_avoid_upload = FALSE; - glGenTextures (1, &state->tex); - glBindTexture (GL_TEXTURE_2D, state->tex); - glTexImage2D (GL_TEXTURE_2D, 0, internal_format, meta->width, meta->height, - 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); - } else { - g_assert_not_reached (); - } - -#if 0 - glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); - glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); -#else - glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); -#endif - - glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); - glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - - assert (glGetError () == GL_NO_ERROR); -} - -static void -render_scene (APP_STATE_T * state) -{ - update_model (state); - redraw_scene (state); - TRACE_VC_MEMORY_ONCE_FOR_ID ("after render_scene", gid2); -} - -static void -update_image (APP_STATE_T * state, GstBuffer * buffer) -{ - GstVideoGLTextureUploadMeta *meta = NULL; - - if (state->current_buffer) { - gst_buffer_unref (state->current_buffer); - } else { - /* Setup the model world */ - init_model_proj (state); - TRACE_VC_MEMORY ("after init_model_proj"); - - /* initialize the OGLES texture(s) */ - init_textures (state, buffer); - TRACE_VC_MEMORY ("after init_textures"); - } - state->current_buffer = gst_buffer_ref (buffer); - - TRACE_VC_MEMORY_ONCE_FOR_ID ("before GstVideoGLTextureUploadMeta", gid0); - - if (state->can_avoid_upload) { - GstMemory *mem = gst_buffer_peek_memory (state->current_buffer, 0); - g_assert (gst_is_gl_memory (mem)); - state->tex = ((GstGLMemory *) mem)->tex_id; - } else if ((meta = gst_buffer_get_video_gl_texture_upload_meta (buffer))) { - if (meta->n_textures == 1) { - guint ids[4] = { state->tex, 0, 0, 0 }; - if (!gst_video_gl_texture_upload_meta_upload (meta, ids)) { - GST_WARNING ("failed to upload to texture"); - } - } - } - - TRACE_VC_MEMORY_ONCE_FOR_ID ("after GstVideoGLTextureUploadMeta", gid1); -} - -static void -init_intercom (APP_STATE_T * state) -{ - state->queue = - g_async_queue_new_full ((GDestroyNotify) gst_mini_object_unref); - g_mutex_init (&state->queue_lock); - g_cond_init (&state->cond); -} - -static void -terminate_intercom (APP_STATE_T * state) -{ - /* Release intercom */ - if (state->queue) { - g_async_queue_unref (state->queue); - } - - g_mutex_clear (&state->queue_lock); - g_cond_clear (&state->cond); -} - -static void -flush_internal (APP_STATE_T * state) -{ - if (state->current_buffer) { - gst_buffer_unref (state->current_buffer); - } - state->current_buffer = NULL; -} - -static void -flush_start (APP_STATE_T * state) -{ - GstMiniObject *object = NULL; - - g_mutex_lock (&state->queue_lock); - state->flushing = TRUE; - g_cond_broadcast (&state->cond); - g_mutex_unlock (&state->queue_lock); - - while ((object = g_async_queue_try_pop (state->queue))) { - gst_mini_object_unref (object); - } - g_mutex_lock (&state->queue_lock); - flush_internal (state); - state->popped_obj = NULL; - g_mutex_unlock (&state->queue_lock); -} - -static void -flush_stop (APP_STATE_T * state) -{ - GstMiniObject *object = NULL; - - g_mutex_lock (&state->queue_lock); - while ((object = GST_MINI_OBJECT_CAST (g_async_queue_try_pop (state->queue)))) { - gst_mini_object_unref (object); - } - flush_internal (state); - state->popped_obj = NULL; - state->flushing = FALSE; - g_mutex_unlock (&state->queue_lock); -} - -static void -pipeline_pause (APP_STATE_T * state) -{ - gst_element_set_state (state->pipeline, GST_STATE_PAUSED); -} - -static void -pipeline_play (APP_STATE_T * state) -{ - gst_element_set_state (state->pipeline, GST_STATE_PLAYING); -} - -static gint64 -pipeline_get_position (APP_STATE_T * state) -{ - gint64 position = -1; - - if (state->pipeline) { - gst_element_query_position (state->vsink, GST_FORMAT_TIME, &position); - } - - return position; -} - -static gint64 -pipeline_get_duration (APP_STATE_T * state) -{ - gint64 duration = -1; - - if (state->pipeline) { - gst_element_query_duration (state->pipeline, GST_FORMAT_TIME, &duration); - } - - return duration; -} - -static void -pipeline_seek (APP_STATE_T * state, gint64 position) -{ - if (state->pipeline) { - GstEvent *event; - event = gst_event_new_seek (1.0, - GST_FORMAT_TIME, GST_SEEK_FLAG_FLUSH | GST_SEEK_FLAG_KEY_UNIT, - GST_SEEK_TYPE_SET, position, GST_SEEK_TYPE_SET, GST_CLOCK_TIME_NONE); - if (!gst_element_send_event (state->vsink, event)) { - g_print ("seek failed\n"); - } - } -} - -static gboolean -handle_queued_objects (APP_STATE_T * state) -{ - GstMiniObject *object = NULL; - - g_mutex_lock (&state->queue_lock); - if (state->flushing) { - g_cond_broadcast (&state->cond); - goto beach; - } else if (g_async_queue_length (state->queue) == 0) { - goto beach; - } - - if ((object = g_async_queue_try_pop (state->queue))) { - if (GST_IS_BUFFER (object)) { - GstBuffer *buffer = GST_BUFFER_CAST (object); - update_image (state, buffer); - render_scene (state); - gst_buffer_unref (buffer); - if (!SYNC_BUFFERS) { - object = NULL; - } - } else if (GST_IS_EVENT (object)) { - GstEvent *event = GST_EVENT_CAST (object); - g_print ("\nevent %p %s\n", event, - gst_event_type_get_name (GST_EVENT_TYPE (event))); - - switch (GST_EVENT_TYPE (event)) { - case GST_EVENT_EOS: - flush_internal (state); - break; - default: - break; - } - gst_event_unref (event); - object = NULL; - } - } - - if (object) { - state->popped_obj = object; - g_cond_broadcast (&state->cond); - } - -beach: - g_mutex_unlock (&state->queue_lock); - - return FALSE; -} - -static gboolean -queue_object (APP_STATE_T * state, GstMiniObject * obj, gboolean synchronous) -{ - gboolean res = TRUE; - - g_mutex_lock (&state->queue_lock); - if (state->flushing) { - gst_mini_object_unref (obj); - res = FALSE; - goto beach; - } - - g_async_queue_push (state->queue, obj); - - if (synchronous) { - /* Waiting for object to be handled */ - do { - g_cond_wait (&state->cond, &state->queue_lock); - } while (!state->flushing && state->popped_obj != obj); - } - -beach: - g_mutex_unlock (&state->queue_lock); - return res; -} - -static void -preroll_cb (GstElement * fakesink, GstBuffer * buffer, GstPad * pad, - gpointer user_data) -{ - APP_STATE_T *state = (APP_STATE_T *) user_data; - queue_object (state, GST_MINI_OBJECT_CAST (gst_buffer_ref (buffer)), FALSE); -} - -static void -buffers_cb (GstElement * fakesink, GstBuffer * buffer, GstPad * pad, - gpointer user_data) -{ - APP_STATE_T *state = (APP_STATE_T *) user_data; - queue_object (state, GST_MINI_OBJECT_CAST (gst_buffer_ref (buffer)), - SYNC_BUFFERS); -} - -static GstPadProbeReturn -events_cb (GstPad * pad, GstPadProbeInfo * probe_info, gpointer user_data) -{ - APP_STATE_T *state = (APP_STATE_T *) user_data; - GstEvent *event = GST_PAD_PROBE_INFO_EVENT (probe_info); - - switch (GST_EVENT_TYPE (event)) { - case GST_EVENT_CAPS: - { - if (state->caps) { - gst_caps_unref (state->caps); - state->caps = NULL; - } - gst_event_parse_caps (event, &state->caps); - if (state->caps) - gst_caps_ref (state->caps); - break; - } - case GST_EVENT_FLUSH_START: - flush_start (state); - break; - case GST_EVENT_FLUSH_STOP: - flush_stop (state); - break; - case GST_EVENT_EOS: - queue_object (state, GST_MINI_OBJECT_CAST (gst_event_ref (event)), FALSE); - break; - default: - break; - } - - return GST_PAD_PROBE_OK; -} - -static GstPadProbeReturn -query_cb (GstPad * pad, GstPadProbeInfo * info, gpointer user_data) -{ - APP_STATE_T *state = (APP_STATE_T *) user_data; - GstQuery *query = GST_PAD_PROBE_INFO_QUERY (info); - - switch (GST_QUERY_TYPE (query)) { - case GST_QUERY_CONTEXT: - { - if (gst_gl_handle_context_query (state->pipeline, query, - (GstGLDisplay *) state->gst_display, NULL, - (GstGLContext *) state->gl_context)) - return GST_PAD_PROBE_HANDLED; - break; - } - case GST_QUERY_DRAIN: - { - flush_internal (state); - break; - } - default: - break; - } - - return GST_PAD_PROBE_OK; -} - -static gboolean -init_playbin_player (APP_STATE_T * state, const gchar * uri) -{ - GstPad *pad = NULL; - GstPad *ghostpad = NULL; - GstElement *vbin = gst_bin_new ("vbin"); - - /* insert a gl filter so that the GstGLBufferPool - * is managed automatically */ - GstElement *glfilter = gst_element_factory_make ("glupload", "glfilter"); - GstElement *capsfilter = gst_element_factory_make ("capsfilter", NULL); - GstElement *vsink = gst_element_factory_make ("fakesink", "vsink"); - - g_object_set (capsfilter, "caps", - gst_caps_from_string ("video/x-raw(memory:GLMemory), format=RGBA"), NULL); - g_object_set (vsink, "sync", TRUE, "silent", TRUE, "qos", TRUE, - "enable-last-sample", FALSE, "max-lateness", 20 * GST_MSECOND, - "signal-handoffs", TRUE, NULL); - - g_signal_connect (vsink, "preroll-handoff", G_CALLBACK (preroll_cb), state); - g_signal_connect (vsink, "handoff", G_CALLBACK (buffers_cb), state); - - gst_bin_add_many (GST_BIN (vbin), glfilter, capsfilter, vsink, NULL); - - pad = gst_element_get_static_pad (glfilter, "sink"); - ghostpad = gst_ghost_pad_new ("sink", pad); - gst_object_unref (pad); - gst_element_add_pad (vbin, ghostpad); - - pad = gst_element_get_static_pad (vsink, "sink"); - gst_pad_add_probe (pad, GST_PAD_PROBE_TYPE_EVENT_DOWNSTREAM, events_cb, state, - NULL); - gst_pad_add_probe (pad, GST_PAD_PROBE_TYPE_QUERY_DOWNSTREAM, query_cb, state, - NULL); - gst_object_unref (pad); - - gst_element_link (glfilter, capsfilter); - gst_element_link (capsfilter, vsink); - - /* Instantiate and configure playbin */ - state->pipeline = gst_element_factory_make ("playbin", "player"); - g_object_set (state->pipeline, "uri", uri, - "video-sink", vbin, "flags", - GST_PLAY_FLAG_NATIVE_VIDEO | GST_PLAY_FLAG_AUDIO, NULL); - - state->vsink = gst_object_ref (vsink); - return TRUE; -} - -static gboolean -init_parse_launch_player (APP_STATE_T * state, const gchar * spipeline) -{ - GstElement *vsink; - GError *error = NULL; - - /* ex: - - ./testegl "filesrc location=big_buck_bunny_720p_h264.mov ! qtdemux ! \ - h264parse ! omxh264dec ! glcolorscale ! fakesink name=vsink" - - ./testegl "filesrc location=big_buck_bunny_720p_h264.mov ! qtdemux ! \ - h264parse ! omxh264dec ! glcolorscale ! \ - video/x-raw(memory:GLMemory) ! fakesink name=vsink" - - ./testegl "filesrc location=big_buck_bunny_720p_h264.mov ! qtdemux ! \ - h264parse ! omxh264dec ! glcolorscale ! \ - video/x-raw(meta:GstVideoGLTextureUploadMeta) ! \ - fakesink name=vsink" - - */ - - /* pipeline 1 and 2 are the same and the most efficient as glcolorscale - * will enter in passthrough mode and testegl will just bind the eglimage - * to a gl texture without any copy. */ - - state->pipeline = gst_parse_launch (spipeline, &error); - - if (!state->pipeline) { - g_printerr ("Unable to instatiate pipeline '%s': %s\n", - spipeline, error->message); - return FALSE; - } - - vsink = gst_bin_get_by_name (GST_BIN (state->pipeline), "vsink"); - - if (!vsink) { - g_printerr ("Unable to find a fakesink named 'vsink'"); - return FALSE; - } - - g_object_set (vsink, "sync", TRUE, "silent", TRUE, "qos", TRUE, - "enable-last-sample", FALSE, - "max-lateness", 20 * GST_MSECOND, "signal-handoffs", TRUE, NULL); - - g_signal_connect (vsink, "preroll-handoff", G_CALLBACK (preroll_cb), state); - g_signal_connect (vsink, "handoff", G_CALLBACK (buffers_cb), state); - - gst_pad_add_probe (gst_element_get_static_pad (vsink, "sink"), - GST_PAD_PROBE_TYPE_EVENT_DOWNSTREAM, events_cb, state, NULL); - gst_pad_add_probe (gst_element_get_static_pad (vsink, "sink"), - GST_PAD_PROBE_TYPE_QUERY_DOWNSTREAM, query_cb, state, NULL); - - state->vsink = gst_object_ref (vsink); - return TRUE; -} - -//------------------------------------------------------------------------------ - -static void -report_position_duration (APP_STATE_T * state) -{ - gint64 position, duration; - - duration = pipeline_get_duration (state); - position = pipeline_get_position (state); - - if (position != -1) { - g_print ("\n position / duration: %" GST_TIME_FORMAT, - GST_TIME_ARGS (position)); - } else { - g_print ("\n position / duration: unknown"); - } - - if (duration != -1) { - g_print (" / %" GST_TIME_FORMAT, GST_TIME_ARGS (duration)); - } else { - g_print (" / unknown"); - } - g_print ("\n"); -} - -static void -seek_forward (APP_STATE_T * state) -{ - gint64 position, duration; - - duration = pipeline_get_duration (state); - position = pipeline_get_position (state); - - if (position != -1) { - position += 30 * GST_SECOND; - if (duration != -1) { - position = MIN (position, duration); - } - pipeline_seek (state, position); - } -} - -static void -seek_backward (APP_STATE_T * state) -{ - gint64 position; - - position = pipeline_get_position (state); - - if (position != -1) { - position -= 30 * GST_SECOND; - position = MAX (position, 0); - pipeline_seek (state, position); - } -} - -#define SKIP(t) \ - while (*t) { \ - if ((*t == ' ') || (*t == '\n') || (*t == '\t') || (*t == '\r')) \ - t++; \ - else \ - break; \ - } - -/* Process keyboard input */ -static gboolean -handle_keyboard (GIOChannel * source, GIOCondition cond, APP_STATE_T * state) -{ - gchar *str = NULL; - char op; - - if (g_io_channel_read_line (source, &str, NULL, NULL, - NULL) == G_IO_STATUS_NORMAL) { - - gchar *cmd = str; - SKIP (cmd) - op = *cmd; - cmd++; - switch (op) { - case 'a': - if (state->animate) { - state->animate = FALSE; - } else { - state->animate = TRUE; - } - break; - case 'p': - pipeline_pause (state); - break; - case 'r': - pipeline_play (state); - break; - case 'l': - report_position_duration (state); - break; - case 'f': - seek_forward (state); - break; - case 'b': - seek_backward (state); - break; - case 'q': - flush_start (state); - gst_element_set_state (state->pipeline, GST_STATE_READY); - break; - } - } - g_free (str); - return TRUE; -} - -static GstBusSyncReply -bus_sync_handler (GstBus * bus, GstMessage * message, GstPipeline * data) -{ - return GST_BUS_PASS; -} - -/* on error print the error and quit the application */ -static void -error_cb (GstBus * bus, GstMessage * msg, APP_STATE_T * state) -{ - GError *err; - gchar *debug_info; - - gst_message_parse_error (msg, &err, &debug_info); - g_printerr ("Error received from element %s: %s\n", - GST_OBJECT_NAME (msg->src), err->message); - g_printerr ("Debugging information: %s\n", debug_info ? debug_info : "none"); - g_clear_error (&err); - g_free (debug_info); - flush_start (state); - gst_element_set_state (state->pipeline, GST_STATE_READY); -} - -/* buffering */ -static void -buffering_cb (GstBus * bus, GstMessage * msg, APP_STATE_T * state) -{ - gint percent; - - gst_message_parse_buffering (msg, &percent); - g_print ("Buffering %3d%%\r", percent); - if (percent < 100) - pipeline_pause (state); - else { - g_print ("\n"); - pipeline_play (state); - } -} - -/* on EOS just quit the application */ -static void -eos_cb (GstBus * bus, GstMessage * msg, APP_STATE_T * state) -{ - if (GST_MESSAGE_SRC (msg) == GST_OBJECT (state->pipeline)) { - g_print ("End-Of-Stream reached.\n"); - gst_element_set_state (state->pipeline, GST_STATE_READY); - } -} - -static void -state_changed_cb (GstBus * bus, GstMessage * msg, APP_STATE_T * state) -{ - GstState old_state, new_state, pending_state; - if (GST_MESSAGE_SRC (msg) == GST_OBJECT (state->pipeline)) { - gst_message_parse_state_changed (msg, &old_state, &new_state, - &pending_state); - g_print ("State changed to %s\n", gst_element_state_get_name (new_state)); - if (old_state == GST_STATE_PAUSED && new_state == GST_STATE_READY) { - g_main_loop_quit (state->main_loop); - } - } -} - -static void -qos_cb (GstBus * bus, GstMessage * msg, APP_STATE_T * state) -{ - GstFormat fmt = GST_FORMAT_BUFFERS; - gchar *name = gst_element_get_name (GST_MESSAGE_SRC (msg)); - gst_message_parse_qos_stats (msg, &fmt, &state->rendered, &state->dropped); - g_print ("%s rendered: %" G_GUINT64_FORMAT " dropped: %" G_GUINT64_FORMAT - " %s\n", - name, state->rendered, state->dropped, - (fmt == GST_FORMAT_BUFFERS ? "frames" : "samples")); - g_free (name); -} - -//============================================================================== - -static void -close_ogl (void) -{ -#if defined (USE_OMX_TARGET_RPI) - DISPMANX_UPDATE_HANDLE_T dispman_update; -#endif - - if (state->fshader) { - glDeleteShader (state->fshader); - glDetachShader (state->program, state->fshader); - } - - if (state->vshader) { - glDeleteShader (state->vshader); - glDetachShader (state->program, state->vshader); - } - - if (state->program) - glDeleteProgram (state->program); - - if (state->tex) - glDeleteTextures (1, &state->tex); - - /* clear screen */ - glClear (GL_COLOR_BUFFER_BIT); - eglSwapBuffers (state->display, state->surface); - - /* Release OpenGL resources */ - eglMakeCurrent (state->display, EGL_NO_SURFACE, EGL_NO_SURFACE, - EGL_NO_CONTEXT); - eglDestroySurface (state->display, state->surface); - eglDestroyContext (state->display, state->context); - gst_object_unref (state->gl_context); - gst_object_unref (state->gst_display); - -#if defined (USE_OMX_TARGET_RPI) - dispman_update = vc_dispmanx_update_start (0); - vc_dispmanx_element_remove (dispman_update, state->dispman_element); - vc_dispmanx_update_submit_sync (dispman_update); - vc_dispmanx_display_close (state->dispman_display); -#elif defined(HAVE_X11) - XSync (state->xdisplay, FALSE); - XUnmapWindow (state->xdisplay, state->xwindow); - XDestroyWindow (state->xdisplay, state->xwindow); - XSync (state->xdisplay, FALSE); - XCloseDisplay (state->xdisplay); -#endif -} - -//============================================================================== - -static void -open_ogl (void) -{ - TRACE_VC_MEMORY ("state 0"); - -#if defined (USE_OMX_TARGET_RPI) - bcm_host_init (); - TRACE_VC_MEMORY ("after bcm_host_init"); -#endif - - /* Create surface and gl context */ - init_ogl (state); - TRACE_VC_MEMORY ("after init_ogl"); -} - -static gpointer -render_func (gpointer data) -{ - open_ogl (); - state->running = TRUE; - - do { - handle_queued_objects (state); - g_usleep (0); - } while (state->running == TRUE); - - close_ogl (); - return NULL; -} - -int -main (int argc, char **argv) -{ - GstBus *bus; - GOptionContext *ctx; - GIOChannel *io_stdin; - GError *err = NULL; - gboolean res; - GOptionEntry options[] = { - {NULL} - }; - GThread *rthread; - - /* Clear application state */ - memset (state, 0, sizeof (*state)); - state->animate = TRUE; - state->current_buffer = NULL; - state->caps = NULL; - - ctx = g_option_context_new ("[ADDITIONAL ARGUMENTS]"); - g_option_context_add_main_entries (ctx, options, NULL); - g_option_context_add_group (ctx, gst_init_get_option_group ()); - if (!g_option_context_parse (ctx, &argc, &argv, &err)) { - g_print ("Error initializing: %s\n", GST_STR_NULL (err->message)); - g_option_context_free (ctx); - g_clear_error (&err); - exit (1); - } - g_option_context_free (ctx); - - if (argc != 2) { - g_print ("Usage: %s or \n", argv[0]); - exit (1); - } - - /* Initialize GStreamer */ - gst_init (&argc, &argv); - - /* initialize inter thread comunnication */ - init_intercom (state); - - TRACE_VC_MEMORY ("state 0"); - - if (!(rthread = g_thread_new ("render", (GThreadFunc) render_func, NULL))) { - g_print ("Render thread create failed\n"); - exit (1); - } - - /* Initialize player */ - if (gst_uri_is_valid (argv[1])) { - res = init_playbin_player (state, argv[1]); - } else { - res = init_parse_launch_player (state, argv[1]); - } - - if (!res) - goto done; - - /* Create a GLib Main Loop */ - state->main_loop = g_main_loop_new (NULL, FALSE); - - /* Add a keyboard watch so we get notified of keystrokes */ - io_stdin = g_io_channel_unix_new (fileno (stdin)); - g_io_add_watch (io_stdin, G_IO_IN, (GIOFunc) handle_keyboard, state); - g_io_channel_unref (io_stdin); - - /* *INDENT-OFF* */ - g_print ("Available commands: \n" - " a - Toggle animation \n" - " p - Pause playback \n" - " r - Resume playback \n" - " l - Query position/duration\n" - " f - Seek 30 seconds forward \n" - " b - Seek 30 seconds backward \n" - " q - Quit \n"); - /* *INDENT-ON* */ - - /* Connect the bus handlers */ - bus = gst_element_get_bus (state->pipeline); - - gst_bus_set_sync_handler (bus, (GstBusSyncHandler) bus_sync_handler, state, - NULL); - - gst_bus_add_signal_watch_full (bus, G_PRIORITY_HIGH); - gst_bus_enable_sync_message_emission (bus); - - g_signal_connect (G_OBJECT (bus), "message::error", (GCallback) error_cb, - state); - g_signal_connect (G_OBJECT (bus), "message::buffering", - (GCallback) buffering_cb, state); - g_signal_connect (G_OBJECT (bus), "message::eos", (GCallback) eos_cb, state); - g_signal_connect (G_OBJECT (bus), "message::qos", (GCallback) qos_cb, state); - g_signal_connect (G_OBJECT (bus), "message::state-changed", - (GCallback) state_changed_cb, state); - gst_object_unref (bus); - - /* Make player start playing */ - gst_element_set_state (state->pipeline, GST_STATE_PLAYING); - - /* Start the mainloop */ - g_main_loop_run (state->main_loop); - -done: - /* Release pipeline */ - if (state->pipeline) { - gst_element_set_state (state->pipeline, GST_STATE_NULL); - if (state->vsink) { - gst_object_unref (state->vsink); - state->vsink = NULL; - } - - gst_object_unref (state->pipeline); - } - - /* Unref the mainloop */ - if (state->main_loop) { - g_main_loop_unref (state->main_loop); - } - - /* Stop rendering thread */ - state->running = FALSE; - g_thread_join (rthread); - - if (state->caps) { - gst_caps_unref (state->caps); - state->caps = NULL; - } - - terminate_intercom (state); - - TRACE_VC_MEMORY ("at exit"); - return 0; -} diff --git a/subprojects/gst-omx/examples/meson.build b/subprojects/gst-omx/examples/meson.build deleted file mode 100644 index edf22bec9b..0000000000 --- a/subprojects/gst-omx/examples/meson.build +++ /dev/null @@ -1,7 +0,0 @@ -if get_option('examples').disabled() or static_build or host_machine.system() == 'windows' - subdir_done() -endif - -if gstgl_dep.found() - subdir('egl') -endif diff --git a/subprojects/gst-omx/gst-omx.doap b/subprojects/gst-omx/gst-omx.doap deleted file mode 100644 index 5dd6a880c8..0000000000 --- a/subprojects/gst-omx/gst-omx.doap +++ /dev/null @@ -1,412 +0,0 @@ - - - GStreamer OpenMAX IL wrapper plugin - gst-omx - - 2005-06-17 - -a basic collection of elements - - - This plugin wraps available OpenMAX IL components and makes - them available as standard GStreamer elements. - - - - - - C - - - - - - - - - - - - - 1.22.0 - main - - 2023-01-23 - - - - - - - 1.21.90 - main - - 2023-01-13 - - - - - - - 1.21.3 - main - - 2022-12-05 - - - - - - - 1.21.2 - main - - 2022-11-07 - - - - - - - 1.21.1 - main - - 2022-10-04 - - - - - - - 1.20.0 - main - - 2022-02-03 - - - - - - - 1.19.90 - main - - 2022-01-28 - - - - - - - 1.19.3 - main - - 2021-11-03 - - - - - - - 1.19.2 - master - - 2021-09-23 - - - - - - - 1.19.1 - master - - 2021-06-01 - - - - - - - 1.18.0 - master - - 2020-09-08 - - - - - - - 1.17.90 - master - - 2020-08-20 - - - - - - - 1.17.2 - master - - 2020-07-03 - - - - - - - 1.17.1 - master - - 2020-06-19 - - - - - - - 1.16.0 - master - - 2019-04-19 - - - - - - - 1.15.90 - master - - 2019-04-11 - - - - - - - 1.15.2 - master - - 2019-02-26 - - - - - - - 1.15.1 - master - - 2019-01-17 - - - - - - - 1.14.0 - master - - 2018-03-19 - - - - - - - 1.13.91 - master - - 2018-03-13 - - - - - - - 1.13.90 - master - - 2018-03-03 - - - - - - - 1.13.1 - master - - 2018-02-15 - - - - - - - - 1.12.4 - 1.12 - - 2017-12-07 - - - - - - - 1.12.3 - 1.12 - - 2017-09-18 - - - - - - - 1.12.2 - 1.12 - - 2017-07-14 - - - - - - - 1.12.1 - 1.12 - - 2017-06-20 - - - - - - - 1.12.0 - master - - 2017-05-04 - - - - - - - 1.11.91 - master - - 2017-04-27 - - - - - - - 1.11.90 - master - - 2017-04-07 - - - - - - - 1.11.2 - master - - 2017-02-24 - - - - - - - 1.11.1 - master - - 2017-01-12 - - - - - - - 1.10.0 - master - - 2016-11-01 - - - - - - - 1.9.90 - master - - 2016-09-30 - - - - - - - 1.9.2 - master - - 2016-09-01 - - - - - - - 1.9.1 - master - - 2016-06-06 - - - - - - - 1.2.0 - 1.2 - - 2014-07-23 - - - - - - - 1.0.0 - 1.0 - - 2013-03-22 - - - - - - - Sebastian Dröge - 7c1069ea873ef7751e4eca5f1a42744b0e9a3a0a - - - - diff --git a/subprojects/gst-omx/meson.build b/subprojects/gst-omx/meson.build deleted file mode 100644 index cd06116a80..0000000000 --- a/subprojects/gst-omx/meson.build +++ /dev/null @@ -1,430 +0,0 @@ -project('gst-omx', 'c', - version : '1.23.0.1', - meson_version : '>= 0.62', - default_options : [ 'warning_level=1', - 'buildtype=debugoptimized' ]) - -gst_version = meson.project_version() -version_arr = gst_version.split('.') -gst_version_major = version_arr[0].to_int() -gst_version_minor = version_arr[1].to_int() -gst_version_micro = version_arr[2].to_int() - if version_arr.length() == 4 - gst_version_nano = version_arr[3].to_int() -else - gst_version_nano = 0 -endif - -glib_req = '>= 2.62.0' -gst_req = '>= @0@.@1@.0'.format(gst_version_major, gst_version_minor) -tizil_req = '>= 0.19.0' -api_version = '1.0' - -plugins_install_dir = '@0@/gstreamer-1.0'.format(get_option('libdir')) - -cc = meson.get_compiler('c') -static_build = get_option('default_library') == 'static' - - -if cc.get_id() == 'msvc' - msvc_args = [ - # Ignore several spurious warnings for things gstreamer does very commonly - # If a warning is completely useless and spammy, use '/wdXXXX' to suppress it - # If a warning is harmless but hard to fix, use '/woXXXX' so it's shown once - # NOTE: Only add warnings here if you are sure they're spurious - '/wd4018', # implicit signed/unsigned conversion - '/wd4146', # unary minus on unsigned (beware INT_MIN) - '/wd4244', # lossy type conversion (e.g. double -> int) - '/wd4305', # truncating type conversion (e.g. double -> float) - cc.get_supported_arguments(['/utf-8']), # set the input encoding to utf-8 - - # Enable some warnings on MSVC to match GCC/Clang behaviour - '/w14062', # enumerator 'identifier' in switch of enum 'enumeration' is not handled - '/w14101', # 'identifier' : unreferenced local variable - '/w14189', # 'identifier' : local variable is initialized but not referenced - ] - add_project_arguments(msvc_args, language: 'c') - # Disable SAFESEH with MSVC for plugins and libs that use external deps that - # are built with MinGW - noseh_link_args = ['/SAFESEH:NO'] -else - noseh_link_args = [] -endif - -# glib doesn't support unloading, which means that unloading and reloading -# any library that registers static types will fail -if cc.has_link_argument('-Wl,-z,nodelete') - add_project_link_arguments('-Wl,-z,nodelete', language: 'c') -endif - -cdata = configuration_data() -check_headers = [ -# ['HAVE_DLFCN_H', 'dlfcn.h'], -# ['HAVE_FCNTL_H', 'fcntl.h'], -# ['HAVE_INTTYPES_H', 'inttypes.h'], -# ['HAVE_MEMORY_H', 'memory.h'], -# ['HAVE_MSACM_H', 'msacm.h'], -# ['HAVE_PTHREAD_H', 'pthread.h'], -# ['HAVE_STDINT_H', 'stdint.h'], -# ['HAVE_STDLIB_H', 'stdlib.h'], -# ['HAVE_STRINGS_H', 'strings.h'], -# ['HAVE_STRING_H', 'string.h'], -# ['HAVE_SYS_PARAM_H', 'sys/param.h'], -# ['HAVE_SYS_SOCKET_H', 'sys/socket.h'], -# ['HAVE_SYS_STAT_H', 'sys/stat.h'], -# ['HAVE_SYS_TIME_H', 'sys/time.h'], -# ['HAVE_SYS_TYPES_H', 'sys/types.h'], -# ['HAVE_SYS_UTSNAME_H', 'sys/utsname.h'], -# ['HAVE_UNISTD_H', 'unistd.h'], -] - -foreach h : check_headers - if cc.has_header(h.get(1)) - cdata.set(h.get(0), 1) - endif -endforeach - -check_functions = [ -# check token HAVE_CPU_ALPHA -# check token HAVE_CPU_ARM -# check token HAVE_CPU_CRIS -# check token HAVE_CPU_CRISV32 -# check token HAVE_CPU_HPPA -# check token HAVE_CPU_I386 -# check token HAVE_CPU_IA64 -# check token HAVE_CPU_M68K -# check token HAVE_CPU_MIPS -# check token HAVE_CPU_PPC -# check token HAVE_CPU_PPC64 -# check token HAVE_CPU_S390 -# check token HAVE_CPU_SPARC -# check token HAVE_CPU_X86_64 -# ['HAVE_DCGETTEXT', 'dcgettext'], -# check token HAVE_EXPERIMENTAL -# check token HAVE_EXTERNAL -# ['HAVE_GETPAGESIZE', 'getpagesize'], -# check token HAVE_GETTEXT -] - -foreach f : check_functions - if cc.has_function(f.get(1)) - cdata.set(f.get(0), 1) - endif -endforeach - -#cdata.set('SIZEOF_CHAR', cc.sizeof('char')) -#cdata.set('SIZEOF_INT', cc.sizeof('int')) -#cdata.set('SIZEOF_LONG', cc.sizeof('long')) -#cdata.set('SIZEOF_SHORT', cc.sizeof('short')) -#cdata.set('SIZEOF_VOIDP', cc.sizeof('void*')) - -cdata.set('VERSION', '"@0@"'.format(gst_version)) -cdata.set('PACKAGE', '"gst-omx"') -cdata.set('PACKAGE_VERSION', '"@0@"'.format(gst_version)) -cdata.set('PACKAGE_BUGREPORT', '"https://gitlab.freedesktop.org/gstreamer/gst-omx/issues/new"') -cdata.set('PACKAGE_NAME', '"GStreamer OMX Plugins"') -cdata.set('GETTEXT_PACKAGE', '"gst-omx-1.0"') -cdata.set('GST_API_VERSION', '"@0@"'.format(api_version)) -cdata.set('GST_PACKAGE_NAME', '"GStreamer OpenMAX Plug-ins"') -cdata.set('GST_PACKAGE_ORIGIN', '"Unknown package origin"') -cdata.set('GST_LICENSE', '"LGPL"') -cdata.set('LIBDIR', '"@0@"'.format(get_option('libdir'))) - -# FIXME: This should be exposed as a configuration option -host_system = host_machine.system() -if host_system == 'linux' - cdata.set('DEFAULT_VIDEOSRC', '"v4l2src"') -elif host_system == 'osx' - cdata.set('DEFAULT_VIDEOSRC', '"avfvideosrc"') -else - cdata.set('DEFAULT_VIDEOSRC', '"videotestsrc"') -endif - -# Mandatory GST deps -gst_dep = dependency('gstreamer-1.0', version : gst_req, - fallback : ['gstreamer', 'gst_dep']) -gstbase_dep = dependency('gstreamer-base-1.0', version : gst_req, - fallback : ['gstreamer', 'gst_base_dep']) -gstcontroller_dep = dependency('gstreamer-controller-1.0', version : gst_req, - fallback : ['gstreamer', 'gst_controller_dep']) -gstallocators_dep = dependency('gstreamer-allocators-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'allocators_dep']) - -gstpbutils_dep = dependency('gstreamer-pbutils-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'pbutils_dep']) -gstaudio_dep = dependency('gstreamer-audio-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'audio_dep']) -gstfft_dep = dependency('gstreamer-fft-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'fft_dep']) -gsttag_dep = dependency('gstreamer-tag-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'tag_dep']) -gstvideo_dep = dependency('gstreamer-video-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'video_dep']) - -gstgl_dep = dependency('gstreamer-gl-1.0', version : gst_req, - fallback : ['gst-plugins-base', 'gstgl_dep'], required : false) - -x11_dep = dependency('x11', required : false) - -gstcheck_dep = dependency('gstreamer-check-1.0', version : gst_req, - required : get_option('tests'), - fallback : ['gstreamer', 'gst_check_dep']) - -libm = cc.find_library('m', required : false) -gmodule_dep = dependency('gmodule-no-export-2.0', version: glib_req) - -gst_omx_args = ['-DHAVE_CONFIG_H'] -configinc = include_directories('.') -omx_header_path = get_option('header_path') -if omx_header_path != '' - omx_inc = [] - gst_omx_args += ['-I' + omx_header_path] -else - omx_inc = include_directories (join_paths ('omx', 'openmax')) -endif - -default_omx_struct_packing = 0 -omx_target = get_option ('target') -if omx_target == 'generic' - cdata.set('USE_OMX_TARGET_GENERIC', 1) -elif omx_target == 'rpi' - cdata.set('USE_OMX_TARGET_RPI', 1) - cdata.set('OMX_SKIP64BIT', 1) - default_omx_struct_packing = 4 - - if gstgl_dep.found() - if gstgl_dep.type_name() == 'pkgconfig' - gl_winsys = gstgl_dep.get_variable('gl_winsys').split(' ') - gl_platforms = gstgl_dep.get_variable('gl_platforms').split(' ') - elif gstgl_dep.type_name() == 'internal' - # XXX assume gst-plugins-base was built with dispmanx and egl support - gl_winsys = ['dispmanx'] - gl_platforms = ['egl'] - else - error ('unreachable dependency type') - endif - - if not gl_winsys.contains('dispmanx') or not gl_platforms.contains ('egl') - gstgl_dep = dependency('', required : false) - endif - endif -elif omx_target == 'bellagio' - cdata.set('USE_OMX_TARGET_BELLAGIO', 1) -elif omx_target == 'zynqultrascaleplus' - cdata.set('USE_OMX_TARGET_ZYNQ_USCALE_PLUS', 1) - have_allegro_header = cc.has_header ( - 'OMX_Allegro.h', - args : gst_omx_args, - include_directories : [omx_inc]) - if not have_allegro_header - error ('Need Allegro OMX headers to build for Zynq UltraScale+. Use -Dheader_path option to specify the path of those headers.') - endif -elif omx_target == 'tizonia' - if omx_header_path != '' - warning('Ignoring -Dheader_path because path is in tizilheaders.pc') - endif - cdata.set('USE_OMX_TARGET_TIZONIA', 1) - tizil_dep = dependency('tizilheaders', version : tizil_req) - cdata.set('TIZONIA_LIBDIR', tizil_dep.get_variable('libdir')) - tizil_includedir = tizil_dep.get_variable('includedir') - gst_omx_args += ['-I' + tizil_includedir + '/tizonia'] - omx_inc = [] -else - error ('Unsupported omx target specified. Use the -Dtarget option') -endif - -message ('OMX target: ' + omx_target) - -extra_video_headers = '' -# Check for optional OpenMAX extension headers - -if cc.has_header ( - 'OMX_VideoExt.h', - args : gst_omx_args, - include_directories : [omx_inc]) - extra_video_headers += ''' -#include ''' - cdata.set ('HAVE_VIDEO_EXT', 1) -endif - -if cc.has_header ( - 'OMX_IndexExt.h', - args : gst_omx_args, - include_directories : [omx_inc]) - cdata.set ('HAVE_INDEX_EXT', 1) -endif - -if cc.has_header ( - 'OMX_ComponentExt.h', - args : gst_omx_args, - include_directories : [omx_inc]) - cdata.set ('HAVE_COMPONENT_EXT', 1) -endif - -if cc.has_header ( - 'OMX_CoreExt.h', - args : gst_omx_args) - cdata.set ('HAVE_CORE_EXT', 1) -endif - -if cc.has_header ( - 'OMX_AudioExt.h', - args : gst_omx_args) - cdata.set ('HAVE_AUDIO_EXT', 1) -endif - -if cc.has_header ( - 'OMX_IVCommonExt.h', - args : gst_omx_args) - cdata.set ('HAVE_IV_COMMON_EXT', 1) -endif - -if cc.has_header ( - 'OMX_ImageExt.h', - args : gst_omx_args) - cdata.set ('HAVE_IMAGE_EXT', 1) -endif - -if cc.has_header ( - 'OMX_OtherExt.h', - args : gst_omx_args) - cdata.set ('HAVE_OTHER_EXT', 1) -endif - -have_omx_vp8 = cc.has_header_symbol( - 'OMX_Video.h', - 'OMX_VIDEO_CodingVP8', - prefix : extra_video_headers, - args : gst_omx_args, - include_directories : [omx_inc]) -if have_omx_vp8 - cdata.set('HAVE_VP8', 1) -endif - -have_omx_theora = cc.has_header_symbol( - 'OMX_Video.h', - 'OMX_VIDEO_CodingTheora', - prefix : extra_video_headers, - args : gst_omx_args, - include_directories : [omx_inc]) -if have_omx_theora - cdata.set('HAVE_THEORA', 1) -endif - -have_omx_hevc = cc.has_header_symbol( - 'OMX_Video.h', - 'OMX_VIDEO_CodingHEVC', - prefix : extra_video_headers, - args : gst_omx_args, - include_directories : [omx_inc]) -if have_omx_hevc - cdata.set('HAVE_HEVC', 1) -endif - -if gstgl_dep.found() - cdata.set ('HAVE_GST_GL', 1) -endif - -if x11_dep.found() - cdata.set ('HAVE_X11', 1) -endif - -omx_struct_packing = get_option ('struct_packing').to_int() -if omx_struct_packing == 0 - omx_struct_packing = default_omx_struct_packing -endif -if omx_struct_packing != 0 - cdata.set('GST_OMX_STRUCT_PACKING', omx_struct_packing) -endif - -omx_conf_dir = join_paths (get_option ('prefix'), get_option ('sysconfdir'), 'xdg') -cdata.set_quoted('GST_OMX_CONFIG_DIR', omx_conf_dir) - -warning_flags = [ - '-Wmissing-declarations', - '-Wredundant-decls', - '-Wwrite-strings', - '-Winit-self', - '-Wmissing-include-dirs', - '-Wno-multichar', - '-Wvla', - '-Wpointer-arith', - '-Wundef', -] - -warning_c_flags = [ - '-Wmissing-prototypes', - '-Wold-style-definition', - '-Waggregate-return', -] - -have_cxx = add_languages('cpp', required : false) - -if have_cxx - cxx = meson.get_compiler('cpp') -endif - -foreach extra_arg : warning_flags - if cc.has_argument (extra_arg) - add_project_arguments([extra_arg], language: 'c') - endif - if have_cxx and cxx.has_argument (extra_arg) - add_project_arguments([extra_arg], language: 'cpp') - endif -endforeach - -foreach extra_arg : warning_c_flags - if cc.has_argument (extra_arg) - add_project_arguments([extra_arg], language: 'c') - endif -endforeach - -# Disable compiler warnings for unused variables and args if gst debug system is disabled -if gst_dep.type_name() == 'internal' - gst_debug_disabled = not subproject('gstreamer').get_variable('gst_debug') -else - # We can't check that in the case of subprojects as we won't - # be able to build against an internal dependency (which is not built yet) - gst_debug_disabled = cc.has_header_symbol('gst/gstconfig.h', 'GST_DISABLE_GST_DEBUG', dependencies: gst_dep) -endif - -if gst_debug_disabled - message('GStreamer debug system is disabled') - if cc.has_argument('-Wno-unused') - add_project_arguments('-Wno-unused', language: 'c') - endif - if have_cxx and cxx.has_argument ('-Wno-unused') - add_project_arguments('-Wno-unused', language: 'cpp') - endif -else - message('GStreamer debug system is enabled') -endif - -subdir('config') - -if not get_option('examples').disabled() - subdir('examples') -endif - -subdir('omx') - -if not get_option('tools').disabled() - subdir('tools') -endif - -subdir('tests') - -subdir('docs') - -# Set release date -if gst_version_nano == 0 - extract_release_date = find_program('scripts/extract-release-date-from-doap-file.py') - run_result = run_command(extract_release_date, gst_version, files('gst-omx.doap'), check: true) - release_date = run_result.stdout().strip() - cdata.set_quoted('GST_PACKAGE_RELEASE_DATETIME', release_date) - message('Package release date: ' + release_date) -endif - -configure_file(output: 'config.h', configuration: cdata) - -meson.add_dist_script('scripts/gen-changelog.py', meson.project_name(), '1.20.0', meson.project_version()) diff --git a/subprojects/gst-omx/meson_options.txt b/subprojects/gst-omx/meson_options.txt deleted file mode 100644 index e18beb25d8..0000000000 --- a/subprojects/gst-omx/meson_options.txt +++ /dev/null @@ -1,14 +0,0 @@ -option('header_path', type : 'string', value : '', - description : 'An extra include directory to find the OpenMax headers') -option('target', type : 'combo', - choices : ['none', 'generic', 'rpi', 'bellagio', 'tizonia', 'zynqultrascaleplus'], value : 'none', - description : 'The OMX platform to target') -option('struct_packing', type : 'combo', - choices : ['0', '1', '2', '4', '8'], value : '0', - description : 'Force OpenMAX struct packing') - -# Common feature options -option('examples', type : 'feature', value : 'auto', yield : true) -option('tests', type : 'feature', value : 'auto', yield : true) -option('tools', type : 'feature', value : 'auto', yield : true) -option('doc', type : 'feature', value : 'auto', yield : true) diff --git a/subprojects/gst-omx/omx/gstomx.c b/subprojects/gst-omx/omx/gstomx.c deleted file mode 100644 index 092ffa3fcf..0000000000 --- a/subprojects/gst-omx/omx/gstomx.c +++ /dev/null @@ -1,4179 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include - -#include "gstomx.h" -#include "gstomxmjpegdec.h" -#include "gstomxmpeg2videodec.h" -#include "gstomxmpeg4videodec.h" -#include "gstomxh264dec.h" -#include "gstomxh263dec.h" -#include "gstomxh265dec.h" -#include "gstomxvp8dec.h" -#include "gstomxtheoradec.h" -#include "gstomxwmvdec.h" -#include "gstomxmpeg4videoenc.h" -#include "gstomxh264enc.h" -#include "gstomxh263enc.h" -#include "gstomxh265enc.h" -#include "gstomxaacdec.h" -#include "gstomxmp3dec.h" -#include "gstomxmp3enc.h" -#include "gstomxaacenc.h" -#include "gstomxamrdec.h" -#include "gstomxanalogaudiosink.h" -#include "gstomxhdmiaudiosink.h" - -GST_DEBUG_CATEGORY (gstomx_debug); -#define GST_CAT_DEFAULT gstomx_debug - -GST_DEBUG_CATEGORY_STATIC (OMX_API_TRACE); - -/* Macros used to log result of OMX calls. Use the requested debug level if the - * operation succeeded and GST_LEVEL_ERROR if not. - * Don't consider OMX_ErrorNoMore as an error as it means we're done iterating. */ -#define DEBUG_IF_OK(obj,err,...) \ - GST_CAT_LEVEL_LOG (GST_CAT_DEFAULT, (err == OMX_ErrorNone || err == OMX_ErrorNoMore) ? GST_LEVEL_DEBUG : GST_LEVEL_ERROR, obj, __VA_ARGS__) -#define INFO_IF_OK(obj,err,...) \ - GST_CAT_LEVEL_LOG (GST_CAT_DEFAULT, (err == OMX_ErrorNone || err == OMX_ErrorNoMore) ? GST_LEVEL_INFO : GST_LEVEL_ERROR, obj, __VA_ARGS__) - -G_LOCK_DEFINE_STATIC (core_handles); -static GHashTable *core_handles; - -/* Cache used by gst_omx_buffer_flags_to_string() */ -G_LOCK_DEFINE_STATIC (buffer_flags_str); -static GHashTable *buffer_flags_str; - -GstOMXCore * -gst_omx_core_acquire (const gchar * filename) -{ - GstOMXCore *core; - - G_LOCK (core_handles); - if (!core_handles) - core_handles = - g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); - - core = g_hash_table_lookup (core_handles, filename); - if (!core) { - core = g_new0 (GstOMXCore, 1); - g_mutex_init (&core->lock); - core->user_count = 0; - g_hash_table_insert (core_handles, g_strdup (filename), core); - - /* Hack for the Broadcom OpenMAX IL implementation */ -#ifdef USE_OMX_TARGET_RPI - { -#else - if (g_str_has_suffix (filename, "vc/lib/libopenmaxil.so")) { -#endif - gchar *bcm_host_filename; - gchar *bcm_host_path; - GModule *bcm_host_module; - void (*bcm_host_init) (void); - - bcm_host_path = g_path_get_dirname (filename); - bcm_host_filename = - g_build_filename (bcm_host_path, "libbcm_host.so", NULL); - - bcm_host_module = - g_module_open (bcm_host_filename, - G_MODULE_BIND_LAZY | G_MODULE_BIND_LOCAL); - - g_free (bcm_host_filename); - g_free (bcm_host_path); - - if (!bcm_host_module) { - /* Retry without an absolute path */ - bcm_host_module = - g_module_open ("libbcm_host.so", - G_MODULE_BIND_LAZY | G_MODULE_BIND_LOCAL); - if (!bcm_host_module) { - GST_ERROR ("Failed to load libbcm_host.so"); - goto error; - } - } - - if (!g_module_symbol (bcm_host_module, "bcm_host_init", - (gpointer *) & bcm_host_init)) { - GST_ERROR ("Failed to load symbol 'bcm_host_init' from libbcm_host.so"); - goto error; - } - - bcm_host_init (); - } - - core->module = - g_module_open (filename, G_MODULE_BIND_LAZY | G_MODULE_BIND_LOCAL); - if (!core->module) - goto load_failed; - - if (!g_module_symbol (core->module, "OMX_Init", (gpointer *) & core->init)) - goto symbol_error; - if (!g_module_symbol (core->module, "OMX_Deinit", - (gpointer *) & core->deinit)) - goto symbol_error; - if (!g_module_symbol (core->module, "OMX_GetHandle", - (gpointer *) & core->get_handle)) - goto symbol_error; - if (!g_module_symbol (core->module, "OMX_FreeHandle", - (gpointer *) & core->free_handle)) - goto symbol_error; - if (!g_module_symbol (core->module, "OMX_SetupTunnel", - (gpointer *) & core->setup_tunnel)) - goto symbol_error; - - GST_DEBUG ("Successfully loaded core '%s'", filename); - } - - g_mutex_lock (&core->lock); - core->user_count++; - if (core->user_count == 1) { - OMX_ERRORTYPE err; - - err = core->init (); - if (err != OMX_ErrorNone) { - GST_ERROR ("Failed to initialize core '%s': 0x%08x", filename, err); - g_mutex_unlock (&core->lock); - goto error; - } - - GST_DEBUG ("Successfully initialized core '%s'", filename); - } - - g_mutex_unlock (&core->lock); - G_UNLOCK (core_handles); - - return core; - -load_failed: - { - GST_ERROR ("Failed to load module '%s': %s", filename, g_module_error ()); - goto error; - } -symbol_error: - { - GST_ERROR ("Failed to locate required OpenMAX symbol in '%s': %s", filename, - g_module_error ()); - g_module_close (core->module); - core->module = NULL; - goto error; - } -error: - { - g_hash_table_remove (core_handles, filename); - g_mutex_clear (&core->lock); - g_free (core); - - G_UNLOCK (core_handles); - - return NULL; - } -} - -void -gst_omx_core_release (GstOMXCore * core) -{ - g_return_if_fail (core != NULL); - - G_LOCK (core_handles); - - g_mutex_lock (&core->lock); - - GST_DEBUG ("Releasing core %p", core); - - core->user_count--; - if (core->user_count == 0) { - GST_DEBUG ("Deinit core %p", core); - core->deinit (); - - G_LOCK (buffer_flags_str); - g_clear_pointer (&buffer_flags_str, g_hash_table_unref); - G_UNLOCK (buffer_flags_str); - } - - g_mutex_unlock (&core->lock); - - G_UNLOCK (core_handles); -} - -/* NOTE: comp->messages_lock will be used */ -static void -gst_omx_component_flush_messages (GstOMXComponent * comp) -{ - GstOMXMessage *msg; - - g_mutex_lock (&comp->messages_lock); - while ((msg = g_queue_pop_head (&comp->messages))) { - g_free (msg); - } - g_mutex_unlock (&comp->messages_lock); -} - -static void -gst_omx_buffer_reset (GstOMXBuffer * buf) -{ - buf->omx_buf->nFlags = 0; - buf->omx_buf->nOffset = 0; - buf->omx_buf->nFilledLen = 0; - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, G_GUINT64_CONSTANT (0)); -} - -static void gst_omx_buffer_unmap (GstOMXBuffer * buffer); - -/* NOTE: Call with comp->lock, comp->messages_lock will be used */ -static void -gst_omx_component_handle_messages (GstOMXComponent * comp) -{ - GstOMXMessage *msg; - - g_mutex_lock (&comp->messages_lock); - while ((msg = g_queue_pop_head (&comp->messages))) { - g_mutex_unlock (&comp->messages_lock); - - switch (msg->type) { - case GST_OMX_MESSAGE_STATE_SET:{ - GST_INFO_OBJECT (comp->parent, "%s state change to %s finished", - comp->name, gst_omx_state_to_string (msg->content.state_set.state)); - comp->state = msg->content.state_set.state; - if (comp->state == comp->pending_state) - comp->pending_state = OMX_StateInvalid; - break; - } - case GST_OMX_MESSAGE_FLUSH:{ - GstOMXPort *port = NULL; - OMX_U32 index = msg->content.flush.port; - - port = gst_omx_component_get_port (comp, index); - if (!port) - break; - - GST_DEBUG_OBJECT (comp->parent, "%s port %u flushed", comp->name, - port->index); - - if (port->flushing) { - port->flushed = TRUE; - } else { - GST_ERROR_OBJECT (comp->parent, "%s port %u was not flushing", - comp->name, port->index); - } - - break; - } - case GST_OMX_MESSAGE_ERROR:{ - OMX_ERRORTYPE error = msg->content.error.error; - - if (error == OMX_ErrorNone) - break; - - GST_ERROR_OBJECT (comp->parent, "%s got error: %s (0x%08x)", comp->name, - gst_omx_error_to_string (error), error); - - /* We only set the first error ever from which - * we can't recover anymore. - */ - if (comp->last_error == OMX_ErrorNone) - comp->last_error = error; - g_cond_broadcast (&comp->messages_cond); - - break; - } - case GST_OMX_MESSAGE_PORT_ENABLE:{ - GstOMXPort *port = NULL; - OMX_U32 index = msg->content.port_enable.port; - OMX_BOOL enable = msg->content.port_enable.enable; - - port = gst_omx_component_get_port (comp, index); - if (!port) - break; - - GST_DEBUG_OBJECT (comp->parent, "%s port %u %s", comp->name, - port->index, (enable ? "enabled" : "disabled")); - - if (enable) - port->enabled_pending = FALSE; - else - port->disabled_pending = FALSE; - break; - } - case GST_OMX_MESSAGE_PORT_SETTINGS_CHANGED:{ - gint i, n; - OMX_U32 index = msg->content.port_settings_changed.port; - GList *outports = NULL, *l, *k; - - GST_DEBUG_OBJECT (comp->parent, "%s settings changed (port %u)", - comp->name, (guint) index); - - /* FIXME: This probably can be done better */ - - /* Now update the ports' states */ - n = (comp->ports ? comp->ports->len : 0); - for (i = 0; i < n; i++) { - GstOMXPort *port = g_ptr_array_index (comp->ports, i); - - if (index == OMX_ALL || index == port->index) { - port->settings_cookie++; - gst_omx_port_update_port_definition (port, NULL); - if (port->port_def.eDir == OMX_DirOutput && !port->tunneled) - outports = g_list_prepend (outports, port); - } - } - - for (k = outports; k; k = k->next) { - gboolean found = FALSE; - - for (l = comp->pending_reconfigure_outports; l; l = l->next) { - if (l->data == k->data) { - found = TRUE; - break; - } - } - - if (!found) - comp->pending_reconfigure_outports = - g_list_prepend (comp->pending_reconfigure_outports, k->data); - } - - g_list_free (outports); - - break; - } - case GST_OMX_MESSAGE_BUFFER_FLAG:{ - GstOMXPort *port = NULL; - OMX_U32 index = msg->content.buffer_flag.port; - OMX_U32 flags = msg->content.buffer_flag.flags; - - port = gst_omx_component_get_port (comp, index); - if (!port) - break; - - GST_DEBUG_OBJECT (comp->parent, - "%s port %u got buffer flags 0x%08x (%s)", comp->name, port->index, - (guint) flags, gst_omx_buffer_flags_to_string (flags)); - if ((flags & OMX_BUFFERFLAG_EOS) - && port->port_def.eDir == OMX_DirOutput && !port->eos) { - GST_DEBUG_OBJECT (comp->parent, "%s port %u is EOS", comp->name, - port->index); - port->eos = TRUE; - } - - break; - } - case GST_OMX_MESSAGE_BUFFER_DONE:{ - GstOMXBuffer *buf = msg->content.buffer_done.buffer->pAppPrivate; - GstOMXPort *port; - - port = buf->port; - - buf->used = FALSE; - - if (msg->content.buffer_done.empty) { - /* Input buffer is empty again and can be used to contain new input */ - GST_LOG_OBJECT (port->comp->parent, - "%s port %u emptied buffer %p (%p)", port->comp->name, - port->index, buf, buf->omx_buf->pBuffer); - - /* Reset all flags, some implementations don't - * reset them themselves and the flags are not - * valid anymore after the buffer was consumed - */ - gst_omx_buffer_reset (buf); - - /* Release and unmap the parent buffer, if any */ - gst_omx_buffer_unmap (buf); - } else { - /* Output buffer contains output now or - * the port was flushed */ - GST_LOG_OBJECT (port->comp->parent, - "%s port %u filled buffer %p (%p)", port->comp->name, port->index, - buf, buf->omx_buf->pBuffer); - - if ((buf->omx_buf->nFlags & OMX_BUFFERFLAG_EOS) - && port->port_def.eDir == OMX_DirOutput && !port->eos) { - GST_DEBUG_OBJECT (comp->parent, "%s port %u is EOS", comp->name, - port->index); - port->eos = TRUE; - } - } - - /* If an input port is managed by a pool, the buffer will be ready to be - * filled again once it's been released to the pool. */ - if (port->port_def.eDir == OMX_DirOutput || !port->using_pool) { - g_queue_push_tail (&port->pending_buffers, buf); - } - - break; - } - default:{ - g_assert_not_reached (); - break; - } - } - - g_free (msg); - - g_mutex_lock (&comp->messages_lock); - } - - g_mutex_unlock (&comp->messages_lock); -} - -/* NOTE: comp->messages_lock will be used */ -static void -gst_omx_component_send_message (GstOMXComponent * comp, GstOMXMessage * msg) -{ - g_mutex_lock (&comp->messages_lock); - if (msg) - g_queue_push_tail (&comp->messages, msg); - g_cond_broadcast (&comp->messages_cond); - g_mutex_unlock (&comp->messages_lock); -} - -/* NOTE: Call with comp->lock, comp->messages_lock will be used */ -static gboolean -gst_omx_component_wait_message (GstOMXComponent * comp, GstClockTime timeout) -{ - gboolean signalled; - gint64 wait_until = -1; - - if (timeout != GST_CLOCK_TIME_NONE) { - gint64 add = timeout / (GST_SECOND / G_TIME_SPAN_SECOND); - - if (add == 0) - return FALSE; - - wait_until = g_get_monotonic_time () + add; - GST_DEBUG_OBJECT (comp->parent, "%s waiting for %" G_GINT64_FORMAT "us", - comp->name, add); - } else { - GST_DEBUG_OBJECT (comp->parent, "%s waiting for signal", comp->name); - } - - g_mutex_lock (&comp->messages_lock); - g_mutex_unlock (&comp->lock); - - if (!g_queue_is_empty (&comp->messages)) { - signalled = TRUE; - } else if (timeout == GST_CLOCK_TIME_NONE) { - g_cond_wait (&comp->messages_cond, &comp->messages_lock); - signalled = TRUE; - } else { - signalled = - g_cond_wait_until (&comp->messages_cond, &comp->messages_lock, - wait_until); - } - - g_mutex_unlock (&comp->messages_lock); - g_mutex_lock (&comp->lock); - - return signalled; -} - -static const gchar * -omx_event_type_to_str (OMX_EVENTTYPE event) -{ - switch (event) { - case OMX_EventCmdComplete: - return "EventCmdComplete"; - case OMX_EventError: - return "EventError"; - case OMX_EventMark: - return "EventMark"; - case OMX_EventPortSettingsChanged: - return "EventPortSettingsChanged"; - case OMX_EventBufferFlag: - return "EventBufferFlag"; - case OMX_EventResourcesAcquired: - return "EventResourcesAcquired"; - case OMX_EventComponentResumed: - return "EventComponentResumed"; - case OMX_EventDynamicResourcesAvailable: - return "EventDynamicResourcesAvailable"; - case OMX_EventPortFormatDetected: - return "EventPortFormatDetected"; -#ifdef OMX_EventIndexSettingChanged - case OMX_EventIndexSettingChanged: - return "EventIndexSettingChanged"; -#endif -#ifdef OMX_EventPortNeedsDisable - case OMX_EventPortNeedsDisable: - return "EventPortNeedsDisable"; -#endif -#ifdef OMX_EventPortNeedsFlush - case OMX_EventPortNeedsFlush: - return "EventPortNeedsFlush"; -#endif - case OMX_EventKhronosExtensions: - case OMX_EventVendorStartUnused: - case OMX_EventMax: - default: - break; - } - - return NULL; -} - -/* See "Table 3-11: Event Parameter Usage" */ -static GstStructure * -omx_event_to_debug_struct (OMX_EVENTTYPE event, - guint32 data1, guint32 data2, gpointer event_data) -{ - const gchar *name; - - name = omx_event_type_to_str (event); - switch (event) { - case OMX_EventCmdComplete: - { - const gchar *cmd = gst_omx_command_to_string (data1); - - if (!cmd) - break; - - switch (data1) { - case OMX_CommandStateSet: - return gst_structure_new (name, - "command", G_TYPE_STRING, cmd, - "state-reached", G_TYPE_STRING, gst_omx_state_to_string (data2), - NULL); - case OMX_CommandFlush: - case OMX_CommandPortDisable: - case OMX_CommandPortEnable: - case OMX_CommandMarkBuffer: - return gst_structure_new (name, - "command", G_TYPE_STRING, cmd, "port", G_TYPE_UINT, data2, - "error", G_TYPE_STRING, - gst_omx_error_to_string (GPOINTER_TO_UINT (event_data)), NULL); - case OMX_CommandKhronosExtensions: - case OMX_CommandVendorStartUnused: - case OMX_CommandMax: - break; - } - } - break; - case OMX_EventError: - return gst_structure_new (name, "error", G_TYPE_STRING, - gst_omx_error_to_string (data1), "extra-info", G_TYPE_STRING, - gst_omx_error_to_string (data2), NULL); - case OMX_EventMark: - case OMX_EventComponentResumed: - case OMX_EventResourcesAcquired: - case OMX_EventDynamicResourcesAvailable: - case OMX_EventPortFormatDetected: - return gst_structure_new_empty (name); - case OMX_EventPortSettingsChanged: -#ifdef OMX_EventIndexSettingChanged - case OMX_EventIndexSettingChanged: -#endif -#ifdef OMX_EventPortNeedsDisable - case OMX_EventPortNeedsDisable: -#endif -#ifdef OMX_EventPortNeedsFlush - case OMX_EventPortNeedsFlush: -#endif - return gst_structure_new (name, "port", G_TYPE_UINT, - data1, "param-config", G_TYPE_UINT, data2, NULL); - case OMX_EventBufferFlag: - return gst_structure_new (name, "port", G_TYPE_UINT, - data1, "flags", G_TYPE_STRING, gst_omx_buffer_flags_to_string (data2), - NULL); - case OMX_EventKhronosExtensions: - case OMX_EventVendorStartUnused: - case OMX_EventMax: - default: - break; - } - - return NULL; -} - -static void -log_omx_api_trace_event (GstOMXComponent * comp, OMX_EVENTTYPE event, - guint32 data1, guint32 data2, gpointer event_data) -{ -#ifndef GST_DISABLE_GST_DEBUG - GstStructure *s; - - /* Don't bother creating useless structs if not needed */ - if (gst_debug_category_get_threshold (OMX_API_TRACE) < GST_LEVEL_DEBUG) - return; - - s = omx_event_to_debug_struct (event, data1, data2, event_data); - if (!s) { - GST_CAT_WARNING_OBJECT (OMX_API_TRACE, comp->parent, - "invalid event 0x%08x Data1 %u Data2 %u EventData %p", event, data1, - data2, event_data); - return; - } - - GST_CAT_DEBUG_OBJECT (OMX_API_TRACE, comp->parent, "%" GST_PTR_FORMAT, s); - - gst_structure_free (s); -#endif /* GST_DISABLE_GST_DEBUG */ -} - -static OMX_ERRORTYPE -EventHandler (OMX_HANDLETYPE hComponent, OMX_PTR pAppData, OMX_EVENTTYPE eEvent, - OMX_U32 nData1, OMX_U32 nData2, OMX_PTR pEventData) -{ - GstOMXComponent *comp = (GstOMXComponent *) pAppData; - - log_omx_api_trace_event (comp, eEvent, nData1, nData2, pEventData); - - switch (eEvent) { - case OMX_EventCmdComplete: - { - OMX_COMMANDTYPE cmd = (OMX_COMMANDTYPE) nData1; - - GST_DEBUG_OBJECT (comp->parent, "%s %s command complete (%d)", - comp->name, gst_omx_command_to_string (cmd), cmd); - - switch (cmd) { - case OMX_CommandStateSet:{ - GstOMXMessage *msg = g_new (GstOMXMessage, 1); - - msg->type = GST_OMX_MESSAGE_STATE_SET; - msg->content.state_set.state = nData2; - - GST_DEBUG_OBJECT (comp->parent, "%s state change to %s finished", - comp->name, - gst_omx_state_to_string (msg->content.state_set.state)); - - gst_omx_component_send_message (comp, msg); - break; - } - case OMX_CommandFlush:{ - GstOMXMessage *msg = g_new (GstOMXMessage, 1); - - msg->type = GST_OMX_MESSAGE_FLUSH; - msg->content.flush.port = nData2; - GST_DEBUG_OBJECT (comp->parent, "%s port %u flushed", comp->name, - (guint) msg->content.flush.port); - - gst_omx_component_send_message (comp, msg); - break; - } - case OMX_CommandPortEnable: - case OMX_CommandPortDisable:{ - GstOMXMessage *msg = g_new (GstOMXMessage, 1); - - msg->type = GST_OMX_MESSAGE_PORT_ENABLE; - msg->content.port_enable.port = nData2; - msg->content.port_enable.enable = (cmd == OMX_CommandPortEnable); - GST_DEBUG_OBJECT (comp->parent, "%s port %u %s", comp->name, - (guint) msg->content.port_enable.port, - (msg->content.port_enable.enable ? "enabled" : "disabled")); - - gst_omx_component_send_message (comp, msg); - break; - } - default: - break; - } - break; - } - case OMX_EventError: - { - GstOMXMessage *msg; - OMX_ERRORTYPE error_type = nData1; - - /* Yes, this really happens... */ - if (error_type == OMX_ErrorNone) - break; - - /* Always ignore PortUnpopulated error. This error is informational - * at best but it is useful for debugging some strange scenarios. - */ - if (error_type == OMX_ErrorPortUnpopulated) { - GST_DEBUG_OBJECT (comp->parent, "%s got error: %s (0x%08x)", - comp->name, gst_omx_error_to_string (error_type), error_type); - break; - } - - msg = g_new (GstOMXMessage, 1); - - msg->type = GST_OMX_MESSAGE_ERROR; - msg->content.error.error = error_type; - GST_ERROR_OBJECT (comp->parent, "%s got error: %s (0x%08x)", comp->name, - gst_omx_error_to_string (msg->content.error.error), - msg->content.error.error); - - gst_omx_component_send_message (comp, msg); - break; - } - case OMX_EventPortSettingsChanged: - { - GstOMXMessage *msg = g_new (GstOMXMessage, 1); - OMX_U32 index; - - if (!(comp->hacks & - GST_OMX_HACK_EVENT_PORT_SETTINGS_CHANGED_NDATA_PARAMETER_SWAP)) { - index = nData1; - } else { - index = nData2; - } - - - if (index == 0 - && (comp->hacks & - GST_OMX_HACK_EVENT_PORT_SETTINGS_CHANGED_PORT_0_TO_1)) - index = 1; - - - msg->type = GST_OMX_MESSAGE_PORT_SETTINGS_CHANGED; - msg->content.port_settings_changed.port = index; - GST_DEBUG_OBJECT (comp->parent, "%s settings changed (port index: %u)", - comp->name, (guint) msg->content.port_settings_changed.port); - - gst_omx_component_send_message (comp, msg); - break; - } - case OMX_EventBufferFlag:{ - GstOMXMessage *msg; - - msg = g_new (GstOMXMessage, 1); - - msg->type = GST_OMX_MESSAGE_BUFFER_FLAG; - msg->content.buffer_flag.port = nData1; - msg->content.buffer_flag.flags = nData2; - GST_DEBUG_OBJECT (comp->parent, "%s port %u got buffer flags 0x%08x (%s)", - comp->name, (guint) msg->content.buffer_flag.port, - (guint) msg->content.buffer_flag.flags, - gst_omx_buffer_flags_to_string (msg->content.buffer_flag.flags)); - - gst_omx_component_send_message (comp, msg); - break; - } - case OMX_EventPortFormatDetected: - default: - GST_DEBUG_OBJECT (comp->parent, "%s unknown event 0x%08x", comp->name, - eEvent); - break; - } - - return OMX_ErrorNone; -} - -static void -gst_omx_buffer_unmap (GstOMXBuffer * buffer) -{ - g_return_if_fail (buffer != NULL); - - if (buffer->input_frame_mapped) { - g_assert (!buffer->input_mem); - g_assert (!buffer->input_buffer); - g_assert (!buffer->input_buffer_mapped); - gst_video_frame_unmap (&buffer->input_frame); - buffer->input_frame_mapped = FALSE; - } else if (buffer->input_mem) { - g_assert (!buffer->input_buffer); - g_assert (!buffer->input_buffer_mapped); - gst_memory_unmap (buffer->input_mem, &buffer->map); - g_clear_pointer (&buffer->input_mem, gst_memory_unref); - } else if (buffer->input_buffer) { - if (buffer->input_buffer_mapped) - gst_buffer_unmap (buffer->input_buffer, &buffer->map); - buffer->input_buffer_mapped = FALSE; - g_clear_pointer (&buffer->input_buffer, gst_buffer_unref); - } -} - -static void -log_omx_api_trace_buffer (GstOMXComponent * comp, const gchar * event, - GstOMXBuffer * buf) -{ -#ifndef GST_DISABLE_GST_DEBUG - GstStructure *s; - - /* Don't bother creating useless structs if not needed */ - if (gst_debug_category_get_threshold (OMX_API_TRACE) < GST_LEVEL_TRACE) - return; - - if (buf) { - gchar *buf_str, *omx_buf_str, *pbuffer_str; - - /* GST_PTR_FORMAT won't serialize G_TYPE_POINTER fields so stringify pointers */ - buf_str = g_strdup_printf ("%p", buf); - omx_buf_str = g_strdup_printf ("%p", buf->omx_buf); - pbuffer_str = g_strdup_printf ("%p", buf->omx_buf->pBuffer); - - /* *INDENT-OFF* */ - s = gst_structure_new (event, - "GstOMXBuffer", G_TYPE_STRING, buf_str, - "OMX-buffer", G_TYPE_STRING, omx_buf_str, - "pBuffer", G_TYPE_STRING, pbuffer_str, - "TimeStamp", G_TYPE_UINT64, GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp), - "AllocLen", G_TYPE_UINT, buf->omx_buf->nAllocLen, - "FilledLen", G_TYPE_UINT, buf->omx_buf->nFilledLen, - "flags", G_TYPE_UINT, buf->omx_buf->nFlags, - "flags-str", G_TYPE_STRING, gst_omx_buffer_flags_to_string (buf->omx_buf->nFlags), - NULL); - /* *INDENT-ON* */ - - g_free (buf_str); - g_free (omx_buf_str); - g_free (pbuffer_str); - } else { - s = gst_structure_new_empty (event); - } - - GST_CAT_TRACE_OBJECT (OMX_API_TRACE, comp->parent, "%" GST_PTR_FORMAT, s); - - gst_structure_free (s); -#endif /* GST_DISABLE_GST_DEBUG */ -} - -static OMX_ERRORTYPE -EmptyBufferDone (OMX_HANDLETYPE hComponent, OMX_PTR pAppData, - OMX_BUFFERHEADERTYPE * pBuffer) -{ - GstOMXBuffer *buf; - GstOMXComponent *comp; - GstOMXMessage *msg; - - buf = pBuffer->pAppPrivate; - if (!buf) { - GST_ERROR ("Have unknown or deallocated buffer %p", pBuffer); - return OMX_ErrorNone; - } - - g_assert (buf->omx_buf == pBuffer); - - if (buf->port->tunneled) { - GST_ERROR ("EmptyBufferDone on tunneled port"); - return OMX_ErrorBadParameter; - } - - comp = buf->port->comp; - - msg = g_new (GstOMXMessage, 1); - msg->type = GST_OMX_MESSAGE_BUFFER_DONE; - msg->content.buffer_done.component = hComponent; - msg->content.buffer_done.app_data = pAppData; - msg->content.buffer_done.buffer = pBuffer; - msg->content.buffer_done.empty = OMX_TRUE; - - log_omx_api_trace_buffer (comp, "EmptyBufferDone", buf); - GST_LOG_OBJECT (comp->parent, "%s port %u emptied buffer %p (%p)", - comp->name, buf->port->index, buf, buf->omx_buf->pBuffer); - - gst_omx_component_send_message (comp, msg); - - return OMX_ErrorNone; -} - -static OMX_ERRORTYPE -FillBufferDone (OMX_HANDLETYPE hComponent, OMX_PTR pAppData, - OMX_BUFFERHEADERTYPE * pBuffer) -{ - GstOMXBuffer *buf; - GstOMXComponent *comp; - GstOMXMessage *msg; - - buf = pBuffer->pAppPrivate; - if (!buf) { - GST_ERROR ("Have unknown or deallocated buffer %p", pBuffer); - return OMX_ErrorNone; - } - - g_assert (buf->omx_buf == pBuffer); - - if (buf->port->tunneled) { - GST_ERROR ("FillBufferDone on tunneled port"); - return OMX_ErrorBadParameter; - } - - comp = buf->port->comp; - - msg = g_new (GstOMXMessage, 1); - msg->type = GST_OMX_MESSAGE_BUFFER_DONE; - msg->content.buffer_done.component = hComponent; - msg->content.buffer_done.app_data = pAppData; - msg->content.buffer_done.buffer = pBuffer; - msg->content.buffer_done.empty = OMX_FALSE; - - log_omx_api_trace_buffer (comp, "FillBufferDone", buf); - GST_LOG_OBJECT (comp->parent, "%s port %u filled buffer %p (%p)", comp->name, - buf->port->index, buf, buf->omx_buf->pBuffer); - - gst_omx_component_send_message (comp, msg); - - return OMX_ErrorNone; -} - -static OMX_CALLBACKTYPE callbacks = - { EventHandler, EmptyBufferDone, FillBufferDone }; - -GST_DEFINE_MINI_OBJECT_TYPE (GstOMXComponent, gst_omx_component); - -static void gst_omx_component_free (GstOMXComponent * comp); - -/* NOTE: Uses comp->lock and comp->messages_lock */ -GstOMXComponent * -gst_omx_component_new (GstObject * parent, const gchar * core_name, - const gchar * component_name, const gchar * component_role, guint64 hacks) -{ - OMX_ERRORTYPE err; - GstOMXCore *core; - GstOMXComponent *comp; - const gchar *dot; - - core = gst_omx_core_acquire (core_name); - if (!core) - return NULL; - - comp = g_new0 (GstOMXComponent, 1); - comp->core = core; - - gst_mini_object_init (GST_MINI_OBJECT_CAST (comp), 0, - gst_omx_component_get_type (), NULL, NULL, - (GstMiniObjectFreeFunction) gst_omx_component_free); - - if ((dot = g_strrstr (component_name, "."))) - comp->name = g_strdup (dot + 1); - else - comp->name = g_strdup (component_name); - - err = - core->get_handle (&comp->handle, (OMX_STRING) component_name, comp, - &callbacks); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (parent, - "Failed to get component handle '%s' from core '%s': 0x%08x", - component_name, core_name, err); - gst_omx_core_release (core); - g_free (comp->name); - g_free (comp); - return NULL; - } - GST_DEBUG_OBJECT (parent, - "Successfully got component handle %p (%s) from core '%s'", comp->handle, - component_name, core_name); - comp->parent = gst_object_ref (parent); - comp->hacks = hacks; - - comp->ports = g_ptr_array_new (); - comp->n_in_ports = 0; - comp->n_out_ports = 0; - - g_mutex_init (&comp->lock); - g_mutex_init (&comp->messages_lock); - g_cond_init (&comp->messages_cond); - - g_queue_init (&comp->messages); - comp->pending_state = OMX_StateInvalid; - comp->last_error = OMX_ErrorNone; - - /* Set component role if any */ - if (component_role && !(hacks & GST_OMX_HACK_NO_COMPONENT_ROLE)) { - OMX_PARAM_COMPONENTROLETYPE param; - - GST_OMX_INIT_STRUCT (¶m); - - g_strlcpy ((gchar *) param.cRole, component_role, sizeof (param.cRole)); - err = - gst_omx_component_set_parameter (comp, - OMX_IndexParamStandardComponentRole, ¶m); - - DEBUG_IF_OK (comp->parent, err, - "Setting component role to '%s': %s (0x%08x)", component_role, - gst_omx_error_to_string (err), err); - - /* If setting the role failed this component is unusable */ - if (err != OMX_ErrorNone) { - gst_omx_component_free (comp); - return NULL; - } - } - - OMX_GetState (comp->handle, &comp->state); - - g_mutex_lock (&comp->lock); - gst_omx_component_handle_messages (comp); - g_mutex_unlock (&comp->lock); - - return comp; -} - -/* NOTE: Uses comp->messages_lock */ -static void -gst_omx_component_free (GstOMXComponent * comp) -{ - gint i, n; - - g_return_if_fail (comp != NULL); - - GST_INFO_OBJECT (comp->parent, "Unloading component %p %s", comp, comp->name); - - if (comp->ports) { - n = comp->ports->len; - for (i = 0; i < n; i++) { - GstOMXPort *port = g_ptr_array_index (comp->ports, i); - - gst_omx_port_deallocate_buffers (port); - g_assert (port->buffers == NULL); - g_assert (g_queue_get_length (&port->pending_buffers) == 0); - - g_free (port); - } - g_ptr_array_unref (comp->ports); - comp->ports = NULL; - } - - comp->core->free_handle (comp->handle); - gst_omx_core_release (comp->core); - - gst_omx_component_flush_messages (comp); - - g_cond_clear (&comp->messages_cond); - g_mutex_clear (&comp->messages_lock); - g_mutex_clear (&comp->lock); - - gst_object_unref (comp->parent); - - g_free (comp->name); - comp->name = NULL; - - g_free (comp); -} - -GstOMXComponent * -gst_omx_component_ref (GstOMXComponent * comp) -{ - g_return_val_if_fail (comp, NULL); - - gst_mini_object_ref (GST_MINI_OBJECT_CAST (comp)); - return comp; -} - -void -gst_omx_component_unref (GstOMXComponent * comp) -{ - g_return_if_fail (comp); - - gst_mini_object_unref (GST_MINI_OBJECT_CAST (comp)); -} - -static GstStructure * -omx_command_to_debug_struct (OMX_COMMANDTYPE cmd, - guint32 param, gpointer cmd_data) -{ - const gchar *cmd_str; - - cmd_str = gst_omx_command_to_string (cmd); - - switch (cmd) { - case OMX_CommandStateSet: - return gst_structure_new ("SendCommand", - "command", G_TYPE_STRING, cmd_str, - "state", G_TYPE_STRING, gst_omx_state_to_string (param), NULL); - case OMX_CommandFlush: - case OMX_CommandPortDisable: - case OMX_CommandPortEnable: - return gst_structure_new ("SendCommand", - "command", G_TYPE_STRING, cmd_str, "port", G_TYPE_UINT, param, NULL); - case OMX_CommandMarkBuffer: - return gst_structure_new ("SendCommand", - "command", G_TYPE_STRING, cmd_str, - "mark-type", G_TYPE_POINTER, cmd_data, NULL); - case OMX_CommandKhronosExtensions: - case OMX_CommandVendorStartUnused: - case OMX_CommandMax: - default: - break; - } - - return NULL; -} - -static void -log_omx_api_trace_send_command (GstOMXComponent * comp, OMX_COMMANDTYPE cmd, - guint32 param, gpointer cmd_data) -{ -#ifndef GST_DISABLE_GST_DEBUG - GstStructure *s; - - /* Don't bother creating useless structs if not needed */ - if (gst_debug_category_get_threshold (OMX_API_TRACE) < GST_LEVEL_DEBUG) - return; - - s = omx_command_to_debug_struct (cmd, param, cmd_data); - if (!s) { - GST_CAT_WARNING_OBJECT (OMX_API_TRACE, comp->parent, - "invalid command 0x%08x Param %u CmdData %p", cmd, param, cmd_data); - return; - } - - GST_CAT_DEBUG_OBJECT (OMX_API_TRACE, comp->parent, "%" GST_PTR_FORMAT, s); - - gst_structure_free (s); -#endif /* GST_DISABLE_GST_DEBUG */ -} - -static OMX_ERRORTYPE -gst_omx_component_send_command (GstOMXComponent * comp, OMX_COMMANDTYPE cmd, - guint32 param, gpointer cmd_data) -{ - OMX_ERRORTYPE err; - - log_omx_api_trace_send_command (comp, cmd, param, cmd_data); - err = OMX_SendCommand (comp->handle, cmd, param, cmd_data); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_component_set_state (GstOMXComponent * comp, OMX_STATETYPE state) -{ - OMX_STATETYPE old_state; - OMX_ERRORTYPE err = OMX_ErrorNone; - - g_return_val_if_fail (comp != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&comp->lock); - - gst_omx_component_handle_messages (comp); - - old_state = comp->state; - GST_INFO_OBJECT (comp->parent, "Setting %s state from %s to %s", comp->name, - gst_omx_state_to_string (old_state), gst_omx_state_to_string (state)); - - if ((err = comp->last_error) != OMX_ErrorNone && state > old_state) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - if (old_state == state || comp->pending_state == state) { - GST_DEBUG_OBJECT (comp->parent, "Component %s already in state %s", - comp->name, gst_omx_state_to_string (state)); - goto done; - } - - comp->pending_state = state; - - /* Reset some things */ - if ((old_state == OMX_StateExecuting || old_state == OMX_StatePause) - && state < old_state) { - g_list_free (comp->pending_reconfigure_outports); - comp->pending_reconfigure_outports = NULL; - /* Notify all inports that are still waiting */ - gst_omx_component_send_message (comp, NULL); - } - - err = gst_omx_component_send_command (comp, OMX_CommandStateSet, state, NULL); - /* No need to check if anything has changed here */ - -done: - - gst_omx_component_handle_messages (comp); - - if (err != OMX_ErrorNone && comp->last_error == OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Last operation returned an error. Setting last_error manually."); - comp->last_error = err; - } - - g_mutex_unlock (&comp->lock); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Error setting %s state from %s to %s: %s (0x%08x)", comp->name, - gst_omx_state_to_string (old_state), gst_omx_state_to_string (state), - gst_omx_error_to_string (err), err); - } - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_STATETYPE -gst_omx_component_get_state (GstOMXComponent * comp, GstClockTime timeout) -{ - OMX_STATETYPE ret; - gboolean signalled = TRUE; - - g_return_val_if_fail (comp != NULL, OMX_StateInvalid); - - GST_DEBUG_OBJECT (comp->parent, "Getting state of %s", comp->name); - - g_mutex_lock (&comp->lock); - - gst_omx_component_handle_messages (comp); - - if (comp->last_error != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (comp->last_error), - comp->last_error); - ret = OMX_StateInvalid; - goto done; - } - - ret = comp->state; - if (comp->pending_state == OMX_StateInvalid) - goto done; - - while (signalled && comp->last_error == OMX_ErrorNone - && comp->pending_state != OMX_StateInvalid) { - - signalled = gst_omx_component_wait_message (comp, timeout); - if (signalled) - gst_omx_component_handle_messages (comp); - }; - - if (signalled) { - if (comp->last_error != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "%s got error while waiting for state change: %s (0x%08x)", - comp->name, gst_omx_error_to_string (comp->last_error), - comp->last_error); - ret = OMX_StateInvalid; - } else if (comp->pending_state == OMX_StateInvalid) { - /* State change finished and everything's fine */ - ret = comp->state; - } else { - ret = OMX_StateInvalid; - g_assert_not_reached (); - } - } else { - ret = OMX_StateInvalid; - GST_WARNING_OBJECT (comp->parent, "%s timeout while waiting for state " - "change", comp->name); - } - -done: - g_mutex_unlock (&comp->lock); - - GST_DEBUG_OBJECT (comp->parent, "%s returning state %s", comp->name, - gst_omx_state_to_string (ret)); - - return ret; -} - -GstOMXPort * -gst_omx_component_add_port (GstOMXComponent * comp, guint32 index) -{ - gint i, n; - GstOMXPort *port; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_ERRORTYPE err; - - g_return_val_if_fail (comp != NULL, NULL); - - /* Check if this port exists already */ - n = comp->ports->len; - for (i = 0; i < n; i++) { - port = g_ptr_array_index (comp->ports, i); - g_return_val_if_fail (port->index != index, NULL); - } - - GST_DEBUG_OBJECT (comp->parent, "%s adding port %u", comp->name, index); - - GST_OMX_INIT_STRUCT (&port_def); - port_def.nPortIndex = index; - - err = gst_omx_component_get_parameter (comp, OMX_IndexParamPortDefinition, - &port_def); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "%s failed to add port %u: %s (0x%08x)", - comp->name, index, gst_omx_error_to_string (err), err); - return NULL; - } - - port = g_new0 (GstOMXPort, 1); - port->comp = comp; - port->index = index; - - port->tunneled = FALSE; - - port->port_def = port_def; - - g_queue_init (&port->pending_buffers); - port->flushing = TRUE; - port->flushed = FALSE; - port->enabled_pending = FALSE; - port->disabled_pending = FALSE; - port->eos = FALSE; - port->using_pool = FALSE; - - if (port->port_def.eDir == OMX_DirInput) - comp->n_in_ports++; - else - comp->n_out_ports++; - - g_ptr_array_add (comp->ports, port); - - return port; -} - -GstOMXPort * -gst_omx_component_get_port (GstOMXComponent * comp, guint32 index) -{ - gint i, n; - - n = comp->ports->len; - for (i = 0; i < n; i++) { - GstOMXPort *tmp = g_ptr_array_index (comp->ports, i); - - if (tmp->index == index) - return tmp; - } - return NULL; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_component_get_last_error (GstOMXComponent * comp) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (comp != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&comp->lock); - gst_omx_component_handle_messages (comp); - err = comp->last_error; - g_mutex_unlock (&comp->lock); - - GST_DEBUG_OBJECT (comp->parent, "Returning last %s error: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - - return err; -} - -const gchar * -gst_omx_component_get_last_error_string (GstOMXComponent * comp) -{ - g_return_val_if_fail (comp != NULL, NULL); - - return gst_omx_error_to_string (gst_omx_component_get_last_error (comp)); -} - -#ifndef GST_DISABLE_GST_DEBUG -static const gchar * -omx_index_type_to_str (OMX_INDEXTYPE index) -{ - switch (index) { - case OMX_IndexComponentStartUnused: - return "OMX_IndexComponentStartUnused"; - case OMX_IndexParamPriorityMgmt: - return "OMX_IndexParamPriorityMgmt"; - case OMX_IndexParamAudioInit: - return "OMX_IndexParamAudioInit"; - case OMX_IndexParamImageInit: - return "OMX_IndexParamImageInit"; - case OMX_IndexParamVideoInit: - return "OMX_IndexParamVideoInit"; - case OMX_IndexParamOtherInit: - return "OMX_IndexParamOtherInit"; - case OMX_IndexParamNumAvailableStreams: - return "OMX_IndexParamNumAvailableStreams"; - case OMX_IndexParamActiveStream: - return "OMX_IndexParamActiveStream"; - case OMX_IndexParamSuspensionPolicy: - return "OMX_IndexParamSuspensionPolicy"; - case OMX_IndexParamComponentSuspended: - return "OMX_IndexParamComponentSuspended"; - case OMX_IndexConfigCapturing: - return "OMX_IndexConfigCapturing"; - case OMX_IndexConfigCaptureMode: - return "OMX_IndexConfigCaptureMode"; - case OMX_IndexAutoPauseAfterCapture: - return "OMX_IndexAutoPauseAfterCapture"; - case OMX_IndexParamContentURI: - return "OMX_IndexParamContentURI"; - case OMX_IndexParamDisableResourceConcealment: - return "OMX_IndexParamDisableResourceConcealment"; - case OMX_IndexConfigMetadataItemCount: - return "OMX_IndexConfigMetadataItemCount"; - case OMX_IndexConfigContainerNodeCount: - return "OMX_IndexConfigContainerNodeCount"; - case OMX_IndexConfigMetadataItem: - return "OMX_IndexConfigMetadataItem"; - case OMX_IndexConfigCounterNodeID: - return "OMX_IndexConfigCounterNodeID"; - case OMX_IndexParamMetadataFilterType: - return "OMX_IndexParamMetadataFilterType"; - case OMX_IndexParamMetadataKeyFilter: - return "OMX_IndexParamMetadataKeyFilter"; - case OMX_IndexConfigPriorityMgmt: - return "OMX_IndexConfigPriorityMgmt"; - case OMX_IndexParamStandardComponentRole: - return "OMX_IndexParamStandardComponentRole"; - case OMX_IndexPortStartUnused: - return "OMX_IndexPortStartUnused"; - case OMX_IndexParamPortDefinition: - return "OMX_IndexParamPortDefinition"; - case OMX_IndexParamCompBufferSupplier: - return "OMX_IndexParamCompBufferSupplier"; - case OMX_IndexReservedStartUnused: - return "OMX_IndexReservedStartUnused"; - case OMX_IndexAudioStartUnused: - return "OMX_IndexAudioStartUnused"; - case OMX_IndexParamAudioPortFormat: - return "OMX_IndexParamAudioPortFormat"; - case OMX_IndexParamAudioPcm: - return "OMX_IndexParamAudioPcm"; - case OMX_IndexParamAudioAac: - return "OMX_IndexParamAudioAac"; - case OMX_IndexParamAudioRa: - return "OMX_IndexParamAudioRa"; - case OMX_IndexParamAudioMp3: - return "OMX_IndexParamAudioMp3"; - case OMX_IndexParamAudioAdpcm: - return "OMX_IndexParamAudioAdpcm"; - case OMX_IndexParamAudioG723: - return "OMX_IndexParamAudioG723"; - case OMX_IndexParamAudioG729: - return "OMX_IndexParamAudioG729"; - case OMX_IndexParamAudioAmr: - return "OMX_IndexParamAudioAmr"; - case OMX_IndexParamAudioWma: - return "OMX_IndexParamAudioWma"; - case OMX_IndexParamAudioSbc: - return "OMX_IndexParamAudioSbc"; - case OMX_IndexParamAudioMidi: - return "OMX_IndexParamAudioMidi"; - case OMX_IndexParamAudioGsm_FR: - return "OMX_IndexParamAudioGsm_FR"; - case OMX_IndexParamAudioMidiLoadUserSound: - return "OMX_IndexParamAudioMidiLoadUserSound"; - case OMX_IndexParamAudioG726: - return "OMX_IndexParamAudioG726"; - case OMX_IndexParamAudioGsm_EFR: - return "OMX_IndexParamAudioGsm_EFR"; - case OMX_IndexParamAudioGsm_HR: - return "OMX_IndexParamAudioGsm_HR"; - case OMX_IndexParamAudioPdc_FR: - return "OMX_IndexParamAudioPdc_FR"; - case OMX_IndexParamAudioPdc_EFR: - return "OMX_IndexParamAudioPdc_EFR"; - case OMX_IndexParamAudioPdc_HR: - return "OMX_IndexParamAudioPdc_HR"; - case OMX_IndexParamAudioTdma_FR: - return "OMX_IndexParamAudioTdma_FR"; - case OMX_IndexParamAudioTdma_EFR: - return "OMX_IndexParamAudioTdma_EFR"; - case OMX_IndexParamAudioQcelp8: - return "OMX_IndexParamAudioQcelp8"; - case OMX_IndexParamAudioQcelp13: - return "OMX_IndexParamAudioQcelp13"; - case OMX_IndexParamAudioEvrc: - return "OMX_IndexParamAudioEvrc"; - case OMX_IndexParamAudioSmv: - return "OMX_IndexParamAudioSmv"; - case OMX_IndexParamAudioVorbis: - return "OMX_IndexParamAudioVorbis"; - case OMX_IndexConfigAudioMidiImmediateEvent: - return "OMX_IndexConfigAudioMidiImmediateEvent"; - case OMX_IndexConfigAudioMidiControl: - return "OMX_IndexConfigAudioMidiControl"; - case OMX_IndexConfigAudioMidiSoundBankProgram: - return "OMX_IndexConfigAudioMidiSoundBankProgram"; - case OMX_IndexConfigAudioMidiStatus: - return "OMX_IndexConfigAudioMidiStatus"; - case OMX_IndexConfigAudioMidiMetaEvent: - return "OMX_IndexConfigAudioMidiMetaEvent"; - case OMX_IndexConfigAudioMidiMetaEventData: - return "OMX_IndexConfigAudioMidiMetaEventData"; - case OMX_IndexConfigAudioVolume: - return "OMX_IndexConfigAudioVolume"; - case OMX_IndexConfigAudioBalance: - return "OMX_IndexConfigAudioBalance"; - case OMX_IndexConfigAudioChannelMute: - return "OMX_IndexConfigAudioChannelMute"; - case OMX_IndexConfigAudioMute: - return "OMX_IndexConfigAudioMute"; - case OMX_IndexConfigAudioLoudness: - return "OMX_IndexConfigAudioLoudness"; - case OMX_IndexConfigAudioEchoCancelation: - return "OMX_IndexConfigAudioEchoCancelation"; - case OMX_IndexConfigAudioNoiseReduction: - return "OMX_IndexConfigAudioNoiseReduction"; - case OMX_IndexConfigAudioBass: - return "OMX_IndexConfigAudioBass"; - case OMX_IndexConfigAudioTreble: - return "OMX_IndexConfigAudioTreble"; - case OMX_IndexConfigAudioStereoWidening: - return "OMX_IndexConfigAudioStereoWidening"; - case OMX_IndexConfigAudioChorus: - return "OMX_IndexConfigAudioChorus"; - case OMX_IndexConfigAudioEqualizer: - return "OMX_IndexConfigAudioEqualizer"; - case OMX_IndexConfigAudioReverberation: - return "OMX_IndexConfigAudioReverberation"; - case OMX_IndexConfigAudioChannelVolume: - return "OMX_IndexConfigAudioChannelVolume"; - case OMX_IndexImageStartUnused: - return "OMX_IndexImageStartUnused"; - case OMX_IndexParamImagePortFormat: - return "OMX_IndexParamImagePortFormat"; - case OMX_IndexParamFlashControl: - return "OMX_IndexParamFlashControl"; - case OMX_IndexConfigFocusControl: - return "OMX_IndexConfigFocusControl"; - case OMX_IndexParamQFactor: - return "OMX_IndexParamQFactor"; - case OMX_IndexParamQuantizationTable: - return "OMX_IndexParamQuantizationTable"; - case OMX_IndexParamHuffmanTable: - return "OMX_IndexParamHuffmanTable"; - case OMX_IndexConfigFlashControl: - return "OMX_IndexConfigFlashControl"; - case OMX_IndexVideoStartUnused: - return "OMX_IndexVideoStartUnused"; - case OMX_IndexParamVideoPortFormat: - return "OMX_IndexParamVideoPortFormat"; - case OMX_IndexParamVideoQuantization: - return "OMX_IndexParamVideoQuantization"; - case OMX_IndexParamVideoFastUpdate: - return "OMX_IndexParamVideoFastUpdate"; - case OMX_IndexParamVideoBitrate: - return "OMX_IndexParamVideoBitrate"; - case OMX_IndexParamVideoMotionVector: - return "OMX_IndexParamVideoMotionVector"; - case OMX_IndexParamVideoIntraRefresh: - return "OMX_IndexParamVideoIntraRefresh"; - case OMX_IndexParamVideoErrorCorrection: - return "OMX_IndexParamVideoErrorCorrection"; - case OMX_IndexParamVideoVBSMC: - return "OMX_IndexParamVideoVBSMC"; - case OMX_IndexParamVideoMpeg2: - return "OMX_IndexParamVideoMpeg2"; - case OMX_IndexParamVideoMpeg4: - return "OMX_IndexParamVideoMpeg4"; - case OMX_IndexParamVideoWmv: - return "OMX_IndexParamVideoWmv"; - case OMX_IndexParamVideoRv: - return "OMX_IndexParamVideoRv"; - case OMX_IndexParamVideoAvc: - return "OMX_IndexParamVideoAvc"; - case OMX_IndexParamVideoH263: - return "OMX_IndexParamVideoH263"; - case OMX_IndexParamVideoProfileLevelQuerySupported: - return "OMX_IndexParamVideoProfileLevelQuerySupported"; - case OMX_IndexParamVideoProfileLevelCurrent: - return "OMX_IndexParamVideoProfileLevelCurrent"; - case OMX_IndexConfigVideoBitrate: - return "OMX_IndexConfigVideoBitrate"; - case OMX_IndexConfigVideoFramerate: - return "OMX_IndexConfigVideoFramerate"; - case OMX_IndexConfigVideoIntraVOPRefresh: - return "OMX_IndexConfigVideoIntraVOPRefresh"; - case OMX_IndexConfigVideoIntraMBRefresh: - return "OMX_IndexConfigVideoIntraMBRefresh"; - case OMX_IndexConfigVideoMBErrorReporting: - return "OMX_IndexConfigVideoMBErrorReporting"; - case OMX_IndexParamVideoMacroblocksPerFrame: - return "OMX_IndexParamVideoMacroblocksPerFrame"; - case OMX_IndexConfigVideoMacroBlockErrorMap: - return "OMX_IndexConfigVideoMacroBlockErrorMap"; - case OMX_IndexParamVideoSliceFMO: - return "OMX_IndexParamVideoSliceFMO"; - case OMX_IndexConfigVideoAVCIntraPeriod: - return "OMX_IndexConfigVideoAVCIntraPeriod"; - case OMX_IndexConfigVideoNalSize: - return "OMX_IndexConfigVideoNalSize"; - case OMX_IndexCommonStartUnused: - return "OMX_IndexCommonStartUnused"; - case OMX_IndexParamCommonDeblocking: - return "OMX_IndexParamCommonDeblocking"; - case OMX_IndexParamCommonSensorMode: - return "OMX_IndexParamCommonSensorMode"; - case OMX_IndexParamCommonInterleave: - return "OMX_IndexParamCommonInterleave"; - case OMX_IndexConfigCommonColorFormatConversion: - return "OMX_IndexConfigCommonColorFormatConversion"; - case OMX_IndexConfigCommonScale: - return "OMX_IndexConfigCommonScale"; - case OMX_IndexConfigCommonImageFilter: - return "OMX_IndexConfigCommonImageFilter"; - case OMX_IndexConfigCommonColorEnhancement: - return "OMX_IndexConfigCommonColorEnhancement"; - case OMX_IndexConfigCommonColorKey: - return "OMX_IndexConfigCommonColorKey"; - case OMX_IndexConfigCommonColorBlend: - return "OMX_IndexConfigCommonColorBlend"; - case OMX_IndexConfigCommonFrameStabilisation: - return "OMX_IndexConfigCommonFrameStabilisation"; - case OMX_IndexConfigCommonRotate: - return "OMX_IndexConfigCommonRotate"; - case OMX_IndexConfigCommonMirror: - return "OMX_IndexConfigCommonMirror"; - case OMX_IndexConfigCommonOutputPosition: - return "OMX_IndexConfigCommonOutputPosition"; - case OMX_IndexConfigCommonInputCrop: - return "OMX_IndexConfigCommonInputCrop"; - case OMX_IndexConfigCommonOutputCrop: - return "OMX_IndexConfigCommonOutputCrop"; - case OMX_IndexConfigCommonDigitalZoom: - return "OMX_IndexConfigCommonDigitalZoom"; - case OMX_IndexConfigCommonOpticalZoom: - return "OMX_IndexConfigCommonOpticalZoom"; - case OMX_IndexConfigCommonWhiteBalance: - return "OMX_IndexConfigCommonWhiteBalance"; - case OMX_IndexConfigCommonExposure: - return "OMX_IndexConfigCommonExposure"; - case OMX_IndexConfigCommonContrast: - return "OMX_IndexConfigCommonContrast"; - case OMX_IndexConfigCommonBrightness: - return "OMX_IndexConfigCommonBrightness"; - case OMX_IndexConfigCommonBacklight: - return "OMX_IndexConfigCommonBacklight"; - case OMX_IndexConfigCommonGamma: - return "OMX_IndexConfigCommonGamma"; - case OMX_IndexConfigCommonSaturation: - return "OMX_IndexConfigCommonSaturation"; - case OMX_IndexConfigCommonLightness: - return "OMX_IndexConfigCommonLightness"; - case OMX_IndexConfigCommonExclusionRect: - return "OMX_IndexConfigCommonExclusionRect"; - case OMX_IndexConfigCommonDithering: - return "OMX_IndexConfigCommonDithering"; - case OMX_IndexConfigCommonPlaneBlend: - return "OMX_IndexConfigCommonPlaneBlend"; - case OMX_IndexConfigCommonExposureValue: - return "OMX_IndexConfigCommonExposureValue"; - case OMX_IndexConfigCommonOutputSize: - return "OMX_IndexConfigCommonOutputSize"; - case OMX_IndexParamCommonExtraQuantData: - return "OMX_IndexParamCommonExtraQuantData"; - case OMX_IndexConfigCommonTransitionEffect: - return "OMX_IndexConfigCommonTransitionEffect"; - case OMX_IndexOtherStartUnused: - return "OMX_IndexOtherStartUnused"; - case OMX_IndexParamOtherPortFormat: - return "OMX_IndexParamOtherPortFormat"; - case OMX_IndexConfigOtherPower: - return "OMX_IndexConfigOtherPower"; - case OMX_IndexConfigOtherStats: - return "OMX_IndexConfigOtherStats"; - case OMX_IndexTimeStartUnused: - return "OMX_IndexTimeStartUnused"; - case OMX_IndexConfigTimeScale: - return "OMX_IndexConfigTimeScale"; - case OMX_IndexConfigTimeClockState: - return "OMX_IndexConfigTimeClockState"; - case OMX_IndexConfigTimeCurrentMediaTime: - return "OMX_IndexConfigTimeCurrentMediaTime"; - case OMX_IndexConfigTimeCurrentWallTime: - return "OMX_IndexConfigTimeCurrentWallTime"; - case OMX_IndexConfigTimeMediaTimeRequest: - return "OMX_IndexConfigTimeMediaTimeRequest"; - case OMX_IndexConfigTimeClientStartTime: - return "OMX_IndexConfigTimeClientStartTime"; - case OMX_IndexConfigTimePosition: - return "OMX_IndexConfigTimePosition"; - case OMX_IndexConfigTimeSeekMode: - return "OMX_IndexConfigTimeSeekMode"; - case OMX_IndexKhronosExtensions: - return "OMX_IndexKhronosExtensions"; - case OMX_IndexVendorStartUnused: - return "OMX_IndexVendorStartUnused"; - case OMX_IndexMax: - return "OMX_IndexMax"; - default: - break; - } - -#if OMX_VERSION_MINOR == 1 - switch (index) { - case OMX_IndexParamCustomContentPipe: - return "OMX_IndexParamCustomContentPipe"; - case OMX_IndexConfigCommonFocusRegion: - return "OMX_IndexConfigCommonFocusRegion"; - case OMX_IndexConfigCommonFocusStatus: - return "OMX_IndexConfigCommonFocusStatus"; - case OMX_IndexConfigTimeActiveRefClock: - return "OMX_IndexConfigTimeActiveRefClock"; - case OMX_IndexConfigTimeCurrentAudioReference: - return "OMX_IndexConfigTimeCurrentAudioReference"; - case OMX_IndexConfigTimeCurrentVideoReference: - return "OMX_IndexConfigTimeCurrentVideoReference"; - default: - break; - } -#endif - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - switch ((OMX_ALG_INDEXTYPE) index) { - case OMX_ALG_IndexVendorComponentStartUnused: - return "OMX_ALG_IndexVendorComponentStartUnused"; - case OMX_ALG_IndexParamReportedLatency: - return "OMX_ALG_IndexParamReportedLatency"; - case OMX_ALG_IndexParamPreallocation: - return "OMX_ALG_IndexParamPreallocation"; - case OMX_ALG_IndexVendorPortStartUnused: - return "OMX_ALG_IndexVendorPortStartUnused"; - case OMX_ALG_IndexPortParamBufferMode: - return "OMX_ALG_IndexPortParamBufferMode"; - case OMX_ALG_IndexParamVendorVideoStartUnused: - return "OMX_ALG_IndexParamVendorVideoStartUnused"; - case OMX_ALG_IndexParamVideoHevc: - return "OMX_ALG_IndexParamVideoHevc"; - case OMX_ALG_IndexParamVideoVp9: - return "OMX_ALG_IndexParamVideoVp9"; - case OMX_ALG_IndexParamVideoGopControl: - return "OMX_ALG_IndexParamVideoGopControl"; - case OMX_ALG_IndexParamVideoSlices: - return "OMX_ALG_IndexParamVideoSlices"; - case OMX_ALG_IndexParamVideoSceneChangeResilience: - return "OMX_ALG_IndexParamVideoSceneChangeResilience"; - case OMX_ALG_IndexParamVideoPrefetchBuffer: - return "OMX_ALG_IndexParamVideoPrefetchBuffer"; - case OMX_ALG_IndexParamVideoCodedPictureBuffer: - return "OMX_ALG_IndexParamVideoCodedPictureBuffer"; - case OMX_ALG_IndexParamVideoQuantizationControl: - return "OMX_ALG_IndexParamVideoQuantizationControl"; - case OMX_ALG_IndexParamVideoQuantizationExtension: - return "OMX_ALG_IndexParamVideoQuantizationExtension"; - case OMX_ALG_IndexParamVideoScalingList: - return "OMX_ALG_IndexParamVideoScalingList"; - case OMX_ALG_IndexParamVideoDecodedPictureBuffer: - return "OMX_ALG_IndexParamVideoDecodedPictureBuffer"; - case OMX_ALG_IndexParamVideoInternalEntropyBuffers: - return "OMX_ALG_IndexParamVideoInternalEntropyBuffers"; - case OMX_ALG_IndexParamVideoLowBandwidth: - return "OMX_ALG_IndexParamVideoLowBandwidth"; - case OMX_ALG_IndexParamVideoAspectRatio: - return "OMX_ALG_IndexParamVideoAspectRatio"; - case OMX_ALG_IndexParamVideoSubframe: - return "OMX_ALG_IndexParamVideoSubframe"; - case OMX_ALG_IndexParamVideoInstantaneousDecodingRefresh: - return "OMX_ALG_IndexParamVideoInstantaneousDecodingRefresh"; - case OMX_ALG_IndexParamVideoMaxBitrate: - return "OMX_ALG_IndexParamVideoMaxBitrate"; - case OMX_ALG_IndexParamVideoFillerData: - return "OMX_ALG_IndexParamVideoFillerData"; - case OMX_ALG_IndexParamVideoBufferMode: - return "OMX_ALG_IndexParamVideoBufferMode"; - case OMX_ALG_IndexParamVideoInterlaceFormatCurrent: - return "OMX_ALG_IndexParamVideoInterlaceFormatCurrent"; - case OMX_ALG_IndexParamVideoLongTerm: - return "OMX_ALG_IndexParamVideoLongTerm"; - case OMX_ALG_IndexParamVideoLookAhead: - return "OMX_ALG_IndexParamVideoLookAhead"; - case OMX_ALG_IndexConfigVendorVideoStartUnused: - return "OMX_ALG_IndexConfigVendorVideoStartUnused"; - case OMX_ALG_IndexConfigVideoInsertInstantaneousDecodingRefresh: - return "OMX_ALG_IndexConfigVideoInsertInstantaneousDecodingRefresh"; - case OMX_ALG_IndexConfigVideoGroupOfPictures: - return "OMX_ALG_IndexConfigVideoGroupOfPictures"; - case OMX_ALG_IndexConfigVideoRegionOfInterest: - return "OMX_ALG_IndexConfigVideoRegionOfInterest"; - case OMX_ALG_IndexConfigVideoNotifySceneChange: - return "OMX_ALG_IndexConfigVideoNotifySceneChange"; - case OMX_ALG_IndexConfigVideoInsertLongTerm: - return "OMX_ALG_IndexConfigVideoInsertLongTerm"; - case OMX_ALG_IndexConfigVideoUseLongTerm: - return "OMX_ALG_IndexConfigVideoUseLongTerm"; - case OMX_ALG_IndexVendorCommonStartUnused: - return "OMX_ALG_IndexVendorCommonStartUnused"; - case OMX_ALG_IndexParamCommonSequencePictureModeCurrent: - return "OMX_ALG_IndexParamCommonSequencePictureModeCurrent"; - case OMX_ALG_IndexParamCommonSequencePictureModeQuerySupported: - return "OMX_ALG_IndexParamCommonSequencePictureModeQuerySupported"; - case OMX_ALG_IndexParamVideoTwoPass: - return "OMX_ALG_IndexParamVideoTwoPass"; - case OMX_ALG_IndexParamVideoColorPrimaries: - return "OMX_ALG_IndexParamVideoColorPrimaries"; - case OMX_ALG_IndexParamVideoSkipFrame: - return "OMX_ALG_IndexParamVideoSkipFrame"; - case OMX_ALG_IndexConfigVideoNotifyResolutionChange: - return "OMX_ALG_IndexConfigVideoNotifyResolutionChange"; - case OMX_ALG_IndexConfigVideoInsertPrefixSEI: - return "OMX_ALG_IndexConfigVideoInsertPrefixSEI"; - case OMX_ALG_IndexConfigVideoInsertSuffixSEI: - return "OMX_ALG_IndexConfigVideoInsertSuffixSEI"; - case OMX_ALG_IndexConfigVideoQuantizationParameterTable: - return "OMX_ALG_IndexConfigVideoQuantizationParameterTable"; - case OMX_ALG_IndexParamVideoInputParsed: - return "OMX_ALG_IndexParamVideoInputParsed"; - case OMX_ALG_IndexParamVideoMaxPictureSize: - return "OMX_ALG_IndexParamVideoMaxPictureSize"; - case OMX_ALG_IndexParamVideoMaxPictureSizes: - return "OMX_ALG_IndexParamVideoMaxPictureSizes"; - case OMX_ALG_IndexConfigVideoLoopFilterBeta: - return "OMX_ALG_IndexConfigVideoLoopFilterBeta"; - case OMX_ALG_IndexConfigVideoLoopFilterTc: - return "OMX_ALG_IndexConfigVideoLoopFilterTc"; - case OMX_ALG_IndexParamVideoLoopFilterBeta: - return "OMX_ALG_IndexParamVideoLoopFilterBeta"; - case OMX_ALG_IndexParamVideoLoopFilterTc: - return "OMX_ALG_IndexParamVideoLoopFilterTc"; - case OMX_ALG_IndexPortParamEarlyCallback: - return "OMX_ALG_IndexPortParamEarlyCallback"; - case OMX_ALG_IndexParamVideoTransferCharacteristics: - return "OMX_ALG_IndexParamVideoTransferCharacteristics"; - case OMX_ALG_IndexParamVideoColorMatrix: - return "OMX_ALG_IndexParamVideoColorMatrix"; - case OMX_ALG_IndexConfigVideoTransferCharacteristics: - return "OMX_ALG_IndexConfigVideoTransferCharacteristics"; - case OMX_ALG_IndexConfigVideoColorMatrix: - return "OMX_ALG_IndexConfigVideoColorMatrix"; - case OMX_ALG_IndexConfigVideoHighDynamicRangeSEI: - return "OMX_ALG_IndexConfigVideoHighDynamicRangeSEI"; - case OMX_ALG_IndexConfigVideoMaxResolutionChange: - return "OMX_ALG_IndexConfigVideoMaxResolutionChange"; - case OMX_ALG_IndexParamVideoQuantizationTable: - return "OMX_ALG_IndexParamVideoQuantizationTable"; - case OMX_ALG_IndexParamVideoAccessUnitDelimiter: - return "OMX_ALG_IndexParamVideoAccessUnitDelimiter"; - case OMX_ALG_IndexParamVideoBufferingPeriodSEI: - return "OMX_ALG_IndexParamVideoBufferingPeriodSEI"; - case OMX_ALG_IndexParamVideoPictureTimingSEI: - return "OMX_ALG_IndexParamVideoPictureTimingSEI"; - case OMX_ALG_IndexParamVideoRecoveryPointSEI: - return "OMX_ALG_IndexParamVideoRecoveryPointSEI"; - case OMX_ALG_IndexParamVideoMasteringDisplayColourVolumeSEI: - return "OMX_ALG_IndexParamVideoMasteringDisplayColourVolumeSEI"; - case OMX_ALG_IndexParamVideoContentLightLevelSEI: - return "OMX_ALG_IndexParamVideoContentLightLevelSEI"; - case OMX_ALG_IndexConfigVideoRegionOfInterestByValue: - return "OMX_ALG_IndexConfigVideoRegionOfInterestByValue"; - case OMX_ALG_IndexConfigVideoColorPrimaries: - return "OMX_ALG_IndexConfigVideoColorPrimaries"; - case OMX_ALG_IndexMaxEnum: - return "OMX_ALG_IndexMaxEnum"; - } -#endif - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - /* Not part of the enum in OMX_IndexAlg.h */ - if (index == OMX_ALG_IndexParamVideoInterlaceFormatSupported) - return "OMX_ALG_IndexParamVideoInterlaceFormatSupported"; -#endif - - return NULL; -} -#endif /* GST_DISABLE_GST_DEBUG */ - -static void -log_omx_api_trace_call (GstOMXComponent * comp, const gchar * function, - OMX_INDEXTYPE index, GstDebugLevel level) -{ -#ifndef GST_DISABLE_GST_DEBUG - GstStructure *s; - const gchar *index_name; - - /* Don't bother creating useless structs if not needed */ - if (gst_debug_category_get_threshold (OMX_API_TRACE) < level) - return; - - index_name = omx_index_type_to_str (index); - if (!index_name) { - GST_CAT_WARNING_OBJECT (OMX_API_TRACE, comp->parent, - "unknown call of %s with index 0x%08x", function, index); - return; - } - - s = gst_structure_new (function, "index", G_TYPE_STRING, index_name, NULL); - GST_CAT_LEVEL_LOG (OMX_API_TRACE, level, comp->parent, "%" GST_PTR_FORMAT, s); - gst_structure_free (s); -#endif /* GST_DISABLE_GST_DEBUG */ -} - -/* comp->lock must be unlocked while calling this */ -OMX_ERRORTYPE -gst_omx_component_get_parameter (GstOMXComponent * comp, OMX_INDEXTYPE index, - gpointer param) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (comp != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (param != NULL, OMX_ErrorUndefined); - - GST_DEBUG_OBJECT (comp->parent, "Getting %s parameter at index 0x%08x", - comp->name, index); - log_omx_api_trace_call (comp, "GetParameter", index, GST_LEVEL_LOG); - err = OMX_GetParameter (comp->handle, index, param); - DEBUG_IF_OK (comp->parent, err, "Got %s parameter at index 0x%08x: %s " - "(0x%08x)", comp->name, index, gst_omx_error_to_string (err), err); - - return err; -} - -/* comp->lock must be unlocked while calling this */ -OMX_ERRORTYPE -gst_omx_component_set_parameter (GstOMXComponent * comp, OMX_INDEXTYPE index, - gpointer param) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (comp != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (param != NULL, OMX_ErrorUndefined); - - GST_DEBUG_OBJECT (comp->parent, "Setting %s parameter at index 0x%08x", - comp->name, index); - - log_omx_api_trace_call (comp, "SetParameter", index, GST_LEVEL_DEBUG); - err = OMX_SetParameter (comp->handle, index, param); - DEBUG_IF_OK (comp->parent, err, "Set %s parameter at index 0x%08x: %s " - "(0x%08x)", comp->name, index, gst_omx_error_to_string (err), err); - - return err; -} - -/* comp->lock must be unlocked while calling this */ -OMX_ERRORTYPE -gst_omx_component_get_config (GstOMXComponent * comp, OMX_INDEXTYPE index, - gpointer config) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (comp != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (config != NULL, OMX_ErrorUndefined); - - GST_DEBUG_OBJECT (comp->parent, "Getting %s configuration at index 0x%08x", - comp->name, index); - log_omx_api_trace_call (comp, "GetConfig", index, GST_LEVEL_LOG); - err = OMX_GetConfig (comp->handle, index, config); - DEBUG_IF_OK (comp->parent, err, "Got %s parameter at index 0x%08x: %s " - "(0x%08x)", comp->name, index, gst_omx_error_to_string (err), err); - - return err; -} - -/* comp->lock must be unlocked while calling this */ -OMX_ERRORTYPE -gst_omx_component_set_config (GstOMXComponent * comp, OMX_INDEXTYPE index, - gpointer config) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (comp != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (config != NULL, OMX_ErrorUndefined); - - GST_DEBUG_OBJECT (comp->parent, "Setting %s configuration at index 0x%08x", - comp->name, index); - log_omx_api_trace_call (comp, "SetConfig", index, GST_LEVEL_DEBUG); - err = OMX_SetConfig (comp->handle, index, config); - DEBUG_IF_OK (comp->parent, err, "Set %s parameter at index 0x%08x: %s " - "(0x%08x)", comp->name, index, gst_omx_error_to_string (err), err); - - return err; -} - -OMX_ERRORTYPE -gst_omx_setup_tunnel (GstOMXPort * port1, GstOMXPort * port2) -{ - GstOMXComponent *comp1; - GstOMXComponent *comp2; - OMX_ERRORTYPE err; - - g_return_val_if_fail (port1 != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (port1->port_def.eDir == OMX_DirOutput, - OMX_ErrorUndefined); - comp1 = port1->comp; - - g_return_val_if_fail (port2 != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (port2->port_def.eDir == OMX_DirInput, - OMX_ErrorUndefined); - comp2 = port2->comp; - - g_return_val_if_fail (comp1->core == comp2->core, OMX_ErrorUndefined); - - g_mutex_lock (&comp1->lock); - g_mutex_lock (&comp2->lock); - GST_DEBUG_OBJECT (comp1->parent, - "Setup tunnel between %s port %u and %s port %u", - comp1->name, port1->index, comp2->name, port2->index); - - err = comp1->core->setup_tunnel (comp1->handle, port1->index, comp2->handle, - port2->index); - - if (err == OMX_ErrorNone) { - port1->tunneled = TRUE; - port2->tunneled = TRUE; - } - - DEBUG_IF_OK (comp1->parent, err, - "Setup tunnel between %s port %u and %s port %u: %s (0x%08x)", - comp1->name, port1->index, - comp2->name, port2->index, gst_omx_error_to_string (err), err); - - g_mutex_unlock (&comp2->lock); - g_mutex_unlock (&comp1->lock); - - return err; -} - -OMX_ERRORTYPE -gst_omx_close_tunnel (GstOMXPort * port1, GstOMXPort * port2) -{ - GstOMXComponent *comp1; - GstOMXComponent *comp2; - OMX_ERRORTYPE err; - - g_return_val_if_fail (port1 != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (port1->port_def.eDir == OMX_DirOutput, - OMX_ErrorUndefined); - comp1 = port1->comp; - - g_return_val_if_fail (port2 != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (port2->port_def.eDir == OMX_DirInput, - OMX_ErrorUndefined); - comp2 = port2->comp; - - g_return_val_if_fail (comp1->core == comp2->core, OMX_ErrorUndefined); - g_return_val_if_fail (port1->tunneled && port2->tunneled, OMX_ErrorUndefined); - - g_mutex_lock (&comp1->lock); - g_mutex_lock (&comp2->lock); - GST_DEBUG_OBJECT (comp1->parent, - "Closing tunnel between %s port %u and %s port %u", - comp1->name, port1->index, comp2->name, port2->index); - - err = comp1->core->setup_tunnel (comp1->handle, port1->index, 0, 0); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp1->parent, - "Failed to close tunnel on output side %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - err = comp2->core->setup_tunnel (0, 0, comp2->handle, port2->index); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp2->parent, - "Failed to close tunnel on input side %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - port1->tunneled = FALSE; - port2->tunneled = FALSE; - - GST_DEBUG_OBJECT (comp1->parent, - "Closed tunnel between %s port %u and %s port %u", - comp1->name, port1->index, comp2->name, port2->index); - - g_mutex_unlock (&comp2->lock); - g_mutex_unlock (&comp1->lock); - - return err; -} - -OMX_ERRORTYPE -gst_omx_port_get_port_definition (GstOMXPort * port, - OMX_PARAM_PORTDEFINITIONTYPE * port_def) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorBadParameter); - - comp = port->comp; - - GST_OMX_INIT_STRUCT (port_def); - port_def->nPortIndex = port->index; - - err = gst_omx_component_get_parameter (comp, OMX_IndexParamPortDefinition, - port_def); - - return err; -} - -OMX_ERRORTYPE -gst_omx_port_update_port_definition (GstOMXPort * port, - OMX_PARAM_PORTDEFINITIONTYPE * port_def) -{ - OMX_ERRORTYPE err_get, err_set = OMX_ErrorNone; - GstOMXComponent *comp; - - g_return_val_if_fail (port != NULL, FALSE); - - comp = port->comp; - - if (port_def) - err_set = - gst_omx_component_set_parameter (comp, OMX_IndexParamPortDefinition, - port_def); - err_get = gst_omx_component_get_parameter (comp, OMX_IndexParamPortDefinition, - &port->port_def); - - DEBUG_IF_OK (comp->parent, err_set, - "Updated %s port %u definition: %s (0x%08x)", comp->name, port->index, - gst_omx_error_to_string (err_set), err_set); - - if (err_set != OMX_ErrorNone) - return err_set; - else - return err_get; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -GstOMXAcquireBufferReturn -gst_omx_port_acquire_buffer (GstOMXPort * port, GstOMXBuffer ** buf, - GstOMXWait wait) -{ - GstOMXAcquireBufferReturn ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - GstOMXComponent *comp; - OMX_ERRORTYPE err; - GstOMXBuffer *_buf = NULL; - gint64 timeout = GST_CLOCK_TIME_NONE; - - g_return_val_if_fail (port != NULL, GST_OMX_ACQUIRE_BUFFER_ERROR); - g_return_val_if_fail (!port->tunneled, GST_OMX_ACQUIRE_BUFFER_ERROR); - g_return_val_if_fail (buf != NULL, GST_OMX_ACQUIRE_BUFFER_ERROR); - - *buf = NULL; - - comp = port->comp; - - g_mutex_lock (&comp->lock); - GST_DEBUG_OBJECT (comp->parent, "Acquiring %s buffer from port %u", - comp->name, port->index); - -retry: - gst_omx_component_handle_messages (comp); - - /* If we are in the case where we waited for a buffer after EOS, - * make sure we don't do that again */ - if (timeout != -1) - timeout = -2; - - /* Check if the component is in an error state */ - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s is in error state: %s", - comp->name, gst_omx_error_to_string (err)); - ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - goto done; - } - - /* Check if the port is flushing */ - if (port->flushing) { - GST_DEBUG_OBJECT (comp->parent, "Component %s port %d is flushing", - comp->name, port->index); - ret = GST_OMX_ACQUIRE_BUFFER_FLUSHING; - goto done; - } - - /* If this is an input port and at least one of the output ports - * needs to be reconfigured, we wait until all output ports are - * reconfigured. Afterwards this port is reconfigured if required - * or buffers are returned to be filled as usual. - */ - if (port->port_def.eDir == OMX_DirInput) { - if (comp->pending_reconfigure_outports) { - gst_omx_component_handle_messages (comp); - while (comp->pending_reconfigure_outports && - (err = comp->last_error) == OMX_ErrorNone && !port->flushing) { - GST_DEBUG_OBJECT (comp->parent, - "Waiting for %s output ports to reconfigure", comp->name); - gst_omx_component_wait_message (comp, GST_CLOCK_TIME_NONE); - gst_omx_component_handle_messages (comp); - } - goto retry; - } - - /* Only if this port needs to be reconfigured too notify - * the caller about it */ - if (port->settings_cookie != port->configured_settings_cookie) { - GST_DEBUG_OBJECT (comp->parent, - "Component %s port %d needs reconfiguring", comp->name, port->index); - ret = GST_OMX_ACQUIRE_BUFFER_RECONFIGURE; - goto done; - } - } - - /* If we have an output port that needs to be reconfigured - * and it still has buffers pending for the old configuration - * we first return them. - * NOTE: If buffers for this configuration arrive later - * we have to drop them... */ - if (port->port_def.eDir == OMX_DirOutput && - port->settings_cookie != port->configured_settings_cookie) { - if (!g_queue_is_empty (&port->pending_buffers)) { - GST_DEBUG_OBJECT (comp->parent, - "%s output port %u needs reconfiguration but has buffers pending", - comp->name, port->index); - _buf = g_queue_pop_head (&port->pending_buffers); - - ret = GST_OMX_ACQUIRE_BUFFER_OK; - goto done; - } - - GST_DEBUG_OBJECT (comp->parent, "Component %s port %d needs reconfiguring", - comp->name, port->index); - ret = GST_OMX_ACQUIRE_BUFFER_RECONFIGURE; - goto done; - } - - if (port->port_def.eDir == OMX_DirOutput && port->eos) { - if (!g_queue_is_empty (&port->pending_buffers)) { - GST_DEBUG_OBJECT (comp->parent, "%s output port %u is EOS but has " - "%d buffers pending", comp->name, port->index, - g_queue_get_length (&port->pending_buffers)); - _buf = g_queue_pop_head (&port->pending_buffers); - - ret = GST_OMX_ACQUIRE_BUFFER_OK; - goto done; - } - - if (comp->hacks & GST_OMX_HACK_SIGNALS_PREMATURE_EOS && timeout != -2) { - timeout = 33 * GST_MSECOND; - - GST_DEBUG_OBJECT (comp->parent, "%s output port %u is EOS but waiting " - "in case it spits out more buffers", comp->name, port->index); - } else { - GST_DEBUG_OBJECT (comp->parent, "Component %s port %d signalled EOS", - comp->name, port->index); - ret = GST_OMX_ACQUIRE_BUFFER_EOS; - port->eos = FALSE; - goto done; - } - } - - /* - * At this point we have no error or flushing/eos port - * and a properly configured port. - * - */ - - /* If the queue is empty we wait until a buffer - * arrives, an error happens, the port is flushing - * or the port needs to be reconfigured. - */ - if (g_queue_is_empty (&port->pending_buffers)) { - GST_DEBUG_OBJECT (comp->parent, "Queue of %s port %u is empty", - comp->name, port->index); - - if (wait == GST_OMX_WAIT) { - gst_omx_component_wait_message (comp, - timeout == -2 ? GST_CLOCK_TIME_NONE : timeout); - - /* And now check everything again and maybe get a buffer */ - goto retry; - } else { - ret = GST_OMX_ACQUIRE_BUFFER_NO_AVAILABLE; - goto done; - } - } - - GST_DEBUG_OBJECT (comp->parent, "%s port %u has pending buffers", - comp->name, port->index); - _buf = g_queue_pop_head (&port->pending_buffers); - ret = GST_OMX_ACQUIRE_BUFFER_OK; - -done: - g_mutex_unlock (&comp->lock); - - if (_buf) { - g_assert (_buf == _buf->omx_buf->pAppPrivate); - *buf = _buf; - } - - GST_DEBUG_OBJECT (comp->parent, "Acquired buffer %p (%p) from %s port %u: %d", - _buf, (_buf ? _buf->omx_buf->pBuffer : NULL), comp->name, port->index, - ret); - - return ret; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_release_buffer (GstOMXPort * port, GstOMXBuffer * buf) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (!port->tunneled, OMX_ErrorUndefined); - g_return_val_if_fail (buf != NULL, OMX_ErrorUndefined); - g_return_val_if_fail (buf->port == port, OMX_ErrorUndefined); - - comp = port->comp; - - g_mutex_lock (&comp->lock); - - GST_DEBUG_OBJECT (comp->parent, "Releasing buffer %p (%p) to %s port %u", - buf, buf->omx_buf->pBuffer, comp->name, port->index); - - gst_omx_component_handle_messages (comp); - - if (port->port_def.eDir == OMX_DirOutput) { - /* Reset all flags, some implementations don't - * reset them themselves and the flags are not - * valid anymore after the buffer was consumed - */ - gst_omx_buffer_reset (buf); - } - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s is in error state: %s " - "(0x%08x)", comp->name, gst_omx_error_to_string (err), err); - g_queue_push_tail (&port->pending_buffers, buf); - gst_omx_component_send_message (comp, NULL); - goto done; - } - - if (port->flushing || port->disabled_pending || !port->port_def.bEnabled) { - GST_DEBUG_OBJECT (comp->parent, - "%s port %u is flushing or disabled, not releasing " "buffer", - comp->name, port->index); - g_queue_push_tail (&port->pending_buffers, buf); - gst_omx_component_send_message (comp, NULL); - goto done; - } - - g_assert (buf == buf->omx_buf->pAppPrivate); - - /* FIXME: What if the settings cookies don't match? */ - - buf->used = TRUE; - - if (port->port_def.eDir == OMX_DirInput) { - log_omx_api_trace_buffer (comp, "EmptyThisBuffer", buf); - err = OMX_EmptyThisBuffer (comp->handle, buf->omx_buf); - } else { - log_omx_api_trace_buffer (comp, "FillThisBuffer", buf); - err = OMX_FillThisBuffer (comp->handle, buf->omx_buf); - } - DEBUG_IF_OK (comp->parent, err, "Released buffer %p to %s port %u: %s " - "(0x%08x)", buf, comp->name, port->index, gst_omx_error_to_string (err), - err); - -done: - gst_omx_component_handle_messages (comp); - g_mutex_unlock (&comp->lock); - - return err; -} - -/* NOTE: Must be called while holding comp->lock */ -static gboolean -should_wait_until_flushed (GstOMXPort * port) -{ - if (!port->flushed) - /* Flush command hasn't been completed yet by OMX */ - return TRUE; - - if (port->buffers) { - guint i; - - /* Wait for all the buffers used by OMX to be released */ - for (i = 0; i < port->buffers->len; i++) { - GstOMXBuffer *buf = g_ptr_array_index (port->buffers, i); - - if (buf->used) - return TRUE; - } - } - - return FALSE; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_set_flushing (GstOMXPort * port, GstClockTime timeout, - gboolean flush) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - comp = port->comp; - - g_mutex_lock (&comp->lock); - - GST_DEBUG_OBJECT (comp->parent, "Setting %s port %d to %sflushing", - comp->name, port->index, (flush ? "" : "not ")); - - gst_omx_component_handle_messages (comp); - - if (flush == port->flushing) { - GST_DEBUG_OBJECT (comp->parent, "%s port %u was %sflushing already", - comp->name, port->index, (flush ? "" : "not ")); - goto done; - } - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s is in error state: %s " - "(0x%08x)", comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - port->flushing = flush; - if (flush) { - gboolean signalled; - OMX_ERRORTYPE last_error; - - gst_omx_component_send_message (comp, NULL); - - /* Now flush the port */ - port->flushed = FALSE; - - err = - gst_omx_component_send_command (comp, OMX_CommandFlush, port->index, - NULL); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Error sending flush command to %s port %u: %s (0x%08x)", comp->name, - port->index, gst_omx_error_to_string (err), err); - goto done; - } - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Component %s is in error state: %s (0x%08x)", comp->name, - gst_omx_error_to_string (err), err); - goto done; - } - - if (port->flushing != flush) { - GST_ERROR_OBJECT (comp->parent, "%s: another flush happened in the " - " meantime", comp->name); - goto done; - } - - if (timeout == 0) { - if (should_wait_until_flushed (port)) - err = OMX_ErrorTimeout; - goto done; - } - - /* Retry until timeout or until an error happend or - * until all buffers were released by the component and - * the flush command completed */ - signalled = TRUE; - last_error = OMX_ErrorNone; - gst_omx_component_handle_messages (comp); - while (should_wait_until_flushed (port)) { - signalled = gst_omx_component_wait_message (comp, timeout); - if (signalled) - gst_omx_component_handle_messages (comp); - - last_error = comp->last_error; - - if (!signalled || last_error != OMX_ErrorNone) - /* Something gone wrong or we timed out */ - break; - } - port->flushed = FALSE; - - GST_DEBUG_OBJECT (comp->parent, "%s port %d flushed", comp->name, - port->index); - if (last_error != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Got error while flushing %s port %u: %s (0x%08x)", comp->name, - port->index, gst_omx_error_to_string (last_error), last_error); - err = last_error; - goto done; - } else if (!signalled) { - GST_ERROR_OBJECT (comp->parent, "Timeout while flushing %s port %u", - comp->name, port->index); - err = OMX_ErrorTimeout; - goto done; - } - } - - /* Reset EOS flag */ - port->eos = FALSE; - -done: - gst_omx_port_update_port_definition (port, NULL); - - DEBUG_IF_OK (comp->parent, err, "Set %s port %u to %sflushing: %s (0x%08x)", - comp->name, port->index, (flush ? "" : "not "), - gst_omx_error_to_string (err), err); - gst_omx_component_handle_messages (comp); - g_mutex_unlock (&comp->lock); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -gboolean -gst_omx_port_is_flushing (GstOMXPort * port) -{ - GstOMXComponent *comp; - gboolean flushing; - - g_return_val_if_fail (port != NULL, FALSE); - - comp = port->comp; - - g_mutex_lock (&comp->lock); - gst_omx_component_handle_messages (port->comp); - flushing = port->flushing; - g_mutex_unlock (&comp->lock); - - GST_DEBUG_OBJECT (comp->parent, "%s port %u is flushing: %d", comp->name, - port->index, flushing); - - return flushing; -} - -static OMX_ERRORTYPE gst_omx_port_deallocate_buffers_unlocked (GstOMXPort * - port); - -/* NOTE: Must be called while holding comp->lock, uses comp->messages_lock */ -static OMX_ERRORTYPE -gst_omx_port_allocate_buffers_unlocked (GstOMXPort * port, - const GList * buffers, const GList * images, guint n) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - gint i; - const GList *l; - - g_assert (!port->buffers || port->buffers->len == 0); - - g_return_val_if_fail (!port->tunneled, OMX_ErrorBadParameter); - - comp = port->comp; - - gst_omx_component_handle_messages (port->comp); - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - /* Update the port definition to check if we need more - * buffers after the port configuration was done and to - * update the buffer size - */ - gst_omx_port_update_port_definition (port, NULL); - - g_return_val_if_fail (n != -1 || (!buffers - && !images), OMX_ErrorBadParameter); - - if (n == -1) - n = port->port_def.nBufferCountActual; - - g_return_val_if_fail (n == port->port_def.nBufferCountActual, - OMX_ErrorBadParameter); - - GST_INFO_OBJECT (comp->parent, - "Allocating %d buffers of size %" G_GSIZE_FORMAT " for %s port %u", n, - (size_t) port->port_def.nBufferSize, comp->name, (guint) port->index); - - if (!port->buffers) - port->buffers = g_ptr_array_sized_new (n); - - l = (buffers ? buffers : images); - for (i = 0; i < n; i++) { - GstOMXBuffer *buf; - - buf = g_new0 (GstOMXBuffer, 1); - buf->port = port; - buf->used = FALSE; - buf->settings_cookie = port->settings_cookie; - g_ptr_array_add (port->buffers, buf); - - if (buffers) { - err = - OMX_UseBuffer (comp->handle, &buf->omx_buf, port->index, buf, - port->port_def.nBufferSize, l->data); - buf->eglimage = FALSE; - } else if (images) { - err = - OMX_UseEGLImage (comp->handle, &buf->omx_buf, port->index, buf, - l->data); - buf->eglimage = TRUE; - } else { - err = - OMX_AllocateBuffer (comp->handle, &buf->omx_buf, port->index, buf, - port->port_def.nBufferSize); - buf->eglimage = FALSE; - } - - /* Let the caller decide to print an error when OMX_UseBuffer or - * OMX_UseEGLImage fail. Indeed it can be part of a trial path. So - * it is not necessary to warn the user if the fallback path succeeds. - */ - if (err != OMX_ErrorNone) { - GST_CAT_LEVEL_LOG (GST_CAT_DEFAULT, (buffers - || images) ? GST_LEVEL_INFO : GST_LEVEL_ERROR, comp->parent, - "Failed to allocate buffer for %s port %u: %s (0x%08x)", comp->name, - port->index, gst_omx_error_to_string (err), err); - gst_omx_port_deallocate_buffers_unlocked (port); - goto done; - } - - GST_DEBUG_OBJECT (comp->parent, "%s: allocated buffer %p (%p)", - comp->name, buf, buf->omx_buf->pBuffer); - - g_assert (buf->omx_buf->pAppPrivate == buf); - - /* In the beginning all buffers are not owned by the component */ - g_queue_push_tail (&port->pending_buffers, buf); - if (buffers || images) - l = l->next; - } - - gst_omx_component_handle_messages (comp); - -done: - gst_omx_port_update_port_definition (port, NULL); - - INFO_IF_OK (comp->parent, err, "Allocated buffers for %s port %u: %s " - "(0x%08x)", comp->name, port->index, gst_omx_error_to_string (err), err); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_allocate_buffers (GstOMXPort * port) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_allocate_buffers_unlocked (port, NULL, NULL, -1); - port->allocation = GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER; - g_mutex_unlock (&port->comp->lock); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_use_buffers (GstOMXPort * port, const GList * buffers) -{ - OMX_ERRORTYPE err; - guint n; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - n = g_list_length ((GList *) buffers); - err = gst_omx_port_allocate_buffers_unlocked (port, buffers, NULL, n); - port->allocation = GST_OMX_BUFFER_ALLOCATION_USE_BUFFER; - g_mutex_unlock (&port->comp->lock); - - return err; -} - -gboolean -gst_omx_is_dynamic_allocation_supported (void) -{ - /* The Zynqultrascaleplus stack implements OMX 1.1.0 but supports the dynamic - * allocation mode from 1.2.0 as an extension. */ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - return TRUE; -#endif - -#if OMX_VERSION_MINOR == 2 - return TRUE; -#else - return FALSE; -#endif -} - -/* OMX 1.2.0 introduced a dynamic allocation mode where only buffer headers are - * being allocated during component's initialization. The actual buffers are - * allocated upstream and passed to OMX by setting the pBuffer dynamically - * for each input buffer. - * - * This function takes care of allocating the buffer headers. Element should - * then use one of the gst_omx_buffer_map_*() method to update buffer's pBuffer - * pointers for each incoming buffer. - * - * NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_use_dynamic_buffers (GstOMXPort * port) -{ - OMX_ERRORTYPE err; - GList *buffers = NULL; - guint i, n; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - n = port->port_def.nBufferCountActual; - for (i = 0; i < port->port_def.nBufferCountActual; i++) - /* Pass NULL to UseBuffer() as the buffer is dynamic and so its payload - * will be set each time before being passed to OMX. */ - buffers = g_list_prepend (buffers, GUINT_TO_POINTER (NULL)); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_allocate_buffers_unlocked (port, buffers, NULL, n); - port->allocation = GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC; - g_mutex_unlock (&port->comp->lock); - - g_list_free (buffers); - - return err; -} - -/* gst_omx_buffer_map_* methods are used in dynamic buffer mode to map - * a frame/memory/buffer and update @buffer so its pBuffer points to the - * mapped data. It also ensures that the input will stay alive until - * gst_omx_buffer_unmap() is called. - * This is used in OMX 1.2.0 dynamic allocation mode so an OMX component can - * safely process @buffer's content without having to copy it. - * The input will be automatically unmapped when @buffer is released by OMX. - */ -gboolean -gst_omx_buffer_map_frame (GstOMXBuffer * buffer, GstBuffer * input, - GstVideoInfo * info) -{ - g_return_val_if_fail (buffer != NULL, FALSE); - g_return_val_if_fail (!buffer->input_frame_mapped, FALSE); - g_return_val_if_fail (!buffer->input_mem, FALSE); - g_return_val_if_fail (!buffer->input_buffer, FALSE); - g_return_val_if_fail (!buffer->input_buffer_mapped, FALSE); - - if (!gst_video_frame_map (&buffer->input_frame, info, input, GST_MAP_READ)) - return FALSE; - - buffer->input_frame_mapped = TRUE; - buffer->omx_buf->pBuffer = - GST_VIDEO_FRAME_PLANE_DATA (&buffer->input_frame, 0); - buffer->omx_buf->nAllocLen = gst_buffer_get_size (input); - buffer->omx_buf->nFilledLen = buffer->omx_buf->nAllocLen; - - return TRUE; -} - -gboolean -gst_omx_buffer_map_memory (GstOMXBuffer * buffer, GstMemory * mem) -{ - g_return_val_if_fail (buffer != NULL, FALSE); - g_return_val_if_fail (mem != NULL, FALSE); - g_return_val_if_fail (!buffer->input_frame_mapped, FALSE); - g_return_val_if_fail (!buffer->input_mem, FALSE); - g_return_val_if_fail (!buffer->input_buffer, FALSE); - g_return_val_if_fail (!buffer->input_buffer_mapped, FALSE); - - if (!gst_memory_map (mem, &buffer->map, GST_MAP_READ)) - return FALSE; - - buffer->input_mem = gst_memory_ref (mem); - buffer->omx_buf->pBuffer = buffer->map.data; - buffer->omx_buf->nAllocLen = buffer->map.size; - buffer->omx_buf->nFilledLen = buffer->omx_buf->nAllocLen; - - return TRUE; -} - -gboolean -gst_omx_buffer_import_fd (GstOMXBuffer * buffer, GstBuffer * input) -{ - gint fd; - GstMemory *mem; - - g_return_val_if_fail (buffer != NULL, FALSE); - g_return_val_if_fail (input != NULL, FALSE); - g_return_val_if_fail (!buffer->input_frame_mapped, FALSE); - g_return_val_if_fail (!buffer->input_mem, FALSE); - g_return_val_if_fail (!buffer->input_buffer, FALSE); - g_return_val_if_fail (!buffer->input_buffer_mapped, FALSE); - - mem = gst_buffer_peek_memory (input, 0); - g_return_val_if_fail (gst_is_dmabuf_memory (mem), FALSE); - - fd = gst_dmabuf_memory_get_fd (mem); - - buffer->input_buffer = gst_buffer_ref (input); - buffer->omx_buf->pBuffer = GUINT_TO_POINTER (fd); - buffer->omx_buf->nAllocLen = gst_memory_get_sizes (mem, NULL, NULL); - buffer->omx_buf->nFilledLen = buffer->omx_buf->nAllocLen; - - return TRUE; -} - -gboolean -gst_omx_buffer_map_buffer (GstOMXBuffer * buffer, GstBuffer * input) -{ - g_return_val_if_fail (buffer != NULL, FALSE); - g_return_val_if_fail (input != NULL, FALSE); - g_return_val_if_fail (!buffer->input_frame_mapped, FALSE); - g_return_val_if_fail (!buffer->input_mem, FALSE); - g_return_val_if_fail (!buffer->input_buffer, FALSE); - g_return_val_if_fail (!buffer->input_buffer_mapped, FALSE); - - if (!gst_buffer_map (input, &buffer->map, GST_MAP_READ)) - return FALSE; - - buffer->input_buffer_mapped = TRUE; - buffer->input_buffer = gst_buffer_ref (input); - buffer->omx_buf->pBuffer = buffer->map.data; - buffer->omx_buf->nAllocLen = buffer->map.size; - buffer->omx_buf->nFilledLen = buffer->omx_buf->nAllocLen; - - return TRUE; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_use_eglimages (GstOMXPort * port, const GList * images) -{ - OMX_ERRORTYPE err; - guint n; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - n = g_list_length ((GList *) images); - err = gst_omx_port_allocate_buffers_unlocked (port, NULL, images, n); - g_mutex_unlock (&port->comp->lock); - - return err; -} - -/* NOTE: Must be called while holding comp->lock, uses comp->messages_lock */ -static OMX_ERRORTYPE -gst_omx_port_deallocate_buffers_unlocked (GstOMXPort * port) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - gint i, n; - - g_return_val_if_fail (!port->tunneled, OMX_ErrorBadParameter); - - comp = port->comp; - - GST_INFO_OBJECT (comp->parent, "Deallocating buffers of %s port %u", - comp->name, port->index); - - gst_omx_component_handle_messages (port->comp); - - if (!port->buffers) { - GST_DEBUG_OBJECT (comp->parent, "No buffers allocated for %s port %u", - comp->name, port->index); - goto done; - } - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - /* We still try to deallocate all buffers */ - } - - /* We only allow deallocation of buffers after they - * were all released from the port, either by flushing - * the port or by disabling it. - */ - n = port->buffers->len; - for (i = 0; i < n; i++) { - GstOMXBuffer *buf = g_ptr_array_index (port->buffers, i); - OMX_ERRORTYPE tmp = OMX_ErrorNone; - - if (buf->used) { - GST_ERROR_OBJECT (comp->parent, "Trying to free used buffer %p of %s " - "port %u", buf, comp->name, port->index); - } - - /* omx_buf can be NULL if allocation failed earlier - * and we're just shutting down - * - * errors do not cause exiting this loop because we want - * to deallocate as much as possible. - */ - if (buf->omx_buf) { - g_assert (buf == buf->omx_buf->pAppPrivate); - buf->omx_buf->pAppPrivate = NULL; - GST_DEBUG_OBJECT (comp->parent, "%s: deallocating buffer %p (%p)", - comp->name, buf, buf->omx_buf->pBuffer); - - tmp = OMX_FreeBuffer (comp->handle, port->index, buf->omx_buf); - - if (tmp != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Failed to deallocate buffer %d of %s port %u: %s (0x%08x)", i, - comp->name, port->index, gst_omx_error_to_string (tmp), tmp); - if (err == OMX_ErrorNone) - err = tmp; - } - } - g_free (buf); - } - g_queue_clear (&port->pending_buffers); - g_ptr_array_unref (port->buffers); - port->buffers = NULL; - - gst_omx_component_handle_messages (comp); - -done: - gst_omx_port_update_port_definition (port, NULL); - - DEBUG_IF_OK (comp->parent, err, "Deallocated buffers of %s port %u: %s " - "(0x%08x)", comp->name, port->index, gst_omx_error_to_string (err), err); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_deallocate_buffers (GstOMXPort * port) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_deallocate_buffers_unlocked (port); - g_mutex_unlock (&port->comp->lock); - - return err; -} - -/* NOTE: Must be called while holding comp->lock, uses comp->messages_lock */ -static OMX_ERRORTYPE -gst_omx_port_set_enabled_unlocked (GstOMXPort * port, gboolean enabled) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - - comp = port->comp; - - gst_omx_component_handle_messages (comp); - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - if (port->enabled_pending || port->disabled_pending) { - GST_ERROR_OBJECT (comp->parent, "%s port %d enabled/disabled pending " - "already", comp->name, port->index); -#if OMX_VERSION_MINOR == 2 - err = OMX_ErrorBadParameter; -#else - err = OMX_ErrorInvalidState; -#endif - goto done; - } - - GST_INFO_OBJECT (comp->parent, "Setting %s port %u to %s", comp->name, - port->index, (enabled ? "enabled" : "disabled")); - - /* Check if the port is already enabled/disabled first */ - gst_omx_port_update_port_definition (port, NULL); - if (!!port->port_def.bEnabled == !!enabled) - goto done; - - if (enabled) - port->enabled_pending = TRUE; - else - port->disabled_pending = TRUE; - - if (enabled) - err = - gst_omx_component_send_command (comp, OMX_CommandPortEnable, - port->index, NULL); - else - err = - gst_omx_component_send_command (comp, OMX_CommandPortDisable, - port->index, NULL); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Failed to send enable/disable command to %s port %u: %s (0x%08x)", - comp->name, port->index, gst_omx_error_to_string (err), err); - goto done; - } - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - goto done; - } - -done: - gst_omx_component_handle_messages (comp); - - gst_omx_port_update_port_definition (port, NULL); - - INFO_IF_OK (comp->parent, err, "Set %s port %u to %s%s: %s (0x%08x)", - comp->name, port->index, (err == OMX_ErrorNone ? "" : "not "), - (enabled ? "enabled" : "disabled"), gst_omx_error_to_string (err), err); - - return err; -} - -static OMX_ERRORTYPE -gst_omx_port_wait_buffers_released_unlocked (GstOMXPort * port, - GstClockTime timeout) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - OMX_ERRORTYPE last_error; - gboolean signalled; - - comp = port->comp; - - gst_omx_component_handle_messages (comp); - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - GST_INFO_OBJECT (comp->parent, "Waiting for %s port %u to release all " - "buffers", comp->name, port->index); - - if (timeout == 0) { - if (!port->flushed || (port->buffers - && port->buffers->len > - g_queue_get_length (&port->pending_buffers))) - err = OMX_ErrorTimeout; - goto done; - } - - /* Wait until all buffers are released by the port */ - signalled = TRUE; - last_error = OMX_ErrorNone; - gst_omx_component_handle_messages (comp); - while (signalled && last_error == OMX_ErrorNone && (port->buffers - && port->buffers->len > - g_queue_get_length (&port->pending_buffers))) { - signalled = gst_omx_component_wait_message (comp, timeout); - if (signalled) - gst_omx_component_handle_messages (comp); - last_error = comp->last_error; - } - - if (last_error != OMX_ErrorNone) { - err = last_error; - GST_ERROR_OBJECT (comp->parent, - "Got error while waiting for %s port %u to release all buffers: %s " - "(0x%08x)", comp->name, port->index, gst_omx_error_to_string (err), - err); - goto done; - } else if (!signalled) { - GST_ERROR_OBJECT (comp->parent, "Timeout waiting for %s port %u to " - "release all buffers", comp->name, port->index); - err = OMX_ErrorTimeout; - goto done; - } - -done: - gst_omx_component_handle_messages (comp); - - gst_omx_port_update_port_definition (port, NULL); - - DEBUG_IF_OK (comp->parent, err, - "Waited for %s port %u to release all buffers: %s (0x%08x)", comp->name, - port->index, gst_omx_error_to_string (err), err); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_wait_buffers_released (GstOMXPort * port, GstClockTime timeout) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_wait_buffers_released_unlocked (port, timeout); - g_mutex_unlock (&port->comp->lock); - - return err; -} - -void -gst_omx_port_requeue_buffer (GstOMXPort * port, GstOMXBuffer * buf) -{ - g_mutex_lock (&port->comp->lock); - g_queue_push_tail (&port->pending_buffers, buf); - g_mutex_unlock (&port->comp->lock); - - /* awake gst_omx_port_acquire_buffer() */ - gst_omx_component_send_message (port->comp, NULL); -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_set_enabled (GstOMXPort * port, gboolean enabled) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_set_enabled_unlocked (port, enabled); - g_mutex_unlock (&port->comp->lock); - - return err; -} - -static OMX_ERRORTYPE -gst_omx_port_populate_unlocked (GstOMXPort * port) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - GstOMXBuffer *buf; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - comp = port->comp; - - GST_DEBUG_OBJECT (comp->parent, "Populating %s port %d", comp->name, - port->index); - - gst_omx_component_handle_messages (comp); - - if (port->flushing || port->disabled_pending || !port->port_def.bEnabled) { - GST_DEBUG_OBJECT (comp->parent, "%s port %u is flushing or disabled", - comp->name, port->index); - err = OMX_ErrorIncorrectStateOperation; - goto done; - } - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s is in error state: %s" - "(0x%08x)", comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - if (port->port_def.eDir == OMX_DirOutput && port->buffers && !port->tunneled) { - /* Enqueue all buffers for the component to fill */ - while ((buf = g_queue_pop_head (&port->pending_buffers))) { - g_assert (!buf->used); - - /* Reset all flags, some implementations don't - * reset them themselves and the flags are not - * valid anymore after the buffer was consumed. - * Also reset nFilledLen as FillThisBuffer() expects an empty buffer. - */ - gst_omx_buffer_reset (buf); - - log_omx_api_trace_buffer (comp, "FillThisBuffer", buf); - err = OMX_FillThisBuffer (comp->handle, buf->omx_buf); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Failed to pass buffer %p (%p) to %s port %u: %s (0x%08x)", buf, - buf->omx_buf->pBuffer, comp->name, port->index, - gst_omx_error_to_string (err), err); - goto done; - } - GST_DEBUG_OBJECT (comp->parent, "Passed buffer %p (%p) to component %s", - buf, buf->omx_buf->pBuffer, comp->name); - } - } - -done: - gst_omx_port_update_port_definition (port, NULL); - - DEBUG_IF_OK (comp->parent, err, "Populated %s port %u: %s (0x%08x)", - comp->name, port->index, gst_omx_error_to_string (err), err); - gst_omx_component_handle_messages (comp); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_populate (GstOMXPort * port) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_populate_unlocked (port); - g_mutex_unlock (&port->comp->lock); - - return err; -} - -/* NOTE: Must be called while holding comp->lock, uses comp->messages_lock */ -static OMX_ERRORTYPE -gst_omx_port_wait_enabled_unlocked (GstOMXPort * port, GstClockTime timeout) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - gboolean signalled; - OMX_ERRORTYPE last_error; - gboolean enabled; - - comp = port->comp; - - /* Check the current port status */ - gst_omx_port_update_port_definition (port, NULL); - - if (port->enabled_pending) - enabled = TRUE; - else if (port->disabled_pending) - enabled = FALSE; - else - enabled = port->port_def.bEnabled; - - gst_omx_component_handle_messages (comp); - - if ((err = comp->last_error) != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, "Component %s in error state: %s (0x%08x)", - comp->name, gst_omx_error_to_string (err), err); - goto done; - } - - GST_INFO_OBJECT (comp->parent, "Waiting for %s port %u to be %s", - comp->name, port->index, (enabled ? "enabled" : "disabled")); - - if (timeout == 0) { - if (port->enabled_pending || port->disabled_pending) - err = OMX_ErrorTimeout; - goto done; - } - - /* And now wait until the enable/disable command is finished */ - signalled = TRUE; - last_error = OMX_ErrorNone; - gst_omx_port_update_port_definition (port, NULL); - gst_omx_component_handle_messages (comp); - while (signalled && last_error == OMX_ErrorNone && - (!!port->port_def.bEnabled != !!enabled || port->enabled_pending - || port->disabled_pending)) { - signalled = gst_omx_component_wait_message (comp, timeout); - if (signalled) - gst_omx_component_handle_messages (comp); - last_error = comp->last_error; - gst_omx_port_update_port_definition (port, NULL); - } - port->enabled_pending = FALSE; - port->disabled_pending = FALSE; - - if (!signalled) { - GST_ERROR_OBJECT (comp->parent, - "Timeout waiting for %s port %u to be %s", comp->name, port->index, - (enabled ? "enabled" : "disabled")); - err = OMX_ErrorTimeout; - goto done; - } else if (last_error != OMX_ErrorNone) { - GST_ERROR_OBJECT (comp->parent, - "Got error while waiting for %s port %u to be %s: %s (0x%08x)", - comp->name, port->index, (enabled ? "enabled" : "disabled"), - gst_omx_error_to_string (err), err); - err = last_error; - } else { - if (enabled) { - /* Reset EOS flag */ - port->eos = FALSE; - } - } - - gst_omx_component_handle_messages (comp); - -done: - gst_omx_port_update_port_definition (port, NULL); - - GST_INFO_OBJECT (comp->parent, "%s port %u is %s%s: %s (0x%08x)", comp->name, - port->index, (err == OMX_ErrorNone ? "" : "not "), - (enabled ? "enabled" : "disabled"), gst_omx_error_to_string (err), err); - - return err; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_wait_enabled (GstOMXPort * port, GstClockTime timeout) -{ - OMX_ERRORTYPE err; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - g_mutex_lock (&port->comp->lock); - err = gst_omx_port_wait_enabled_unlocked (port, timeout); - g_mutex_unlock (&port->comp->lock); - - return err; -} - -gboolean -gst_omx_port_is_enabled (GstOMXPort * port) -{ - gboolean enabled; - - g_return_val_if_fail (port != NULL, FALSE); - - gst_omx_port_update_port_definition (port, NULL); - enabled = !!port->port_def.bEnabled; - - GST_DEBUG_OBJECT (port->comp->parent, "%s port %u is enabled: %d", - port->comp->name, port->index, enabled); - - return enabled; -} - -/* NOTE: Uses comp->lock and comp->messages_lock */ -OMX_ERRORTYPE -gst_omx_port_mark_reconfigured (GstOMXPort * port) -{ - GstOMXComponent *comp; - OMX_ERRORTYPE err = OMX_ErrorNone; - - g_return_val_if_fail (port != NULL, OMX_ErrorUndefined); - - comp = port->comp; - - g_mutex_lock (&comp->lock); - GST_INFO_OBJECT (comp->parent, "Marking %s port %u is reconfigured", - comp->name, port->index); - - gst_omx_component_handle_messages (comp); - - if ((err = comp->last_error) != OMX_ErrorNone) - goto done; - - port->configured_settings_cookie = port->settings_cookie; - - if (port->port_def.eDir == OMX_DirOutput) { - GList *l; - - for (l = comp->pending_reconfigure_outports; l; l = l->next) { - if (l->data == (gpointer) port) { - comp->pending_reconfigure_outports = - g_list_delete_link (comp->pending_reconfigure_outports, l); - break; - } - } - if (!comp->pending_reconfigure_outports) - gst_omx_component_send_message (comp, NULL); - } - -done: - gst_omx_port_update_port_definition (port, NULL); - - INFO_IF_OK (comp->parent, err, "Marked %s port %u as reconfigured: %s " - "(0x%08x)", comp->name, port->index, gst_omx_error_to_string (err), err); - - g_mutex_unlock (&comp->lock); - - return err; -} - -/* The OMX specs states that the nBufferCountActual of a port has to default - * to its nBufferCountMin. If we don't change nBufferCountActual we purely rely - * on this default. But in some cases, OMX may change nBufferCountMin before we - * allocate buffers. Like for example when configuring the input ports with the - * actual format, it may decrease the number of minimal buffers required. - * This method checks this and update nBufferCountActual if needed so we'll use - * less buffers than the worst case in such scenarios. - */ -gboolean -gst_omx_port_ensure_buffer_count_actual (GstOMXPort * port, guint extra) -{ - OMX_PARAM_PORTDEFINITIONTYPE port_def; - guint nb; - - gst_omx_port_get_port_definition (port, &port_def); - - nb = port_def.nBufferCountMin + extra; - if (port_def.nBufferCountActual != nb) { - port_def.nBufferCountActual = nb; - - GST_DEBUG_OBJECT (port->comp->parent, - "set port %d nBufferCountActual to %d", (guint) port->index, nb); - - if (gst_omx_port_update_port_definition (port, &port_def) != OMX_ErrorNone) - return FALSE; - } - - return TRUE; -} - -gboolean -gst_omx_port_update_buffer_count_actual (GstOMXPort * port, guint nb) -{ - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - - if (nb < port_def.nBufferCountMin) { - GST_DEBUG_OBJECT (port->comp->parent, - "Requested to use %d buffers on port %d but it's minimum is %d", nb, - (guint) port->index, (guint) port_def.nBufferCountMin); - - nb = port_def.nBufferCountMin; - } - - if (port_def.nBufferCountActual != nb) { - port_def.nBufferCountActual = nb; - - GST_DEBUG_OBJECT (port->comp->parent, - "set port %d nBufferCountActual to %d", (guint) port->index, nb); - - if (gst_omx_port_update_port_definition (port, &port_def) != OMX_ErrorNone) - return FALSE; - } - - return TRUE; -} - -gboolean -gst_omx_port_set_dmabuf (GstOMXPort * port, gboolean dmabuf) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - OMX_ALG_PORT_PARAM_BUFFER_MODE buffer_mode; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&buffer_mode); - buffer_mode.nPortIndex = port->index; - - if (dmabuf) - buffer_mode.eMode = OMX_ALG_BUF_DMA; - else - buffer_mode.eMode = OMX_ALG_BUF_NORMAL; - - err = - gst_omx_component_set_parameter (port->comp, - (OMX_INDEXTYPE) OMX_ALG_IndexPortParamBufferMode, &buffer_mode); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (port->comp->parent, - "Failed to set port %d in %sdmabuf mode: %s (0x%08x)", - port->index, dmabuf ? "" : "non-", gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -#else - /* dmabuf not supported for this platform */ - return FALSE; -#endif -} - -gboolean -gst_omx_port_set_subframe (GstOMXPort * port, gboolean enabled) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - OMX_ALG_VIDEO_PARAM_SUBFRAME subframe_mode; - OMX_ERRORTYPE err; - GST_DEBUG_OBJECT (port->comp->parent, "%s subframe mode for Zynq", - enabled ? "Enable" : "Disable"); - GST_OMX_INIT_STRUCT (&subframe_mode); - subframe_mode.nPortIndex = port->index; - - subframe_mode.bEnableSubframe = enabled; - - err = gst_omx_component_set_parameter (port->comp, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoSubframe, &subframe_mode); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (port->comp->parent, - "Failed to %s subframe mode on port %d: %s (0x%08x)", - enabled ? "enable" : "disable", port->index, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -#else - /* subframe mode is not supported on this platform */ - return FALSE; -#endif -} - -gboolean -gst_omx_port_get_subframe (GstOMXPort * port) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - OMX_ALG_VIDEO_PARAM_SUBFRAME subframe_mode; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&subframe_mode); - subframe_mode.nPortIndex = port->index; - - err = gst_omx_component_get_parameter (port->comp, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoSubframe, &subframe_mode); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (port->comp->parent, - "Failed to get subframe mode on port %d: %s (0x%08x)", - port->index, gst_omx_error_to_string (err), err); - return FALSE; - } - - return subframe_mode.bEnableSubframe; -#else - /* subframe mode is not supported on this platform */ - return FALSE; -#endif -} - -typedef GType (*GGetTypeFunction) (void); - -static const GGetTypeFunction types[] = { - gst_omx_analog_audio_sink_get_type, gst_omx_hdmi_audio_sink_get_type, - gst_omx_mpeg2_video_dec_get_type, gst_omx_mpeg4_video_dec_get_type, - gst_omx_h264_dec_get_type, gst_omx_h263_dec_get_type, - gst_omx_wmv_dec_get_type, gst_omx_mpeg4_video_enc_get_type, - gst_omx_h264_enc_get_type, gst_omx_h263_enc_get_type, - gst_omx_aac_enc_get_type, gst_omx_mjpeg_dec_get_type, - gst_omx_aac_dec_get_type, gst_omx_mp3_dec_get_type, - gst_omx_aac_dec_get_type, gst_omx_mp3_enc_get_type, - gst_omx_amr_dec_get_type -#ifdef HAVE_VP8 - , gst_omx_vp8_dec_get_type -#endif -#ifdef HAVE_THEORA - , gst_omx_theora_dec_get_type -#endif -#ifdef HAVE_HEVC - , gst_omx_h265_enc_get_type, gst_omx_h265_dec_get_type -#endif -}; - -struct TypeOffest -{ - GType (*get_type) (void); - glong offset; -}; - -static const struct TypeOffest base_types[] = { - {gst_omx_audio_sink_get_type, G_STRUCT_OFFSET (GstOMXAudioSinkClass, cdata)}, - {gst_omx_video_dec_get_type, G_STRUCT_OFFSET (GstOMXVideoDecClass, cdata)}, - {gst_omx_video_enc_get_type, G_STRUCT_OFFSET (GstOMXVideoEncClass, cdata)}, - {gst_omx_audio_dec_get_type, G_STRUCT_OFFSET (GstOMXAudioDecClass, cdata)}, - {gst_omx_audio_enc_get_type, G_STRUCT_OFFSET (GstOMXAudioEncClass, cdata)}, -}; - -static GKeyFile *config = NULL; -GKeyFile * -gst_omx_get_configuration (void) -{ - return config; -} - -const gchar * -gst_omx_error_to_string (OMX_ERRORTYPE err) -{ - guint err_u = (guint) err; - - switch (err_u) { - case OMX_ErrorNone: - return "None"; - case OMX_ErrorInsufficientResources: - return "Insufficient resources"; - case OMX_ErrorUndefined: - return "Undefined"; - case OMX_ErrorInvalidComponentName: - return "Invalid component name"; - case OMX_ErrorComponentNotFound: - return "Component not found"; - case OMX_ErrorBadParameter: - return "Bad parameter"; - case OMX_ErrorNotImplemented: - return "Not implemented"; - case OMX_ErrorUnderflow: - return "Underflow"; - case OMX_ErrorOverflow: - return "Overflow"; - case OMX_ErrorHardware: - return "Hardware"; - case OMX_ErrorStreamCorrupt: - return "Stream corrupt"; - case OMX_ErrorPortsNotCompatible: - return "Ports not compatible"; - case OMX_ErrorResourcesLost: - return "Resources lost"; - case OMX_ErrorNoMore: - return "No more"; - case OMX_ErrorVersionMismatch: - return "Version mismatch"; - case OMX_ErrorNotReady: - return "Not ready"; - case OMX_ErrorTimeout: - return "Timeout"; - case OMX_ErrorSameState: - return "Same state"; - case OMX_ErrorResourcesPreempted: - return "Resources preempted"; - case OMX_ErrorIncorrectStateTransition: - return "Incorrect state transition"; - case OMX_ErrorIncorrectStateOperation: - return "Incorrect state operation"; - case OMX_ErrorUnsupportedSetting: - return "Unsupported setting"; - case OMX_ErrorUnsupportedIndex: - return "Unsupported index"; - case OMX_ErrorBadPortIndex: - return "Bad port index"; - case OMX_ErrorPortUnpopulated: - return "Port unpopulated"; - case OMX_ErrorComponentSuspended: - return "Component suspended"; - case OMX_ErrorDynamicResourcesUnavailable: - return "Dynamic resources unavailable"; - case OMX_ErrorMbErrorsInFrame: - return "Macroblock errors in frame"; - case OMX_ErrorFormatNotDetected: - return "Format not detected"; - case OMX_ErrorSeperateTablesUsed: - return "Separate tables used"; - case OMX_ErrorTunnelingUnsupported: - return "Tunneling unsupported"; -#if OMX_VERSION_MINOR == 1 - case OMX_ErrorInvalidComponent: - return "Invalid component"; - case OMX_ErrorInvalidState: - return "Invalid state"; - case OMX_ErrorPortUnresponsiveDuringAllocation: - return "Port unresponsive during allocation"; - case OMX_ErrorPortUnresponsiveDuringDeallocation: - return "Port unresponsive during deallocation"; - case OMX_ErrorPortUnresponsiveDuringStop: - return "Port unresponsive during stop"; - case OMX_ErrorContentPipeOpenFailed: - return "Content pipe open failed"; - case OMX_ErrorContentPipeCreationFailed: - return "Content pipe creation failed"; -#endif - default: - if (err_u >= (guint) OMX_ErrorKhronosExtensions - && err_u < (guint) OMX_ErrorVendorStartUnused) { - return "Khronos extension error"; - } else if (err_u >= (guint) OMX_ErrorVendorStartUnused - && err_u < (guint) OMX_ErrorMax) { - return "Vendor specific error"; - } else { - return "Unknown error"; - } - } -} - -const gchar * -gst_omx_state_to_string (OMX_STATETYPE state) -{ - switch (state) { - case OMX_StateInvalid: - return "Invalid"; - case OMX_StateLoaded: - return "Loaded"; - case OMX_StateIdle: - return "Idle"; - case OMX_StateExecuting: - return "Executing"; - case OMX_StatePause: - return "Pause"; - case OMX_StateWaitForResources: - return "WaitForResources"; - default: - if (state >= OMX_StateKhronosExtensions - && state < OMX_StateVendorStartUnused) - return "KhronosExtensionState"; - else if (state >= OMX_StateVendorStartUnused && state < OMX_StateMax) - return "CustomVendorState"; - break; - } - return "Unknown state"; -} - -const gchar * -gst_omx_command_to_string (OMX_COMMANDTYPE cmd) -{ - switch (cmd) { - case OMX_CommandStateSet: - return "SetState"; - case OMX_CommandFlush: - return "Flush"; - case OMX_CommandPortDisable: - return "DisablePort"; - case OMX_CommandPortEnable: - return "EnablePort"; - case OMX_CommandMarkBuffer: - return "MarkBuffer"; - default: - if (cmd >= OMX_CommandKhronosExtensions - && cmd < OMX_CommandVendorStartUnused) - return "KhronosExtensionCommand"; - if (cmd >= OMX_CommandVendorStartUnused && cmd < OMX_CommandMax) - return "VendorExtensionCommand"; - break; - } - return "Unknown command"; -} - -struct BufferFlagString -{ - guint32 flag; - const gchar *str; -}; - -struct BufferFlagString buffer_flags_map[] = { - {OMX_BUFFERFLAG_EOS, "eos"}, - {OMX_BUFFERFLAG_STARTTIME, "start-time"}, - {OMX_BUFFERFLAG_DECODEONLY, "decode-only"}, - {OMX_BUFFERFLAG_DATACORRUPT, "data-corrupt"}, - {OMX_BUFFERFLAG_ENDOFFRAME, "end-of-frame"}, - {OMX_BUFFERFLAG_SYNCFRAME, "sync-frame"}, - {OMX_BUFFERFLAG_EXTRADATA, "extra-data"}, - {OMX_BUFFERFLAG_CODECCONFIG, "codec-config"}, - /* Introduced in OMX 1.2.0 */ -#ifdef OMX_BUFFERFLAG_TIMESTAMPINVALID - {OMX_BUFFERFLAG_TIMESTAMPINVALID, "timestamp-invalid"}, -#endif -#ifdef OMX_BUFFERFLAG_READONLY - {OMX_BUFFERFLAG_READONLY, "read-only"}, -#endif -#ifdef OMX_BUFFERFLAG_ENDOFSUBFRAME - {OMX_BUFFERFLAG_ENDOFSUBFRAME, "end-of-subframe"}, -#endif -#ifdef OMX_BUFFERFLAG_SKIPFRAME - {OMX_BUFFERFLAG_SKIPFRAME, "skip-frame"}, -#endif -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - {OMX_ALG_BUFFERFLAG_TOP_FIELD, "top-field"}, - {OMX_ALG_BUFFERFLAG_BOT_FIELD, "bottom-field"}, -#endif - {0, NULL}, -}; - - -const gchar * -gst_omx_buffer_flags_to_string (guint32 flags) -{ - GString *s = NULL; - guint i; - const gchar *str; - - if (flags == 0) - return ""; - - /* Keep a cache of the string representation of the flags so we don't allocate - * and free strings for each buffer. In practice we should only have a handfull - * of flags so the cache won't consume much memory. */ - if (!buffer_flags_str) { - G_LOCK (buffer_flags_str); - buffer_flags_str = g_hash_table_new_full (NULL, NULL, NULL, g_free); - G_UNLOCK (buffer_flags_str); - } - - str = g_hash_table_lookup (buffer_flags_str, GUINT_TO_POINTER (flags)); - if (str) - return str; - - for (i = 0; buffer_flags_map[i].str != NULL; i++) { - if ((flags & buffer_flags_map[i].flag) == 0) - continue; - - if (!s) - s = g_string_new (buffer_flags_map[i].str); - else - g_string_append_printf (s, ", %s", buffer_flags_map[i].str); - } - - if (!s) - return ""; - - str = g_string_free (s, FALSE); - - G_LOCK (buffer_flags_str); - /* Transfer ownership of str to hash table */ - g_hash_table_insert (buffer_flags_str, GUINT_TO_POINTER (flags), - (gchar *) str); - G_UNLOCK (buffer_flags_str); - - return str; -} - -#if defined(USE_OMX_TARGET_RPI) -#define DEFAULT_HACKS (GST_OMX_HACK_NO_COMPONENT_ROLE | GST_OMX_HACK_HEIGHT_MULTIPLE_16) -#else -#define DEFAULT_HACKS (0) -#endif - -guint64 -gst_omx_parse_hacks (gchar ** hacks) -{ - guint64 hacks_flags = DEFAULT_HACKS; - - if (!hacks) - return 0; - - while (*hacks) { - if (g_str_equal (*hacks, - "event-port-settings-changed-ndata-parameter-swap")) - hacks_flags |= - GST_OMX_HACK_EVENT_PORT_SETTINGS_CHANGED_NDATA_PARAMETER_SWAP; - else if (g_str_equal (*hacks, "event-port-settings-changed-port-0-to-1")) - hacks_flags |= GST_OMX_HACK_EVENT_PORT_SETTINGS_CHANGED_PORT_0_TO_1; - else if (g_str_equal (*hacks, "video-framerate-integer")) - hacks_flags |= GST_OMX_HACK_VIDEO_FRAMERATE_INTEGER; - else if (g_str_equal (*hacks, "syncframe-flag-not-used")) - hacks_flags |= GST_OMX_HACK_SYNCFRAME_FLAG_NOT_USED; - else if (g_str_equal (*hacks, "no-component-reconfigure")) - hacks_flags |= GST_OMX_HACK_NO_COMPONENT_RECONFIGURE; - else if (g_str_equal (*hacks, "no-empty-eos-buffer")) - hacks_flags |= GST_OMX_HACK_NO_EMPTY_EOS_BUFFER; - else if (g_str_equal (*hacks, "drain-may-not-return")) - hacks_flags |= GST_OMX_HACK_DRAIN_MAY_NOT_RETURN; - else if (g_str_equal (*hacks, "no-component-role")) - hacks_flags |= GST_OMX_HACK_NO_COMPONENT_ROLE; - else if (g_str_equal (*hacks, "no-disable-outport")) - hacks_flags |= GST_OMX_HACK_NO_DISABLE_OUTPORT; - else if (g_str_equal (*hacks, "signals-premature-eos")) - hacks_flags |= GST_OMX_HACK_SIGNALS_PREMATURE_EOS; - else if (g_str_equal (*hacks, "height-multiple-16")) - hacks_flags |= GST_OMX_HACK_HEIGHT_MULTIPLE_16; - else if (g_str_equal (*hacks, "pass-profile-to-decoder")) - hacks_flags |= GST_OMX_HACK_PASS_PROFILE_TO_DECODER; - else if (g_str_equal (*hacks, "pass-color-format-to-decoder")) - hacks_flags |= GST_OMX_HACK_PASS_COLOR_FORMAT_TO_DECODER; - else if (g_str_equal (*hacks, "ensure-buffer-count-actual")) - hacks_flags |= GST_OMX_HACK_ENSURE_BUFFER_COUNT_ACTUAL; - else - GST_WARNING ("Unknown hack: %s", *hacks); - hacks++; - } - - return hacks_flags; -} - - -void -gst_omx_set_default_role (GstOMXClassData * class_data, - const gchar * default_role) -{ - if (!class_data->component_role) - class_data->component_role = default_role; -} - -static void -_class_init (gpointer g_class, gpointer data) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (g_class); - GstOMXClassData *class_data = NULL; - GKeyFile *config; - const gchar *element_name = data; - GError *err; - gchar *core_name, *component_name, *component_role; - gint in_port_index, out_port_index; - gchar *template_caps; - GstPadTemplate *templ; - GstCaps *caps; - gchar **hacks; - int i; - - if (!element_name) - return; - - /* Find the GstOMXClassData for this class */ - for (i = 0; i < G_N_ELEMENTS (base_types); i++) { - GType gtype = base_types[i].get_type (); - - if (G_TYPE_CHECK_CLASS_TYPE (g_class, gtype)) { - class_data = (GstOMXClassData *) - (((guint8 *) g_class) + base_types[i].offset); - break; - } - } - - g_assert (class_data != NULL); - - config = gst_omx_get_configuration (); - - /* This will alwaxys succeed, see check in plugin_init */ - core_name = g_key_file_get_string (config, element_name, "core-name", NULL); - g_assert (core_name != NULL); - class_data->core_name = core_name; - component_name = - g_key_file_get_string (config, element_name, "component-name", NULL); - g_assert (component_name != NULL); - class_data->component_name = component_name; - - /* If this fails we simply don't set a role */ - if ((component_role = - g_key_file_get_string (config, element_name, "component-role", - NULL))) { - GST_DEBUG ("Using component-role '%s' for element '%s'", component_role, - element_name); - class_data->component_role = component_role; - } - - - /* Now set the inport/outport indizes and assume sane defaults */ - err = NULL; - in_port_index = - g_key_file_get_integer (config, element_name, "in-port-index", &err); - if (err != NULL) { - GST_DEBUG ("No 'in-port-index' set for element '%s', auto-detecting: %s", - element_name, err->message); - in_port_index = -1; - g_error_free (err); - } - class_data->in_port_index = in_port_index; - - err = NULL; - out_port_index = - g_key_file_get_integer (config, element_name, "out-port-index", &err); - if (err != NULL) { - GST_DEBUG ("No 'out-port-index' set for element '%s', auto-detecting: %s", - element_name, err->message); - out_port_index = -1; - g_error_free (err); - } - class_data->out_port_index = out_port_index; - - /* Add pad templates */ - err = NULL; - if (class_data->type != GST_OMX_COMPONENT_TYPE_SOURCE) { - if (!(template_caps = - g_key_file_get_string (config, element_name, "sink-template-caps", - &err))) { - GST_DEBUG - ("No sink template caps specified for element '%s', using default '%s'", - element_name, class_data->default_sink_template_caps); - caps = gst_caps_from_string (class_data->default_sink_template_caps); - g_assert (caps != NULL); - g_error_free (err); - } else { - caps = gst_caps_from_string (template_caps); - if (!caps) { - GST_DEBUG - ("Could not parse sink template caps '%s' for element '%s', using default '%s'", - template_caps, element_name, - class_data->default_sink_template_caps); - caps = gst_caps_from_string (class_data->default_sink_template_caps); - g_assert (caps != NULL); - } - } - templ = gst_pad_template_new ("sink", GST_PAD_SINK, GST_PAD_ALWAYS, caps); - g_free (template_caps); - gst_element_class_add_pad_template (element_class, templ); - gst_caps_unref (caps); - } - - err = NULL; - if (class_data->type != GST_OMX_COMPONENT_TYPE_SINK) { - if (!(template_caps = - g_key_file_get_string (config, element_name, "src-template-caps", - &err))) { - GST_DEBUG - ("No src template caps specified for element '%s', using default '%s'", - element_name, class_data->default_src_template_caps); - caps = gst_caps_from_string (class_data->default_src_template_caps); - g_assert (caps != NULL); - g_error_free (err); - } else { - caps = gst_caps_from_string (template_caps); - if (!caps) { - GST_DEBUG - ("Could not parse src template caps '%s' for element '%s', using default '%s'", - template_caps, element_name, class_data->default_src_template_caps); - caps = gst_caps_from_string (class_data->default_src_template_caps); - g_assert (caps != NULL); - } - } - templ = gst_pad_template_new ("src", GST_PAD_SRC, GST_PAD_ALWAYS, caps); - g_free (template_caps); - gst_element_class_add_pad_template (element_class, templ); - gst_caps_unref (caps); - } - - if ((hacks = - g_key_file_get_string_list (config, element_name, "hacks", NULL, - NULL))) { -#ifndef GST_DISABLE_GST_DEBUG - gchar **walk = hacks; - - while (*walk) { - GST_DEBUG ("Using hack: %s", *walk); - walk++; - } -#endif - - class_data->hacks = gst_omx_parse_hacks (hacks); - g_strfreev (hacks); - } -} - -static gboolean -plugin_init (GstPlugin * plugin) -{ - GError *err = NULL; - gchar **config_dirs; - gchar **elements; - gchar *env_config_dir; - const gchar *user_config_dir; - const gchar *const *system_config_dirs; - gint i, j; - gsize n_elements; - static const gchar *config_name[] = { "gstomx.conf", NULL }; - static const gchar *env_config_name[] = { "GST_OMX_CONFIG_DIR", NULL }; - static const gchar *gst_omx_config_dir = GST_OMX_CONFIG_DIR; - - GST_DEBUG_CATEGORY_INIT (gstomx_debug, "omx", 0, "gst-omx"); - GST_DEBUG_CATEGORY_INIT (gst_omx_video_debug_category, "omxvideo", 0, - "gst-omx-video"); - GST_DEBUG_CATEGORY_INIT (OMX_API_TRACE, "OMX_API_TRACE", 0, - "gst-omx performace"); - - /* Read configuration file gstomx.conf from the preferred - * configuration directories */ - env_config_dir = g_strdup (g_getenv (*env_config_name)); - user_config_dir = g_get_user_config_dir (); - system_config_dirs = g_get_system_config_dirs (); - config_dirs = - g_new (gchar *, g_strv_length ((gchar **) system_config_dirs) + 4); - - i = 0; - j = 0; - if (env_config_dir) - config_dirs[i++] = (gchar *) env_config_dir; - config_dirs[i++] = (gchar *) user_config_dir; - while (system_config_dirs[j]) - config_dirs[i++] = (gchar *) system_config_dirs[j++]; - config_dirs[i++] = (gchar *) gst_omx_config_dir; - config_dirs[i++] = NULL; - - gst_plugin_add_dependency (plugin, env_config_name, - (const gchar **) (config_dirs + (env_config_dir ? 1 : 0)), config_name, - GST_PLUGIN_DEPENDENCY_FLAG_NONE); - - config = g_key_file_new (); - if (!g_key_file_load_from_dirs (config, *config_name, - (const gchar **) config_dirs, NULL, G_KEY_FILE_NONE, &err)) { -#ifdef USE_OMX_TARGET_GENERIC - GST_INFO ("No configuration file found; " - "ignore as gst-omx has been built with the generic target used only for testing"); -#else - { - gchar *paths; - - paths = g_strjoinv (":", config_dirs); - GST_ERROR - ("Failed to load configuration file: %s (searched in: %s as per " - "GST_OMX_CONFIG_DIR environment variable, the xdg user config " - "directory (or XDG_CONFIG_HOME) and the system config directory " - "(or XDG_CONFIG_DIRS)", err->message, paths); - g_free (paths); - } -#endif /* USE_OMX_TARGET_GENERIC */ - - g_error_free (err); - goto done; - } - - /* Initialize all types */ - for (i = 0; i < G_N_ELEMENTS (types); i++) - types[i] (); - - elements = g_key_file_get_groups (config, &n_elements); - for (i = 0; i < n_elements; i++) { - GTypeQuery type_query; - GTypeInfo type_info = { 0, }; - GType type, subtype; - gchar *type_name, *core_name, *component_name; - gint rank; - - GST_DEBUG ("Registering element '%s'", elements[i]); - - err = NULL; - if (!(type_name = - g_key_file_get_string (config, elements[i], "type-name", &err))) { - GST_ERROR - ("Unable to read 'type-name' configuration for element '%s': %s", - elements[i], err->message); - g_error_free (err); - continue; - } - - type = g_type_from_name (type_name); - if (type == G_TYPE_INVALID) { - GST_ERROR ("Invalid type name '%s' for element '%s'", type_name, - elements[i]); - g_free (type_name); - continue; - } - if (!g_type_is_a (type, GST_TYPE_ELEMENT)) { - GST_ERROR ("Type '%s' is no GstElement subtype for element '%s'", - type_name, elements[i]); - g_free (type_name); - continue; - } - g_free (type_name); - - /* And now some sanity checking */ - err = NULL; - if (!(core_name = - g_key_file_get_string (config, elements[i], "core-name", &err))) { - GST_ERROR - ("Unable to read 'core-name' configuration for element '%s': %s", - elements[i], err->message); - g_error_free (err); - continue; - } - if (!g_file_test (core_name, G_FILE_TEST_IS_REGULAR)) { - GST_ERROR ("Core '%s' does not exist for element '%s'", core_name, - elements[i]); - g_free (core_name); - continue; - } - g_free (core_name); - - err = NULL; - if (!(component_name = - g_key_file_get_string (config, elements[i], "component-name", - &err))) { - GST_ERROR - ("Unable to read 'component-name' configuration for element '%s': %s", - elements[i], err->message); - g_error_free (err); - continue; - } - g_free (component_name); - - err = NULL; - rank = g_key_file_get_integer (config, elements[i], "rank", &err); - if (err != NULL) { - GST_ERROR ("No rank set for element '%s': %s", elements[i], err->message); - g_error_free (err); - continue; - } - - /* And now register the type, all other configuration will - * be handled by the type itself */ - g_type_query (type, &type_query); - memset (&type_info, 0, sizeof (type_info)); - type_info.class_size = type_query.class_size; - type_info.instance_size = type_query.instance_size; - type_info.class_init = _class_init; - type_info.class_data = g_strdup (elements[i]); - type_name = g_strdup_printf ("%s-%s", g_type_name (type), elements[i]); - if (g_type_from_name (type_name) != G_TYPE_INVALID) { - GST_ERROR ("Type '%s' already exists for element '%s'", type_name, - elements[i]); - g_free (type_name); - continue; - } - subtype = g_type_register_static (type, type_name, &type_info, 0); - g_free (type_name); - gst_element_register (plugin, elements[i], rank, subtype); - } - g_strfreev (elements); - -done: - g_free (env_config_dir); - g_free (config_dirs); - - return TRUE; -} - -GST_PLUGIN_DEFINE (GST_VERSION_MAJOR, - GST_VERSION_MINOR, - omx, - "GStreamer OpenMAX Plug-ins", - plugin_init, - PACKAGE_VERSION, GST_LICENSE, GST_PACKAGE_NAME, GST_PACKAGE_ORIGIN) diff --git a/subprojects/gst-omx/omx/gstomx.h b/subprojects/gst-omx/omx/gstomx.h deleted file mode 100644 index 68624632df..0000000000 --- a/subprojects/gst-omx/omx/gstomx.h +++ /dev/null @@ -1,493 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H__ -#define __GST_OMX_H__ - -#include -#include -#include -#include - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#ifdef GST_OMX_STRUCT_PACKING -# if GST_OMX_STRUCT_PACKING == 1 -# pragma pack(1) -# elif GST_OMX_STRUCT_PACKING == 2 -# pragma pack(2) -# elif GST_OMX_STRUCT_PACKING == 4 -# pragma pack(4) -# elif GST_OMX_STRUCT_PACKING == 8 -# pragma pack(8) -# else -# error "Unsupported struct packing value" -# endif -#endif - -/* If the component may signal EOS before it has finished pushing - * out all of its buffers. Happens with egl_render on the rpi. - */ -#define GST_OMX_HACK_SIGNALS_PREMATURE_EOS G_GUINT64_CONSTANT (0x0000000000000400) - -#include -#include - -#ifdef USE_OMX_TARGET_RPI -#include -#endif - -#ifdef HAVE_VIDEO_EXT -#include -#endif - -#ifdef HAVE_INDEX_EXT -#include -#endif - -#ifdef HAVE_COMPONENT_EXT -#include -#endif - -#ifdef HAVE_CORE_EXT -#include -#endif - -#ifdef HAVE_AUDIO_EXT -#include -#endif - -#ifdef HAVE_IV_COMMON_EXT -#include -#endif - -#ifdef HAVE_IMAGE_EXT -#include -#endif - -#ifdef HAVE_OTHER_EXT -#include -#endif - -#ifdef GST_OMX_STRUCT_PACKING -#pragma pack() -#endif - -G_BEGIN_DECLS - -#define GST_OMX_INIT_STRUCT(st) G_STMT_START { \ - memset ((st), 0, sizeof (*(st))); \ - (st)->nSize = sizeof (*(st)); \ - (st)->nVersion.s.nVersionMajor = OMX_VERSION_MAJOR; \ - (st)->nVersion.s.nVersionMinor = OMX_VERSION_MINOR; \ - (st)->nVersion.s.nRevision = OMX_VERSION_REVISION; \ - (st)->nVersion.s.nStep = OMX_VERSION_STEP; \ -} G_STMT_END - -#ifdef OMX_SKIP64BIT -#define GST_OMX_GET_TICKS(ticks) ((((guint64) (ticks).nHighPart) << 32) | ((ticks).nLowPart)) -#define GST_OMX_SET_TICKS(ticks, i) G_STMT_START { \ - ticks.nLowPart = ((guint64) (i)) & 0xffffffff; \ - ticks.nHighPart = ((guint64) (i)) >> 32; \ -} G_STMT_END -#else -#define GST_OMX_GET_TICKS(ticks) (ticks) -#define GST_OMX_SET_TICKS(ticks, i) G_STMT_START { \ - ticks = i; \ -} G_STMT_END -#endif - -/* If set on an element property means "use the OMX default value". - * If set on a default_* variable means that the default values hasn't been - * retrieved from OMX yet. */ -#define GST_OMX_PROP_OMX_DEFAULT G_MAXUINT32 - -/* OMX_StateInvalid does not exist in 1.2.0 spec. The initial state is now - * StateLoaded. Problem is that gst-omx still needs an initial state different - * than StateLoaded. Otherwise gst_omx_component_set_state(StateLoaded) will - * early return because it will think it is already in StateLoaded. Also note - * that there is no call to gst_omx_component_set_state(StateInvalid) so this - * also shows that StateInvalid is used as a helper in gst-omx. - */ -#if OMX_VERSION_MINOR == 2 -#define OMX_StateInvalid OMX_StateReserved_0x00000000 -#endif - -/* Different hacks that are required to work around - * bugs in different OpenMAX implementations - */ -/* In the EventSettingsChanged callback use nData2 instead of nData1 for - * the port index. Happens with Bellagio. - */ -#define GST_OMX_HACK_EVENT_PORT_SETTINGS_CHANGED_NDATA_PARAMETER_SWAP G_GUINT64_CONSTANT (0x0000000000000001) -/* In the EventSettingsChanged callback assume that port index 0 really - * means port index 1. Happens with the Bellagio ffmpegdist video decoder. - */ -#define GST_OMX_HACK_EVENT_PORT_SETTINGS_CHANGED_PORT_0_TO_1 G_GUINT64_CONSTANT (0x0000000000000002) -/* If the video framerate is not specified as fraction (Q.16) but as - * integer number. Happens with the Bellagio ffmpegdist video encoder. - */ -#define GST_OMX_HACK_VIDEO_FRAMERATE_INTEGER G_GUINT64_CONSTANT (0x0000000000000004) -/* If the SYNCFRAME flag on encoder output buffers is not used and we - * have to assume that all frames are sync frames. - * Happens with the Bellagio ffmpegdist video encoder. - */ -#define GST_OMX_HACK_SYNCFRAME_FLAG_NOT_USED G_GUINT64_CONSTANT (0x0000000000000008) -/* If the component needs to be re-created if the caps change. - * Happens with Qualcomm's OpenMAX implementation. - */ -#define GST_OMX_HACK_NO_COMPONENT_RECONFIGURE G_GUINT64_CONSTANT (0x0000000000000010) - -/* If the component does not accept empty EOS buffers. - * Happens with Qualcomm's OpenMAX implementation. - */ -#define GST_OMX_HACK_NO_EMPTY_EOS_BUFFER G_GUINT64_CONSTANT (0x0000000000000020) - -/* If the component might not acknowledge a drain. - * Happens with TI's Ducati OpenMAX implementation. - */ -#define GST_OMX_HACK_DRAIN_MAY_NOT_RETURN G_GUINT64_CONSTANT (0x0000000000000040) - -/* If the component doesn't allow any component role to be set. - * Happens with Broadcom's OpenMAX implementation. - */ -#define GST_OMX_HACK_NO_COMPONENT_ROLE G_GUINT64_CONSTANT (0x0000000000000080) - -/* If the component doesn't allow disabling the outport while - * when setting the format until the output format is known. - */ -#define GST_OMX_HACK_NO_DISABLE_OUTPORT G_GUINT64_CONSTANT (0x0000000000000100) - -/* If the encoder requires input buffers that have a height - * which is a multiple of 16 pixels - */ -#define GST_OMX_HACK_HEIGHT_MULTIPLE_16 G_GUINT64_CONSTANT (0x0000000000000200) - -/* If we should pass the profile/level information from upstream to the - * OMX decoder. This is a violation of the OMX spec as - * OMX_IndexParamVideoProfileLevelCurrent is supposed to be r-o so - * do it as a platform specific hack. - */ -#define GST_OMX_HACK_PASS_PROFILE_TO_DECODER G_GUINT64_CONSTANT (0x0000000000000800) - -/* If we should pass the color format information from upstream to the - * OMX decoder input. This is a violation of the OMX spec as - * the eColorFormat field is supposed to only be used if eCompressionFormat is - * set to OMX_IMAGE_CodingUnused. - * Do this as a platform specific hack for OMX implementation which may use - * this information to pre-allocate internal buffers for example. - */ -#define GST_OMX_HACK_PASS_COLOR_FORMAT_TO_DECODER G_GUINT64_CONSTANT (0x0000000000001000) - -/* If set, automatically update nBufferCountActual to nBufferCountMin before - * allocating buffers. This can be used on OMX implementation decreasing - * nBufferCountMin depending of the format and so can reduce the number - * of allocated buffers. - */ -#define GST_OMX_HACK_ENSURE_BUFFER_COUNT_ACTUAL G_GUINT64_CONSTANT (0x0000000000002000) - -typedef struct _GstOMXCore GstOMXCore; -typedef struct _GstOMXPort GstOMXPort; -typedef enum _GstOMXPortDirection GstOMXPortDirection; -typedef struct _GstOMXComponent GstOMXComponent; -typedef struct _GstOMXBuffer GstOMXBuffer; -typedef struct _GstOMXClassData GstOMXClassData; -typedef struct _GstOMXMessage GstOMXMessage; - -typedef enum { - /* Everything good and the buffer is valid */ - GST_OMX_ACQUIRE_BUFFER_OK = 0, - /* The port is flushing, exit ASAP */ - GST_OMX_ACQUIRE_BUFFER_FLUSHING, - /* The port must be reconfigured */ - GST_OMX_ACQUIRE_BUFFER_RECONFIGURE, - /* The port is EOS */ - GST_OMX_ACQUIRE_BUFFER_EOS, - /* A fatal error happened */ - GST_OMX_ACQUIRE_BUFFER_ERROR, - /* No buffer is currently available (used when calling gst_omx_port_acquire_buffer() in not waiting mode) */ - GST_OMX_ACQUIRE_BUFFER_NO_AVAILABLE, -} GstOMXAcquireBufferReturn; - -struct _GstOMXCore { - /* Handle to the OpenMAX IL core shared library */ - GModule *module; - - /* Current number of users, transitions from/to 0 - * call init/deinit */ - GMutex lock; - gint user_count; /* LOCK */ - - /* OpenMAX core library functions, protected with LOCK */ - OMX_ERRORTYPE (*init) (void); - OMX_ERRORTYPE (*deinit) (void); - OMX_ERRORTYPE (*get_handle) (OMX_HANDLETYPE * handle, - OMX_STRING name, OMX_PTR data, OMX_CALLBACKTYPE * callbacks); - OMX_ERRORTYPE (*free_handle) (OMX_HANDLETYPE handle); - OMX_ERRORTYPE (*setup_tunnel) (OMX_HANDLETYPE output, OMX_U32 outport, OMX_HANDLETYPE input, OMX_U32 inport); -}; - -typedef enum { - GST_OMX_MESSAGE_STATE_SET, - GST_OMX_MESSAGE_FLUSH, - GST_OMX_MESSAGE_ERROR, - GST_OMX_MESSAGE_PORT_ENABLE, - GST_OMX_MESSAGE_PORT_SETTINGS_CHANGED, - GST_OMX_MESSAGE_BUFFER_FLAG, - GST_OMX_MESSAGE_BUFFER_DONE, -} GstOMXMessageType; - -typedef enum { - GST_OMX_COMPONENT_TYPE_SINK, - GST_OMX_COMPONENT_TYPE_SOURCE, - GST_OMX_COMPONENT_TYPE_FILTER -} GstOmxComponentType; - -/* How the port's buffers are allocated */ -typedef enum { - GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER, - GST_OMX_BUFFER_ALLOCATION_USE_BUFFER, - GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC, /* Only supported by OMX 1.2.0 */ -} GstOMXBufferAllocation; - -typedef enum { - GST_OMX_WAIT, - GST_OMX_DONT_WAIT, -} GstOMXWait; - -struct _GstOMXMessage { - GstOMXMessageType type; - - union { - struct { - OMX_STATETYPE state; - } state_set; - struct { - OMX_U32 port; - } flush; - struct { - OMX_ERRORTYPE error; - } error; - struct { - OMX_U32 port; - OMX_BOOL enable; - } port_enable; - struct { - OMX_U32 port; - } port_settings_changed; - struct { - OMX_U32 port; - OMX_U32 flags; - } buffer_flag; - struct { - OMX_HANDLETYPE component; - OMX_PTR app_data; - OMX_BUFFERHEADERTYPE *buffer; - OMX_BOOL empty; - } buffer_done; - } content; -}; - -struct _GstOMXPort { - GstOMXComponent *comp; - guint32 index; - - gboolean tunneled; - - OMX_PARAM_PORTDEFINITIONTYPE port_def; - GPtrArray *buffers; /* Contains GstOMXBuffer* */ - GQueue pending_buffers; /* Contains GstOMXBuffer* */ - gboolean flushing; - gboolean flushed; /* TRUE after OMX_CommandFlush was done */ - gboolean enabled_pending; /* TRUE after OMX_Command{En,Dis}able */ - gboolean disabled_pending; /* was done until it took effect */ - gboolean eos; /* TRUE after a buffer with EOS flag was received */ - GstOMXBufferAllocation allocation; - gboolean using_pool; /* TRUE if the buffers of this port are managed by a pool */ - - /* Increased whenever the settings of these port change. - * If settings_cookie != configured_settings_cookie - * the port has to be reconfigured. - */ - gint settings_cookie; - gint configured_settings_cookie; -}; - -struct _GstOMXComponent { - GstMiniObject mini_object; - - GstObject *parent; - - gchar *name; /* for debugging mostly */ - - OMX_HANDLETYPE handle; - GstOMXCore *core; - - guint64 hacks; /* Flags, GST_OMX_HACK_* */ - - /* Added once, never changed. No locks necessary */ - GPtrArray *ports; /* Contains GstOMXPort* */ - gint n_in_ports, n_out_ports; - - /* Locking order: lock -> messages_lock - * - * Never hold lock while waiting for messages_cond - * Always check that messages is empty before waiting */ - GMutex lock; - - GQueue messages; /* Queue of GstOMXMessages */ - GMutex messages_lock; - GCond messages_cond; - - OMX_STATETYPE state; - /* OMX_StateInvalid if no pending state */ - OMX_STATETYPE pending_state; - /* OMX_ErrorNone usually, if different nothing will work */ - OMX_ERRORTYPE last_error; - - GList *pending_reconfigure_outports; -}; - -struct _GstOMXBuffer { - GstOMXPort *port; - OMX_BUFFERHEADERTYPE *omx_buf; - - /* TRUE if the buffer is used by the port, i.e. - * between {Empty,Fill}ThisBuffer and the callback - */ - gboolean used; - - /* Cookie of the settings when this buffer was allocated */ - gint settings_cookie; - - /* TRUE if this is an EGLImage */ - gboolean eglimage; - - /* Used in dynamic buffer mode to keep track of the mapped content while it's - * being processed by the OMX component. */ - GstVideoFrame input_frame; - gboolean input_frame_mapped; /* TRUE if input_frame is valid */ - GstMemory *input_mem; - GstBuffer *input_buffer; - gboolean input_buffer_mapped; - GstMapInfo map; -}; - -struct _GstOMXClassData { - const gchar *core_name; - const gchar *component_name; - const gchar *component_role; - - const gchar *default_src_template_caps; - const gchar *default_sink_template_caps; - - guint32 in_port_index, out_port_index; - - guint64 hacks; - - GstOmxComponentType type; -}; - -GKeyFile * gst_omx_get_configuration (void); - -const gchar * gst_omx_error_to_string (OMX_ERRORTYPE err); -const gchar * gst_omx_state_to_string (OMX_STATETYPE state); -const gchar * gst_omx_command_to_string (OMX_COMMANDTYPE cmd); -const gchar * gst_omx_buffer_flags_to_string (guint32 flags); - -guint64 gst_omx_parse_hacks (gchar ** hacks); - -GstOMXCore * gst_omx_core_acquire (const gchar * filename); -void gst_omx_core_release (GstOMXCore * core); - -GType gst_omx_component_get_type (void); - -GstOMXComponent * gst_omx_component_new (GstObject * parent, const gchar *core_name, const gchar *component_name, const gchar * component_role, guint64 hacks); -GstOMXComponent * gst_omx_component_ref (GstOMXComponent * comp); -void gst_omx_component_unref (GstOMXComponent * comp); - -OMX_ERRORTYPE gst_omx_component_set_state (GstOMXComponent * comp, OMX_STATETYPE state); -OMX_STATETYPE gst_omx_component_get_state (GstOMXComponent * comp, GstClockTime timeout); - -OMX_ERRORTYPE gst_omx_component_get_last_error (GstOMXComponent * comp); -const gchar * gst_omx_component_get_last_error_string (GstOMXComponent * comp); - -GstOMXPort * gst_omx_component_add_port (GstOMXComponent * comp, guint32 index); -GstOMXPort * gst_omx_component_get_port (GstOMXComponent * comp, guint32 index); - -OMX_ERRORTYPE gst_omx_component_get_parameter (GstOMXComponent * comp, OMX_INDEXTYPE index, gpointer param); -OMX_ERRORTYPE gst_omx_component_set_parameter (GstOMXComponent * comp, OMX_INDEXTYPE index, gpointer param); - -OMX_ERRORTYPE gst_omx_component_get_config (GstOMXComponent * comp, OMX_INDEXTYPE index, gpointer config); -OMX_ERRORTYPE gst_omx_component_set_config (GstOMXComponent * comp, OMX_INDEXTYPE index, gpointer config); - -OMX_ERRORTYPE gst_omx_setup_tunnel (GstOMXPort * port1, GstOMXPort * port2); -OMX_ERRORTYPE gst_omx_close_tunnel (GstOMXPort * port1, GstOMXPort * port2); - - -OMX_ERRORTYPE gst_omx_port_get_port_definition (GstOMXPort * port, OMX_PARAM_PORTDEFINITIONTYPE * port_def); -OMX_ERRORTYPE gst_omx_port_update_port_definition (GstOMXPort *port, OMX_PARAM_PORTDEFINITIONTYPE *port_definition); - -GstOMXAcquireBufferReturn gst_omx_port_acquire_buffer (GstOMXPort *port, GstOMXBuffer **buf, GstOMXWait wait); -OMX_ERRORTYPE gst_omx_port_release_buffer (GstOMXPort *port, GstOMXBuffer *buf); - -OMX_ERRORTYPE gst_omx_port_set_flushing (GstOMXPort *port, GstClockTime timeout, gboolean flush); -gboolean gst_omx_port_is_flushing (GstOMXPort *port); - -OMX_ERRORTYPE gst_omx_port_allocate_buffers (GstOMXPort *port); -OMX_ERRORTYPE gst_omx_port_use_buffers (GstOMXPort *port, const GList *buffers); -OMX_ERRORTYPE gst_omx_port_use_eglimages (GstOMXPort *port, const GList *images); -OMX_ERRORTYPE gst_omx_port_deallocate_buffers (GstOMXPort *port); -OMX_ERRORTYPE gst_omx_port_populate (GstOMXPort *port); -OMX_ERRORTYPE gst_omx_port_wait_buffers_released (GstOMXPort * port, GstClockTime timeout); -void gst_omx_port_requeue_buffer (GstOMXPort * port, GstOMXBuffer * buf); - -OMX_ERRORTYPE gst_omx_port_mark_reconfigured (GstOMXPort * port); - -OMX_ERRORTYPE gst_omx_port_set_enabled (GstOMXPort * port, gboolean enabled); -OMX_ERRORTYPE gst_omx_port_wait_enabled (GstOMXPort * port, GstClockTime timeout); -gboolean gst_omx_port_is_enabled (GstOMXPort * port); -gboolean gst_omx_port_ensure_buffer_count_actual (GstOMXPort * port, guint extra); -gboolean gst_omx_port_update_buffer_count_actual (GstOMXPort * port, guint nb); - -gboolean gst_omx_port_set_dmabuf (GstOMXPort * port, gboolean dmabuf); -gboolean gst_omx_port_set_subframe (GstOMXPort * port, gboolean enabled); -gboolean gst_omx_port_get_subframe (GstOMXPort * port); - -/* OMX 1.2.0 dynamic allocation mode */ -gboolean gst_omx_is_dynamic_allocation_supported (void); -OMX_ERRORTYPE gst_omx_port_use_dynamic_buffers (GstOMXPort * port); -gboolean gst_omx_buffer_map_frame (GstOMXBuffer * buffer, GstBuffer * input, GstVideoInfo * info); -gboolean gst_omx_buffer_map_memory (GstOMXBuffer * buffer, GstMemory * mem); -gboolean gst_omx_buffer_map_buffer (GstOMXBuffer * buffer, GstBuffer * input); -gboolean gst_omx_buffer_import_fd (GstOMXBuffer * buffer, GstBuffer * input); - -void gst_omx_set_default_role (GstOMXClassData *class_data, const gchar *default_role); - -/* refered by plugin_init */ -GST_DEBUG_CATEGORY_EXTERN (gst_omx_video_debug_category); - -G_END_DECLS - -#endif /* __GST_OMX_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxaacdec.c b/subprojects/gst-omx/omx/gstomxaacdec.c deleted file mode 100644 index 9606b7fd33..0000000000 --- a/subprojects/gst-omx/omx/gstomxaacdec.c +++ /dev/null @@ -1,296 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxaacdec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_aac_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_aac_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_aac_dec_set_format (GstOMXAudioDec * dec, - GstOMXPort * port, GstCaps * caps); -static gboolean gst_omx_aac_dec_is_format_change (GstOMXAudioDec * dec, - GstOMXPort * port, GstCaps * caps); -static gint gst_omx_aac_dec_get_samples_per_frame (GstOMXAudioDec * dec, - GstOMXPort * port); -static gboolean gst_omx_aac_dec_get_channel_positions (GstOMXAudioDec * dec, - GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]); - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_aac_dec_debug_category, "omxaacdec", 0, \ - "debug category for gst-omx aac audio decoder"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXAACDec, gst_omx_aac_dec, - GST_TYPE_OMX_AUDIO_DEC, DEBUG_INIT); - -static void -gst_omx_aac_dec_class_init (GstOMXAACDecClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXAudioDecClass *audiodec_class = GST_OMX_AUDIO_DEC_CLASS (klass); - - audiodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_aac_dec_set_format); - audiodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_aac_dec_is_format_change); - audiodec_class->get_samples_per_frame = - GST_DEBUG_FUNCPTR (gst_omx_aac_dec_get_samples_per_frame); - audiodec_class->get_channel_positions = - GST_DEBUG_FUNCPTR (gst_omx_aac_dec_get_channel_positions); - - audiodec_class->cdata.default_sink_template_caps = "audio/mpeg, " - "mpegversion=(int){2, 4}, " - "stream-format=(string) { raw, adts, adif, loas }, " - "rate=(int)[8000,48000], " - "channels=(int)[1,9], " "framed=(boolean) true"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX AAC Audio Decoder", - "Codec/Decoder/Audio/Hardware", - "Decode AAC audio streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&audiodec_class->cdata, "audio_decoder.aac"); -} - -static void -gst_omx_aac_dec_init (GstOMXAACDec * self) -{ - /* FIXME: Other values exist too! */ - self->spf = 1024; -} - -static gboolean -gst_omx_aac_dec_set_format (GstOMXAudioDec * dec, GstOMXPort * port, - GstCaps * caps) -{ - GstOMXAACDec *self = GST_OMX_AAC_DEC (dec); - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_AUDIO_PARAM_AACPROFILETYPE aac_param; - OMX_ERRORTYPE err; - GstStructure *s; - gint rate, channels, mpegversion; - const gchar *stream_format; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.audio.eEncoding = OMX_AUDIO_CodingAAC; - err = gst_omx_port_update_port_definition (port, &port_def); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set AAC format on component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_OMX_INIT_STRUCT (&aac_param); - aac_param.nPortIndex = port->index; - - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioAac, - &aac_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get AAC parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - s = gst_caps_get_structure (caps, 0); - - if (!gst_structure_get_int (s, "mpegversion", &mpegversion) || - !gst_structure_get_int (s, "rate", &rate) || - !gst_structure_get_int (s, "channels", &channels)) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - stream_format = gst_structure_get_string (s, "stream-format"); - if (!stream_format) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - aac_param.nChannels = channels; - aac_param.nSampleRate = rate; - aac_param.nBitRate = 0; /* unknown */ - aac_param.nAudioBandWidth = 0; /* decoder decision */ - aac_param.eChannelMode = 0; /* FIXME */ - if (mpegversion == 2) - aac_param.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP2ADTS; - else if (strcmp (stream_format, "adts") == 0) - aac_param.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4ADTS; - else if (strcmp (stream_format, "loas") == 0) - aac_param.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4LOAS; - else if (strcmp (stream_format, "adif") == 0) - aac_param.eAACStreamFormat = OMX_AUDIO_AACStreamFormatADIF; - else if (strcmp (stream_format, "raw") == 0) - aac_param.eAACStreamFormat = OMX_AUDIO_AACStreamFormatRAW; - else { - GST_ERROR_OBJECT (self, "Unexpected format: %s", stream_format); - return FALSE; - } - - err = - gst_omx_component_set_parameter (dec->dec, OMX_IndexParamAudioAac, - &aac_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Error setting AAC parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -static gboolean -gst_omx_aac_dec_is_format_change (GstOMXAudioDec * dec, GstOMXPort * port, - GstCaps * caps) -{ - GstOMXAACDec *self = GST_OMX_AAC_DEC (dec); - OMX_AUDIO_PARAM_AACPROFILETYPE aac_param; - OMX_ERRORTYPE err; - GstStructure *s; - gint rate, channels, mpegversion; - const gchar *stream_format; - - GST_OMX_INIT_STRUCT (&aac_param); - aac_param.nPortIndex = port->index; - - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioAac, - &aac_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get AAC parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - s = gst_caps_get_structure (caps, 0); - - if (!gst_structure_get_int (s, "mpegversion", &mpegversion) || - !gst_structure_get_int (s, "rate", &rate) || - !gst_structure_get_int (s, "channels", &channels)) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - stream_format = gst_structure_get_string (s, "stream-format"); - if (!stream_format) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - if (aac_param.nChannels != channels) - return TRUE; - - if (aac_param.nSampleRate != rate) - return TRUE; - - if (mpegversion == 2 - && aac_param.eAACStreamFormat != OMX_AUDIO_AACStreamFormatMP2ADTS) - return TRUE; - if (aac_param.eAACStreamFormat == OMX_AUDIO_AACStreamFormatMP4ADTS && - strcmp (stream_format, "adts") != 0) - return TRUE; - if (aac_param.eAACStreamFormat == OMX_AUDIO_AACStreamFormatMP4LOAS && - strcmp (stream_format, "loas") != 0) - return TRUE; - if (aac_param.eAACStreamFormat == OMX_AUDIO_AACStreamFormatADIF && - strcmp (stream_format, "adif") != 0) - return TRUE; - if (aac_param.eAACStreamFormat == OMX_AUDIO_AACStreamFormatRAW && - strcmp (stream_format, "raw") != 0) - return TRUE; - - return FALSE; -} - -static gint -gst_omx_aac_dec_get_samples_per_frame (GstOMXAudioDec * dec, GstOMXPort * port) -{ - return GST_OMX_AAC_DEC (dec)->spf; -} - -static gboolean -gst_omx_aac_dec_get_channel_positions (GstOMXAudioDec * dec, - GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]) -{ - OMX_AUDIO_PARAM_PCMMODETYPE pcm_param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&pcm_param); - pcm_param.nPortIndex = port->index; - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioPcm, - &pcm_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (dec, "Failed to get PCM parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - /* FIXME: Rather arbitrary values here, based on what we do in gstfaac.c */ - switch (pcm_param.nChannels) { - case 1: - position[0] = GST_AUDIO_CHANNEL_POSITION_MONO; - break; - case 2: - position[0] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - position[1] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - break; - case 3: - position[0] = GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER; - position[1] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - position[2] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - break; - case 4: - position[0] = GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER; - position[1] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - position[2] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - position[3] = GST_AUDIO_CHANNEL_POSITION_REAR_CENTER; - break; - case 5: - position[0] = GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER; - position[1] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - position[2] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - position[3] = GST_AUDIO_CHANNEL_POSITION_REAR_LEFT; - position[4] = GST_AUDIO_CHANNEL_POSITION_REAR_RIGHT; - break; - case 6: - position[0] = GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER; - position[1] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - position[2] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - position[3] = GST_AUDIO_CHANNEL_POSITION_REAR_LEFT; - position[4] = GST_AUDIO_CHANNEL_POSITION_REAR_RIGHT; - position[5] = GST_AUDIO_CHANNEL_POSITION_LFE1; - break; - default: - return FALSE; - } - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxaacdec.h b/subprojects/gst-omx/omx/gstomxaacdec.h deleted file mode 100644 index 891589b01e..0000000000 --- a/subprojects/gst-omx/omx/gstomxaacdec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_AAC_DEC_H__ -#define __GST_OMX_AAC_DEC_H__ - -#include -#include "gstomxaudiodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_AAC_DEC \ - (gst_omx_aac_dec_get_type()) -#define GST_OMX_AAC_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_AAC_DEC,GstOMXAACDec)) -#define GST_OMX_AAC_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_AAC_DEC,GstOMXAACDecClass)) -#define GST_OMX_AAC_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_AAC_DEC,GstOMXAACDecClass)) -#define GST_IS_OMX_AAC_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_AAC_DEC)) -#define GST_IS_OMX_AAC_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_AAC_DEC)) - -typedef struct _GstOMXAACDec GstOMXAACDec; -typedef struct _GstOMXAACDecClass GstOMXAACDecClass; - -struct _GstOMXAACDec -{ - GstOMXAudioDec parent; - gint spf; -}; - -struct _GstOMXAACDecClass -{ - GstOMXAudioDecClass parent_class; -}; - -GType gst_omx_aac_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_AAC_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxaacenc.c b/subprojects/gst-omx/omx/gstomxaacenc.c deleted file mode 100644 index c568ddd184..0000000000 --- a/subprojects/gst-omx/omx/gstomxaacenc.c +++ /dev/null @@ -1,511 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxaacenc.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_aac_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_aac_enc_debug_category - -/* prototypes */ -static void gst_omx_aac_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec); -static void gst_omx_aac_enc_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec); -static gboolean gst_omx_aac_enc_set_format (GstOMXAudioEnc * enc, - GstOMXPort * port, GstAudioInfo * info); -static GstCaps *gst_omx_aac_enc_get_caps (GstOMXAudioEnc * enc, - GstOMXPort * port, GstAudioInfo * info); -static guint gst_omx_aac_enc_get_num_samples (GstOMXAudioEnc * enc, - GstOMXPort * port, GstAudioInfo * info, GstOMXBuffer * buf); - -enum -{ - PROP_0, - PROP_BITRATE, - PROP_AAC_TOOLS, - PROP_AAC_ERROR_RESILIENCE_TOOLS -}; - -#define DEFAULT_BITRATE (128000) -#define DEFAULT_AAC_TOOLS (OMX_AUDIO_AACToolMS | OMX_AUDIO_AACToolIS | OMX_AUDIO_AACToolTNS | OMX_AUDIO_AACToolPNS | OMX_AUDIO_AACToolLTP) -#define DEFAULT_AAC_ER_TOOLS (OMX_AUDIO_AACERNone) - -#define GST_TYPE_OMX_AAC_TOOLS (gst_omx_aac_tools_get_type ()) -static GType -gst_omx_aac_tools_get_type (void) -{ - static gsize id = 0; - static const GFlagsValue values[] = { - {OMX_AUDIO_AACToolMS, "Mid/side joint coding", "ms"}, - {OMX_AUDIO_AACToolIS, "Intensity stereo", "is"}, - {OMX_AUDIO_AACToolTNS, "Temporal noise shaping", "tns"}, - {OMX_AUDIO_AACToolPNS, "Perceptual noise substitution", "pns"}, - {OMX_AUDIO_AACToolLTP, "Long term prediction", "ltp"}, - {0, NULL, NULL} - }; - - if (g_once_init_enter (&id)) { - GType tmp = g_flags_register_static ("GstOMXAACTools", values); - g_once_init_leave (&id, tmp); - } - - return (GType) id; -} - -#define GST_TYPE_OMX_AAC_ER_TOOLS (gst_omx_aac_er_tools_get_type ()) -static GType -gst_omx_aac_er_tools_get_type (void) -{ - static gsize id = 0; - static const GFlagsValue values[] = { - {OMX_AUDIO_AACERVCB11, "Virtual code books", "vcb11"}, - {OMX_AUDIO_AACERRVLC, "Reversible variable length coding", "rvlc"}, - {OMX_AUDIO_AACERHCR, "Huffman codeword reordering", "hcr"}, - {0, NULL, NULL} - }; - - if (g_once_init_enter (&id)) { - GType tmp = g_flags_register_static ("GstOMXAACERTools", values); - g_once_init_leave (&id, tmp); - } - - return (GType) id; -} - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_aac_enc_debug_category, "omxaacenc", 0, \ - "debug category for gst-omx audio encoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXAACEnc, gst_omx_aac_enc, - GST_TYPE_OMX_AUDIO_ENC, DEBUG_INIT); - - -static void -gst_omx_aac_enc_class_init (GstOMXAACEncClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXAudioEncClass *audioenc_class = GST_OMX_AUDIO_ENC_CLASS (klass); - - gobject_class->set_property = gst_omx_aac_enc_set_property; - gobject_class->get_property = gst_omx_aac_enc_get_property; - - g_object_class_install_property (gobject_class, PROP_BITRATE, - g_param_spec_uint ("bitrate", "Bitrate", - "Bitrate", - 0, G_MAXUINT, DEFAULT_BITRATE, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_AAC_TOOLS, - g_param_spec_flags ("aac-tools", "AAC Tools", - "Allowed AAC tools", - GST_TYPE_OMX_AAC_TOOLS, - DEFAULT_AAC_TOOLS, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, - PROP_AAC_ERROR_RESILIENCE_TOOLS, - g_param_spec_flags ("aac-error-resilience-tools", - "AAC Error Resilience Tools", "Allowed AAC error resilience tools", - GST_TYPE_OMX_AAC_ER_TOOLS, DEFAULT_AAC_ER_TOOLS, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - audioenc_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_aac_enc_set_format); - audioenc_class->get_caps = GST_DEBUG_FUNCPTR (gst_omx_aac_enc_get_caps); - audioenc_class->get_num_samples = - GST_DEBUG_FUNCPTR (gst_omx_aac_enc_get_num_samples); - - audioenc_class->cdata.default_src_template_caps = "audio/mpeg, " - "mpegversion=(int){2, 4}, " - "stream-format=(string){raw, adts, adif, loas, latm}"; - - - gst_element_class_set_static_metadata (element_class, - "OpenMAX AAC Audio Encoder", - "Codec/Encoder/Audio/Hardware", - "Encode AAC audio streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&audioenc_class->cdata, "audio_encoder.aac"); -} - -static void -gst_omx_aac_enc_init (GstOMXAACEnc * self) -{ - self->bitrate = DEFAULT_BITRATE; - self->aac_tools = DEFAULT_AAC_TOOLS; - self->aac_er_tools = DEFAULT_AAC_ER_TOOLS; -} - -static void -gst_omx_aac_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ - GstOMXAACEnc *self = GST_OMX_AAC_ENC (object); - - switch (prop_id) { - case PROP_BITRATE: - self->bitrate = g_value_get_uint (value); - break; - case PROP_AAC_TOOLS: - self->aac_tools = g_value_get_flags (value); - break; - case PROP_AAC_ERROR_RESILIENCE_TOOLS: - self->aac_er_tools = g_value_get_flags (value); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_aac_enc_get_property (GObject * object, guint prop_id, GValue * value, - GParamSpec * pspec) -{ - GstOMXAACEnc *self = GST_OMX_AAC_ENC (object); - - switch (prop_id) { - case PROP_BITRATE: - g_value_set_uint (value, self->bitrate); - break; - case PROP_AAC_TOOLS: - g_value_set_flags (value, self->aac_tools); - break; - case PROP_AAC_ERROR_RESILIENCE_TOOLS: - g_value_set_flags (value, self->aac_er_tools); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static gboolean -gst_omx_aac_enc_set_format (GstOMXAudioEnc * enc, GstOMXPort * port, - GstAudioInfo * info) -{ - GstOMXAACEnc *self = GST_OMX_AAC_ENC (enc); - OMX_AUDIO_PARAM_AACPROFILETYPE aac_profile; - GstCaps *peercaps; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&aac_profile); - aac_profile.nPortIndex = enc->enc_out_port->index; - - err = - gst_omx_component_get_parameter (enc->enc, OMX_IndexParamAudioAac, - &aac_profile); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get AAC parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - peercaps = gst_pad_peer_query_caps (GST_AUDIO_ENCODER_SRC_PAD (self), - gst_pad_get_pad_template_caps (GST_AUDIO_ENCODER_SRC_PAD (self))); - if (peercaps) { - GstStructure *s; - gint mpegversion = 0; - const gchar *profile_string, *stream_format_string; - - if (gst_caps_is_empty (peercaps)) { - gst_caps_unref (peercaps); - GST_ERROR_OBJECT (self, "Empty caps"); - return FALSE; - } - - s = gst_caps_get_structure (peercaps, 0); - - if (gst_structure_get_int (s, "mpegversion", &mpegversion)) { - profile_string = - gst_structure_get_string (s, - ((mpegversion == 2) ? "profile" : "base-profile")); - - if (profile_string) { - if (g_str_equal (profile_string, "main")) { - aac_profile.eAACProfile = OMX_AUDIO_AACObjectMain; - } else if (g_str_equal (profile_string, "lc")) { - aac_profile.eAACProfile = OMX_AUDIO_AACObjectLC; - } else if (g_str_equal (profile_string, "ssr")) { - aac_profile.eAACProfile = OMX_AUDIO_AACObjectSSR; - } else if (g_str_equal (profile_string, "ltp")) { - aac_profile.eAACProfile = OMX_AUDIO_AACObjectLTP; - } else { - GST_ERROR_OBJECT (self, "Unsupported profile '%s'", profile_string); - gst_caps_unref (peercaps); - return FALSE; - } - } - } - - stream_format_string = gst_structure_get_string (s, "stream-format"); - if (stream_format_string) { - if (g_str_equal (stream_format_string, "raw")) { - aac_profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatRAW; - } else if (g_str_equal (stream_format_string, "adts")) { - if (mpegversion == 2) { - aac_profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP2ADTS; - } else { - aac_profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4ADTS; - } - } else if (g_str_equal (stream_format_string, "loas")) { - aac_profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4LOAS; - } else if (g_str_equal (stream_format_string, "latm")) { - aac_profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4LATM; - } else if (g_str_equal (stream_format_string, "adif")) { - aac_profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatADIF; - } else { - GST_ERROR_OBJECT (self, "Unsupported stream-format '%s'", - stream_format_string); - gst_caps_unref (peercaps); - return FALSE; - } - } - - gst_caps_unref (peercaps); - - aac_profile.nSampleRate = info->rate; - aac_profile.nChannels = info->channels; - } - - aac_profile.nAACtools = self->aac_tools; - aac_profile.nAACERtools = self->aac_er_tools; - - aac_profile.nBitRate = self->bitrate; - - err = - gst_omx_component_set_parameter (enc->enc, OMX_IndexParamAudioAac, - &aac_profile); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Error setting AAC parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -typedef enum adts_sample_index__ -{ - ADTS_SAMPLE_INDEX_96000 = 0x0, - ADTS_SAMPLE_INDEX_88200, - ADTS_SAMPLE_INDEX_64000, - ADTS_SAMPLE_INDEX_48000, - ADTS_SAMPLE_INDEX_44100, - ADTS_SAMPLE_INDEX_32000, - ADTS_SAMPLE_INDEX_24000, - ADTS_SAMPLE_INDEX_22050, - ADTS_SAMPLE_INDEX_16000, - ADTS_SAMPLE_INDEX_12000, - ADTS_SAMPLE_INDEX_11025, - ADTS_SAMPLE_INDEX_8000, - ADTS_SAMPLE_INDEX_7350, - ADTS_SAMPLE_INDEX_MAX -} adts_sample_index; - -static adts_sample_index -map_adts_sample_index (guint32 srate) -{ - adts_sample_index ret; - - switch (srate) { - - case 96000: - ret = ADTS_SAMPLE_INDEX_96000; - break; - case 88200: - ret = ADTS_SAMPLE_INDEX_88200; - break; - case 64000: - ret = ADTS_SAMPLE_INDEX_64000; - break; - case 48000: - ret = ADTS_SAMPLE_INDEX_48000; - break; - case 44100: - ret = ADTS_SAMPLE_INDEX_44100; - break; - case 32000: - ret = ADTS_SAMPLE_INDEX_32000; - break; - case 24000: - ret = ADTS_SAMPLE_INDEX_24000; - break; - case 22050: - ret = ADTS_SAMPLE_INDEX_22050; - break; - case 16000: - ret = ADTS_SAMPLE_INDEX_16000; - break; - case 12000: - ret = ADTS_SAMPLE_INDEX_12000; - break; - case 11025: - ret = ADTS_SAMPLE_INDEX_11025; - break; - case 8000: - ret = ADTS_SAMPLE_INDEX_8000; - break; - case 7350: - ret = ADTS_SAMPLE_INDEX_7350; - break; - default: - ret = ADTS_SAMPLE_INDEX_44100; - break; - } - return ret; -} - -static GstCaps * -gst_omx_aac_enc_get_caps (GstOMXAudioEnc * enc, GstOMXPort * port, - GstAudioInfo * info) -{ - GstCaps *caps; - OMX_ERRORTYPE err; - OMX_AUDIO_PARAM_AACPROFILETYPE aac_profile; - gint mpegversion = 4; - const gchar *stream_format = NULL, *profile = NULL; - - GST_OMX_INIT_STRUCT (&aac_profile); - aac_profile.nPortIndex = enc->enc_out_port->index; - - err = - gst_omx_component_get_parameter (enc->enc, OMX_IndexParamAudioAac, - &aac_profile); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (enc, - "Failed to get AAC parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return NULL; - } - - switch (aac_profile.eAACProfile) { - case OMX_AUDIO_AACObjectMain: - profile = "main"; - break; - case OMX_AUDIO_AACObjectLC: - profile = "lc"; - break; - case OMX_AUDIO_AACObjectSSR: - profile = "ssr"; - break; - case OMX_AUDIO_AACObjectLTP: - profile = "ltp"; - break; - case OMX_AUDIO_AACObjectHE: - case OMX_AUDIO_AACObjectScalable: - case OMX_AUDIO_AACObjectERLC: - case OMX_AUDIO_AACObjectLD: - case OMX_AUDIO_AACObjectHE_PS: - default: - GST_ERROR_OBJECT (enc, "Unsupported profile %d", aac_profile.eAACProfile); - break; - } - - switch (aac_profile.eAACStreamFormat) { - case OMX_AUDIO_AACStreamFormatMP2ADTS: - mpegversion = 2; - stream_format = "adts"; - break; - case OMX_AUDIO_AACStreamFormatMP4ADTS: - mpegversion = 4; - stream_format = "adts"; - break; - case OMX_AUDIO_AACStreamFormatMP4LOAS: - mpegversion = 4; - stream_format = "loas"; - break; - case OMX_AUDIO_AACStreamFormatMP4LATM: - mpegversion = 4; - stream_format = "latm"; - break; - case OMX_AUDIO_AACStreamFormatADIF: - mpegversion = 4; - stream_format = "adif"; - break; - case OMX_AUDIO_AACStreamFormatRAW: - mpegversion = 4; - stream_format = "raw"; - break; - case OMX_AUDIO_AACStreamFormatMP4FF: - default: - GST_ERROR_OBJECT (enc, "Unsupported stream-format %u", - aac_profile.eAACStreamFormat); - break; - } - - caps = gst_caps_new_empty_simple ("audio/mpeg"); - - if (mpegversion != 0) - gst_caps_set_simple (caps, "mpegversion", G_TYPE_INT, mpegversion, - "stream-format", G_TYPE_STRING, stream_format, NULL); - if (profile != NULL && (mpegversion == 2 || mpegversion == 4)) - gst_caps_set_simple (caps, "profile", G_TYPE_STRING, profile, NULL); - if (profile != NULL && mpegversion == 4) - gst_caps_set_simple (caps, "base-profile", G_TYPE_STRING, profile, NULL); - if (aac_profile.nChannels != 0) - gst_caps_set_simple (caps, "channels", G_TYPE_INT, aac_profile.nChannels, - NULL); - if (aac_profile.nSampleRate != 0) - gst_caps_set_simple (caps, "rate", G_TYPE_INT, aac_profile.nSampleRate, - NULL); - - if (aac_profile.eAACStreamFormat == OMX_AUDIO_AACStreamFormatRAW) { - GstBuffer *codec_data; - adts_sample_index sr_idx; - GstMapInfo map = GST_MAP_INFO_INIT; - - codec_data = gst_buffer_new_and_alloc (2); - gst_buffer_map (codec_data, &map, GST_MAP_WRITE); - sr_idx = map_adts_sample_index (aac_profile.nSampleRate); - map.data[0] = ((aac_profile.eAACProfile & 0x1F) << 3) | - ((sr_idx & 0xE) >> 1); - map.data[1] = ((sr_idx & 0x1) << 7) | ((aac_profile.nChannels & 0xF) << 3); - gst_buffer_unmap (codec_data, &map); - - GST_DEBUG_OBJECT (enc, "setting new codec_data"); - gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, codec_data, NULL); - - gst_buffer_unref (codec_data); - } - return caps; - -} - -static guint -gst_omx_aac_enc_get_num_samples (GstOMXAudioEnc * enc, GstOMXPort * port, - GstAudioInfo * info, GstOMXBuffer * buf) -{ - /* FIXME: Depends on the profile at least */ - return 1024; -} diff --git a/subprojects/gst-omx/omx/gstomxaacenc.h b/subprojects/gst-omx/omx/gstomxaacenc.h deleted file mode 100644 index b6c3daa9b7..0000000000 --- a/subprojects/gst-omx/omx/gstomxaacenc.h +++ /dev/null @@ -1,65 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_AAC_ENC_H__ -#define __GST_OMX_AAC_ENC_H__ - -#include -#include "gstomxaudioenc.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_AAC_ENC \ - (gst_omx_aac_enc_get_type()) -#define GST_OMX_AAC_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_AAC_ENC,GstOMXAACEnc)) -#define GST_OMX_AAC_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_AAC_ENC,GstOMXAACEncClass)) -#define GST_OMX_AAC_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_AAC_ENC,GstOMXAACEncClass)) -#define GST_IS_OMX_AAC_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_AAC_ENC)) -#define GST_IS_OMX_AAC_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_AAC_ENC)) - -typedef struct _GstOMXAACEnc GstOMXAACEnc; -typedef struct _GstOMXAACEncClass GstOMXAACEncClass; - -struct _GstOMXAACEnc -{ - GstOMXAudioEnc parent; - - /* properties */ - guint bitrate; - guint aac_tools; - guint aac_er_tools; -}; - -struct _GstOMXAACEncClass -{ - GstOMXAudioEncClass parent_class; -}; - -GType gst_omx_aac_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_AAC_ENC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxallocator.c b/subprojects/gst-omx/omx/gstomxallocator.c deleted file mode 100644 index db7c662ece..0000000000 --- a/subprojects/gst-omx/omx/gstomxallocator.c +++ /dev/null @@ -1,554 +0,0 @@ -/* - * Copyright (C) 2019, Collabora Ltd. - * Author: George Kiagiadakis - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "gstomxallocator.h" -#include - -GST_DEBUG_CATEGORY_STATIC (gst_omx_allocator_debug_category); -#define GST_CAT_DEFAULT gst_omx_allocator_debug_category - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_allocator_debug_category, "omxallocator", 0, \ - "debug category for gst-omx allocator class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXAllocator, gst_omx_allocator, GST_TYPE_ALLOCATOR, - DEBUG_INIT); - -enum -{ - SIG_OMXBUF_RELEASED, - SIG_FOREIGN_MEM_RELEASED, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL] = { 0 }; - -/* Custom allocator for memory associated with OpenMAX buffers - * - * The main purpose of this allocator is to track memory that is associated - * with OpenMAX buffers, so that we know when the buffers can be released - * back to OpenMAX. - * - * This allocator looks and behaves more like a buffer pool. It allocates - * the memory objects before starting and sets a miniobject dispose function - * on them, which allows them to return when their last ref count is dropped. - * - * The type of memory that this allocator manages is GstOMXMemory. However, it - * is possible to manage a different type of memory, in which case the - * GstOMXMemory object is used only internally. There are two supported cases: - * - Allocate memory from the dmabuf allocator - * - Take memory that was allocated externally and manage it here - * - * In both cases, this allocator will replace the miniobject dispose function - * of these memory objects, so if they were acquired from here, they will also - * return here on their last unref. - * - * The caller initially needs to configure how many memory objects will be - * managed here by calling configure(). After that it needs to call - * set_active(TRUE) and finally allocate() for each memory. Allocation is done - * like this to facilitate calling allocate() from the alloc() function of - * the buffer pool for each OMX buffer on the port. - * - * After the allocator has been activated and all buffers have been allocated, - * the acquire() method can be called to retrieve a memory object. acquire() can - * be given an OMX buffer index or pointer to locate and return the memory - * object that corresponds to this OMX buffer. If the buffer is already - * acquired, this will result in a GST_FLOW_ERROR. - * - * When the last reference count is dropped on a memory that was acquired from - * here, its dispose function will ref it again and allow it to be acquired - * again. In addition, the omxbuf-released signal is fired to let the caller - * know that it can return this OMX buffer to the port, as it is no longer - * used outside this allocator. - */ - -/******************/ -/** GstOMXMemory **/ -/******************/ - -#define GST_OMX_MEMORY_TYPE "openmax" - -GQuark -gst_omx_memory_quark (void) -{ - static GQuark quark = 0; - - if (quark == 0) - quark = g_quark_from_static_string ("GstOMXMemory"); - - return quark; -} - -static GstOMXMemory * -gst_omx_memory_new (GstOMXAllocator * allocator, GstOMXBuffer * omx_buf, - GstMemoryFlags flags, GstMemory * parent, gssize offset, gssize size) -{ - GstOMXMemory *mem; - gint align; - gsize maxsize; - - /* GStreamer uses a bitmask for the alignment while - * OMX uses the alignment itself. So we have to convert - * here */ - align = allocator->port->port_def.nBufferAlignment; - if (align > 0) - align -= 1; - if (((align + 1) & align) != 0) { - GST_WARNING ("Invalid alignment that is not a power of two: %u", - (guint) allocator->port->port_def.nBufferAlignment); - align = 0; - } - - maxsize = omx_buf->omx_buf->nAllocLen; - - if (size == -1) { - size = maxsize - offset; - } - - mem = g_new0 (GstOMXMemory, 1); - gst_memory_init (GST_MEMORY_CAST (mem), flags, (GstAllocator *) allocator, - parent, maxsize, align, offset, size); - - mem->buf = omx_buf; - - return mem; -} - -static gpointer -gst_omx_memory_map (GstMemory * mem, gsize maxsize, GstMapFlags flags) -{ - GstOMXMemory *omem = (GstOMXMemory *) mem; - - /* if we are using foreign_mem, the GstOMXMemory should never appear - * anywhere outside this allocator, therefore it should never be mapped */ - g_return_val_if_fail (!omem->foreign_mem, NULL); - - return omem->buf->omx_buf->pBuffer; -} - -static void -gst_omx_memory_unmap (GstMemory * mem) -{ -} - -static GstMemory * -gst_omx_memory_share (GstMemory * mem, gssize offset, gssize size) -{ - GstOMXMemory *omem = (GstOMXMemory *) mem; - GstOMXMemory *sub; - GstMemory *parent; - - /* find the real parent */ - if ((parent = mem->parent) == NULL) - parent = mem; - - if (size == -1) - size = mem->size - offset; - - /* the shared memory is always readonly */ - sub = gst_omx_memory_new ((GstOMXAllocator *) mem->allocator, omem->buf, - GST_MINI_OBJECT_FLAGS (parent) | GST_MINI_OBJECT_FLAG_LOCK_READONLY, - parent, offset, size); - - return (GstMemory *) sub; -} - -GstOMXBuffer * -gst_omx_memory_get_omx_buf (GstMemory * mem) -{ - GstOMXMemory *omx_mem; - - if (GST_IS_OMX_ALLOCATOR (mem->allocator)) - omx_mem = (GstOMXMemory *) mem; - else - omx_mem = gst_mini_object_get_qdata (GST_MINI_OBJECT (mem), - GST_OMX_MEMORY_QUARK); - - if (!omx_mem) - return NULL; - - return omx_mem->buf; -} - -/*********************/ -/** GstOMXAllocator **/ -/*********************/ - -static void -gst_omx_allocator_init (GstOMXAllocator * allocator) -{ - GstAllocator *alloc = GST_ALLOCATOR_CAST (allocator); - - alloc->mem_type = GST_OMX_MEMORY_TYPE; - - alloc->mem_map = gst_omx_memory_map; - alloc->mem_unmap = gst_omx_memory_unmap; - alloc->mem_share = gst_omx_memory_share; - /* default copy & is_span */ - - GST_OBJECT_FLAG_SET (allocator, GST_ALLOCATOR_FLAG_CUSTOM_ALLOC); - - g_mutex_init (&allocator->lock); - g_cond_init (&allocator->cond); -} - -GstOMXAllocator * -gst_omx_allocator_new (GstOMXComponent * component, GstOMXPort * port) -{ - GstOMXAllocator *allocator; - - allocator = g_object_new (gst_omx_allocator_get_type (), NULL); - allocator->component = gst_omx_component_ref (component); - allocator->port = port; - - return allocator; -} - -static void -gst_omx_allocator_finalize (GObject * object) -{ - GstOMXAllocator *allocator = GST_OMX_ALLOCATOR (object); - - gst_omx_component_unref (allocator->component); - g_mutex_clear (&allocator->lock); - g_cond_clear (&allocator->cond); - - G_OBJECT_CLASS (gst_omx_allocator_parent_class)->finalize (object); -} - -gboolean -gst_omx_allocator_configure (GstOMXAllocator * allocator, guint count, - GstOMXAllocatorForeignMemMode mode) -{ - /* check if already configured */ - if (allocator->n_memories > 0) - return FALSE; - - allocator->n_memories = count; - allocator->foreign_mode = mode; - if (mode == GST_OMX_ALLOCATOR_FOREIGN_MEM_DMABUF) - allocator->foreign_allocator = gst_dmabuf_allocator_new (); - - return TRUE; -} - -/* must be protected with allocator->lock */ -static void -gst_omx_allocator_dealloc (GstOMXAllocator * allocator) -{ - /* might be called more than once */ - if (!allocator->memories) - return; - - /* return foreign memory back to whoever lended it to us. - * the signal handler is expected to increase the ref count of foreign_mem */ - if (allocator->foreign_mode == GST_OMX_ALLOCATOR_FOREIGN_MEM_OTHER_POOL) { - gint i; - GstOMXMemory *m; - - for (i = 0; i < allocator->memories->len; i++) { - m = g_ptr_array_index (allocator->memories, i); - - /* this should not happen, but let's not crash for this */ - if (!m->foreign_mem) { - GST_WARNING_OBJECT (allocator, "no foreign_mem to release"); - continue; - } - - /* restore the original dispose function */ - GST_MINI_OBJECT_CAST (m->foreign_mem)->dispose = - (GstMiniObjectDisposeFunction) m->foreign_dispose; - - g_signal_emit (allocator, signals[SIG_FOREIGN_MEM_RELEASED], 0, i, - m->foreign_mem); - } - } - - g_ptr_array_foreach (allocator->memories, (GFunc) gst_memory_unref, NULL); - g_ptr_array_free (allocator->memories, TRUE); - allocator->memories = NULL; - allocator->n_memories = 0; - allocator->foreign_mode = GST_OMX_ALLOCATOR_FOREIGN_MEM_NONE; - if (allocator->foreign_allocator) { - g_object_unref (allocator->foreign_allocator); - allocator->foreign_allocator = NULL; - } - - g_cond_broadcast (&allocator->cond); -} - -gboolean -gst_omx_allocator_set_active (GstOMXAllocator * allocator, gboolean active) -{ - gboolean changed = FALSE; - - /* on activation, _configure() must be called first */ - g_return_val_if_fail (!active || allocator->n_memories > 0, FALSE); - - g_mutex_lock (&allocator->lock); - - if (allocator->active != active) - changed = TRUE; - - if (changed) { - if (active) { - allocator->memories = g_ptr_array_sized_new (allocator->n_memories); - g_ptr_array_set_size (allocator->memories, allocator->n_memories); - } else { - if (g_atomic_int_get (&allocator->n_outstanding) == 0) - gst_omx_allocator_dealloc (allocator); - } - } - - allocator->active = active; - g_mutex_unlock (&allocator->lock); - - return changed; -} - -void -gst_omx_allocator_wait_inactive (GstOMXAllocator * allocator) -{ - g_mutex_lock (&allocator->lock); - while (allocator->memories) - g_cond_wait (&allocator->cond, &allocator->lock); - g_mutex_unlock (&allocator->lock); -} - -static inline void -dec_outstanding (GstOMXAllocator * allocator) -{ - if (g_atomic_int_dec_and_test (&allocator->n_outstanding)) { - /* keep a ref to the allocator because _dealloc() will free - * all the memories and the memories might be the only thing holding - * a reference to the allocator; we need to keep it alive until the - * end of this function call */ - g_object_ref (allocator); - - /* take the lock so that _set_active() is not run concurrently */ - g_mutex_lock (&allocator->lock); - - /* now that we have the lock, check if we have been de-activated with - * outstanding buffers */ - if (!allocator->active) - gst_omx_allocator_dealloc (allocator); - - g_mutex_unlock (&allocator->lock); - g_object_unref (allocator); - } -} - -GstFlowReturn -gst_omx_allocator_acquire (GstOMXAllocator * allocator, GstMemory ** memory, - gint index, GstOMXBuffer * omx_buf) -{ - GstFlowReturn ret = GST_FLOW_OK; - GstOMXMemory *omx_mem = NULL; - - /* ensure memories are not going to disappear concurrently */ - g_atomic_int_inc (&allocator->n_outstanding); - - if (!allocator->active) { - ret = GST_FLOW_FLUSHING; - goto beach; - } - - if (index >= 0 && index < allocator->n_memories) - omx_mem = g_ptr_array_index (allocator->memories, index); - else if (omx_buf) { - for (index = 0; index < allocator->n_memories; index++) { - omx_mem = g_ptr_array_index (allocator->memories, index); - if (omx_mem->buf == omx_buf) - break; - } - } - - if (G_UNLIKELY (!omx_mem || index >= allocator->n_memories)) { - GST_ERROR_OBJECT (allocator, "Failed to find OMX memory"); - ret = GST_FLOW_ERROR; - goto beach; - } - - if (G_UNLIKELY (omx_mem->buf->used)) { - GST_ERROR_OBJECT (allocator, - "Trying to acquire a buffer that is being used by the OMX port"); - ret = GST_FLOW_ERROR; - goto beach; - } - - omx_mem->acquired = TRUE; - - if (omx_mem->foreign_mem) - *memory = omx_mem->foreign_mem; - else - *memory = GST_MEMORY_CAST (omx_mem); - -beach: - if (ret != GST_FLOW_OK) - dec_outstanding (allocator); - return ret; -} - -/* installed as the GstMiniObject::dispose function of the acquired GstMemory */ -static gboolean -gst_omx_allocator_memory_dispose (GstMemory * mem) -{ - GstOMXMemory *omx_mem; - GstOMXAllocator *allocator; - - /* memory may be from our allocator, but - * may as well be from the dmabuf allocator */ - if (GST_IS_OMX_ALLOCATOR (mem->allocator)) - omx_mem = (GstOMXMemory *) mem; - else - omx_mem = gst_mini_object_get_qdata (GST_MINI_OBJECT (mem), - GST_OMX_MEMORY_QUARK); - - if (omx_mem->acquired) { - /* keep the memory alive */ - gst_memory_ref (mem); - - omx_mem->acquired = FALSE; - - allocator = GST_OMX_ALLOCATOR (GST_MEMORY_CAST (omx_mem)->allocator); - - /* inform the upper layer that we are no longer using this GstOMXBuffer */ - g_signal_emit (allocator, signals[SIG_OMXBUF_RELEASED], 0, omx_mem->buf); - - dec_outstanding (allocator); - - /* be careful here, both the memory and the allocator - * may have been free'd as part of the call to dec_outstanding() */ - - return FALSE; - } - - /* if the foreign memory had a dispose function, let that one decide - * the fate of this memory. We are no longer going to be using it here */ - if (omx_mem->foreign_dispose) - return omx_mem->foreign_dispose (GST_MINI_OBJECT_CAST (mem)); - - return TRUE; -} - -static inline void -install_mem_dispose (GstOMXMemory * mem) -{ - GstMemory *managed_mem = (GstMemory *) mem; - - if (mem->foreign_mem) { - managed_mem = mem->foreign_mem; - mem->foreign_dispose = GST_MINI_OBJECT_CAST (managed_mem)->dispose; - } - - GST_MINI_OBJECT_CAST (managed_mem)->dispose = - (GstMiniObjectDisposeFunction) gst_omx_allocator_memory_dispose; -} - -/* the returned memory is transfer:none, ref still belongs to the allocator */ -GstMemory * -gst_omx_allocator_allocate (GstOMXAllocator * allocator, gint index, - GstMemory * foreign_mem) -{ - GstOMXMemory *mem; - GstOMXBuffer *omx_buf; - - g_return_val_if_fail (allocator->port->buffers, NULL); - g_return_val_if_fail (allocator->memories, NULL); - g_return_val_if_fail (index >= 0 && index < allocator->n_memories, NULL); - g_return_val_if_fail ((foreign_mem == NULL && - allocator->foreign_mode != GST_OMX_ALLOCATOR_FOREIGN_MEM_OTHER_POOL) - || (foreign_mem != NULL - && allocator->foreign_mode == - GST_OMX_ALLOCATOR_FOREIGN_MEM_OTHER_POOL), NULL); - - omx_buf = g_ptr_array_index (allocator->port->buffers, index); - g_return_val_if_fail (omx_buf != NULL, NULL); - - mem = gst_omx_memory_new (allocator, omx_buf, 0, NULL, 0, -1); - - switch (allocator->foreign_mode) { - case GST_OMX_ALLOCATOR_FOREIGN_MEM_NONE: - install_mem_dispose (mem); - break; - case GST_OMX_ALLOCATOR_FOREIGN_MEM_DMABUF: - { - gint fd = GPOINTER_TO_INT (omx_buf->omx_buf->pBuffer); - mem->foreign_mem = - gst_dmabuf_allocator_alloc (allocator->foreign_allocator, fd, - omx_buf->omx_buf->nAllocLen); - gst_mini_object_set_qdata (GST_MINI_OBJECT (mem->foreign_mem), - GST_OMX_MEMORY_QUARK, mem, NULL); - install_mem_dispose (mem); - break; - } - case GST_OMX_ALLOCATOR_FOREIGN_MEM_OTHER_POOL: - mem->foreign_mem = foreign_mem; - gst_mini_object_set_qdata (GST_MINI_OBJECT (mem->foreign_mem), - GST_OMX_MEMORY_QUARK, mem, NULL); - install_mem_dispose (mem); - break; - default: - g_assert_not_reached (); - break; - } - - g_ptr_array_index (allocator->memories, index) = mem; - return mem->foreign_mem ? mem->foreign_mem : (GstMemory *) mem; -} - -static void -gst_omx_allocator_free (GstAllocator * allocator, GstMemory * mem) -{ - GstOMXMemory *omem = (GstOMXMemory *) mem; - - g_warn_if_fail (!omem->acquired); - - if (omem->foreign_mem) - gst_memory_unref (omem->foreign_mem); - - g_free (omem); -} - -static void -gst_omx_allocator_class_init (GstOMXAllocatorClass * klass) -{ - GObjectClass *object_class; - GstAllocatorClass *allocator_class; - - object_class = (GObjectClass *) klass; - allocator_class = (GstAllocatorClass *) klass; - - object_class->finalize = gst_omx_allocator_finalize; - allocator_class->alloc = NULL; - allocator_class->free = gst_omx_allocator_free; - - signals[SIG_OMXBUF_RELEASED] = g_signal_new ("omxbuf-released", - G_TYPE_FROM_CLASS (klass), G_SIGNAL_RUN_LAST, 0, - NULL, NULL, NULL, G_TYPE_NONE, 1, G_TYPE_POINTER); - - signals[SIG_FOREIGN_MEM_RELEASED] = g_signal_new ("foreign-mem-released", - G_TYPE_FROM_CLASS (klass), G_SIGNAL_RUN_LAST, 0, - NULL, NULL, NULL, G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_POINTER); -} diff --git a/subprojects/gst-omx/omx/gstomxallocator.h b/subprojects/gst-omx/omx/gstomxallocator.h deleted file mode 100644 index 5c94584ec2..0000000000 --- a/subprojects/gst-omx/omx/gstomxallocator.h +++ /dev/null @@ -1,114 +0,0 @@ -/* - * Copyright (C) 2019, Collabora Ltd. - * Author: George Kiagiadakis - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_ALLOCATOR_H__ -#define __GST_OMX_ALLOCATOR_H__ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -#define GST_OMX_MEMORY_QUARK gst_omx_memory_quark () - -#define GST_TYPE_OMX_ALLOCATOR (gst_omx_allocator_get_type()) -#define GST_IS_OMX_ALLOCATOR(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GST_TYPE_OMX_ALLOCATOR)) -#define GST_OMX_ALLOCATOR(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GST_TYPE_OMX_ALLOCATOR, GstOMXAllocator)) - -typedef struct _GstOMXMemory GstOMXMemory; -typedef struct _GstOMXAllocator GstOMXAllocator; -typedef struct _GstOMXAllocatorClass GstOMXAllocatorClass; - -typedef enum { - GST_OMX_ALLOCATOR_FOREIGN_MEM_NONE, - GST_OMX_ALLOCATOR_FOREIGN_MEM_DMABUF, - GST_OMX_ALLOCATOR_FOREIGN_MEM_OTHER_POOL, -} GstOMXAllocatorForeignMemMode; - -struct _GstOMXMemory -{ - GstMemory mem; - GstOMXBuffer *buf; - - /* TRUE if the memory is in use outside the allocator */ - gboolean acquired; - - /* memory allocated from the foreign_allocator - * or planted externally when using a foreign buffer pool */ - GstMemory *foreign_mem; - /* the original dispose function of foreign_mem */ - GstMiniObjectDisposeFunction foreign_dispose; -}; - -struct _GstOMXAllocator -{ - GstAllocator parent; - - GstOMXComponent *component; - GstOMXPort *port; - - GstOMXAllocatorForeignMemMode foreign_mode; - GstAllocator *foreign_allocator; - - /* array of GstOMXMemory */ - GPtrArray *memories; - guint n_memories; - - guint n_outstanding; - gboolean active; - - GMutex lock; - GCond cond; -}; - -struct _GstOMXAllocatorClass -{ - GstAllocatorClass parent_class; -}; - -GType gst_omx_allocator_get_type (void); - -GQuark gst_omx_memory_quark (void); - -GstOMXBuffer * gst_omx_memory_get_omx_buf (GstMemory * mem); - -GstOMXAllocator * gst_omx_allocator_new (GstOMXComponent * component, - GstOMXPort * port); - -gboolean gst_omx_allocator_configure (GstOMXAllocator * allocator, guint count, - GstOMXAllocatorForeignMemMode mode); -gboolean gst_omx_allocator_set_active (GstOMXAllocator * allocator, - gboolean active); -void gst_omx_allocator_wait_inactive (GstOMXAllocator * allocator); - -GstFlowReturn gst_omx_allocator_acquire (GstOMXAllocator * allocator, - GstMemory ** memory, gint index, GstOMXBuffer * omx_buf); - -GstMemory * gst_omx_allocator_allocate (GstOMXAllocator * allocator, gint index, - GstMemory * foreign_mem); - -G_END_DECLS - -#endif diff --git a/subprojects/gst-omx/omx/gstomxamrdec.c b/subprojects/gst-omx/omx/gstomxamrdec.c deleted file mode 100644 index d7e468fbbf..0000000000 --- a/subprojects/gst-omx/omx/gstomxamrdec.c +++ /dev/null @@ -1,220 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * Copyright (C) 2014, LG Electronics, Inc. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxamrdec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_amr_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_amr_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_amr_dec_set_format (GstOMXAudioDec * dec, - GstOMXPort * port, GstCaps * caps); -static gboolean gst_omx_amr_dec_is_format_change (GstOMXAudioDec * dec, - GstOMXPort * port, GstCaps * caps); -static gint gst_omx_amr_dec_get_samples_per_frame (GstOMXAudioDec * dec, - GstOMXPort * port); -static gboolean gst_omx_amr_dec_get_channel_positions (GstOMXAudioDec * dec, - GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]); - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_amr_dec_debug_category, "omxamrdec", 0, \ - "debug category for gst-omx amr audio decoder"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXAMRDec, gst_omx_amr_dec, - GST_TYPE_OMX_AUDIO_DEC, DEBUG_INIT); - -static void -gst_omx_amr_dec_class_init (GstOMXAMRDecClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXAudioDecClass *audiodec_class = GST_OMX_AUDIO_DEC_CLASS (klass); - - audiodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_amr_dec_set_format); - audiodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_amr_dec_is_format_change); - audiodec_class->get_samples_per_frame = - GST_DEBUG_FUNCPTR (gst_omx_amr_dec_get_samples_per_frame); - audiodec_class->get_channel_positions = - GST_DEBUG_FUNCPTR (gst_omx_amr_dec_get_channel_positions); - - audiodec_class->cdata.default_sink_template_caps = - "audio/AMR, rate=(int)8000, channels=(int)1; " - "audio/AMR-WB, rate=(int)16000, channels=(int)1"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX AMR Audio Decoder", - "Codec/Decoder/Audio/Hardware", - "Decode AMR audio streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&audiodec_class->cdata, "audio_decoder.amrnb"); -} - -static void -gst_omx_amr_dec_init (GstOMXAMRDec * self) -{ - self->spf = -1; -} - -static gboolean -gst_omx_amr_dec_set_format (GstOMXAudioDec * dec, GstOMXPort * port, - GstCaps * caps) -{ - GstOMXAMRDec *self = GST_OMX_AMR_DEC (dec); - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_AUDIO_PARAM_AMRTYPE amr_param; - OMX_ERRORTYPE err; - GstStructure *s; - gint rate, channels; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.audio.eEncoding = OMX_AUDIO_CodingAMR; /* not tested for AMRWB */ - err = gst_omx_port_update_port_definition (port, &port_def); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set AMR format on component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_OMX_INIT_STRUCT (&amr_param); - amr_param.nPortIndex = port->index; - - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioAmr, - &amr_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get AMR parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - s = gst_caps_get_structure (caps, 0); - - if (!gst_structure_get_int (s, "rate", &rate) || - !gst_structure_get_int (s, "channels", &channels)) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - self->rate = rate; - - if (rate == 8000) - self->spf = 160; /* (8000/50) */ - else if (rate == 16000) - self->spf = 320; /* (16000/50) */ - - amr_param.nChannels = channels; - amr_param.eAMRBandMode = 0; /*FIXME: It may require a specific value */ - amr_param.eAMRDTXMode = 0; - amr_param.eAMRFrameFormat = 0; - - err = - gst_omx_component_set_parameter (dec->dec, OMX_IndexParamAudioAmr, - &amr_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Error setting AMR parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -static gboolean -gst_omx_amr_dec_is_format_change (GstOMXAudioDec * dec, GstOMXPort * port, - GstCaps * caps) -{ - GstOMXAMRDec *self = GST_OMX_AMR_DEC (dec); - OMX_AUDIO_PARAM_AMRTYPE amr_param; - OMX_ERRORTYPE err; - GstStructure *s; - gint rate, channels; - - GST_OMX_INIT_STRUCT (&amr_param); - amr_param.nPortIndex = port->index; - - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioAmr, - &amr_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get AMR parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - s = gst_caps_get_structure (caps, 0); - - if (!gst_structure_get_int (s, "rate", &rate) || - !gst_structure_get_int (s, "channels", &channels)) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - if (self->rate != rate) - return TRUE; - - if (amr_param.nChannels != channels) - return TRUE; - - return FALSE; -} - -static gint -gst_omx_amr_dec_get_samples_per_frame (GstOMXAudioDec * dec, GstOMXPort * port) -{ - return GST_OMX_AMR_DEC (dec)->spf; -} - -static gboolean -gst_omx_amr_dec_get_channel_positions (GstOMXAudioDec * dec, - GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]) -{ - OMX_AUDIO_PARAM_PCMMODETYPE pcm_param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&pcm_param); - pcm_param.nPortIndex = port->index; - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioPcm, - &pcm_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (dec, "Failed to get PCM parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - - g_return_val_if_fail (pcm_param.nChannels == 1, FALSE); /* AMR supports only mono */ - - position[0] = GST_AUDIO_CHANNEL_POSITION_MONO; - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxamrdec.h b/subprojects/gst-omx/omx/gstomxamrdec.h deleted file mode 100644 index 7a2df33050..0000000000 --- a/subprojects/gst-omx/omx/gstomxamrdec.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_AMR_DEC_H__ -#define __GST_OMX_AMR_DEC_H__ - -#include -#include "gstomxaudiodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_AMR_DEC \ - (gst_omx_amr_dec_get_type()) -#define GST_OMX_AMR_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_AMR_DEC,GstOMXAMRDec)) -#define GST_OMX_AMR_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_AMR_DEC,GstOMXAMRDecClass)) -#define GST_OMX_AMR_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_AMR_DEC,GstOMXAMRDecClass)) -#define GST_IS_OMX_AMR_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_AMR_DEC)) -#define GST_IS_OMX_AMR_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_AMR_DEC)) - -typedef struct _GstOMXAMRDec GstOMXAMRDec; -typedef struct _GstOMXAMRDecClass GstOMXAMRDecClass; - -struct _GstOMXAMRDec -{ - GstOMXAudioDec parent; - gint spf; - gint rate; -}; - -struct _GstOMXAMRDecClass -{ - GstOMXAudioDecClass parent_class; -}; - -GType gst_omx_amr_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_AMR_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxanalogaudiosink.c b/subprojects/gst-omx/omx/gstomxanalogaudiosink.c deleted file mode 100644 index 7c8c885273..0000000000 --- a/subprojects/gst-omx/omx/gstomxanalogaudiosink.c +++ /dev/null @@ -1,64 +0,0 @@ -/* - * Copyright (C) 2014, Fluendo, S.A. - * Copyright (C) 2014, Metrological Media Innovations B.V. - * Author: Josep Torra - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxanalogaudiosink.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_analog_audio_sink_debug_category); -#define GST_CAT_DEFAULT gst_omx_analog_audio_sink_debug_category - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_analog_audio_sink_debug_category, \ - "omxanalogaudiosink", 0, "debug category for gst-omx analog audio sink"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXAnalogAudioSink, gst_omx_analog_audio_sink, - GST_TYPE_OMX_AUDIO_SINK, DEBUG_INIT); - -static void -gst_omx_analog_audio_sink_class_init (GstOMXAnalogAudioSinkClass * klass) -{ - GstOMXAudioSinkClass *audiosink_class = GST_OMX_AUDIO_SINK_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - audiosink_class->cdata.default_sink_template_caps = "audio/x-raw, " - "format = (string) " GST_AUDIO_FORMATS_ALL ", " - "layout = (string) interleaved, " - "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, 2 ] "; - audiosink_class->destination = "local"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX Analog Audio Sink", - "Sink/Audio", "Output analog audio", "Josep Torra "); - - gst_omx_set_default_role (&audiosink_class->cdata, "audio_render.local"); -} - -static void -gst_omx_analog_audio_sink_init (GstOMXAnalogAudioSink * self) -{ -} diff --git a/subprojects/gst-omx/omx/gstomxanalogaudiosink.h b/subprojects/gst-omx/omx/gstomxanalogaudiosink.h deleted file mode 100644 index 7f5704812f..0000000000 --- a/subprojects/gst-omx/omx/gstomxanalogaudiosink.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (C) 2014, Fluendo, S.A. - * Copyright (C) 2014, Metrological Media Innovations B.V. - * Author: Josep Torra - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_ANALOG_AUDIO_SINK_H__ -#define __GST_OMX_ANALOG_AUDIO_SINK_H__ - -#include -#include "gstomxaudiosink.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_ANALOG_AUDIO_SINK \ - (gst_omx_analog_audio_sink_get_type()) -#define GST_OMX_ANALOG_AUDIO_SINK(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_ANALOG_AUDIO_SINK,GstOMXAnalogAudioSink)) -#define GST_OMX_ANALOG_AUDIO_SINK_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_ANALOG_AUDIO_SINK,GstOMXAnalogAudioSinkClass)) -#define GST_OMX_ANALOG_AUDIO_SINK_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_ANALOG_AUDIO_SINK,GstOMXAnalogAudioSinkClass)) -#define GST_IS_OMX_ANALOG_AUDIO_SINK(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_ANALOG_AUDIO_SINK)) -#define GST_IS_OMX_ANALOG_AUDIO_SINK_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_ANALOG_AUDIO_SINK)) - -typedef struct _GstOMXAnalogAudioSink GstOMXAnalogAudioSink; -typedef struct _GstOMXAnalogAudioSinkClass GstOMXAnalogAudioSinkClass; - -struct _GstOMXAnalogAudioSink -{ - GstOMXAudioSink parent; -}; - -struct _GstOMXAnalogAudioSinkClass -{ - GstOMXAudioSinkClass parent_class; -}; - -GType gst_omx_analog_audio_sink_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_ANALOG_AUDIO_SINK_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxaudiodec.c b/subprojects/gst-omx/omx/gstomxaudiodec.c deleted file mode 100644 index 8275b7204f..0000000000 --- a/subprojects/gst-omx/omx/gstomxaudiodec.c +++ /dev/null @@ -1,1404 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include - -#include "gstomxaudiodec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_audio_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_audio_dec_debug_category - -/* prototypes */ -static void gst_omx_audio_dec_finalize (GObject * object); - -static GstStateChangeReturn -gst_omx_audio_dec_change_state (GstElement * element, - GstStateChange transition); - -static gboolean gst_omx_audio_dec_open (GstAudioDecoder * decoder); -static gboolean gst_omx_audio_dec_close (GstAudioDecoder * decoder); -static gboolean gst_omx_audio_dec_start (GstAudioDecoder * decoder); -static gboolean gst_omx_audio_dec_stop (GstAudioDecoder * decoder); -static gboolean gst_omx_audio_dec_set_format (GstAudioDecoder * decoder, - GstCaps * caps); -static void gst_omx_audio_dec_flush (GstAudioDecoder * decoder, gboolean hard); -static GstFlowReturn gst_omx_audio_dec_handle_frame (GstAudioDecoder * decoder, - GstBuffer * buffer); -static GstFlowReturn gst_omx_audio_dec_drain (GstOMXAudioDec * self); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_audio_dec_debug_category, "omxaudiodec", 0, \ - "debug category for gst-omx audio decoder base class"); - - -G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GstOMXAudioDec, gst_omx_audio_dec, - GST_TYPE_AUDIO_DECODER, DEBUG_INIT); - -static void -gst_omx_audio_dec_class_init (GstOMXAudioDecClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstAudioDecoderClass *audio_decoder_class = GST_AUDIO_DECODER_CLASS (klass); - - gobject_class->finalize = gst_omx_audio_dec_finalize; - - element_class->change_state = - GST_DEBUG_FUNCPTR (gst_omx_audio_dec_change_state); - - audio_decoder_class->open = GST_DEBUG_FUNCPTR (gst_omx_audio_dec_open); - audio_decoder_class->close = GST_DEBUG_FUNCPTR (gst_omx_audio_dec_close); - audio_decoder_class->start = GST_DEBUG_FUNCPTR (gst_omx_audio_dec_start); - audio_decoder_class->stop = GST_DEBUG_FUNCPTR (gst_omx_audio_dec_stop); - audio_decoder_class->flush = GST_DEBUG_FUNCPTR (gst_omx_audio_dec_flush); - audio_decoder_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_audio_dec_set_format); - audio_decoder_class->handle_frame = - GST_DEBUG_FUNCPTR (gst_omx_audio_dec_handle_frame); - - klass->cdata.type = GST_OMX_COMPONENT_TYPE_FILTER; - klass->cdata.default_src_template_caps = - "audio/x-raw, " - "rate = (int) [ 1, MAX ], " - "channels = (int) [ 1, " G_STRINGIFY (OMX_AUDIO_MAXCHANNELS) " ], " - "format = (string) " GST_AUDIO_FORMATS_ALL; -} - -static void -gst_omx_audio_dec_init (GstOMXAudioDec * self) -{ - gst_audio_decoder_set_needs_format (GST_AUDIO_DECODER (self), TRUE); - gst_audio_decoder_set_drainable (GST_AUDIO_DECODER (self), TRUE); - gst_audio_decoder_set_use_default_pad_acceptcaps (GST_AUDIO_DECODER_CAST - (self), TRUE); - GST_PAD_SET_ACCEPT_TEMPLATE (GST_AUDIO_DECODER_SINK_PAD (self)); - - g_mutex_init (&self->drain_lock); - g_cond_init (&self->drain_cond); - - self->output_adapter = gst_adapter_new (); -} - -static gboolean -gst_omx_audio_dec_open (GstAudioDecoder * decoder) -{ - GstOMXAudioDec *self = GST_OMX_AUDIO_DEC (decoder); - GstOMXAudioDecClass *klass = GST_OMX_AUDIO_DEC_GET_CLASS (self); - gint in_port_index, out_port_index; - - GST_DEBUG_OBJECT (self, "Opening decoder"); - - self->dec = - gst_omx_component_new (GST_OBJECT_CAST (self), klass->cdata.core_name, - klass->cdata.component_name, klass->cdata.component_role, - klass->cdata.hacks); - self->started = FALSE; - - if (!self->dec) - return FALSE; - - if (gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded) - return FALSE; - - in_port_index = klass->cdata.in_port_index; - out_port_index = klass->cdata.out_port_index; - - if (in_port_index == -1 || out_port_index == -1) { - OMX_PORT_PARAM_TYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->dec, OMX_IndexParamAudioInit, - ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - in_port_index = 0; - out_port_index = 1; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", - (guint) param.nPorts, (guint) param.nStartPortNumber); - in_port_index = param.nStartPortNumber + 0; - out_port_index = param.nStartPortNumber + 1; - } - } - self->dec_in_port = gst_omx_component_add_port (self->dec, in_port_index); - self->dec_out_port = gst_omx_component_add_port (self->dec, out_port_index); - - if (!self->dec_in_port || !self->dec_out_port) - return FALSE; - - GST_DEBUG_OBJECT (self, "Opened decoder"); - - return TRUE; -} - -static gboolean -gst_omx_audio_dec_shutdown (GstOMXAudioDec * self) -{ - OMX_STATETYPE state; - - GST_DEBUG_OBJECT (self, "Shutting down decoder"); - - state = gst_omx_component_get_state (self->dec, 0); - if (state > OMX_StateLoaded || state == OMX_StateInvalid) { - if (state > OMX_StateIdle) { - gst_omx_component_set_state (self->dec, OMX_StateIdle); - gst_omx_component_get_state (self->dec, 5 * GST_SECOND); - } - gst_omx_component_set_state (self->dec, OMX_StateLoaded); - gst_omx_port_deallocate_buffers (self->dec_in_port); - gst_omx_port_deallocate_buffers (self->dec_out_port); - if (state > OMX_StateLoaded) - gst_omx_component_get_state (self->dec, 5 * GST_SECOND); - } - - return TRUE; -} - -static gboolean -gst_omx_audio_dec_close (GstAudioDecoder * decoder) -{ - GstOMXAudioDec *self = GST_OMX_AUDIO_DEC (decoder); - - GST_DEBUG_OBJECT (self, "Closing decoder"); - - if (!gst_omx_audio_dec_shutdown (self)) - return FALSE; - - self->dec_in_port = NULL; - self->dec_out_port = NULL; - if (self->dec) - gst_omx_component_unref (self->dec); - self->dec = NULL; - - self->started = FALSE; - - GST_DEBUG_OBJECT (self, "Closed decoder"); - - return TRUE; -} - -static void -gst_omx_audio_dec_finalize (GObject * object) -{ - GstOMXAudioDec *self = GST_OMX_AUDIO_DEC (object); - - g_mutex_clear (&self->drain_lock); - g_cond_clear (&self->drain_cond); - - if (self->output_adapter) - gst_object_unref (self->output_adapter); - self->output_adapter = NULL; - - G_OBJECT_CLASS (gst_omx_audio_dec_parent_class)->finalize (object); -} - -static GstStateChangeReturn -gst_omx_audio_dec_change_state (GstElement * element, GstStateChange transition) -{ - GstOMXAudioDec *self; - GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; - - g_return_val_if_fail (GST_IS_OMX_AUDIO_DEC (element), - GST_STATE_CHANGE_FAILURE); - self = GST_OMX_AUDIO_DEC (element); - - switch (transition) { - case GST_STATE_CHANGE_NULL_TO_READY: - break; - case GST_STATE_CHANGE_READY_TO_PAUSED: - self->downstream_flow_ret = GST_FLOW_OK; - self->draining = FALSE; - self->started = FALSE; - break; - case GST_STATE_CHANGE_PAUSED_TO_PLAYING: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - if (self->dec_in_port) - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - if (self->dec_out_port) - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - break; - default: - break; - } - - ret = - GST_ELEMENT_CLASS (gst_omx_audio_dec_parent_class)->change_state - (element, transition); - - if (ret == GST_STATE_CHANGE_FAILURE) - return ret; - - switch (transition) { - case GST_STATE_CHANGE_PLAYING_TO_PAUSED: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - - if (!gst_omx_audio_dec_shutdown (self)) - ret = GST_STATE_CHANGE_FAILURE; - break; - case GST_STATE_CHANGE_READY_TO_NULL: - break; - default: - break; - } - - return ret; -} - -static void -gst_omx_audio_dec_loop (GstOMXAudioDec * self) -{ - GstOMXAudioDecClass *klass = GST_OMX_AUDIO_DEC_GET_CLASS (self); - GstOMXPort *port = self->dec_out_port; - GstOMXBuffer *buf = NULL; - GstFlowReturn flow_ret = GST_FLOW_OK; - GstOMXAcquireBufferReturn acq_return; - OMX_ERRORTYPE err; - gint spf; - - acq_return = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - if (acq_return == GST_OMX_ACQUIRE_BUFFER_ERROR) { - goto component_error; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - goto flushing; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_EOS) { - goto eos; - } - - if (!gst_pad_has_current_caps (GST_AUDIO_DECODER_SRC_PAD (self)) || - acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_AUDIO_PARAM_PCMMODETYPE pcm_param; - GstAudioChannelPosition omx_position[OMX_AUDIO_MAXCHANNELS]; - GstOMXAudioDecClass *klass = GST_OMX_AUDIO_DEC_GET_CLASS (self); - gint i; - - GST_DEBUG_OBJECT (self, "Port settings have changed, updating caps"); - - /* Reallocate all buffers */ - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE - && gst_omx_port_is_enabled (port)) { - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } - - /* Just update caps */ - GST_AUDIO_DECODER_STREAM_LOCK (self); - - gst_omx_port_get_port_definition (port, &port_def); - g_assert (port_def.format.audio.eEncoding == OMX_AUDIO_CodingPCM); - - GST_OMX_INIT_STRUCT (&pcm_param); - pcm_param.nPortIndex = self->dec_out_port->index; - err = - gst_omx_component_get_parameter (self->dec, OMX_IndexParamAudioPcm, - &pcm_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to get PCM parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto caps_failed; - } - - g_assert (pcm_param.ePCMMode == OMX_AUDIO_PCMModeLinear); - g_assert (pcm_param.bInterleaved == OMX_TRUE); - - gst_audio_info_init (&self->info); - - for (i = 0; i < pcm_param.nChannels; i++) { - switch (pcm_param.eChannelMapping[i]) { - case OMX_AUDIO_ChannelLF: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - break; - case OMX_AUDIO_ChannelRF: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - break; - case OMX_AUDIO_ChannelCF: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER; - break; - case OMX_AUDIO_ChannelLS: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_SIDE_LEFT; - break; - case OMX_AUDIO_ChannelRS: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_SIDE_RIGHT; - break; - case OMX_AUDIO_ChannelLFE: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_LFE1; - break; - case OMX_AUDIO_ChannelCS: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_REAR_CENTER; - break; - case OMX_AUDIO_ChannelLR: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_REAR_LEFT; - break; - case OMX_AUDIO_ChannelRR: - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_REAR_RIGHT; - break; - case OMX_AUDIO_ChannelNone: - default: - /* This will break the outer loop too as the - * i == pcm_param.nChannels afterwards */ - for (i = 0; i < pcm_param.nChannels; i++) - omx_position[i] = GST_AUDIO_CHANNEL_POSITION_NONE; - break; - } - } - if (pcm_param.nChannels == 1 - && omx_position[0] == GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER) - omx_position[0] = GST_AUDIO_CHANNEL_POSITION_MONO; - - if (omx_position[0] == GST_AUDIO_CHANNEL_POSITION_NONE - && klass->get_channel_positions) { - GST_WARNING_OBJECT (self, - "Failed to get a valid channel layout, trying fallback"); - klass->get_channel_positions (self, self->dec_out_port, omx_position); - } - - memcpy (self->position, omx_position, sizeof (omx_position)); - gst_audio_channel_positions_to_valid_order (self->position, - pcm_param.nChannels); - self->needs_reorder = - (memcmp (self->position, omx_position, - sizeof (GstAudioChannelPosition) * pcm_param.nChannels) != 0); - if (self->needs_reorder) - gst_audio_get_channel_reorder_map (pcm_param.nChannels, self->position, - omx_position, self->reorder_map); - - gst_audio_info_set_format (&self->info, - gst_audio_format_build_integer (pcm_param.eNumData == - OMX_NumericalDataSigned, - pcm_param.eEndian == - OMX_EndianLittle ? G_LITTLE_ENDIAN : G_BIG_ENDIAN, - pcm_param.nBitPerSample, pcm_param.nBitPerSample), - pcm_param.nSamplingRate, pcm_param.nChannels, self->position); - - GST_DEBUG_OBJECT (self, - "Setting output state: format %s, rate %u, channels %u", - gst_audio_format_to_string (self->info.finfo->format), - (guint) pcm_param.nSamplingRate, (guint) pcm_param.nChannels); - - if (!gst_audio_decoder_set_output_format (GST_AUDIO_DECODER (self), - &self->info) - || !gst_audio_decoder_negotiate (GST_AUDIO_DECODER (self))) { - if (buf) - gst_omx_port_release_buffer (port, buf); - goto caps_failed; - } - - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_allocate_buffers (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_populate (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } - - /* Now get a buffer */ - if (acq_return != GST_OMX_ACQUIRE_BUFFER_OK) { - return; - } - } - - g_assert (acq_return == GST_OMX_ACQUIRE_BUFFER_OK); - if (!buf) { - g_assert ((klass->cdata.hacks & GST_OMX_HACK_NO_EMPTY_EOS_BUFFER)); - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto eos; - } - - /* This prevents a deadlock between the srcpad stream - * lock and the audiocodec stream lock, if ::reset() - * is called at the wrong time - */ - if (gst_omx_port_is_flushing (port)) { - GST_DEBUG_OBJECT (self, "Flushing"); - gst_omx_port_release_buffer (port, buf); - goto flushing; - } - - GST_DEBUG_OBJECT (self, "Handling buffer: 0x%08x %" G_GUINT64_FORMAT, - (guint) buf->omx_buf->nFlags, - (guint64) GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp)); - - GST_AUDIO_DECODER_STREAM_LOCK (self); - - spf = klass->get_samples_per_frame (self, self->dec_out_port); - - if (buf->omx_buf->nFilledLen > 0) { - GstBuffer *outbuf; - GstMapInfo minfo; - - GST_DEBUG_OBJECT (self, "Handling output data"); - - if (buf->omx_buf->nFilledLen % self->info.bpf != 0) { - gst_omx_port_release_buffer (port, buf); - goto invalid_buffer; - } - - outbuf = - gst_audio_decoder_allocate_output_buffer (GST_AUDIO_DECODER (self), - buf->omx_buf->nFilledLen); - - gst_buffer_map (outbuf, &minfo, GST_MAP_WRITE); - if (self->needs_reorder) { - gint i, n_samples, c, n_channels; - gint *reorder_map = self->reorder_map; - gint16 *dest, *source; - - dest = (gint16 *) minfo.data; - source = (gint16 *) (buf->omx_buf->pBuffer + buf->omx_buf->nOffset); - n_samples = buf->omx_buf->nFilledLen / self->info.bpf; - n_channels = self->info.channels; - - for (i = 0; i < n_samples; i++) { - for (c = 0; c < n_channels; c++) { - dest[i * n_channels + reorder_map[c]] = source[i * n_channels + c]; - } - } - } else { - memcpy (minfo.data, buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - } - gst_buffer_unmap (outbuf, &minfo); - - if (spf != -1) { - gst_adapter_push (self->output_adapter, outbuf); - } else { - flow_ret = - gst_audio_decoder_finish_frame (GST_AUDIO_DECODER (self), outbuf, 1); - } - } - - GST_DEBUG_OBJECT (self, "Read frame from component"); - - if (spf != -1) { - GstBuffer *outbuf; - guint avail = gst_adapter_available (self->output_adapter); - guint nframes; - - /* We take a multiple of codec frames and push - * them downstream - */ - avail /= self->info.bpf; - nframes = avail / spf; - avail = nframes * spf; - avail *= self->info.bpf; - - if (avail > 0) { - outbuf = gst_adapter_take_buffer (self->output_adapter, avail); - flow_ret = - gst_audio_decoder_finish_frame (GST_AUDIO_DECODER (self), outbuf, - nframes); - } - } - - GST_DEBUG_OBJECT (self, "Finished frame: %s", gst_flow_get_name (flow_ret)); - - if (buf) { - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - } - - self->downstream_flow_ret = flow_ret; - - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - - return; - -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec))); - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_ERROR; - self->started = FALSE; - return; - } - -flushing: - { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - g_mutex_lock (&self->drain_lock); - if (self->draining) { - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - } - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - g_mutex_unlock (&self->drain_lock); - return; - } - -eos: - { - spf = klass->get_samples_per_frame (self, self->dec_out_port); - if (spf != -1) { - GstBuffer *outbuf; - guint avail = gst_adapter_available (self->output_adapter); - guint nframes; - - /* On EOS we take the complete adapter content, no matter - * if it is a multiple of the codec frame size or not. - */ - avail /= self->info.bpf; - nframes = (avail + spf - 1) / spf; - avail *= self->info.bpf; - - if (avail > 0) { - outbuf = gst_adapter_take_buffer (self->output_adapter, avail); - flow_ret = - gst_audio_decoder_finish_frame (GST_AUDIO_DECODER (self), outbuf, - nframes); - } - } - - g_mutex_lock (&self->drain_lock); - if (self->draining) { - GST_DEBUG_OBJECT (self, "Drained"); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - flow_ret = GST_FLOW_OK; - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - } else { - GST_DEBUG_OBJECT (self, "Component signalled EOS"); - flow_ret = GST_FLOW_EOS; - } - g_mutex_unlock (&self->drain_lock); - - GST_AUDIO_DECODER_STREAM_LOCK (self); - self->downstream_flow_ret = flow_ret; - - /* Here we fallback and pause the task for the EOS case */ - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - - return; - } - -flow_error: - { - if (flow_ret == GST_FLOW_EOS) { - GST_DEBUG_OBJECT (self, "EOS"); - - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), - gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->started = FALSE; - } else if (flow_ret < GST_FLOW_EOS) { - GST_ELEMENT_ERROR (self, STREAM, FAILED, - ("Internal data stream error."), ("stream stopped, reason %s", - gst_flow_get_name (flow_ret))); - - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), - gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->started = FALSE; - } else if (flow_ret == GST_FLOW_FLUSHING) { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - g_mutex_lock (&self->drain_lock); - if (self->draining) { - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - } - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->started = FALSE; - g_mutex_unlock (&self->drain_lock); - } - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - return; - } - -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure output port")); - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_ERROR; - self->started = FALSE; - return; - } - -invalid_buffer: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Invalid sized input buffer")); - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_NOT_NEGOTIATED; - self->started = FALSE; - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - return; - } - -caps_failed: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), ("Failed to set caps")); - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - self->downstream_flow_ret = GST_FLOW_NOT_NEGOTIATED; - self->started = FALSE; - return; - } -release_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase output buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - gst_pad_push_event (GST_AUDIO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_DECODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_ERROR; - self->started = FALSE; - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - return; - } -} - -static gboolean -gst_omx_audio_dec_start (GstAudioDecoder * decoder) -{ - GstOMXAudioDec *self; - - self = GST_OMX_AUDIO_DEC (decoder); - - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - - return TRUE; -} - -static gboolean -gst_omx_audio_dec_stop (GstAudioDecoder * decoder) -{ - GstOMXAudioDec *self; - - self = GST_OMX_AUDIO_DEC (decoder); - - GST_DEBUG_OBJECT (self, "Stopping decoder"); - - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); - - gst_pad_stop_task (GST_AUDIO_DECODER_SRC_PAD (decoder)); - - if (gst_omx_component_get_state (self->dec, 0) > OMX_StateIdle) - gst_omx_component_set_state (self->dec, OMX_StateIdle); - - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - - gst_adapter_flush (self->output_adapter, - gst_adapter_available (self->output_adapter)); - - gst_omx_component_get_state (self->dec, 5 * GST_SECOND); - - gst_buffer_replace (&self->codec_data, NULL); - - GST_DEBUG_OBJECT (self, "Stopped decoder"); - - return TRUE; -} - -static gboolean -gst_omx_audio_dec_set_format (GstAudioDecoder * decoder, GstCaps * caps) -{ - GstOMXAudioDec *self; - GstOMXAudioDecClass *klass; - GstStructure *s; - const GValue *codec_data; - gboolean is_format_change = FALSE; - gboolean needs_disable = FALSE; - - self = GST_OMX_AUDIO_DEC (decoder); - klass = GST_OMX_AUDIO_DEC_GET_CLASS (decoder); - - GST_DEBUG_OBJECT (self, "Setting new caps %" GST_PTR_FORMAT, caps); - - /* Check if the caps change is a real format change or if only irrelevant - * parts of the caps have changed or nothing at all. - */ - if (klass->is_format_change) - is_format_change = klass->is_format_change (self, self->dec_in_port, caps); - - needs_disable = - gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded; - /* If the component is not in Loaded state and a real format change happens - * we have to disable the port and re-allocate all buffers. If no real - * format change happened we can just exit here. - */ - if (needs_disable && !is_format_change) { - GST_DEBUG_OBJECT (self, - "Already running and caps did not change the format"); - return TRUE; - } - - if (needs_disable && is_format_change) { - GstOMXPort *out_port = self->dec_out_port; - - GST_DEBUG_OBJECT (self, "Need to disable and drain decoder"); - - gst_omx_audio_dec_drain (self); - gst_omx_audio_dec_flush (decoder, FALSE); - gst_omx_port_set_flushing (out_port, 5 * GST_SECOND, TRUE); - - if (klass->cdata.hacks & GST_OMX_HACK_NO_COMPONENT_RECONFIGURE) { - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - gst_omx_audio_dec_stop (GST_AUDIO_DECODER (self)); - gst_omx_audio_dec_close (GST_AUDIO_DECODER (self)); - GST_AUDIO_DECODER_STREAM_LOCK (self); - - if (!gst_omx_audio_dec_open (GST_AUDIO_DECODER (self))) - return FALSE; - needs_disable = FALSE; - } else { - /* Disabling at the same time input port and output port is only - * required when a buffer is shared between the ports. This cannot - * be the case for a decoder because its input and output buffers - * are of different nature. So let's disable ports sequencially. - * Starting from IL 1.2.0, this point has been clarified. - * OMX_SendCommand will return an error if the IL client attempts to - * call it when there is already an on-going command being processed. - * The exception is for buffer sharing above and the event - * OMX_EventPortNeedsDisable will be sent to request disabling the - * other port at the same time. */ - if (gst_omx_port_set_enabled (self->dec_in_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (self->dec_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_deallocate_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_enabled (self->dec_in_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_set_enabled (out_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_deallocate_buffers (out_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_enabled (out_port, 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - GST_DEBUG_OBJECT (self, "Decoder drained and disabled"); - } - - if (klass->set_format) { - if (!klass->set_format (self, self->dec_in_port, caps)) { - GST_ERROR_OBJECT (self, "Subclass failed to set the new format"); - return FALSE; - } - } - - GST_DEBUG_OBJECT (self, "Updating outport port definition"); - if (gst_omx_port_update_port_definition (self->dec_out_port, - NULL) != OMX_ErrorNone) - return FALSE; - - /* Get codec data from caps */ - gst_buffer_replace (&self->codec_data, NULL); - s = gst_caps_get_structure (caps, 0); - codec_data = gst_structure_get_value (s, "codec_data"); - if (codec_data) { - /* Vorbis and some other codecs have multiple buffers in - * the stream-header field */ - self->codec_data = gst_value_get_buffer (codec_data); - if (self->codec_data) - gst_buffer_ref (self->codec_data); - } - - GST_DEBUG_OBJECT (self, "Enabling component"); - - if (needs_disable) { - if (gst_omx_port_set_enabled (self->dec_in_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - if (gst_omx_port_set_enabled (self->dec_out_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->dec_out_port) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->dec_out_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_port_wait_enabled (self->dec_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_mark_reconfigured (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - } else { - if (!(klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - /* Disable output port */ - if (gst_omx_port_set_enabled (self->dec_out_port, FALSE) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->dec_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_set_state (self->dec, - OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (gst_omx_port_allocate_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - } else { - if (gst_omx_component_set_state (self->dec, - OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (gst_omx_port_allocate_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->dec_out_port) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateIdle) - return FALSE; - - if (gst_omx_component_set_state (self->dec, - OMX_StateExecuting) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateExecuting) - return FALSE; - } - - /* Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, FALSE); - - if (gst_omx_component_get_last_error (self->dec) != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Component in error state: %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec)); - return FALSE; - } - - self->downstream_flow_ret = GST_FLOW_OK; - - return TRUE; -} - -static void -gst_omx_audio_dec_flush (GstAudioDecoder * decoder, gboolean hard) -{ - GstOMXAudioDec *self = GST_OMX_AUDIO_DEC (decoder); - OMX_ERRORTYPE err = OMX_ErrorNone; - - GST_DEBUG_OBJECT (self, "Flushing decoder"); - - if (gst_omx_component_get_state (self->dec, 0) == OMX_StateLoaded) - return; - - /* 0) Pause the components */ - if (gst_omx_component_get_state (self->dec, 0) == OMX_StateExecuting) { - gst_omx_component_set_state (self->dec, OMX_StatePause); - gst_omx_component_get_state (self->dec, GST_CLOCK_TIME_NONE); - } - - /* 1) Flush the ports */ - GST_DEBUG_OBJECT (self, "flushing ports"); - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); - - /* 2) Wait until the srcpad loop is stopped, - * unlock GST_AUDIO_DECODER_STREAM_LOCK to prevent deadlocks - * caused by using this lock from inside the loop function */ - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - gst_pad_stop_task (GST_AUDIO_DECODER_SRC_PAD (decoder)); - GST_DEBUG_OBJECT (self, "Flushing -- task stopped"); - GST_AUDIO_DECODER_STREAM_LOCK (self); - - /* 3) Resume components */ - gst_omx_component_set_state (self->dec, OMX_StateExecuting); - gst_omx_component_get_state (self->dec, GST_CLOCK_TIME_NONE); - - /* 4) Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, FALSE); - - err = gst_omx_port_populate (self->dec_out_port); - - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Failed to populate output port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - /* Reset our state */ - gst_adapter_flush (self->output_adapter, - gst_adapter_available (self->output_adapter)); - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - self->started = FALSE; - GST_DEBUG_OBJECT (self, "Flush finished"); -} - -static GstFlowReturn -gst_omx_audio_dec_handle_frame (GstAudioDecoder * decoder, GstBuffer * inbuf) -{ - GstOMXAcquireBufferReturn acq_ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - GstOMXAudioDec *self; - GstOMXPort *port; - GstOMXBuffer *buf; - GstBuffer *codec_data = NULL; - guint offset = 0; - GstClockTime timestamp, duration; - OMX_ERRORTYPE err; - GstMapInfo minfo; - - self = GST_OMX_AUDIO_DEC (decoder); - - GST_DEBUG_OBJECT (self, "Handling frame"); - - if (self->downstream_flow_ret != GST_FLOW_OK) { - return self->downstream_flow_ret; - } - - if (!self->started) { - GST_DEBUG_OBJECT (self, "Starting task"); - gst_pad_start_task (GST_AUDIO_DECODER_SRC_PAD (self), - (GstTaskFunction) gst_omx_audio_dec_loop, decoder, NULL); - } - - if (inbuf == NULL) - return gst_omx_audio_dec_drain (self); - - /* Make sure to keep a reference to the input here, - * it can be unreffed from the other thread if - * finish_frame() is called */ - gst_buffer_ref (inbuf); - - timestamp = GST_BUFFER_TIMESTAMP (inbuf); - duration = GST_BUFFER_DURATION (inbuf); - - port = self->dec_in_port; - - gst_buffer_map (inbuf, &minfo, GST_MAP_READ); - - while (offset < minfo.size) { - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - acq_ret = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - - if (acq_ret == GST_OMX_ACQUIRE_BUFFER_ERROR) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto component_error; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto flushing; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - /* Reallocate all buffers */ - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_allocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - /* Now get a new buffer and fill it */ - GST_AUDIO_DECODER_STREAM_LOCK (self); - continue; - } - GST_AUDIO_DECODER_STREAM_LOCK (self); - - g_assert (acq_ret == GST_OMX_ACQUIRE_BUFFER_OK && buf != NULL); - - if (buf->omx_buf->nAllocLen - buf->omx_buf->nOffset <= 0) { - gst_omx_port_release_buffer (port, buf); - goto full_buffer; - } - - if (self->downstream_flow_ret != GST_FLOW_OK) { - gst_omx_port_release_buffer (port, buf); - goto flow_error; - } - - if (self->codec_data) { - GST_DEBUG_OBJECT (self, "Passing codec data to the component"); - - codec_data = self->codec_data; - - if (buf->omx_buf->nAllocLen - buf->omx_buf->nOffset < - gst_buffer_get_size (codec_data)) { - gst_omx_port_release_buffer (port, buf); - goto too_large_codec_data; - } - - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_CODECCONFIG; - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_ENDOFFRAME; - buf->omx_buf->nFilledLen = gst_buffer_get_size (codec_data); - gst_buffer_extract (codec_data, 0, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - - if (GST_CLOCK_TIME_IS_VALID (timestamp)) - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (timestamp, OMX_TICKS_PER_SECOND, - GST_SECOND)); - else - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, G_GUINT64_CONSTANT (0)); - buf->omx_buf->nTickCount = 0; - - self->started = TRUE; - err = gst_omx_port_release_buffer (port, buf); - gst_buffer_replace (&self->codec_data, NULL); - if (err != OMX_ErrorNone) - goto release_error; - /* Acquire new buffer for the actual frame */ - continue; - } - - /* Now handle the frame */ - GST_DEBUG_OBJECT (self, "Passing frame offset %d to the component", offset); - - /* Copy the buffer content in chunks of size as requested - * by the port */ - buf->omx_buf->nFilledLen = - MIN (minfo.size - offset, - buf->omx_buf->nAllocLen - buf->omx_buf->nOffset); - gst_buffer_extract (inbuf, offset, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - - if (timestamp != GST_CLOCK_TIME_NONE) { - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (timestamp, OMX_TICKS_PER_SECOND, GST_SECOND)); - self->last_upstream_ts = timestamp; - } else { - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, G_GUINT64_CONSTANT (0)); - } - - if (duration != GST_CLOCK_TIME_NONE && offset == 0) { - buf->omx_buf->nTickCount = - gst_util_uint64_scale (duration, OMX_TICKS_PER_SECOND, GST_SECOND); - self->last_upstream_ts += duration; - } else { - buf->omx_buf->nTickCount = 0; - } - - if (offset == 0) - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_SYNCFRAME; - - /* TODO: Set flags - * - OMX_BUFFERFLAG_DECODEONLY for buffers that are outside - * the segment - */ - - offset += buf->omx_buf->nFilledLen; - - if (offset == minfo.size) - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_ENDOFFRAME; - - self->started = TRUE; - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - } - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_DEBUG_OBJECT (self, "Passed frame to component"); - - return self->downstream_flow_ret; - -full_buffer: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Got OpenMAX buffer with no free space (%p, %u/%u)", buf, - (guint) buf->omx_buf->nOffset, (guint) buf->omx_buf->nAllocLen)); - return GST_FLOW_ERROR; - } - -flow_error: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - return self->downstream_flow_ret; - } - -too_large_codec_data: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("codec_data larger than supported by OpenMAX port " - "(%" G_GSIZE_FORMAT " > %u)", gst_buffer_get_size (codec_data), - (guint) self->dec_in_port->port_def.nBufferSize)); - return GST_FLOW_ERROR; - } - -component_error: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec))); - return GST_FLOW_ERROR; - } - -flushing: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_DEBUG_OBJECT (self, "Flushing -- returning FLUSHING"); - return GST_FLOW_FLUSHING; - } -reconfigure_error: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure input port")); - return GST_FLOW_ERROR; - } -release_error: - { - gst_buffer_unmap (inbuf, &minfo); - gst_buffer_unref (inbuf); - - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase input buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - - return GST_FLOW_ERROR; - } -} - -static GstFlowReturn -gst_omx_audio_dec_drain (GstOMXAudioDec * self) -{ - GstOMXAudioDecClass *klass; - GstOMXBuffer *buf; - GstOMXAcquireBufferReturn acq_ret; - OMX_ERRORTYPE err; - - GST_DEBUG_OBJECT (self, "Draining component"); - - klass = GST_OMX_AUDIO_DEC_GET_CLASS (self); - - if (!self->started) { - GST_DEBUG_OBJECT (self, "Component not started yet"); - return GST_FLOW_OK; - } - self->started = FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_EMPTY_EOS_BUFFER)) { - GST_WARNING_OBJECT (self, "Component does not support empty EOS buffers"); - return GST_FLOW_OK; - } - - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_AUDIO_DECODER_STREAM_UNLOCK (self); - - /* Send an EOS buffer to the component and let the base - * class drop the EOS event. We will send it later when - * the EOS buffer arrives on the output port. */ - acq_ret = gst_omx_port_acquire_buffer (self->dec_in_port, &buf, GST_OMX_WAIT); - if (acq_ret != GST_OMX_ACQUIRE_BUFFER_OK) { - GST_AUDIO_DECODER_STREAM_LOCK (self); - GST_ERROR_OBJECT (self, "Failed to acquire buffer for draining: %d", - acq_ret); - return GST_FLOW_ERROR; - } - - g_mutex_lock (&self->drain_lock); - self->draining = TRUE; - buf->omx_buf->nFilledLen = 0; - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (self->last_upstream_ts, OMX_TICKS_PER_SECOND, - GST_SECOND)); - buf->omx_buf->nTickCount = 0; - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_EOS; - err = gst_omx_port_release_buffer (self->dec_in_port, buf); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to drain component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_mutex_unlock (&self->drain_lock); - GST_AUDIO_DECODER_STREAM_LOCK (self); - return GST_FLOW_ERROR; - } - - GST_DEBUG_OBJECT (self, "Waiting until component is drained"); - - if (G_UNLIKELY (self->dec->hacks & GST_OMX_HACK_DRAIN_MAY_NOT_RETURN)) { - gint64 wait_until = g_get_monotonic_time () + G_TIME_SPAN_SECOND / 2; - - if (!g_cond_wait_until (&self->drain_cond, &self->drain_lock, wait_until)) - GST_WARNING_OBJECT (self, "Drain timed out"); - else - GST_DEBUG_OBJECT (self, "Drained component"); - - } else { - g_cond_wait (&self->drain_cond, &self->drain_lock); - GST_DEBUG_OBJECT (self, "Drained component"); - } - - g_mutex_unlock (&self->drain_lock); - GST_AUDIO_DECODER_STREAM_LOCK (self); - - gst_adapter_flush (self->output_adapter, - gst_adapter_available (self->output_adapter)); - self->started = FALSE; - - return GST_FLOW_OK; -} diff --git a/subprojects/gst-omx/omx/gstomxaudiodec.h b/subprojects/gst-omx/omx/gstomxaudiodec.h deleted file mode 100644 index 0f4adc693e..0000000000 --- a/subprojects/gst-omx/omx/gstomxaudiodec.h +++ /dev/null @@ -1,100 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_AUDIO_DEC_H__ -#define __GST_OMX_AUDIO_DEC_H__ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_AUDIO_DEC \ - (gst_omx_audio_dec_get_type()) -#define GST_OMX_AUDIO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_AUDIO_DEC,GstOMXAudioDec)) -#define GST_OMX_AUDIO_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_AUDIO_DEC,GstOMXAudioDecClass)) -#define GST_OMX_AUDIO_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_AUDIO_DEC,GstOMXAudioDecClass)) -#define GST_IS_OMX_AUDIO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_AUDIO_DEC)) -#define GST_IS_OMX_AUDIO_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_AUDIO_DEC)) - -typedef struct _GstOMXAudioDec GstOMXAudioDec; -typedef struct _GstOMXAudioDecClass GstOMXAudioDecClass; - -struct _GstOMXAudioDec -{ - GstAudioDecoder parent; - - /* < protected > */ - GstOMXComponent *dec; - GstOMXPort *dec_in_port, *dec_out_port; - - GstBufferPool *in_port_pool, *out_port_pool; - - /* < private > */ - GstAudioInfo info; - GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]; - gint reorder_map[OMX_AUDIO_MAXCHANNELS]; - gboolean needs_reorder; - GstBuffer *codec_data; - /* TRUE if the component is configured and saw - * the first buffer */ - gboolean started; - - GstClockTime last_upstream_ts; - - /* Draining state */ - GMutex drain_lock; - GCond drain_cond; - /* TRUE if EOS buffers shouldn't be forwarded */ - gboolean draining; - - GstAdapter *output_adapter; - - GstFlowReturn downstream_flow_ret; -}; - -struct _GstOMXAudioDecClass -{ - GstAudioDecoderClass parent_class; - - GstOMXClassData cdata; - - gboolean (*is_format_change) (GstOMXAudioDec * self, GstOMXPort * port, GstCaps * caps); - gboolean (*set_format) (GstOMXAudioDec * self, GstOMXPort * port, GstCaps * caps); - gint (*get_samples_per_frame) (GstOMXAudioDec * self, GstOMXPort * port); - gboolean (*get_channel_positions) (GstOMXAudioDec * self, GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]); -}; - -GType gst_omx_audio_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_AUDIO_DEC_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxaudioenc.c b/subprojects/gst-omx/omx/gstomxaudioenc.c deleted file mode 100644 index c5c1d6fffd..0000000000 --- a/subprojects/gst-omx/omx/gstomxaudioenc.c +++ /dev/null @@ -1,1181 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include - -#include "gstomxaudioenc.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_audio_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_audio_enc_debug_category - -/* prototypes */ -static void gst_omx_audio_enc_finalize (GObject * object); - -static GstStateChangeReturn -gst_omx_audio_enc_change_state (GstElement * element, - GstStateChange transition); - -static gboolean gst_omx_audio_enc_open (GstAudioEncoder * encoder); -static gboolean gst_omx_audio_enc_close (GstAudioEncoder * encoder); -static gboolean gst_omx_audio_enc_start (GstAudioEncoder * encoder); -static gboolean gst_omx_audio_enc_stop (GstAudioEncoder * encoder); -static gboolean gst_omx_audio_enc_set_format (GstAudioEncoder * encoder, - GstAudioInfo * info); -static GstFlowReturn gst_omx_audio_enc_handle_frame (GstAudioEncoder * - encoder, GstBuffer * buffer); -static void gst_omx_audio_enc_flush (GstAudioEncoder * encoder); - -static GstFlowReturn gst_omx_audio_enc_drain (GstOMXAudioEnc * self); - -enum -{ - PROP_0 -}; - -/* class initialization */ -#define do_init \ -{ \ - GST_DEBUG_CATEGORY_INIT (gst_omx_audio_enc_debug_category, "omxaudioenc", 0, \ - "debug category for gst-omx audio encoder base class"); \ - G_IMPLEMENT_INTERFACE (GST_TYPE_PRESET, NULL); \ -} - -G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GstOMXAudioEnc, gst_omx_audio_enc, - GST_TYPE_AUDIO_ENCODER, do_init); - -static void -gst_omx_audio_enc_class_init (GstOMXAudioEncClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstAudioEncoderClass *audio_encoder_class = GST_AUDIO_ENCODER_CLASS (klass); - - gobject_class->finalize = gst_omx_audio_enc_finalize; - - element_class->change_state = - GST_DEBUG_FUNCPTR (gst_omx_audio_enc_change_state); - - audio_encoder_class->open = GST_DEBUG_FUNCPTR (gst_omx_audio_enc_open); - audio_encoder_class->close = GST_DEBUG_FUNCPTR (gst_omx_audio_enc_close); - audio_encoder_class->start = GST_DEBUG_FUNCPTR (gst_omx_audio_enc_start); - audio_encoder_class->stop = GST_DEBUG_FUNCPTR (gst_omx_audio_enc_stop); - audio_encoder_class->flush = GST_DEBUG_FUNCPTR (gst_omx_audio_enc_flush); - audio_encoder_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_audio_enc_set_format); - audio_encoder_class->handle_frame = - GST_DEBUG_FUNCPTR (gst_omx_audio_enc_handle_frame); - - klass->cdata.type = GST_OMX_COMPONENT_TYPE_FILTER; - klass->cdata.default_sink_template_caps = "audio/x-raw, " - "rate = (int) [ 1, MAX ], " - "channels = (int) [ 1, " G_STRINGIFY (OMX_AUDIO_MAXCHANNELS) " ], " - "format = (string) { S8, U8, S16LE, S16BE, U16LE, U16BE, " - "S24LE, S24BE, U24LE, U24BE, S32LE, S32BE, U32LE, U32BE }"; -} - -static void -gst_omx_audio_enc_init (GstOMXAudioEnc * self) -{ - g_mutex_init (&self->drain_lock); - g_cond_init (&self->drain_cond); -} - -static gboolean -gst_omx_audio_enc_open (GstAudioEncoder * encoder) -{ - GstOMXAudioEnc *self = GST_OMX_AUDIO_ENC (encoder); - GstOMXAudioEncClass *klass = GST_OMX_AUDIO_ENC_GET_CLASS (self); - gint in_port_index, out_port_index; - - self->enc = - gst_omx_component_new (GST_OBJECT_CAST (self), klass->cdata.core_name, - klass->cdata.component_name, klass->cdata.component_role, - klass->cdata.hacks); - self->started = FALSE; - - if (!self->enc) - return FALSE; - - if (gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded) - return FALSE; - - in_port_index = klass->cdata.in_port_index; - out_port_index = klass->cdata.out_port_index; - - if (in_port_index == -1 || out_port_index == -1) { - OMX_PORT_PARAM_TYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->enc, OMX_IndexParamAudioInit, - ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - in_port_index = 0; - out_port_index = 1; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", - (guint) param.nPorts, (guint) param.nStartPortNumber); - in_port_index = param.nStartPortNumber + 0; - out_port_index = param.nStartPortNumber + 1; - } - } - - self->enc_in_port = gst_omx_component_add_port (self->enc, in_port_index); - self->enc_out_port = gst_omx_component_add_port (self->enc, out_port_index); - - if (!self->enc_in_port || !self->enc_out_port) - return FALSE; - - return TRUE; -} - - -static gboolean -gst_omx_audio_enc_shutdown (GstOMXAudioEnc * self) -{ - OMX_STATETYPE state; - - GST_DEBUG_OBJECT (self, "Shutting down encoder"); - - state = gst_omx_component_get_state (self->enc, 0); - if (state > OMX_StateLoaded || state == OMX_StateInvalid) { - if (state > OMX_StateIdle) { - gst_omx_component_set_state (self->enc, OMX_StateIdle); - gst_omx_component_get_state (self->enc, 5 * GST_SECOND); - } - gst_omx_component_set_state (self->enc, OMX_StateLoaded); - gst_omx_port_deallocate_buffers (self->enc_in_port); - gst_omx_port_deallocate_buffers (self->enc_out_port); - if (state > OMX_StateLoaded) - gst_omx_component_get_state (self->enc, 5 * GST_SECOND); - } - - return TRUE; -} - -static gboolean -gst_omx_audio_enc_close (GstAudioEncoder * encoder) -{ - GstOMXAudioEnc *self = GST_OMX_AUDIO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Closing encoder"); - - if (!gst_omx_audio_enc_shutdown (self)) - return FALSE; - - self->enc_in_port = NULL; - self->enc_out_port = NULL; - if (self->enc) - gst_omx_component_unref (self->enc); - self->enc = NULL; - - return TRUE; -} - -static void -gst_omx_audio_enc_finalize (GObject * object) -{ - GstOMXAudioEnc *self = GST_OMX_AUDIO_ENC (object); - - g_mutex_clear (&self->drain_lock); - g_cond_clear (&self->drain_cond); - - G_OBJECT_CLASS (gst_omx_audio_enc_parent_class)->finalize (object); -} - -static GstStateChangeReturn -gst_omx_audio_enc_change_state (GstElement * element, GstStateChange transition) -{ - GstOMXAudioEnc *self; - GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; - - g_return_val_if_fail (GST_IS_OMX_AUDIO_ENC (element), - GST_STATE_CHANGE_FAILURE); - self = GST_OMX_AUDIO_ENC (element); - - switch (transition) { - case GST_STATE_CHANGE_NULL_TO_READY: - break; - case GST_STATE_CHANGE_READY_TO_PAUSED: - self->downstream_flow_ret = GST_FLOW_OK; - - self->draining = FALSE; - self->started = FALSE; - break; - case GST_STATE_CHANGE_PAUSED_TO_PLAYING: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - if (self->enc_in_port) - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, TRUE); - if (self->enc_out_port) - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - break; - default: - break; - } - - ret = - GST_ELEMENT_CLASS (gst_omx_audio_enc_parent_class)->change_state (element, - transition); - - if (ret == GST_STATE_CHANGE_FAILURE) - return ret; - - switch (transition) { - case GST_STATE_CHANGE_PLAYING_TO_PAUSED: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - - if (!gst_omx_audio_enc_shutdown (self)) - ret = GST_STATE_CHANGE_FAILURE; - break; - case GST_STATE_CHANGE_READY_TO_NULL: - break; - default: - break; - } - - return ret; -} - -static void -gst_omx_audio_enc_loop (GstOMXAudioEnc * self) -{ - GstOMXAudioEncClass *klass; - GstOMXPort *port = self->enc_out_port; - GstOMXBuffer *buf = NULL; - GstFlowReturn flow_ret = GST_FLOW_OK; - GstOMXAcquireBufferReturn acq_return; - OMX_ERRORTYPE err; - - klass = GST_OMX_AUDIO_ENC_GET_CLASS (self); - - acq_return = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - if (acq_return == GST_OMX_ACQUIRE_BUFFER_ERROR) { - goto component_error; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - goto flushing; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_EOS) { - goto eos; - } - - if (!gst_pad_has_current_caps (GST_AUDIO_ENCODER_SRC_PAD (self)) - || acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - GstAudioInfo *info = - gst_audio_encoder_get_audio_info (GST_AUDIO_ENCODER (self)); - GstCaps *caps; - - GST_DEBUG_OBJECT (self, "Port settings have changed, updating caps"); - - /* Reallocate all buffers */ - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - } - - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - caps = klass->get_caps (self, self->enc_out_port, info); - if (!caps) { - if (buf) - gst_omx_port_release_buffer (self->enc_out_port, buf); - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - goto caps_failed; - } - - GST_DEBUG_OBJECT (self, "Setting output caps: %" GST_PTR_FORMAT, caps); - - if (!gst_audio_encoder_set_output_format (GST_AUDIO_ENCODER (self), caps)) { - gst_caps_unref (caps); - if (buf) - gst_omx_port_release_buffer (self->enc_out_port, buf); - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - goto caps_failed; - } - gst_caps_unref (caps); - - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_allocate_buffers (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_populate (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } - - /* Now get a buffer */ - if (acq_return != GST_OMX_ACQUIRE_BUFFER_OK) { - return; - } - } - - g_assert (acq_return == GST_OMX_ACQUIRE_BUFFER_OK); - if (!buf) { - g_assert ((klass->cdata.hacks & GST_OMX_HACK_NO_EMPTY_EOS_BUFFER)); - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto eos; - } - - GST_DEBUG_OBJECT (self, "Handling buffer: 0x%08x %" G_GUINT64_FORMAT, - (guint) buf->omx_buf->nFlags, - (guint64) GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp)); - - /* This prevents a deadlock between the srcpad stream - * lock and the videocodec stream lock, if ::reset() - * is called at the wrong time - */ - if (gst_omx_port_is_flushing (self->enc_out_port)) { - GST_DEBUG_OBJECT (self, "Flushing"); - gst_omx_port_release_buffer (self->enc_out_port, buf); - goto flushing; - } - - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - if ((buf->omx_buf->nFlags & OMX_BUFFERFLAG_CODECCONFIG) - && buf->omx_buf->nFilledLen > 0) { - GstCaps *caps; - GstBuffer *codec_data; - GstMapInfo map = GST_MAP_INFO_INIT; - - GST_DEBUG_OBJECT (self, "Handling codec data"); - caps = - gst_caps_copy (gst_pad_get_current_caps (GST_AUDIO_ENCODER_SRC_PAD - (self))); - codec_data = gst_buffer_new_and_alloc (buf->omx_buf->nFilledLen); - - gst_buffer_map (codec_data, &map, GST_MAP_WRITE); - memcpy (map.data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - gst_buffer_unmap (codec_data, &map); - - gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, codec_data, NULL); - if (!gst_pad_set_caps (GST_AUDIO_ENCODER_SRC_PAD (self), caps)) { - gst_caps_unref (caps); - if (buf) - gst_omx_port_release_buffer (self->enc_out_port, buf); - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - goto caps_failed; - } - gst_caps_unref (caps); - flow_ret = GST_FLOW_OK; - } else if (buf->omx_buf->nFilledLen > 0) { - GstBuffer *outbuf; - guint n_samples; - - GST_DEBUG_OBJECT (self, "Handling output data"); - - n_samples = - klass->get_num_samples (self, self->enc_out_port, - gst_audio_encoder_get_audio_info (GST_AUDIO_ENCODER (self)), buf); - - if (buf->omx_buf->nFilledLen > 0) { - GstMapInfo map = GST_MAP_INFO_INIT; - outbuf = gst_buffer_new_and_alloc (buf->omx_buf->nFilledLen); - - gst_buffer_map (outbuf, &map, GST_MAP_WRITE); - - memcpy (map.data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - gst_buffer_unmap (outbuf, &map); - - } else { - outbuf = gst_buffer_new (); - } - - GST_BUFFER_TIMESTAMP (outbuf) = - gst_util_uint64_scale (GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp), - GST_SECOND, OMX_TICKS_PER_SECOND); - if (buf->omx_buf->nTickCount != 0) - GST_BUFFER_DURATION (outbuf) = - gst_util_uint64_scale (buf->omx_buf->nTickCount, GST_SECOND, - OMX_TICKS_PER_SECOND); - - flow_ret = - gst_audio_encoder_finish_frame (GST_AUDIO_ENCODER (self), - outbuf, n_samples); - } - - GST_DEBUG_OBJECT (self, "Handled output data"); - - GST_DEBUG_OBJECT (self, "Finished frame: %s", gst_flow_get_name (flow_ret)); - - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - - self->downstream_flow_ret = flow_ret; - - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - - return; - -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc))); - gst_pad_push_event (GST_AUDIO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_ERROR; - self->started = FALSE; - return; - } -flushing: - { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - g_mutex_lock (&self->drain_lock); - if (self->draining) { - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - } - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - g_mutex_unlock (&self->drain_lock); - return; - } -eos: - { - g_mutex_lock (&self->drain_lock); - if (self->draining) { - GST_DEBUG_OBJECT (self, "Drained"); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - flow_ret = GST_FLOW_OK; - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - } else { - GST_DEBUG_OBJECT (self, "Component signalled EOS"); - flow_ret = GST_FLOW_EOS; - } - g_mutex_unlock (&self->drain_lock); - - GST_AUDIO_ENCODER_STREAM_LOCK (self); - self->downstream_flow_ret = flow_ret; - - /* Here we fallback and pause the task for the EOS case */ - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - - return; - } -flow_error: - { - if (flow_ret == GST_FLOW_EOS) { - GST_DEBUG_OBJECT (self, "EOS"); - - gst_pad_push_event (GST_AUDIO_ENCODER_SRC_PAD (self), - gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->started = FALSE; - } else if (flow_ret < GST_FLOW_EOS) { - GST_ELEMENT_ERROR (self, STREAM, FAILED, ("Internal data stream error."), - ("stream stopped, reason %s", gst_flow_get_name (flow_ret))); - - gst_pad_push_event (GST_AUDIO_ENCODER_SRC_PAD (self), - gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->started = FALSE; - } else if (flow_ret == GST_FLOW_FLUSHING) { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - g_mutex_lock (&self->drain_lock); - if (self->draining) { - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - } - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->started = FALSE; - g_mutex_unlock (&self->drain_lock); - } - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - return; - } -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure output port")); - gst_pad_push_event (GST_AUDIO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_NOT_NEGOTIATED; - self->started = FALSE; - return; - } -caps_failed: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), ("Failed to set caps")); - gst_pad_push_event (GST_AUDIO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_NOT_NEGOTIATED; - self->started = FALSE; - return; - } -release_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase output buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - gst_pad_push_event (GST_AUDIO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_pad_pause_task (GST_AUDIO_ENCODER_SRC_PAD (self)); - self->downstream_flow_ret = GST_FLOW_ERROR; - self->started = FALSE; - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - return; - } -} - -static gboolean -gst_omx_audio_enc_start (GstAudioEncoder * encoder) -{ - GstOMXAudioEnc *self; - - self = GST_OMX_AUDIO_ENC (encoder); - - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - - return TRUE; -} - -static gboolean -gst_omx_audio_enc_stop (GstAudioEncoder * encoder) -{ - GstOMXAudioEnc *self; - - self = GST_OMX_AUDIO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Stopping encoder"); - - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - gst_pad_stop_task (GST_AUDIO_ENCODER_SRC_PAD (encoder)); - - if (gst_omx_component_get_state (self->enc, 0) > OMX_StateIdle) - gst_omx_component_set_state (self->enc, OMX_StateIdle); - - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - - gst_omx_component_get_state (self->enc, 5 * GST_SECOND); - - return TRUE; -} - -static gboolean -gst_omx_audio_enc_set_format (GstAudioEncoder * encoder, GstAudioInfo * info) -{ - GstOMXAudioEnc *self; - GstOMXAudioEncClass *klass; - gboolean needs_disable = FALSE; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_AUDIO_PARAM_PCMMODETYPE pcm_param; - gint i; - OMX_ERRORTYPE err; - - self = GST_OMX_AUDIO_ENC (encoder); - klass = GST_OMX_AUDIO_ENC_GET_CLASS (encoder); - - GST_DEBUG_OBJECT (self, "Setting new caps"); - - /* Set audio encoder base class properties */ - gst_audio_encoder_set_frame_samples_min (encoder, - gst_util_uint64_scale_ceil (OMX_MIN_PCMPAYLOAD_MSEC, - GST_MSECOND * info->rate, GST_SECOND)); - gst_audio_encoder_set_frame_samples_max (encoder, 0); - - gst_omx_port_get_port_definition (self->enc_in_port, &port_def); - - needs_disable = - gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded; - /* If the component is not in Loaded state and a real format change happens - * we have to disable the port and re-allocate all buffers. If no real - * format change happened we can just exit here. - */ - if (needs_disable) { - GST_DEBUG_OBJECT (self, "Need to disable and drain encoder"); - gst_omx_audio_enc_drain (self); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - /* Wait until the srcpad loop is finished, - * unlock GST_AUDIO_ENCODER_STREAM_LOCK to prevent deadlocks - * caused by using this lock from inside the loop function */ - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - gst_pad_stop_task (GST_AUDIO_ENCODER_SRC_PAD (encoder)); - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - if (klass->cdata.hacks & GST_OMX_HACK_NO_COMPONENT_RECONFIGURE) { - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - gst_omx_audio_enc_stop (GST_AUDIO_ENCODER (self)); - gst_omx_audio_enc_close (GST_AUDIO_ENCODER (self)); - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - if (!gst_omx_audio_enc_open (GST_AUDIO_ENCODER (self))) - return FALSE; - needs_disable = FALSE; - - /* The local port_def is now obsolete so get it again. */ - gst_omx_port_get_port_definition (self->enc_in_port, &port_def); - } else { - /* Disabling at the same time input port and output port is only - * required when a buffer is shared between the ports. This cannot - * be the case for a encoder because its input and output buffers - * are of different nature. So let's disable ports sequencially. - * Starting from IL 1.2.0, this point has been clarified. - * OMX_SendCommand will return an error if the IL client attempts to - * call it when there is already an on-going command being processed. - * The exception is for buffer sharing above and the event - * OMX_EventPortNeedsDisable will be sent to request disabling the - * other port at the same time. */ - if (gst_omx_port_set_enabled (self->enc_in_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (self->enc_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_deallocate_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_enabled (self->enc_in_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_set_enabled (self->enc_out_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (self->enc_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_deallocate_buffers (self->enc_out_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_enabled (self->enc_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - GST_DEBUG_OBJECT (self, "Encoder drained and disabled"); - } - - port_def.format.audio.eEncoding = OMX_AUDIO_CodingPCM; - GST_DEBUG_OBJECT (self, "Setting inport port definition"); - if (gst_omx_port_update_port_definition (self->enc_in_port, - &port_def) != OMX_ErrorNone) - return FALSE; - - GST_OMX_INIT_STRUCT (&pcm_param); - pcm_param.nPortIndex = self->enc_in_port->index; - pcm_param.nChannels = info->channels; - pcm_param.eNumData = - ((info->finfo->flags & GST_AUDIO_FORMAT_FLAG_SIGNED) ? - OMX_NumericalDataSigned : OMX_NumericalDataUnsigned); - pcm_param.eEndian = - ((info->finfo->endianness == G_LITTLE_ENDIAN) ? - OMX_EndianLittle : OMX_EndianBig); - pcm_param.bInterleaved = OMX_TRUE; - pcm_param.nBitPerSample = info->finfo->width; - pcm_param.nSamplingRate = info->rate; - pcm_param.ePCMMode = OMX_AUDIO_PCMModeLinear; - - for (i = 0; i < pcm_param.nChannels; i++) { - OMX_AUDIO_CHANNELTYPE pos; - - switch (info->position[i]) { - case GST_AUDIO_CHANNEL_POSITION_MONO: - case GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER: - pos = OMX_AUDIO_ChannelCF; - break; - case GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT: - pos = OMX_AUDIO_ChannelLF; - break; - case GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT: - pos = OMX_AUDIO_ChannelRF; - break; - case GST_AUDIO_CHANNEL_POSITION_SIDE_LEFT: - pos = OMX_AUDIO_ChannelLS; - break; - case GST_AUDIO_CHANNEL_POSITION_SIDE_RIGHT: - pos = OMX_AUDIO_ChannelRS; - break; - case GST_AUDIO_CHANNEL_POSITION_LFE1: - pos = OMX_AUDIO_ChannelLFE; - break; - case GST_AUDIO_CHANNEL_POSITION_REAR_CENTER: - pos = OMX_AUDIO_ChannelCS; - break; - case GST_AUDIO_CHANNEL_POSITION_REAR_LEFT: - pos = OMX_AUDIO_ChannelLR; - break; - case GST_AUDIO_CHANNEL_POSITION_REAR_RIGHT: - pos = OMX_AUDIO_ChannelRR; - break; - default: - pos = OMX_AUDIO_ChannelNone; - break; - } - pcm_param.eChannelMapping[i] = pos; - } - - GST_DEBUG_OBJECT (self, "Setting PCM parameters"); - err = - gst_omx_component_set_parameter (self->enc, OMX_IndexParamAudioPcm, - &pcm_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set PCM parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - if (klass->set_format) { - if (!klass->set_format (self, self->enc_in_port, info)) { - GST_ERROR_OBJECT (self, "Subclass failed to set the new format"); - return FALSE; - } - } - - GST_DEBUG_OBJECT (self, "Updating outport port definition"); - if (gst_omx_port_update_port_definition (self->enc_out_port, - NULL) != OMX_ErrorNone) - return FALSE; - - GST_DEBUG_OBJECT (self, "Enabling component"); - if (needs_disable) { - if (gst_omx_port_set_enabled (self->enc_in_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - if (gst_omx_port_set_enabled (self->enc_out_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->enc_out_port) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->enc_out_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_port_wait_enabled (self->enc_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_mark_reconfigured (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - } else { - if (!(klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - /* Disable output port */ - if (gst_omx_port_set_enabled (self->enc_out_port, FALSE) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->enc_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_set_state (self->enc, - OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (gst_omx_port_allocate_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - } else { - if (gst_omx_component_set_state (self->enc, - OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (gst_omx_port_allocate_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->enc_out_port) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateIdle) - return FALSE; - - if (gst_omx_component_set_state (self->enc, - OMX_StateExecuting) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateExecuting) - return FALSE; - } - - /* Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, FALSE); - - if (gst_omx_component_get_last_error (self->enc) != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Component in error state: %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc)); - return FALSE; - } - - /* Start the srcpad loop again */ - GST_DEBUG_OBJECT (self, "Starting task again"); - self->downstream_flow_ret = GST_FLOW_OK; - gst_pad_start_task (GST_AUDIO_ENCODER_SRC_PAD (self), - (GstTaskFunction) gst_omx_audio_enc_loop, encoder, NULL); - - return TRUE; -} - -static void -gst_omx_audio_enc_flush (GstAudioEncoder * encoder) -{ - GstOMXAudioEnc *self; - - self = GST_OMX_AUDIO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Resetting encoder"); - - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - /* Wait until the srcpad loop is finished */ - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - GST_PAD_STREAM_LOCK (GST_AUDIO_ENCODER_SRC_PAD (self)); - GST_PAD_STREAM_UNLOCK (GST_AUDIO_ENCODER_SRC_PAD (self)); - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, FALSE); - gst_omx_port_populate (self->enc_out_port); - - /* Start the srcpad loop again */ - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - self->started = FALSE; - gst_pad_start_task (GST_AUDIO_ENCODER_SRC_PAD (self), - (GstTaskFunction) gst_omx_audio_enc_loop, encoder, NULL); -} - -static GstFlowReturn -gst_omx_audio_enc_handle_frame (GstAudioEncoder * encoder, GstBuffer * inbuf) -{ - GstOMXAcquireBufferReturn acq_ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - GstOMXAudioEnc *self; - GstOMXPort *port; - GstOMXBuffer *buf; - gsize size; - guint offset = 0; - GstClockTime timestamp, duration, timestamp_offset = 0; - OMX_ERRORTYPE err; - - self = GST_OMX_AUDIO_ENC (encoder); - - if (self->downstream_flow_ret != GST_FLOW_OK) { - return self->downstream_flow_ret; - } - - if (inbuf == NULL) - return gst_omx_audio_enc_drain (self); - - GST_DEBUG_OBJECT (self, "Handling frame"); - - timestamp = GST_BUFFER_TIMESTAMP (inbuf); - duration = GST_BUFFER_DURATION (inbuf); - - port = self->enc_in_port; - - size = gst_buffer_get_size (inbuf); - while (offset < size) { - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - acq_ret = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - - if (acq_ret == GST_OMX_ACQUIRE_BUFFER_ERROR) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto component_error; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto flushing; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - /* Reallocate all buffers */ - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_allocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - /* Now get a new buffer and fill it */ - GST_AUDIO_ENCODER_STREAM_LOCK (self); - continue; - } - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - g_assert (acq_ret == GST_OMX_ACQUIRE_BUFFER_OK && buf != NULL); - - if (self->downstream_flow_ret != GST_FLOW_OK) { - gst_omx_port_release_buffer (port, buf); - return self->downstream_flow_ret; - } - - if (buf->omx_buf->nAllocLen - buf->omx_buf->nOffset <= 0) { - gst_omx_port_release_buffer (port, buf); - goto full_buffer; - } - - GST_DEBUG_OBJECT (self, "Handling frame at offset %d", offset); - - /* Copy the buffer content in chunks of size as requested - * by the port */ - buf->omx_buf->nFilledLen = - MIN (size - offset, buf->omx_buf->nAllocLen - buf->omx_buf->nOffset); - gst_buffer_extract (inbuf, offset, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - - /* Interpolate timestamps if we're passing the buffer - * in multiple chunks */ - if (offset != 0 && duration != GST_CLOCK_TIME_NONE) { - timestamp_offset = gst_util_uint64_scale (offset, duration, size); - } - - if (timestamp != GST_CLOCK_TIME_NONE) { - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (timestamp + timestamp_offset, - OMX_TICKS_PER_SECOND, GST_SECOND)); - self->last_upstream_ts = timestamp + timestamp_offset; - } - if (duration != GST_CLOCK_TIME_NONE) { - buf->omx_buf->nTickCount = - gst_util_uint64_scale (buf->omx_buf->nFilledLen, duration, size); - buf->omx_buf->nTickCount = - gst_util_uint64_scale (buf->omx_buf->nTickCount, - OMX_TICKS_PER_SECOND, GST_SECOND); - self->last_upstream_ts += duration; - } - - offset += buf->omx_buf->nFilledLen; - self->started = TRUE; - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - } - - GST_DEBUG_OBJECT (self, "Passed frame to component"); - - return self->downstream_flow_ret; - -full_buffer: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Got OpenMAX buffer with no free space (%p, %u/%u)", buf, - (guint) buf->omx_buf->nOffset, (guint) buf->omx_buf->nAllocLen)); - return GST_FLOW_ERROR; - } -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc))); - return GST_FLOW_ERROR; - } - -flushing: - { - GST_DEBUG_OBJECT (self, "Flushing -- returning FLUSHING"); - return GST_FLOW_FLUSHING; - } -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure input port")); - return GST_FLOW_ERROR; - } -release_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase input buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - return GST_FLOW_ERROR; - } -} - -static GstFlowReturn -gst_omx_audio_enc_drain (GstOMXAudioEnc * self) -{ - GstOMXAudioEncClass *klass; - GstOMXBuffer *buf; - GstOMXAcquireBufferReturn acq_ret; - OMX_ERRORTYPE err; - - GST_DEBUG_OBJECT (self, "Draining component"); - - klass = GST_OMX_AUDIO_ENC_GET_CLASS (self); - - if (!self->started) { - GST_DEBUG_OBJECT (self, "Component not started yet"); - return GST_FLOW_OK; - } - self->started = FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_EMPTY_EOS_BUFFER)) { - GST_WARNING_OBJECT (self, "Component does not support empty EOS buffers"); - return GST_FLOW_OK; - } - - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_AUDIO_ENCODER_STREAM_UNLOCK (self); - - /* Send an EOS buffer to the component and let the base - * class drop the EOS event. We will send it later when - * the EOS buffer arrives on the output port. */ - acq_ret = gst_omx_port_acquire_buffer (self->enc_in_port, &buf, GST_OMX_WAIT); - if (acq_ret != GST_OMX_ACQUIRE_BUFFER_OK) { - GST_AUDIO_ENCODER_STREAM_LOCK (self); - GST_ERROR_OBJECT (self, "Failed to acquire buffer for draining: %d", - acq_ret); - return GST_FLOW_ERROR; - } - - g_mutex_lock (&self->drain_lock); - self->draining = TRUE; - buf->omx_buf->nFilledLen = 0; - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (self->last_upstream_ts, OMX_TICKS_PER_SECOND, - GST_SECOND)); - buf->omx_buf->nTickCount = 0; - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_EOS; - err = gst_omx_port_release_buffer (self->enc_in_port, buf); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to drain component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_mutex_unlock (&self->drain_lock); - GST_AUDIO_ENCODER_STREAM_LOCK (self); - return GST_FLOW_ERROR; - } - GST_DEBUG_OBJECT (self, "Waiting until component is drained"); - g_cond_wait (&self->drain_cond, &self->drain_lock); - GST_DEBUG_OBJECT (self, "Drained component"); - g_mutex_unlock (&self->drain_lock); - GST_AUDIO_ENCODER_STREAM_LOCK (self); - - self->started = FALSE; - - return GST_FLOW_OK; -} diff --git a/subprojects/gst-omx/omx/gstomxaudioenc.h b/subprojects/gst-omx/omx/gstomxaudioenc.h deleted file mode 100644 index 8fe5369cdf..0000000000 --- a/subprojects/gst-omx/omx/gstomxaudioenc.h +++ /dev/null @@ -1,87 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_AUDIO_ENC_H__ -#define __GST_OMX_AUDIO_ENC_H__ - -#include -#include -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_AUDIO_ENC \ - (gst_omx_audio_enc_get_type()) -#define GST_OMX_AUDIO_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_AUDIO_ENC,GstOMXAudioEnc)) -#define GST_OMX_AUDIO_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_AUDIO_ENC,GstOMXAudioEncClass)) -#define GST_OMX_AUDIO_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_AUDIO_ENC,GstOMXAudioEncClass)) -#define GST_IS_OMX_AUDIO_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_AUDIO_ENC)) -#define GST_IS_OMX_AUDIO_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_AUDIO_ENC)) - -typedef struct _GstOMXAudioEnc GstOMXAudioEnc; -typedef struct _GstOMXAudioEncClass GstOMXAudioEncClass; - -struct _GstOMXAudioEnc -{ - GstAudioEncoder parent; - - /* < protected > */ - GstOMXComponent *enc; - GstOMXPort *enc_in_port, *enc_out_port; - - /* < private > */ - /* TRUE if the component is configured and saw - * the first buffer */ - gboolean started; - - GstClockTime last_upstream_ts; - - /* Draining state */ - GMutex drain_lock; - GCond drain_cond; - /* TRUE if EOS buffers shouldn't be forwarded */ - gboolean draining; - - GstFlowReturn downstream_flow_ret; -}; - -struct _GstOMXAudioEncClass -{ - GstAudioEncoderClass parent_class; - - GstOMXClassData cdata; - - gboolean (*set_format) (GstOMXAudioEnc * self, GstOMXPort * port, GstAudioInfo * info); - GstCaps *(*get_caps) (GstOMXAudioEnc * self, GstOMXPort * port, GstAudioInfo * info); - guint (*get_num_samples) (GstOMXAudioEnc * self, GstOMXPort * port, GstAudioInfo * info, GstOMXBuffer * buffer); -}; - -GType gst_omx_audio_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_AUDIO_ENC_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxaudiosink.c b/subprojects/gst-omx/omx/gstomxaudiosink.c deleted file mode 100644 index d4e684f3b5..0000000000 --- a/subprojects/gst-omx/omx/gstomxaudiosink.c +++ /dev/null @@ -1,1228 +0,0 @@ -/* - * Copyright (C) 2014, Fluendo, S.A. - * Copyright (C) 2014, Metrological Media Innovations B.V. - * Author: Josep Torra - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - - -#include -#include - -#include - -#include "gstomxaudiosink.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_audio_sink_debug_category); -#define GST_CAT_DEFAULT gst_omx_audio_sink_debug_category - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_audio_sink_debug_category, "omxaudiosink", \ - 0, "debug category for gst-omx audio sink base class"); - -#define DEFAULT_PROP_MUTE FALSE -#define DEFAULT_PROP_VOLUME 1.0 - -#define VOLUME_MAX_DOUBLE 10.0 -#define OUT_CHANNELS(num_channels) ((num_channels) > 4 ? 8: (num_channels) > 2 ? 4: (num_channels)) - -enum -{ - PROP_0, - PROP_MUTE, - PROP_VOLUME -}; - -#define gst_omx_audio_sink_parent_class parent_class -G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GstOMXAudioSink, gst_omx_audio_sink, - GST_TYPE_AUDIO_SINK, G_IMPLEMENT_INTERFACE (GST_TYPE_STREAM_VOLUME, NULL); - DEBUG_INIT); - -#define transform_3_4(type) \ -static inline void \ -transform_3_4_##type (gpointer psrc, gpointer pdst, guint len) \ -{ \ - g##type *src = (g##type *) psrc; \ - g##type *dst = (g##type *) pdst; \ - for (; len > 0; len--) { \ - dst[0] = src[0]; \ - dst[1] = src[1]; \ - dst[2] = src[2]; \ - dst[3] = 0; \ - src += 3; \ - dst += 4; \ - } \ -} - -#define transform_5_8(type) \ -static inline void \ -transform_5_8_##type (gpointer psrc, gpointer pdst, guint len) \ -{ \ - g##type *src = (g##type *) psrc; \ - g##type *dst = (g##type *) pdst; \ - for (; len > 0; len--) { \ - dst[0] = src[0]; \ - dst[1] = src[1]; \ - dst[2] = src[2]; \ - dst[3] = src[3]; \ - dst[4] = src[4]; \ - dst[5] = 0; \ - dst[6] = 0; \ - dst[7] = 0; \ - src += 5; \ - dst += 8; \ - } \ -} - -#define transform_6_8(type) \ -static inline void \ -transform_6_8_##type (gpointer psrc, gpointer pdst, guint len) \ -{ \ - g##type *src = (g##type *) psrc; \ - g##type *dst = (g##type *) pdst; \ - for (; len > 0; len--) { \ - dst[0] = src[0]; \ - dst[1] = src[1]; \ - dst[2] = src[2]; \ - dst[3] = src[3]; \ - dst[4] = src[4]; \ - dst[5] = src[5]; \ - dst[6] = 0; \ - dst[7] = 0; \ - src += 6; \ - dst += 8; \ - } \ -} - -#define transform_7_8(type) \ -static inline void \ -transform_7_8_##type (gpointer psrc, gpointer pdst, guint len) \ -{ \ - g##type *src = (g##type *) psrc; \ - g##type *dst = (g##type *) pdst; \ - for (; len > 0; len--) { \ - dst[0] = src[0]; \ - dst[1] = src[1]; \ - dst[2] = src[2]; \ - dst[3] = src[3]; \ - dst[4] = src[4]; \ - dst[5] = src[5]; \ - dst[6] = src[6]; \ - dst[7] = 0; \ - src += 7; \ - dst += 8; \ - } \ -} - -transform_3_4 (int16); -transform_5_8 (int16); -transform_6_8 (int16); -transform_7_8 (int16); - -transform_3_4 (int32); -transform_5_8 (int32); -transform_6_8 (int32); -transform_7_8 (int32); - -static void inline -transform (guint in_chan, guint width, gpointer psrc, gpointer pdst, guint len) -{ - guint out_chan = OUT_CHANNELS (in_chan); - if (width == 16) { - switch (out_chan) { - case 4: - if (in_chan == 3) { - transform_3_4_int16 (psrc, pdst, len); - } else { - g_assert (FALSE); - } - break; - case 8: - switch (in_chan) { - case 5: - transform_5_8_int16 (psrc, pdst, len); - break; - case 6: - transform_6_8_int16 (psrc, pdst, len); - break; - case 7: - transform_7_8_int16 (psrc, pdst, len); - break; - default: - g_assert (FALSE); - } - break; - default: - g_assert (FALSE); - } - } else if (width == 32) { - switch (out_chan) { - case 4: - if (in_chan == 3) { - transform_3_4_int32 (psrc, pdst, len); - } else { - g_assert (FALSE); - } - break; - case 8: - switch (in_chan) { - case 5: - transform_5_8_int32 (psrc, pdst, len); - break; - case 6: - transform_6_8_int32 (psrc, pdst, len); - break; - case 7: - transform_7_8_int32 (psrc, pdst, len); - break; - default: - g_assert (FALSE); - } - break; - default: - g_assert (FALSE); - } - } else { - g_assert (FALSE); - } -} - -static void -gst_omx_audio_sink_mute_set (GstOMXAudioSink * self, gboolean mute) -{ - if (self->comp) { - OMX_ERRORTYPE err; - OMX_AUDIO_CONFIG_MUTETYPE param; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = self->in_port->index; - param.bMute = (mute ? OMX_TRUE : OMX_FALSE); - err = gst_omx_component_set_config (self->comp, - OMX_IndexConfigAudioMute, ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set mute to %d: %s (0x%08x)", - param.bMute, gst_omx_error_to_string (err), err); - } - } - self->mute = mute; -} - -static void -gst_omx_audio_sink_volume_set (GstOMXAudioSink * self, gdouble volume) -{ - if (self->comp) { - OMX_ERRORTYPE err; - OMX_AUDIO_CONFIG_VOLUMETYPE param; - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = self->in_port->index; - param.bLinear = OMX_TRUE; - param.sVolume.nValue = volume * 100; - err = gst_omx_component_set_config (self->comp, - OMX_IndexConfigAudioVolume, ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set volume to %d: %s (0x%08x)", - (gint) param.sVolume.nValue, gst_omx_error_to_string (err), err); - } - } - self->volume = volume; -} - -static gboolean -gst_omx_audio_sink_open (GstAudioSink * audiosink) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - GstOMXAudioSinkClass *klass = GST_OMX_AUDIO_SINK_GET_CLASS (self); - gint port_index; - OMX_ERRORTYPE err; - - GST_DEBUG_OBJECT (self, "Opening audio sink"); - - self->comp = - gst_omx_component_new (GST_OBJECT_CAST (self), klass->cdata.core_name, - klass->cdata.component_name, klass->cdata.component_role, - klass->cdata.hacks); - - if (!self->comp) - return FALSE; - - if (gst_omx_component_get_state (self->comp, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded) - return FALSE; - - port_index = klass->cdata.in_port_index; - - if (port_index == -1) { - OMX_PORT_PARAM_TYPE param; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->comp, OMX_IndexParamAudioInit, - ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - port_index = 0; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", - (guint) param.nPorts, (guint) param.nStartPortNumber); - port_index = param.nStartPortNumber + 0; - } - } - self->in_port = gst_omx_component_add_port (self->comp, port_index); - - port_index = klass->cdata.out_port_index; - - if (port_index == -1) { - OMX_PORT_PARAM_TYPE param; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->comp, OMX_IndexParamAudioInit, - ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - port_index = 0; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", - (guint) param.nPorts, (guint) param.nStartPortNumber); - port_index = param.nStartPortNumber + 1; - } - } - self->out_port = gst_omx_component_add_port (self->comp, port_index); - - if (!self->in_port || !self->out_port) - return FALSE; - - err = gst_omx_port_set_enabled (self->in_port, FALSE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to disable port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - err = gst_omx_port_set_enabled (self->out_port, FALSE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to disable port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_DEBUG_OBJECT (self, "Opened audio sink"); - - return TRUE; -} - -static gboolean -gst_omx_audio_sink_close (GstAudioSink * audiosink) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - OMX_STATETYPE state; - - GST_DEBUG_OBJECT (self, "Closing audio sink"); - - state = gst_omx_component_get_state (self->comp, 0); - if (state > OMX_StateLoaded || state == OMX_StateInvalid) { - if (state > OMX_StateIdle) { - gst_omx_component_set_state (self->comp, OMX_StateIdle); - gst_omx_component_get_state (self->comp, 5 * GST_SECOND); - } - gst_omx_component_set_state (self->comp, OMX_StateLoaded); - gst_omx_port_deallocate_buffers (self->in_port); - if (state > OMX_StateLoaded) - gst_omx_component_get_state (self->comp, 5 * GST_SECOND); - } - - self->in_port = NULL; - self->out_port = NULL; - if (self->comp) - gst_omx_component_unref (self->comp); - self->comp = NULL; - - GST_DEBUG_OBJECT (self, "Closed audio sink"); - - return TRUE; -} - -static gboolean -gst_omx_audio_sink_parse_spec (GstOMXAudioSink * self, - GstAudioRingBufferSpec * spec) -{ - self->iec61937 = FALSE; - self->endianness = GST_AUDIO_INFO_ENDIANNESS (&spec->info); - self->rate = GST_AUDIO_INFO_RATE (&spec->info); - self->channels = GST_AUDIO_INFO_CHANNELS (&spec->info); - self->width = GST_AUDIO_INFO_WIDTH (&spec->info); - self->is_signed = GST_AUDIO_INFO_IS_SIGNED (&spec->info); - self->is_float = GST_AUDIO_INFO_IS_FLOAT (&spec->info); - - switch (spec->type) { - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_RAW: - { - guint out_channels = OUT_CHANNELS (self->channels); - - self->samples = spec->segsize / self->channels / (self->width >> 3); - if (self->channels == out_channels) { - self->buffer_size = spec->segsize; - } else { - self->buffer_size = (spec->segsize / self->channels) * out_channels; - } - break; - } - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_AC3: - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_EAC3: - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_DTS: - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_MPEG: - self->iec61937 = TRUE; - self->endianness = G_LITTLE_ENDIAN; - self->channels = 2; - self->width = 16; - self->is_signed = TRUE; - self->is_float = FALSE; - self->buffer_size = spec->segsize; - break; - default: - return FALSE; - } - - return TRUE; -} - -static inline void -channel_mapping (GstAudioRingBufferSpec * spec, - OMX_AUDIO_CHANNELTYPE * eChannelMapping) -{ - gint i, nchan = GST_AUDIO_INFO_CHANNELS (&spec->info); - - for (i = 0; i < nchan; i++) { - OMX_AUDIO_CHANNELTYPE pos; - - switch (GST_AUDIO_INFO_POSITION (&spec->info, i)) { - case GST_AUDIO_CHANNEL_POSITION_MONO: - case GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER: - pos = OMX_AUDIO_ChannelCF; - break; - case GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT: - pos = OMX_AUDIO_ChannelLF; - break; - case GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT: - pos = OMX_AUDIO_ChannelRF; - break; - case GST_AUDIO_CHANNEL_POSITION_SIDE_LEFT: - pos = OMX_AUDIO_ChannelLS; - break; - case GST_AUDIO_CHANNEL_POSITION_SIDE_RIGHT: - pos = OMX_AUDIO_ChannelRS; - break; - case GST_AUDIO_CHANNEL_POSITION_LFE1: - pos = OMX_AUDIO_ChannelLFE; - break; - case GST_AUDIO_CHANNEL_POSITION_REAR_CENTER: - pos = OMX_AUDIO_ChannelCS; - break; - case GST_AUDIO_CHANNEL_POSITION_REAR_LEFT: - pos = OMX_AUDIO_ChannelLR; - break; - case GST_AUDIO_CHANNEL_POSITION_REAR_RIGHT: - pos = OMX_AUDIO_ChannelRR; - break; - default: - pos = OMX_AUDIO_ChannelNone; - break; - } - eChannelMapping[i] = pos; - } -} - -static inline const gchar * -ch2str (OMX_AUDIO_CHANNELTYPE ch) -{ - switch (ch) { - case OMX_AUDIO_ChannelNone: - return "OMX_AUDIO_ChannelNone"; - case OMX_AUDIO_ChannelLF: - return "OMX_AUDIO_ChannelLF"; - case OMX_AUDIO_ChannelRF: - return "OMX_AUDIO_ChannelRF"; - case OMX_AUDIO_ChannelCF: - return "OMX_AUDIO_ChannelCF"; - case OMX_AUDIO_ChannelLS: - return "OMX_AUDIO_ChannelLS"; - case OMX_AUDIO_ChannelRS: - return "OMX_AUDIO_ChannelRS"; - case OMX_AUDIO_ChannelLFE: - return "OMX_AUDIO_ChannelLFE"; - case OMX_AUDIO_ChannelCS: - return "OMX_AUDIO_ChannelCS"; - case OMX_AUDIO_ChannelLR: - return "OMX_AUDIO_ChannelLR"; - case OMX_AUDIO_ChannelRR: - return "OMX_AUDIO_ChannelRR"; - default: - return "Invalid value"; - } -} - -static inline gboolean -gst_omx_audio_sink_configure_pcm (GstOMXAudioSink * self, - GstAudioRingBufferSpec * spec) -{ - OMX_AUDIO_PARAM_PCMMODETYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = self->in_port->index; - param.nChannels = OUT_CHANNELS (self->channels); - param.eNumData = - (self->is_signed ? OMX_NumericalDataSigned : OMX_NumericalDataUnsigned); - param.eEndian = - ((self->endianness == - G_LITTLE_ENDIAN) ? OMX_EndianLittle : OMX_EndianBig); - param.bInterleaved = OMX_TRUE; - param.nBitPerSample = self->width; - param.nSamplingRate = self->rate; - - if (self->is_float) { - /* This is cherrypicked from xbmc but it doesn't seems to be valid on my RPI. - * https://github.com/xbmc/xbmc/blob/master/xbmc/cores/AudioEngine/Sinks/AESinkPi.cpp - */ - param.ePCMMode = (OMX_AUDIO_PCMMODETYPE) 0x8000; - } else { - param.ePCMMode = OMX_AUDIO_PCMModeLinear; - } - - if (spec->type == GST_AUDIO_RING_BUFFER_FORMAT_TYPE_RAW) { - channel_mapping (spec, ¶m.eChannelMapping[0]); - } - - GST_DEBUG_OBJECT (self, "Setting PCM parameters"); - GST_DEBUG_OBJECT (self, " nChannels: %u", (guint) param.nChannels); - GST_DEBUG_OBJECT (self, " eNumData: %s", - (param.eNumData == OMX_NumericalDataSigned ? "signed" : "unsigned")); - GST_DEBUG_OBJECT (self, " eEndian: %s", - (param.eEndian == OMX_EndianLittle ? "little endian" : "big endian")); - GST_DEBUG_OBJECT (self, " bInterleaved: %d", param.bInterleaved); - GST_DEBUG_OBJECT (self, " nBitPerSample: %u", (guint) param.nBitPerSample); - GST_DEBUG_OBJECT (self, " nSamplingRate: %u", (guint) param.nSamplingRate); - GST_DEBUG_OBJECT (self, " ePCMMode: %04x", param.ePCMMode); - GST_DEBUG_OBJECT (self, " eChannelMapping: {%s, %s, %s, %s, %s, %s, %s, %s}", - ch2str (param.eChannelMapping[0]), ch2str (param.eChannelMapping[1]), - ch2str (param.eChannelMapping[2]), ch2str (param.eChannelMapping[3]), - ch2str (param.eChannelMapping[4]), ch2str (param.eChannelMapping[5]), - ch2str (param.eChannelMapping[6]), ch2str (param.eChannelMapping[7])); - - err = - gst_omx_component_set_parameter (self->comp, OMX_IndexParamAudioPcm, - ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set PCM parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -static gboolean -gst_omx_audio_sink_prepare (GstAudioSink * audiosink, - GstAudioRingBufferSpec * spec) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_ERRORTYPE err; - - if (!gst_omx_audio_sink_parse_spec (self, spec)) - goto spec_parse; - - gst_omx_port_get_port_definition (self->in_port, &port_def); - - port_def.nBufferSize = self->buffer_size; - /* Only allocate a min number of buffers for transfers from our ringbuffer to - * the hw ringbuffer as we want to keep our small */ - port_def.nBufferCountActual = MAX (port_def.nBufferCountMin, 2); - port_def.format.audio.eEncoding = OMX_AUDIO_CodingPCM; - - GST_DEBUG_OBJECT (self, "Updating outport port definition"); - GST_DEBUG_OBJECT (self, " nBufferSize: %u", (guint) port_def.nBufferSize); - GST_DEBUG_OBJECT (self, " nBufferCountActual: %u", (guint) - port_def.nBufferCountActual); - GST_DEBUG_OBJECT (self, " audio.eEncoding: 0x%08x", - port_def.format.audio.eEncoding); - - err = gst_omx_port_update_port_definition (self->in_port, &port_def); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to configure port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto configuration; - } - - if (!gst_omx_audio_sink_configure_pcm (self, spec)) { - goto configuration; - } - - err = gst_omx_component_set_state (self->comp, OMX_StateIdle); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set state idle: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - err = gst_omx_port_set_flushing (self->in_port, 5 * GST_SECOND, FALSE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set port not flushing: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - err = gst_omx_port_set_enabled (self->in_port, TRUE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to enable port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - GST_DEBUG_OBJECT (self, "Allocate buffers"); - err = gst_omx_port_allocate_buffers (self->in_port); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed on buffer allocation: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - err = gst_omx_port_wait_enabled (self->in_port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "port not enabled: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - err = gst_omx_port_mark_reconfigured (self->in_port); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Couln't mark port as reconfigured: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - err = gst_omx_component_set_state (self->comp, OMX_StatePause); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set state paused: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - - if (gst_omx_component_get_state (self->comp, - GST_CLOCK_TIME_NONE) != OMX_StatePause) - goto activation; - - /* Configure some parameters */ - GST_OBJECT_LOCK (self); - gst_omx_audio_sink_mute_set (self, self->mute); - gst_omx_audio_sink_volume_set (self, self->volume); - GST_OBJECT_UNLOCK (self); - -#if defined (USE_OMX_TARGET_RPI) - { - GstOMXAudioSinkClass *klass = GST_OMX_AUDIO_SINK_GET_CLASS (self); - OMX_ERRORTYPE err; - OMX_CONFIG_BRCMAUDIODESTINATIONTYPE param; - - if (klass->destination - && strlen (klass->destination) < sizeof (param.sName)) { - GST_DEBUG_OBJECT (self, "Setting destination: %s", klass->destination); - GST_OMX_INIT_STRUCT (¶m); - strcpy ((char *) param.sName, klass->destination); - err = gst_omx_component_set_config (self->comp, - OMX_IndexConfigBrcmAudioDestination, ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to configuring destination: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto activation; - } - } - } -#endif - - return TRUE; - - /* ERRORS */ -spec_parse: - { - GST_ELEMENT_ERROR (self, RESOURCE, SETTINGS, (NULL), - ("Error parsing spec")); - return FALSE; - } - -configuration: - { - GST_ELEMENT_ERROR (self, RESOURCE, SETTINGS, (NULL), - ("Configuration failed")); - return FALSE; - } -activation: - { - GST_ELEMENT_ERROR (self, RESOURCE, SETTINGS, (NULL), - ("Component activation failed")); - return FALSE; - } -} - -static gboolean -gst_omx_audio_sink_unprepare (GstAudioSink * audiosink) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - OMX_ERRORTYPE err; - - if (gst_omx_component_get_state (self->comp, 0) == OMX_StateIdle) - return TRUE; - - err = gst_omx_port_set_flushing (self->in_port, 5 * GST_SECOND, TRUE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set port flushing: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto failed; - } - - err = gst_omx_component_set_state (self->comp, OMX_StateIdle); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set state idle: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto failed; - } - - err = gst_omx_port_set_enabled (self->in_port, FALSE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set port disabled: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto failed; - } - - err = gst_omx_port_wait_buffers_released (self->in_port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - goto failed; - } - - err = gst_omx_port_deallocate_buffers (self->in_port); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Couldn't deallocate buffers: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto failed; - } - - err = gst_omx_port_wait_enabled (self->in_port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) { - goto failed; - } - - gst_omx_component_get_state (self->comp, GST_CLOCK_TIME_NONE); - - return TRUE; - - /* ERRORS */ -failed: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->comp), - gst_omx_component_get_last_error (self->comp))); - return FALSE; - } -} - -static GstOMXBuffer * -gst_omx_audio_sink_acquire_buffer (GstOMXAudioSink * self) -{ - GstOMXAcquireBufferReturn acq_ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - GstOMXPort *port = self->in_port; - OMX_ERRORTYPE err; - GstOMXBuffer *buf = NULL; - - while (!buf) { - acq_ret = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - if (acq_ret == GST_OMX_ACQUIRE_BUFFER_ERROR) { - goto component_error; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - GST_DEBUG_OBJECT (self, "Flushing..."); - goto flushing; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - GST_DEBUG_OBJECT (self, "Reconfigure..."); - /* Reallocate all buffers */ - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set port disabled: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto reconfigure_error; - } - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - goto reconfigure_error; - } - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Couldn't deallocate buffers: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) { - goto reconfigure_error; - } - - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - goto reconfigure_error; - } - - err = gst_omx_port_allocate_buffers (port); - if (err != OMX_ErrorNone) { - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - goto reconfigure_error; - } - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) { - goto reconfigure_error; - } - continue; - } - } - - return buf; - - /* ERRORS */ -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->comp), - gst_omx_component_get_last_error (self->comp))); - return NULL; - } -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure input port")); - return NULL; - } -flushing: - { - return NULL; - } -} - -static gint -gst_omx_audio_sink_write (GstAudioSink * audiosink, gpointer data, guint length) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - GstOMXBuffer *buf; - OMX_ERRORTYPE err; - - GST_LOG_OBJECT (self, "received audio samples buffer of %u bytes", length); - - GST_OMX_AUDIO_SINK_LOCK (self); - - if (!(buf = gst_omx_audio_sink_acquire_buffer (self))) { - goto beach; - } - - if (buf->omx_buf->nAllocLen == length) { - memcpy (buf->omx_buf->pBuffer + buf->omx_buf->nOffset, data, length); - } else { - transform (self->channels, self->width, data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, self->samples); - } - buf->omx_buf->nFilledLen = buf->omx_buf->nAllocLen; - - err = gst_omx_port_release_buffer (self->in_port, buf); - if (err != OMX_ErrorNone) - goto release_error; - -beach: - - GST_OMX_AUDIO_SINK_UNLOCK (self); - - return length; - - /* ERRORS */ -release_error: - { - GST_OMX_AUDIO_SINK_UNLOCK (self); - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase input buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - return 0; - } -} - -static guint -gst_omx_audio_sink_delay (GstAudioSink * audiosink) -{ -#if defined (USE_OMX_TARGET_RPI) - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - OMX_PARAM_U32TYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = self->in_port->index; - param.nU32 = 0; - err = gst_omx_component_get_config (self->comp, - OMX_IndexConfigAudioRenderingLatency, ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to get rendering latency: %s (0x%08x)", - gst_omx_error_to_string (err), err); - param.nU32 = 0; - } - - GST_DEBUG_OBJECT (self, "reported delay %u samples", (guint) param.nU32); - return param.nU32; -#else - return 0; -#endif -} - -static void -gst_omx_audio_sink_reset (GstAudioSink * audiosink) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiosink); - OMX_STATETYPE state; - - GST_DEBUG_OBJECT (self, "Flushing sink"); - - gst_omx_port_set_flushing (self->in_port, 5 * GST_SECOND, TRUE); - - GST_OMX_AUDIO_SINK_LOCK (self); - if ((state = gst_omx_component_get_state (self->comp, 0)) > OMX_StatePause) { - gst_omx_component_set_state (self->comp, OMX_StatePause); - gst_omx_component_get_state (self->comp, GST_CLOCK_TIME_NONE); - } - - gst_omx_component_set_state (self->comp, state); - gst_omx_component_get_state (self->comp, GST_CLOCK_TIME_NONE); - - gst_omx_port_set_flushing (self->in_port, 5 * GST_SECOND, FALSE); - - GST_OMX_AUDIO_SINK_UNLOCK (self); -} - -static GstBuffer * -gst_omx_audio_sink_payload (GstAudioBaseSink * audiobasesink, GstBuffer * buf) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (audiobasesink); - - if (self->iec61937) { - GstBuffer *out; - gint framesize; - GstMapInfo iinfo, oinfo; - GstAudioRingBufferSpec *spec = &audiobasesink->ringbuffer->spec; - - framesize = gst_audio_iec61937_frame_size (spec); - if (framesize <= 0) - return NULL; - - out = gst_buffer_new_and_alloc (framesize); - - gst_buffer_map (buf, &iinfo, GST_MAP_READ); - gst_buffer_map (out, &oinfo, GST_MAP_WRITE); - - if (!gst_audio_iec61937_payload (iinfo.data, iinfo.size, - oinfo.data, oinfo.size, spec, G_BIG_ENDIAN)) { - gst_buffer_unref (out); - return NULL; - } - - gst_buffer_unmap (buf, &iinfo); - gst_buffer_unmap (out, &oinfo); - - gst_buffer_copy_into (out, buf, GST_BUFFER_COPY_METADATA, 0, -1); - return out; - } - - return gst_buffer_ref (buf); -} - -static gboolean -gst_omx_audio_sink_accept_caps (GstOMXAudioSink * self, GstCaps * caps) -{ - GstPad *pad = GST_BASE_SINK (self)->sinkpad; - GstCaps *pad_caps; - GstStructure *st; - gboolean ret = FALSE; - GstAudioRingBufferSpec spec = { 0 }; - - pad_caps = gst_pad_query_caps (pad, caps); - if (!pad_caps || gst_caps_is_empty (pad_caps)) { - if (pad_caps) - gst_caps_unref (pad_caps); - ret = FALSE; - goto done; - } - gst_caps_unref (pad_caps); - - /* If we've not got fixed caps, creating a stream might fail, so let's just - * return from here with default acceptcaps behaviour */ - if (!gst_caps_is_fixed (caps)) - goto done; - - /* parse helper expects this set, so avoid nasty warning - * will be set properly later on anyway */ - spec.latency_time = GST_SECOND; - if (!gst_audio_ring_buffer_parse_caps (&spec, caps)) - goto done; - - /* Make sure input is framed (one frame per buffer) and can be payloaded */ - switch (spec.type) { - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_AC3: - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_EAC3: - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_DTS: - case GST_AUDIO_RING_BUFFER_FORMAT_TYPE_MPEG: - { - gboolean framed = FALSE, parsed = FALSE; - st = gst_caps_get_structure (caps, 0); - - gst_structure_get_boolean (st, "framed", &framed); - gst_structure_get_boolean (st, "parsed", &parsed); - if ((!framed && !parsed) || gst_audio_iec61937_frame_size (&spec) <= 0) - goto done; - } - default:{ - } - } - ret = TRUE; - -done: - gst_caps_replace (&spec.caps, NULL); - return ret; -} - -static gboolean -gst_omx_audio_sink_query (GstBaseSink * basesink, GstQuery * query) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (basesink); - gboolean ret; - - switch (GST_QUERY_TYPE (query)) { - case GST_QUERY_ACCEPT_CAPS: - { - GstCaps *caps; - - gst_query_parse_accept_caps (query, &caps); - ret = gst_omx_audio_sink_accept_caps (self, caps); - gst_query_set_accept_caps_result (query, ret); - ret = TRUE; - break; - } - default: - ret = GST_BASE_SINK_CLASS (parent_class)->query (basesink, query); - break; - } - return ret; -} - -static void -gst_omx_audio_sink_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (object); - - switch (prop_id) { - case PROP_MUTE: - { - gboolean mute = g_value_get_boolean (value); - GST_OBJECT_LOCK (self); - if (self->mute != mute) { - gst_omx_audio_sink_mute_set (self, mute); - } - GST_OBJECT_UNLOCK (self); - break; - } - case PROP_VOLUME: - { - gdouble volume = g_value_get_double (value); - GST_OBJECT_LOCK (self); - if (volume != self->volume) { - gst_omx_audio_sink_volume_set (self, volume); - } - GST_OBJECT_UNLOCK (self); - break; - } - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_audio_sink_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (object); - - switch (prop_id) { - case PROP_MUTE: - GST_OBJECT_LOCK (self); - g_value_set_boolean (value, self->mute); - GST_OBJECT_UNLOCK (self); - break; - case PROP_VOLUME: - GST_OBJECT_LOCK (self); - g_value_set_double (value, self->volume); - GST_OBJECT_UNLOCK (self); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static GstStateChangeReturn -gst_omx_audio_sink_change_state (GstElement * element, - GstStateChange transition) -{ - GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (element); - OMX_ERRORTYPE err; - - switch (transition) { - case GST_STATE_CHANGE_PAUSED_TO_PLAYING: - { - GST_DEBUG_OBJECT (self, "going to PLAYING state"); - err = gst_omx_component_set_state (self->comp, OMX_StateExecuting); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set state executing: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return GST_STATE_CHANGE_FAILURE; - } - - if (gst_omx_component_get_state (self->comp, - GST_CLOCK_TIME_NONE) != OMX_StateExecuting) { - return GST_STATE_CHANGE_FAILURE; - } - GST_DEBUG_OBJECT (self, "in PLAYING state"); - break; - } - default: - break; - } - - ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition); - - switch (transition) { - case GST_STATE_CHANGE_PLAYING_TO_PAUSED: - { - GST_DEBUG_OBJECT (self, "going to PAUSED state"); - err = gst_omx_component_set_state (self->comp, OMX_StatePause); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set state paused: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return GST_STATE_CHANGE_FAILURE; - } - - if (gst_omx_component_get_state (self->comp, - GST_CLOCK_TIME_NONE) != OMX_StatePause) { - return GST_STATE_CHANGE_FAILURE; - } - GST_DEBUG_OBJECT (self, "in PAUSED state"); - break; - } - default: - break; - } - - return ret; -} - -static void -gst_omx_audio_sink_finalize (GObject * object) -{ - GstOMXAudioSink *self = GST_OMX_AUDIO_SINK (object); - - g_mutex_clear (&self->lock); - - G_OBJECT_CLASS (parent_class)->finalize (object); -} - -static void -gst_omx_audio_sink_class_init (GstOMXAudioSinkClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstBaseSinkClass *basesink_class = GST_BASE_SINK_CLASS (klass); - GstAudioBaseSinkClass *baudiosink_class = GST_AUDIO_BASE_SINK_CLASS (klass); - GstAudioSinkClass *audiosink_class = GST_AUDIO_SINK_CLASS (klass); - - gobject_class->set_property = gst_omx_audio_sink_set_property; - gobject_class->get_property = gst_omx_audio_sink_get_property; - gobject_class->finalize = gst_omx_audio_sink_finalize; - - g_object_class_install_property (gobject_class, PROP_MUTE, - g_param_spec_boolean ("mute", "Mute", "mute channel", - DEFAULT_PROP_MUTE, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, PROP_VOLUME, - g_param_spec_double ("volume", "Volume", "volume factor, 1.0=100%", - 0.0, VOLUME_MAX_DOUBLE, DEFAULT_PROP_VOLUME, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)); - - element_class->change_state = - GST_DEBUG_FUNCPTR (gst_omx_audio_sink_change_state); - - basesink_class->query = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_query); - - baudiosink_class->payload = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_payload); - - audiosink_class->open = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_open); - audiosink_class->close = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_close); - audiosink_class->prepare = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_prepare); - audiosink_class->unprepare = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_unprepare); - audiosink_class->write = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_write); - audiosink_class->delay = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_delay); - audiosink_class->reset = GST_DEBUG_FUNCPTR (gst_omx_audio_sink_reset); - - - klass->cdata.type = GST_OMX_COMPONENT_TYPE_SINK; -} - -static void -gst_omx_audio_sink_init (GstOMXAudioSink * self) -{ - g_mutex_init (&self->lock); - - self->mute = DEFAULT_PROP_MUTE; - self->volume = DEFAULT_PROP_VOLUME; - - /* For the Raspberry PI there's a big hw buffer and 400 ms seems a good - * size for our ringbuffer. OpenSL ES Sink also allocates a buffer of 400 ms - * in Android so I guess that this should be a sane value for OpenMax in - * general. */ - GST_AUDIO_BASE_SINK (self)->buffer_time = 400000; - gst_audio_base_sink_set_provide_clock (GST_AUDIO_BASE_SINK (self), TRUE); -} diff --git a/subprojects/gst-omx/omx/gstomxaudiosink.h b/subprojects/gst-omx/omx/gstomxaudiosink.h deleted file mode 100644 index 481b18a513..0000000000 --- a/subprojects/gst-omx/omx/gstomxaudiosink.h +++ /dev/null @@ -1,103 +0,0 @@ -/* - * Copyright (C) 2014, Fluendo, S.A. - * Copyright (C) 2014, Metrological Media Innovations B.V. - * Author: Josep Torra - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_AUDIO_SINK_H__ -#define __GST_OMX_AUDIO_SINK_H__ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_AUDIO_SINK \ - (gst_omx_audio_sink_get_type()) -#define GST_OMX_AUDIO_SINK(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_AUDIO_SINK,GstOMXAudioSink)) -#define GST_OMX_AUDIO_SINK_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_AUDIO_SINK,GstOMXAudioSinkClass)) -#define GST_OMX_AUDIO_SINK_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_AUDIO_SINK,GstOMXAudioSinkClass)) -#define GST_IS_OMX_AUDIO_SINK(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_AUDIO_SINK)) -#define GST_IS_OMX_AUDIO_SINK_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_AUDIO_SINK)) -#define GST_OMX_AUDIO_SINK_CAST(obj) ((GstOMXAudioSink *) (obj)) - -#define GST_OMX_AUDIO_SINK_GET_LOCK(obj) (&GST_OMX_AUDIO_SINK_CAST (obj)->lock) -#define GST_OMX_AUDIO_SINK_LOCK(obj) (g_mutex_lock (GST_OMX_AUDIO_SINK_GET_LOCK (obj))) -#define GST_OMX_AUDIO_SINK_UNLOCK(obj) (g_mutex_unlock (GST_OMX_AUDIO_SINK_GET_LOCK (obj))) - -#define PASSTHROUGH_CAPS \ - "audio/x-ac3, framed = (boolean) true;" \ - "audio/x-eac3, framed = (boolean) true; " \ - "audio/x-dts, framed = (boolean) true, " \ - "block-size = (int) { 512, 1024, 2048 }; " \ - "audio/mpeg, mpegversion = (int) 1, " \ - "mpegaudioversion = (int) [ 1, 2 ], parsed = (boolean) true;" - -typedef struct _GstOMXAudioSink GstOMXAudioSink; -typedef struct _GstOMXAudioSinkClass GstOMXAudioSinkClass; - -struct _GstOMXAudioSink -{ - GstAudioSink parent; - - /* < protected > */ - GstOMXComponent *comp; - GstOMXPort *in_port, *out_port; - - gboolean mute; - gdouble volume; - - gboolean iec61937; - guint endianness; - guint rate; - guint channels; - guint width; - gboolean is_signed; - gboolean is_float; - - guint buffer_size; - guint samples; - - GMutex lock; -}; - -struct _GstOMXAudioSinkClass -{ - GstAudioSinkClass parent_class; - - GstOMXClassData cdata; - const gchar * destination; -}; - -GType gst_omx_audio_sink_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_AUDIO_SINK_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxbufferpool.c b/subprojects/gst-omx/omx/gstomxbufferpool.c deleted file mode 100644 index b88568524c..0000000000 --- a/subprojects/gst-omx/omx/gstomxbufferpool.c +++ /dev/null @@ -1,674 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * Copyright (C) 2013-2019, Collabora Ltd. - * Author: Sebastian Dröge - * George Kiagiadakis - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "gstomxbufferpool.h" -#include "gstomxvideo.h" - -#include - -GST_DEBUG_CATEGORY_STATIC (gst_omx_buffer_pool_debug_category); -#define GST_CAT_DEFAULT gst_omx_buffer_pool_debug_category - -enum -{ - SIG_ALLOCATE, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL] = { 0 }; - -/* Buffer pool for the buffers of an OpenMAX port. - * - * This pool is only used if we either passed buffers from another - * pool to the OMX port or provide the OMX buffers directly to other - * elements. - * - * An output buffer is in the pool if it is currently owned by the port, - * i.e. after OMX_FillThisBuffer(). An output buffer is outside - * the pool after it was taken from the port after it was handled - * by the port, i.e. FillBufferDone. - * - * An input buffer is in the pool if it is currently available to be filled - * upstream. It will be put back into the pool when it has been processed by - * OMX, (EmptyBufferDone). - * - * Buffers can be allocated by us (OMX_AllocateBuffer()) or allocated - * by someone else and (temporarily) passed to this pool - * (OMX_UseBuffer(), OMX_UseEGLImage()). In the latter case the pool of - * the buffer will be overriden, and restored in free_buffer(). Other - * buffers are just freed there. - * - * The pool always has a fixed number of minimum and maximum buffers - * and these are allocated while starting the pool and released afterwards. - * They correspond 1:1 to the OMX buffers of the port, which are allocated - * before the pool is started. - * - * Acquiring an output buffer from this pool happens after the OMX buffer has - * been acquired from the port. gst_buffer_pool_acquire_buffer() is - * supposed to return the buffer that corresponds to the OMX buffer. - * - * For buffers provided to upstream, the buffer will be passed to - * the component manually when it arrives and then unreffed. If the - * buffer is released before reaching the component it will be just put - * back into the pool as if EmptyBufferDone has happened. If it was - * passed to the component, it will be back into the pool when it was - * released and EmptyBufferDone has happened. - * - * For buffers provided to downstream, the buffer will be returned - * back to the component (OMX_FillThisBuffer()) when it is released. - * - * This pool uses a special allocator object, GstOMXAllocator. The main purpose - * of this allocator is to track GstMemory objects in the same way that a - * GstBufferPool tracks buffers. When a buffer is inserted into this pool - * (either because it was just allocated or because it was released back to - * the pool), its memory is ripped off and is tracked separately by the - * allocator. When a buffer is then acquired, we acquire the corresponding - * GstMemory from the allocator and put it back in the buffer. - * - * This allocator mechanism allows us to track memory that has been shared - * with buffers that are not part of this pool. When a memory is shared, then - * its ref count is > 1, which means it will not be released to the allocator - * until the sub-memory is destroyed. - * - * When a memory returns to the allocator, the allocator fires the - * omxbuf-released signal, which is handled by the buffer pool to return the - * omx buffer to the port or the queue. - */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_buffer_pool_debug_category, "omxbufferpool", 0, \ - "debug category for gst-omx buffer pool base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXBufferPool, gst_omx_buffer_pool, - GST_TYPE_BUFFER_POOL, DEBUG_INIT); - -static void gst_omx_buffer_pool_free_buffer (GstBufferPool * bpool, - GstBuffer * buffer); - -static gboolean -gst_omx_buffer_pool_start (GstBufferPool * bpool) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - gboolean has_buffers; - GstStructure *config; - guint min, max; - GstOMXAllocatorForeignMemMode mode; - - /* Only allow to start the pool if we still are attached - * to a component and port */ - GST_OBJECT_LOCK (pool); - if (!pool->component || !pool->port) { - GST_OBJECT_UNLOCK (pool); - return FALSE; - } - - pool->port->using_pool = TRUE; - - has_buffers = (pool->port->buffers != NULL); - GST_OBJECT_UNLOCK (pool); - - config = gst_buffer_pool_get_config (bpool); - gst_buffer_pool_config_get_params (config, NULL, NULL, &min, &max); - gst_structure_free (config); - if (max > min) { - GST_WARNING_OBJECT (bpool, - "max (%d) cannot be higher than min (%d) as pool cannot allocate buffers on the fly", - max, min); - return FALSE; - } - - if (!has_buffers) { - gboolean result = FALSE; - - GST_DEBUG_OBJECT (bpool, "Buffers not yet allocated on port %d of %s", - pool->port->index, pool->component->name); - - g_signal_emit (pool, signals[SIG_ALLOCATE], 0, &result); - - if (!result) { - GST_WARNING_OBJECT (bpool, - "Element failed to allocate buffers, can't start pool"); - return FALSE; - } - } - - g_assert (pool->port->buffers); - - if (pool->other_pool) - /* Importing buffers from downstream, either normal or dmabuf ones */ - mode = GST_OMX_ALLOCATOR_FOREIGN_MEM_OTHER_POOL; - else if (pool->output_mode == GST_OMX_BUFFER_MODE_DMABUF) - /* Exporting dmabuf */ - mode = GST_OMX_ALLOCATOR_FOREIGN_MEM_DMABUF; - else - /* Exporting normal buffers */ - mode = GST_OMX_ALLOCATOR_FOREIGN_MEM_NONE; - - if (!gst_omx_allocator_configure (pool->allocator, min, mode)) - return FALSE; - - if (!gst_omx_allocator_set_active (pool->allocator, TRUE)) - return FALSE; - - return - GST_BUFFER_POOL_CLASS (gst_omx_buffer_pool_parent_class)->start (bpool); -} - -static gboolean -gst_omx_buffer_pool_stop (GstBufferPool * bpool) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - - /* Remove any buffers that are there */ - g_ptr_array_set_size (pool->buffers, 0); - - GST_DEBUG_OBJECT (pool, "deactivating OMX allocator"); - gst_omx_allocator_set_active (pool->allocator, FALSE); - - /* ensure all memories have been deallocated; - * this may take a while if some memories are being shared - * and therefore are in use somewhere else in the pipeline */ - gst_omx_allocator_wait_inactive (pool->allocator); - - GST_DEBUG_OBJECT (pool, "deallocate OMX buffers"); - gst_omx_port_deallocate_buffers (pool->port); - - if (pool->caps) - gst_caps_unref (pool->caps); - pool->caps = NULL; - - pool->add_videometa = FALSE; - pool->deactivated = TRUE; - pool->port->using_pool = TRUE; - - return GST_BUFFER_POOL_CLASS (gst_omx_buffer_pool_parent_class)->stop (bpool); -} - -static const gchar ** -gst_omx_buffer_pool_get_options (GstBufferPool * bpool) -{ - static const gchar *raw_video_options[] = - { GST_BUFFER_POOL_OPTION_VIDEO_META, NULL }; - static const gchar *options[] = { NULL }; - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - - GST_OBJECT_LOCK (pool); - if (pool->port && pool->port->port_def.eDomain == OMX_PortDomainVideo - && pool->port->port_def.format.video.eCompressionFormat == - OMX_VIDEO_CodingUnused) { - GST_OBJECT_UNLOCK (pool); - return raw_video_options; - } - GST_OBJECT_UNLOCK (pool); - - return options; -} - -static gboolean -gst_omx_buffer_pool_set_config (GstBufferPool * bpool, GstStructure * config) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - GstCaps *caps; - guint size, min; - GstStructure *fake_config; - gboolean ret; - - GST_OBJECT_LOCK (pool); - - if (!gst_buffer_pool_config_get_params (config, &caps, &size, &min, NULL)) - goto wrong_config; - - if (caps == NULL) - goto no_caps; - - if (pool->port && pool->port->port_def.eDomain == OMX_PortDomainVideo - && pool->port->port_def.format.video.eCompressionFormat == - OMX_VIDEO_CodingUnused) { - GstVideoInfo info; - - /* now parse the caps from the config */ - if (!gst_video_info_from_caps (&info, caps)) - goto wrong_video_caps; - - /* enable metadata based on config of the pool */ - pool->add_videometa = - gst_buffer_pool_config_has_option (config, - GST_BUFFER_POOL_OPTION_VIDEO_META); - - pool->video_info = info; - } - - if (pool->caps) - gst_caps_unref (pool->caps); - pool->caps = gst_caps_ref (caps); - - /* Ensure max=min as the pool won't be able to allocate more buffers while active */ - gst_buffer_pool_config_set_params (config, caps, size, min, min); - - GST_OBJECT_UNLOCK (pool); - - /* give a fake config to the parent default_set_config() with size == 0 - * this prevents default_release_buffer() from free'ing the buffers, since - * we release them with no memory */ - fake_config = gst_structure_copy (config); - gst_buffer_pool_config_set_params (fake_config, caps, 0, min, min); - - ret = GST_BUFFER_POOL_CLASS (gst_omx_buffer_pool_parent_class)->set_config - (bpool, fake_config); - gst_structure_free (fake_config); - - return ret; - - /* ERRORS */ -wrong_config: - { - GST_OBJECT_UNLOCK (pool); - GST_WARNING_OBJECT (pool, "invalid config"); - return FALSE; - } -no_caps: - { - GST_OBJECT_UNLOCK (pool); - GST_WARNING_OBJECT (pool, "no caps in config"); - return FALSE; - } -wrong_video_caps: - { - GST_OBJECT_UNLOCK (pool); - GST_WARNING_OBJECT (pool, - "failed getting geometry from caps %" GST_PTR_FORMAT, caps); - return FALSE; - } -} - -static GstFlowReturn -gst_omx_buffer_pool_alloc_buffer (GstBufferPool * bpool, - GstBuffer ** buffer, GstBufferPoolAcquireParams * params) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - GstBuffer *buf; - GstMemory *mem; - GstMemory *foreign_mem = NULL; - - if (pool->other_pool) { - guint n; - - buf = g_ptr_array_index (pool->buffers, pool->current_buffer_index); - g_assert (pool->other_pool == buf->pool); - gst_object_replace ((GstObject **) & buf->pool, NULL); - - n = gst_buffer_n_memory (buf); - g_return_val_if_fail (n == 1, GST_FLOW_ERROR); - - /* rip the memory out of the buffer; - * we like to keep them separate in this pool */ - foreign_mem = gst_buffer_get_memory (buf, 0); - gst_buffer_remove_all_memory (buf); - - if (pool->add_videometa) { - GstVideoMeta *meta; - - meta = gst_buffer_get_video_meta (buf); - if (!meta) { - gst_buffer_add_video_meta (buf, GST_VIDEO_FRAME_FLAG_NONE, - GST_VIDEO_INFO_FORMAT (&pool->video_info), - GST_VIDEO_INFO_WIDTH (&pool->video_info), - GST_VIDEO_INFO_HEIGHT (&pool->video_info)); - } - } - - pool->need_copy = FALSE; - } else { - const guint nstride = pool->port->port_def.format.video.nStride; - const guint nslice = pool->port->port_def.format.video.nSliceHeight; - gsize offset[GST_VIDEO_MAX_PLANES] = { 0, }; - gint stride[GST_VIDEO_MAX_PLANES] = { nstride, 0, }; - - buf = gst_buffer_new (); - - switch (GST_VIDEO_INFO_FORMAT (&pool->video_info)) { - case GST_VIDEO_FORMAT_ABGR: - case GST_VIDEO_FORMAT_ARGB: - case GST_VIDEO_FORMAT_RGB16: - case GST_VIDEO_FORMAT_BGR16: - case GST_VIDEO_FORMAT_YUY2: - case GST_VIDEO_FORMAT_UYVY: - case GST_VIDEO_FORMAT_YVYU: - case GST_VIDEO_FORMAT_GRAY8: - break; - case GST_VIDEO_FORMAT_I420: - stride[1] = nstride / 2; - offset[1] = offset[0] + stride[0] * nslice; - stride[2] = nstride / 2; - offset[2] = offset[1] + (stride[1] * nslice / 2); - break; - case GST_VIDEO_FORMAT_NV12: - case GST_VIDEO_FORMAT_NV12_10LE32: - case GST_VIDEO_FORMAT_NV16: - case GST_VIDEO_FORMAT_NV16_10LE32: - stride[1] = nstride; - offset[1] = offset[0] + stride[0] * nslice; - break; - default: - g_assert_not_reached (); - break; - } - - if (pool->add_videometa) { - pool->need_copy = FALSE; - } else { - GstVideoInfo info; - gboolean need_copy = FALSE; - gint i; - - gst_video_info_init (&info); - gst_video_info_set_format (&info, - GST_VIDEO_INFO_FORMAT (&pool->video_info), - GST_VIDEO_INFO_WIDTH (&pool->video_info), - GST_VIDEO_INFO_HEIGHT (&pool->video_info)); - - for (i = 0; i < GST_VIDEO_INFO_N_PLANES (&pool->video_info); i++) { - if (info.stride[i] != stride[i] || info.offset[i] != offset[i]) { - GST_DEBUG_OBJECT (pool, - "Need to copy output frames because of stride/offset mismatch: plane %d stride %d (expected: %d) offset %" - G_GSIZE_FORMAT " (expected: %" G_GSIZE_FORMAT - ") nStride: %d nSliceHeight: %d ", i, stride[i], info.stride[i], - offset[i], info.offset[i], nstride, nslice); - - need_copy = TRUE; - break; - } - } - - pool->need_copy = need_copy; - } - - if (pool->need_copy || pool->add_videometa) { - /* We always add the videometa. It's the job of the user - * to copy the buffer if pool->need_copy is TRUE - */ - GstVideoMeta *meta; - GstVideoAlignment align; - - meta = gst_buffer_add_video_meta_full (buf, GST_VIDEO_FRAME_FLAG_NONE, - GST_VIDEO_INFO_FORMAT (&pool->video_info), - GST_VIDEO_INFO_WIDTH (&pool->video_info), - GST_VIDEO_INFO_HEIGHT (&pool->video_info), - GST_VIDEO_INFO_N_PLANES (&pool->video_info), offset, stride); - - if (gst_omx_video_get_port_padding (pool->port, &pool->video_info, - &align)) - gst_video_meta_set_alignment (meta, align); - } - } - - mem = gst_omx_allocator_allocate (pool->allocator, pool->current_buffer_index, - foreign_mem); - if (!mem) - return GST_FLOW_ERROR; - - if (pool->output_mode == GST_OMX_BUFFER_MODE_DMABUF) { - GstMapInfo map; - - if (!gst_caps_features_contains (gst_caps_get_features (pool->caps, 0), - GST_CAPS_FEATURE_MEMORY_DMABUF)) { - /* Check if the memory is actually mappable */ - if (!gst_memory_map (mem, &map, GST_MAP_READWRITE)) { - GST_ERROR_OBJECT (pool, - "dmabuf memory is not mappable but caps does not have the 'memory:DMABuf' feature"); - gst_memory_unref (mem); - return GST_FLOW_ERROR; - } - - gst_memory_unmap (mem, &map); - } - } - - /* mem still belongs to the allocator; do not add it in the buffer just yet */ - - *buffer = buf; - - pool->current_buffer_index++; - - return GST_FLOW_OK; -} - -/* called by the allocator when we are using other_pool in order - * to restore the foreign GstMemory back to its original GstBuffer */ -static void -on_allocator_foreign_mem_released (GstOMXAllocator * allocator, - gint index, GstMemory * mem, GstOMXBufferPool * pool) -{ - GstBuffer *buf; - - buf = g_ptr_array_index (pool->buffers, index); - gst_buffer_append_memory (buf, mem); - - /* the buffer consumed the passed reference. - * we still need one more reference for the allocator */ - gst_memory_ref (mem); -} - -static void -gst_omx_buffer_pool_free_buffer (GstBufferPool * bpool, GstBuffer * buffer) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - - /* If the buffers belong to another pool, restore them now */ - GST_OBJECT_LOCK (pool); - if (pool->other_pool) { - gst_object_replace ((GstObject **) & buffer->pool, - (GstObject *) pool->other_pool); - } - GST_OBJECT_UNLOCK (pool); - - GST_BUFFER_POOL_CLASS (gst_omx_buffer_pool_parent_class)->free_buffer (bpool, - buffer); -} - -static GstFlowReturn -gst_omx_buffer_pool_acquire_buffer (GstBufferPool * bpool, - GstBuffer ** buffer, GstBufferPoolAcquireParams * params) -{ - GstFlowReturn ret; - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - GstMemory *mem; - - if (pool->port->port_def.eDir == OMX_DirOutput) { - g_return_val_if_fail (pool->current_buffer_index != -1, GST_FLOW_ERROR); - - ret = gst_omx_allocator_acquire (pool->allocator, &mem, - pool->current_buffer_index, NULL); - if (ret != GST_FLOW_OK) - return ret; - - /* If it's our own memory we have to set the sizes */ - if (!pool->other_pool) { - GstOMXBuffer *omx_buf = gst_omx_memory_get_omx_buf (mem); - mem->size = omx_buf->omx_buf->nFilledLen; - mem->offset = omx_buf->omx_buf->nOffset; - } - } else { - /* Acquire any buffer that is available to be filled by upstream */ - GstOMXBuffer *omx_buf; - GstOMXAcquireBufferReturn r; - GstOMXWait wait = GST_OMX_WAIT; - - if (params && (params->flags & GST_BUFFER_POOL_ACQUIRE_FLAG_DONTWAIT)) - wait = GST_OMX_DONT_WAIT; - - r = gst_omx_port_acquire_buffer (pool->port, &omx_buf, wait); - if (r == GST_OMX_ACQUIRE_BUFFER_OK) { - ret = gst_omx_allocator_acquire (pool->allocator, &mem, -1, omx_buf); - if (ret != GST_FLOW_OK) - return ret; - } else if (r == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - return GST_FLOW_FLUSHING; - } else { - return GST_FLOW_ERROR; - } - } - - /* get some GstBuffer available in this pool */ - ret = GST_BUFFER_POOL_CLASS (gst_omx_buffer_pool_parent_class)->acquire_buffer - (bpool, buffer, params); - - if (ret == GST_FLOW_OK) { - /* attach the acquired memory on it */ - gst_buffer_append_memory (*buffer, mem); - } else { - gst_memory_unref (mem); - } - - return ret; -} - -static void -gst_omx_buffer_pool_reset_buffer (GstBufferPool * bpool, GstBuffer * buffer) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (bpool); - guint n; - - n = gst_buffer_n_memory (buffer); - if (G_UNLIKELY (n != 1)) { - GST_ERROR_OBJECT (pool, "Released buffer does not have 1 memory... " - "(n = %u) something went terribly wrong", n); - } - - /* rip the memory out of the buffer; - * we like to keep them separate in this pool. - * if this was the last ref count of the memory, it will be returned - * to the allocator, otherwise it will be returned later */ - gst_buffer_remove_all_memory (buffer); - - /* reset before removing the TAG_MEMORY flag so that the parent impl - * doesn't try to restore the original buffer size */ - GST_BUFFER_POOL_CLASS (gst_omx_buffer_pool_parent_class)->reset_buffer - (bpool, buffer); - - /* pretend nothing happened to the memory to avoid discarding the buffer */ - GST_MINI_OBJECT_FLAG_UNSET (buffer, GST_BUFFER_FLAG_TAG_MEMORY); -} - -static void -on_allocator_omxbuf_released (GstOMXAllocator * allocator, - GstOMXBuffer * omx_buf, GstOMXBufferPool * pool) -{ - OMX_ERRORTYPE err; - - if (pool->port->port_def.eDir == OMX_DirOutput && !omx_buf->used && - !pool->deactivated) { - /* Release back to the port, can be filled again */ - err = gst_omx_port_release_buffer (pool->port, omx_buf); - - if (err != OMX_ErrorNone) { - GST_ELEMENT_ERROR (pool->element, LIBRARY, SETTINGS, (NULL), - ("Failed to relase output buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - } - } else if (pool->port->port_def.eDir == OMX_DirInput) { - gst_omx_port_requeue_buffer (pool->port, omx_buf); - } -} - -static void -gst_omx_buffer_pool_finalize (GObject * object) -{ - GstOMXBufferPool *pool = GST_OMX_BUFFER_POOL (object); - - if (pool->element) - gst_object_unref (pool->element); - pool->element = NULL; - - if (pool->buffers) - g_ptr_array_unref (pool->buffers); - pool->buffers = NULL; - - if (pool->other_pool) - gst_object_unref (pool->other_pool); - pool->other_pool = NULL; - - if (pool->allocator) - gst_object_unref (pool->allocator); - pool->allocator = NULL; - - if (pool->caps) - gst_caps_unref (pool->caps); - pool->caps = NULL; - - g_clear_pointer (&pool->component, gst_omx_component_unref); - - G_OBJECT_CLASS (gst_omx_buffer_pool_parent_class)->finalize (object); -} - -static void -gst_omx_buffer_pool_class_init (GstOMXBufferPoolClass * klass) -{ - GObjectClass *gobject_class = (GObjectClass *) klass; - GstBufferPoolClass *gstbufferpool_class = (GstBufferPoolClass *) klass; - - gobject_class->finalize = gst_omx_buffer_pool_finalize; - gstbufferpool_class->start = gst_omx_buffer_pool_start; - gstbufferpool_class->stop = gst_omx_buffer_pool_stop; - gstbufferpool_class->get_options = gst_omx_buffer_pool_get_options; - gstbufferpool_class->set_config = gst_omx_buffer_pool_set_config; - gstbufferpool_class->alloc_buffer = gst_omx_buffer_pool_alloc_buffer; - gstbufferpool_class->free_buffer = gst_omx_buffer_pool_free_buffer; - gstbufferpool_class->acquire_buffer = gst_omx_buffer_pool_acquire_buffer; - gstbufferpool_class->reset_buffer = gst_omx_buffer_pool_reset_buffer; - - signals[SIG_ALLOCATE] = g_signal_new ("allocate", - G_TYPE_FROM_CLASS (gobject_class), G_SIGNAL_RUN_LAST, 0, NULL, NULL, NULL, - G_TYPE_BOOLEAN, 0); -} - -static void -gst_omx_buffer_pool_init (GstOMXBufferPool * pool) -{ - pool->buffers = g_ptr_array_new (); -} - -GstBufferPool * -gst_omx_buffer_pool_new (GstElement * element, GstOMXComponent * component, - GstOMXPort * port, GstOMXBufferMode output_mode) -{ - GstOMXBufferPool *pool; - - pool = g_object_new (gst_omx_buffer_pool_get_type (), NULL); - pool->element = gst_object_ref (element); - pool->component = gst_omx_component_ref (component); - pool->port = port; - pool->output_mode = output_mode; - pool->allocator = gst_omx_allocator_new (component, port); - - g_signal_connect_object (pool->allocator, "omxbuf-released", - (GCallback) on_allocator_omxbuf_released, pool, 0); - g_signal_connect_object (pool->allocator, "foreign-mem-released", - (GCallback) on_allocator_foreign_mem_released, pool, 0); - - return GST_BUFFER_POOL (pool); -} diff --git a/subprojects/gst-omx/omx/gstomxbufferpool.h b/subprojects/gst-omx/omx/gstomxbufferpool.h deleted file mode 100644 index bc5ac60588..0000000000 --- a/subprojects/gst-omx/omx/gstomxbufferpool.h +++ /dev/null @@ -1,101 +0,0 @@ -/* - * Copyright 2014 Advanced Micro Devices, Inc. - * Author: Christian König - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_BUFFER_POOL_H__ -#define __GST_OMX_BUFFER_POOL_H__ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include - -#include "gstomx.h" -#include "gstomxallocator.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_BUFFER_POOL \ - (gst_omx_buffer_pool_get_type()) -#define GST_OMX_BUFFER_POOL(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_BUFFER_POOL,GstOMXBufferPool)) -#define GST_IS_OMX_BUFFER_POOL(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_BUFFER_POOL)) - -typedef struct _GstOMXBufferPool GstOMXBufferPool; -typedef struct _GstOMXBufferPoolClass GstOMXBufferPoolClass; - -typedef enum { - GST_OMX_BUFFER_MODE_SYSTEM_MEMORY, - GST_OMX_BUFFER_MODE_DMABUF, -} GstOMXBufferMode; - -struct _GstOMXBufferPool -{ - GstVideoBufferPool parent; - - GstElement *element; - - GstCaps *caps; - gboolean add_videometa; - gboolean need_copy; - GstVideoInfo video_info; - - /* Owned by element, element has to stop this pool before - * it destroys component or port */ - GstOMXComponent *component; - GstOMXPort *port; - - /* For handling OpenMAX allocated memory */ - GstOMXAllocator *allocator; - - /* Set from outside this pool */ - /* TRUE if the pool is not used anymore */ - gboolean deactivated; - - /* For populating the pool from another one */ - GstBufferPool *other_pool; - GPtrArray *buffers; - - /* Used during acquire for output ports to - * specify which buffer has to be retrieved - * and during alloc, which buffer has to be - * wrapped - */ - gint current_buffer_index; - - /* The type of buffers produced by the decoder */ - GstOMXBufferMode output_mode; -}; - -struct _GstOMXBufferPoolClass -{ - GstVideoBufferPoolClass parent_class; -}; - -GType gst_omx_buffer_pool_get_type (void); - -GstBufferPool *gst_omx_buffer_pool_new (GstElement * element, GstOMXComponent * component, GstOMXPort * port, GstOMXBufferMode output_mode); - -G_END_DECLS - -#endif /* __GST_OMX_BUFFER_POOL_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxh263dec.c b/subprojects/gst-omx/omx/gstomxh263dec.c deleted file mode 100644 index d76f1b9a57..0000000000 --- a/subprojects/gst-omx/omx/gstomxh263dec.c +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxh263dec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_h263_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_h263_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_h263_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_h263_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_h263_dec_debug_category, "omxh263dec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXH263Dec, gst_omx_h263_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -static void -gst_omx_h263_dec_class_init (GstOMXH263DecClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_h263_dec_is_format_change); - videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h263_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "video/x-h263, " - "variant=(string) itu, " - "parsed=(boolean) true, " "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX H.263 Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode H.263 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.h263"); -} - -static void -gst_omx_h263_dec_init (GstOMXH263Dec * self) -{ -} - -static gboolean -gst_omx_h263_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_h263_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingH263; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} diff --git a/subprojects/gst-omx/omx/gstomxh263dec.h b/subprojects/gst-omx/omx/gstomxh263dec.h deleted file mode 100644 index aa24c2f7f8..0000000000 --- a/subprojects/gst-omx/omx/gstomxh263dec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H263_DEC_H__ -#define __GST_OMX_H263_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_H263_DEC \ - (gst_omx_h263_dec_get_type()) -#define GST_OMX_H263_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_H263_DEC,GstOMXH263Dec)) -#define GST_OMX_H263_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_H263_DEC,GstOMXH263DecClass)) -#define GST_OMX_H263_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_H263_DEC,GstOMXH263DecClass)) -#define GST_IS_OMX_H263_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_H263_DEC)) -#define GST_IS_OMX_H263_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_H263_DEC)) - -typedef struct _GstOMXH263Dec GstOMXH263Dec; -typedef struct _GstOMXH263DecClass GstOMXH263DecClass; - -struct _GstOMXH263Dec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXH263DecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_h263_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_H263_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxh263enc.c b/subprojects/gst-omx/omx/gstomxh263enc.c deleted file mode 100644 index 9e80bfbb19..0000000000 --- a/subprojects/gst-omx/omx/gstomxh263enc.c +++ /dev/null @@ -1,302 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxh263enc.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_h263_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_h263_enc_debug_category - -/* prototypes */ -static gboolean gst_omx_h263_enc_set_format (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); -static GstCaps *gst_omx_h263_enc_get_caps (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_h263_enc_debug_category, "omxh263enc", 0, \ - "debug category for gst-omx video encoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXH263Enc, gst_omx_h263_enc, - GST_TYPE_OMX_VIDEO_ENC, DEBUG_INIT); - -static void -gst_omx_h263_enc_class_init (GstOMXH263EncClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXVideoEncClass *videoenc_class = GST_OMX_VIDEO_ENC_CLASS (klass); - - videoenc_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h263_enc_set_format); - videoenc_class->get_caps = GST_DEBUG_FUNCPTR (gst_omx_h263_enc_get_caps); - - videoenc_class->cdata.default_src_template_caps = "video/x-h263, " - "width=(int) [ 16, 4096 ], " "height=(int) [ 16, 4096 ]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX H.263 Video Encoder", - "Codec/Encoder/Video/Hardware", - "Encode H.263 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videoenc_class->cdata, "video_encoder.h263"); -} - -static void -gst_omx_h263_enc_init (GstOMXH263Enc * self) -{ -} - -static gboolean -gst_omx_h263_enc_set_format (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXH263Enc *self = GST_OMX_H263_ENC (enc); - GstCaps *peercaps; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - OMX_ERRORTYPE err; - guint profile_id, level_id; - - gst_omx_port_get_port_definition (GST_OMX_VIDEO_ENC (self)->enc_out_port, - &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingH263; - err = - gst_omx_port_update_port_definition (GST_OMX_VIDEO_ENC - (self)->enc_out_port, &port_def); - if (err != OMX_ErrorNone) - return FALSE; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Getting profile/level not supported by component"); - return TRUE; - } - - peercaps = gst_pad_peer_query_caps (GST_VIDEO_ENCODER_SRC_PAD (enc), - gst_pad_get_pad_template_caps (GST_VIDEO_ENCODER_SRC_PAD (enc))); - if (peercaps) { - GstStructure *s; - - if (gst_caps_is_empty (peercaps)) { - gst_caps_unref (peercaps); - GST_ERROR_OBJECT (self, "Empty caps"); - return FALSE; - } - - s = gst_caps_get_structure (peercaps, 0); - if (gst_structure_get_uint (s, "profile", &profile_id)) { - switch (profile_id) { - case 0: - param.eProfile = OMX_VIDEO_H263ProfileBaseline; - break; - case 1: - param.eProfile = OMX_VIDEO_H263ProfileH320Coding; - break; - case 2: - param.eProfile = OMX_VIDEO_H263ProfileBackwardCompatible; - break; - case 3: - param.eProfile = OMX_VIDEO_H263ProfileISWV2; - break; - case 4: - param.eProfile = OMX_VIDEO_H263ProfileISWV3; - break; - case 5: - param.eProfile = OMX_VIDEO_H263ProfileHighCompression; - break; - case 6: - param.eProfile = OMX_VIDEO_H263ProfileInternet; - break; - case 7: - param.eProfile = OMX_VIDEO_H263ProfileInterlace; - break; - case 8: - param.eProfile = OMX_VIDEO_H263ProfileHighLatency; - break; - default: - goto unsupported_profile; - } - } - if (gst_structure_get_uint (s, "level", &level_id)) { - switch (level_id) { - case 10: - param.eLevel = OMX_VIDEO_H263Level10; - break; - case 20: - param.eLevel = OMX_VIDEO_H263Level20; - break; - case 30: - param.eLevel = OMX_VIDEO_H263Level30; - break; - case 40: - param.eLevel = OMX_VIDEO_H263Level40; - break; - case 50: - param.eLevel = OMX_VIDEO_H263Level50; - break; - case 60: - param.eLevel = OMX_VIDEO_H263Level60; - break; - case 70: - param.eLevel = OMX_VIDEO_H263Level70; - break; - default: - goto unsupported_level; - } - } - gst_caps_unref (peercaps); - } - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting profile/level not supported by component"); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting profile %u and level %u: %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; - -unsupported_profile: - GST_ERROR_OBJECT (self, "Unsupported profile %u", profile_id); - gst_caps_unref (peercaps); - return FALSE; - -unsupported_level: - GST_ERROR_OBJECT (self, "Unsupported level %u", level_id); - gst_caps_unref (peercaps); - return FALSE; -} - -static GstCaps * -gst_omx_h263_enc_get_caps (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXH263Enc *self = GST_OMX_H263_ENC (enc); - GstCaps *caps; - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - guint profile, level; - - caps = gst_caps_new_empty_simple ("video/x-h263"); - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone && err != OMX_ErrorUnsupportedIndex) { - gst_caps_unref (caps); - return NULL; - } - - if (err == OMX_ErrorNone) { - switch (param.eProfile) { - case OMX_VIDEO_H263ProfileBaseline: - profile = 0; - break; - case OMX_VIDEO_H263ProfileH320Coding: - profile = 1; - break; - case OMX_VIDEO_H263ProfileBackwardCompatible: - profile = 2; - break; - case OMX_VIDEO_H263ProfileISWV2: - profile = 3; - break; - case OMX_VIDEO_H263ProfileISWV3: - profile = 4; - break; - case OMX_VIDEO_H263ProfileHighCompression: - profile = 5; - break; - case OMX_VIDEO_H263ProfileInternet: - profile = 6; - break; - case OMX_VIDEO_H263ProfileInterlace: - profile = 7; - break; - case OMX_VIDEO_H263ProfileHighLatency: - profile = 8; - break; - default: - g_assert_not_reached (); - gst_caps_unref (caps); - return NULL; - } - - switch (param.eLevel) { - case OMX_VIDEO_H263Level10: - level = 10; - break; - case OMX_VIDEO_H263Level20: - level = 20; - break; - case OMX_VIDEO_H263Level30: - level = 30; - break; - case OMX_VIDEO_H263Level40: - level = 40; - break; - case OMX_VIDEO_H263Level50: - level = 50; - break; - case OMX_VIDEO_H263Level60: - level = 60; - break; - case OMX_VIDEO_H263Level70: - level = 70; - break; - default: - g_assert_not_reached (); - gst_caps_unref (caps); - return NULL; - } - - gst_caps_set_simple (caps, - "profile", G_TYPE_UINT, profile, "level", G_TYPE_UINT, level, NULL); - } - - return caps; -} diff --git a/subprojects/gst-omx/omx/gstomxh263enc.h b/subprojects/gst-omx/omx/gstomxh263enc.h deleted file mode 100644 index 0dbd0deb23..0000000000 --- a/subprojects/gst-omx/omx/gstomxh263enc.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H263_ENC_H__ -#define __GST_OMX_H263_ENC_H__ - -#include -#include "gstomxvideoenc.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_H263_ENC \ - (gst_omx_h263_enc_get_type()) -#define GST_OMX_H263_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_H263_ENC,GstOMXH263Enc)) -#define GST_OMX_H263_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_H263_ENC,GstOMXH263EncClass)) -#define GST_OMX_H263_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_H263_ENC,GstOMXH263EncClass)) -#define GST_IS_OMX_H263_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_H263_ENC)) -#define GST_IS_OMX_H263_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_H263_ENC)) - -typedef struct _GstOMXH263Enc GstOMXH263Enc; -typedef struct _GstOMXH263EncClass GstOMXH263EncClass; - -struct _GstOMXH263Enc -{ - GstOMXVideoEnc parent; -}; - -struct _GstOMXH263EncClass -{ - GstOMXVideoEncClass parent_class; -}; - -GType gst_omx_h263_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_H263_ENC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxh264dec.c b/subprojects/gst-omx/omx/gstomxh264dec.c deleted file mode 100644 index 32b575742c..0000000000 --- a/subprojects/gst-omx/omx/gstomxh264dec.c +++ /dev/null @@ -1,216 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxh264dec.h" -#include "gstomxh264utils.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_h264_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_h264_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_h264_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_h264_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_h264_dec_debug_category, "omxh264dec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXH264Dec, gst_omx_h264_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -#define MAKE_CAPS(alignment) \ - "video/x-h264, " \ - "alignment=(string) " alignment ", " \ - "stream-format=(string) byte-stream, " \ - "width=(int) [1,MAX], height=(int) [1,MAX]" - -/* The Zynq supports decoding subframes, though we want "au" to be the - * default, so we keep it prepended. This is the only way that it works with - * rtph264depay. */ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -#define SINK_CAPS MAKE_CAPS ("au") ";" MAKE_CAPS ("nal") -#else -#define SINK_CAPS MAKE_CAPS ("au") -#endif - -static void -gst_omx_h264_dec_class_init (GstOMXH264DecClass * klass) -{ - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_h264_dec_is_format_change); - videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h264_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = SINK_CAPS; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX H.264 Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode H.264 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.avc"); -} - -static void -gst_omx_h264_dec_init (GstOMXH264Dec * self) -{ -} - -static gboolean -gst_omx_h264_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - GstCaps *old_caps = NULL; - GstCaps *new_caps = state->caps; - GstStructure *old_structure, *new_structure; - const gchar *old_profile, *old_level, *old_alignment, *new_profile, - *new_level, *new_alignment; - - if (dec->input_state) { - old_caps = dec->input_state->caps; - } - - if (!old_caps) { - return FALSE; - } - - old_structure = gst_caps_get_structure (old_caps, 0); - new_structure = gst_caps_get_structure (new_caps, 0); - old_profile = gst_structure_get_string (old_structure, "profile"); - old_level = gst_structure_get_string (old_structure, "level"); - old_alignment = gst_structure_get_string (old_structure, "alignment"); - new_profile = gst_structure_get_string (new_structure, "profile"); - new_level = gst_structure_get_string (new_structure, "level"); - new_alignment = gst_structure_get_string (new_structure, "alignment"); - - if (g_strcmp0 (old_profile, new_profile) != 0 - || g_strcmp0 (old_level, new_level) != 0 - || g_strcmp0 (old_alignment, new_alignment) != 0) { - return TRUE; - } - - return FALSE; -} - -static gboolean -set_profile_and_level (GstOMXH264Dec * self, GstVideoCodecState * state) -{ - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - const gchar *profile_string, *level_string; - GstStructure *s; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_DEC (self)->dec_in_port->index; - - /* Pass profile and level to the decoder if we have both info from the - * caps. */ - s = gst_caps_get_structure (state->caps, 0); - profile_string = gst_structure_get_string (s, "profile"); - if (!profile_string) - return TRUE; - - param.eProfile = gst_omx_h264_utils_get_profile_from_str (profile_string); - if (param.eProfile == OMX_VIDEO_AVCProfileMax) - goto unsupported_profile; - - level_string = gst_structure_get_string (s, "level"); - if (!level_string) - return TRUE; - - param.eLevel = gst_omx_h264_utils_get_level_from_str (level_string); - if (param.eLevel == OMX_VIDEO_AVCLevelMax) - goto unsupported_level; - - GST_DEBUG_OBJECT (self, "Set profile (%s) and level (%s) on decoder", - profile_string, level_string); - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_DEC (self)->dec, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting profile/level not supported by component"); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting profile %u and level %u: %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; - -unsupported_profile: - GST_ERROR_OBJECT (self, "Unsupported profile %s", profile_string); - return FALSE; - -unsupported_level: - GST_ERROR_OBJECT (self, "Unsupported level %s", level_string); - return FALSE; -} - -static gboolean -gst_omx_h264_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (dec); - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_ERRORTYPE err; - const GstStructure *s; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingAVC; - err = gst_omx_port_update_port_definition (port, &port_def); - if (err != OMX_ErrorNone) - return FALSE; - - if (klass->cdata.hacks & GST_OMX_HACK_PASS_PROFILE_TO_DECODER) { - if (!set_profile_and_level (GST_OMX_H264_DEC (dec), state)) - return FALSE; - } - - /* Enable subframe mode if NAL aligned */ - s = gst_caps_get_structure (state->caps, 0); - if (!g_strcmp0 (gst_structure_get_string (s, "alignment"), "nal") - && gst_omx_port_set_subframe (dec->dec_in_port, TRUE)) { - gst_video_decoder_set_subframe_mode (GST_VIDEO_DECODER (dec), TRUE); - } - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxh264dec.h b/subprojects/gst-omx/omx/gstomxh264dec.h deleted file mode 100644 index 4c0ea1f37b..0000000000 --- a/subprojects/gst-omx/omx/gstomxh264dec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H264_DEC_H__ -#define __GST_OMX_H264_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_H264_DEC \ - (gst_omx_h264_dec_get_type()) -#define GST_OMX_H264_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_H264_DEC,GstOMXH264Dec)) -#define GST_OMX_H264_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_H264_DEC,GstOMXH264DecClass)) -#define GST_OMX_H264_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_H264_DEC,GstOMXH264DecClass)) -#define GST_IS_OMX_H264_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_H264_DEC)) -#define GST_IS_OMX_H264_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_H264_DEC)) - -typedef struct _GstOMXH264Dec GstOMXH264Dec; -typedef struct _GstOMXH264DecClass GstOMXH264DecClass; - -struct _GstOMXH264Dec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXH264DecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_h264_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_H264_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxh264enc.c b/subprojects/gst-omx/omx/gstomxh264enc.c deleted file mode 100644 index 51d84a805a..0000000000 --- a/subprojects/gst-omx/omx/gstomxh264enc.c +++ /dev/null @@ -1,894 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxh264enc.h" -#include "gstomxh264utils.h" - -#ifdef USE_OMX_TARGET_RPI -#include -#include -#endif - -GST_DEBUG_CATEGORY_STATIC (gst_omx_h264_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_h264_enc_debug_category - -/* prototypes */ -static gboolean gst_omx_h264_enc_set_format (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); -static GstCaps *gst_omx_h264_enc_get_caps (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); -static GstFlowReturn gst_omx_h264_enc_handle_output_frame (GstOMXVideoEnc * - self, GstOMXPort * port, GstOMXBuffer * buf, GstVideoCodecFrame * frame); -static gboolean gst_omx_h264_enc_flush (GstVideoEncoder * enc); -static gboolean gst_omx_h264_enc_stop (GstVideoEncoder * enc); -static void gst_omx_h264_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec); -static void gst_omx_h264_enc_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec); - -enum -{ - PROP_0, -#ifdef USE_OMX_TARGET_RPI - PROP_INLINESPSPPSHEADERS, -#endif - PROP_PERIODICITYOFIDRFRAMES, - PROP_PERIODICITYOFIDRFRAMES_COMPAT, - PROP_INTERVALOFCODINGINTRAFRAMES, - PROP_B_FRAMES, - PROP_ENTROPY_MODE, - PROP_CONSTRAINED_INTRA_PREDICTION, - PROP_LOOP_FILTER_MODE, - PROP_REF_FRAMES -}; - -#ifdef USE_OMX_TARGET_RPI -#define GST_OMX_H264_VIDEO_ENC_INLINE_SPS_PPS_HEADERS_DEFAULT TRUE -#endif -#define GST_OMX_H264_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT (0xffffffff) -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -#define GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT (0) -#define ALIGNMENT "{ au, nal }" -#else -#define GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT (0xffffffff) -#define ALIGNMENT "au" -#endif -#define GST_OMX_H264_VIDEO_ENC_ENTROPY_MODE_DEFAULT (0xffffffff) -#define GST_OMX_H264_VIDEO_ENC_CONSTRAINED_INTRA_PREDICTION_DEFAULT (FALSE) -#define GST_OMX_H264_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT (0xffffffff) -#define GST_OMX_H264_VIDEO_ENC_REF_FRAMES_DEFAULT 0 -#define GST_OMX_H264_VIDEO_ENC_REF_FRAMES_MIN 0 -#define GST_OMX_H264_VIDEO_ENC_REF_FRAMES_MAX 16 - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_h264_enc_debug_category, "omxh264enc", 0, \ - "debug category for gst-omx video encoder base class"); - -#define parent_class gst_omx_h264_enc_parent_class -G_DEFINE_TYPE_WITH_CODE (GstOMXH264Enc, gst_omx_h264_enc, - GST_TYPE_OMX_VIDEO_ENC, DEBUG_INIT); - -#define GST_TYPE_OMX_H264_ENC_ENTROPY_MODE (gst_omx_h264_enc_entropy_mode_get_type ()) -static GType -gst_omx_h264_enc_entropy_mode_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {FALSE, "CAVLC entropy mode", "CAVLC"}, - {TRUE, "CABAC entropy mode", "CABAC"}, - {0xffffffff, "Component Default", "default"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXH264EncEntropyMode", values); - } - return qtype; -} - -#define GST_TYPE_OMX_H264_ENC_LOOP_FILTER_MODE (gst_omx_h264_enc_loop_filter_mode_get_type ()) -static GType -gst_omx_h264_enc_loop_filter_mode_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_VIDEO_AVCLoopFilterEnable, "Enable deblocking filter", "enable"}, - {OMX_VIDEO_AVCLoopFilterDisable, "Disable deblocking filter", "disable"}, - {OMX_VIDEO_AVCLoopFilterDisableSliceBoundary, - "Disables deblocking filter on slice boundary", - "disable-slice-boundary"}, - {0xffffffff, "Component Default", "default"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXH264EncLoopFilter", values); - } - return qtype; -} - -static void -gst_omx_h264_enc_class_init (GstOMXH264EncClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstVideoEncoderClass *basevideoenc_class = GST_VIDEO_ENCODER_CLASS (klass); - GstOMXVideoEncClass *videoenc_class = GST_OMX_VIDEO_ENC_CLASS (klass); - - videoenc_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h264_enc_set_format); - videoenc_class->get_caps = GST_DEBUG_FUNCPTR (gst_omx_h264_enc_get_caps); - - gobject_class->set_property = gst_omx_h264_enc_set_property; - gobject_class->get_property = gst_omx_h264_enc_get_property; - -#ifdef USE_OMX_TARGET_RPI - g_object_class_install_property (gobject_class, PROP_INLINESPSPPSHEADERS, - g_param_spec_boolean ("inline-header", - "Inline SPS/PPS headers before IDR", - "Inline SPS/PPS header before IDR", - GST_OMX_H264_VIDEO_ENC_INLINE_SPS_PPS_HEADERS_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); -#endif - - g_object_class_install_property (gobject_class, PROP_PERIODICITYOFIDRFRAMES, - g_param_spec_uint ("periodicity-idr", "IDR periodicity", - "Periodicity of IDR frames (0xffffffff=component default)", - 0, G_MAXUINT, - GST_OMX_H264_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, - PROP_PERIODICITYOFIDRFRAMES_COMPAT, g_param_spec_uint ("periodicty-idr", - "IDR periodicity", - "Periodicity of IDR frames (0xffffffff=component default) DEPRECATED - only for backwards compat", - 0, G_MAXUINT, - GST_OMX_H264_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, - PROP_INTERVALOFCODINGINTRAFRAMES, - g_param_spec_uint ("interval-intraframes", - "Interval of coding Intra frames", - "Interval of coding Intra frames (0xffffffff=component default)", 0, - G_MAXUINT, - GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_B_FRAMES, - g_param_spec_uint ("b-frames", "Number of B-frames", - "Number of B-frames between two consecutive I-frames (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_ENTROPY_MODE, - g_param_spec_enum ("entropy-mode", "Entropy Mode", - "Entropy mode for encoding process", - GST_TYPE_OMX_H264_ENC_ENTROPY_MODE, - GST_OMX_H264_VIDEO_ENC_ENTROPY_MODE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, - PROP_CONSTRAINED_INTRA_PREDICTION, - g_param_spec_boolean ("constrained-intra-prediction", - "Constrained Intra Prediction", - "If enabled, prediction only uses residual data and decoded samples " - "from neighbouring coding blocks coded using intra prediction modes", - GST_OMX_H264_VIDEO_ENC_CONSTRAINED_INTRA_PREDICTION_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_LOOP_FILTER_MODE, - g_param_spec_enum ("loop-filter-mode", "Loop Filter mode", - "Enable or disable the deblocking filter (0xffffffff=component default)", - GST_TYPE_OMX_H264_ENC_LOOP_FILTER_MODE, - GST_OMX_H264_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_REF_FRAMES, - g_param_spec_uchar ("ref-frames", "Reference frames", - "Number of reference frames used for inter-motion search (0=component default)", - GST_OMX_H264_VIDEO_ENC_REF_FRAMES_MIN, - GST_OMX_H264_VIDEO_ENC_REF_FRAMES_MAX, - GST_OMX_H264_VIDEO_ENC_REF_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - basevideoenc_class->flush = gst_omx_h264_enc_flush; - basevideoenc_class->stop = gst_omx_h264_enc_stop; - - videoenc_class->cdata.default_src_template_caps = "video/x-h264, " - "width = (int) [ 16, 4096 ], height = (int) [ 16, 4096 ], " - "framerate = (fraction) [0, MAX], stream-format=(string) byte-stream, " - "alignment = (string) " ALIGNMENT; - videoenc_class->handle_output_frame = - GST_DEBUG_FUNCPTR (gst_omx_h264_enc_handle_output_frame); - - gst_element_class_set_static_metadata (element_class, - "OpenMAX H.264 Video Encoder", - "Codec/Encoder/Video/Hardware", - "Encode H.264 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videoenc_class->cdata, "video_encoder.avc"); -} - -static void -gst_omx_h264_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (object); - - switch (prop_id) { -#ifdef USE_OMX_TARGET_RPI - case PROP_INLINESPSPPSHEADERS: - self->inline_sps_pps_headers = g_value_get_boolean (value); - break; -#endif - case PROP_PERIODICITYOFIDRFRAMES: - case PROP_PERIODICITYOFIDRFRAMES_COMPAT: - self->periodicty_idr = g_value_get_uint (value); - break; - case PROP_INTERVALOFCODINGINTRAFRAMES: - self->interval_intraframes = g_value_get_uint (value); - break; - case PROP_B_FRAMES: - self->b_frames = g_value_get_uint (value); - break; - case PROP_ENTROPY_MODE: - self->entropy_mode = g_value_get_enum (value); - break; - case PROP_CONSTRAINED_INTRA_PREDICTION: - self->constrained_intra_prediction = g_value_get_boolean (value); - break; - case PROP_LOOP_FILTER_MODE: - self->loop_filter_mode = g_value_get_enum (value); - break; - case PROP_REF_FRAMES: - self->ref_frames = g_value_get_uchar (value); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_h264_enc_get_property (GObject * object, guint prop_id, GValue * value, - GParamSpec * pspec) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (object); - - switch (prop_id) { -#ifdef USE_OMX_TARGET_RPI - case PROP_INLINESPSPPSHEADERS: - g_value_set_boolean (value, self->inline_sps_pps_headers); - break; -#endif - case PROP_PERIODICITYOFIDRFRAMES: - case PROP_PERIODICITYOFIDRFRAMES_COMPAT: - g_value_set_uint (value, self->periodicty_idr); - break; - case PROP_INTERVALOFCODINGINTRAFRAMES: - g_value_set_uint (value, self->interval_intraframes); - break; - case PROP_B_FRAMES: - g_value_set_uint (value, self->b_frames); - break; - case PROP_ENTROPY_MODE: - g_value_set_enum (value, self->entropy_mode); - break; - case PROP_CONSTRAINED_INTRA_PREDICTION: - g_value_set_boolean (value, self->constrained_intra_prediction); - break; - case PROP_LOOP_FILTER_MODE: - g_value_set_enum (value, self->loop_filter_mode); - break; - case PROP_REF_FRAMES: - g_value_set_uchar (value, self->ref_frames); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_h264_enc_init (GstOMXH264Enc * self) -{ -#ifdef USE_OMX_TARGET_RPI - self->inline_sps_pps_headers = - GST_OMX_H264_VIDEO_ENC_INLINE_SPS_PPS_HEADERS_DEFAULT; -#endif - self->periodicty_idr = - GST_OMX_H264_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT; - self->interval_intraframes = - GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT; - self->b_frames = GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT; - self->entropy_mode = GST_OMX_H264_VIDEO_ENC_ENTROPY_MODE_DEFAULT; - self->constrained_intra_prediction = - GST_OMX_H264_VIDEO_ENC_CONSTRAINED_INTRA_PREDICTION_DEFAULT; - self->loop_filter_mode = GST_OMX_H264_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT; - self->ref_frames = GST_OMX_H264_VIDEO_ENC_REF_FRAMES_DEFAULT; -} - -static gboolean -gst_omx_h264_enc_flush (GstVideoEncoder * enc) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (enc); - - g_list_free_full (self->headers, (GDestroyNotify) gst_buffer_unref); - self->headers = NULL; - - return GST_VIDEO_ENCODER_CLASS (parent_class)->flush (enc); -} - -static gboolean -gst_omx_h264_enc_stop (GstVideoEncoder * enc) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (enc); - - g_list_free_full (self->headers, (GDestroyNotify) gst_buffer_unref); - self->headers = NULL; - - return GST_VIDEO_ENCODER_CLASS (parent_class)->stop (enc); -} - -/* Update OMX_VIDEO_PARAM_PROFILELEVELTYPE.{eProfile,eLevel} - * - * Returns TRUE if succeeded or if not supported, FALSE if failed */ -static gboolean -update_param_profile_level (GstOMXH264Enc * self, - OMX_VIDEO_AVCPROFILETYPE profile, OMX_VIDEO_AVCLEVELTYPE level) -{ - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Getting OMX_IndexParamVideoProfileLevelCurrent not supported by component"); - return TRUE; - } - - if (profile != OMX_VIDEO_AVCProfileMax) - param.eProfile = profile; - if (level != OMX_VIDEO_AVCLevelMax) - param.eLevel = level; - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting OMX_IndexParamVideoProfileLevelCurrent not supported by component"); - return TRUE; - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting profile %u and level %u: %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -/* Update OMX_VIDEO_PARAM_AVCTYPE - * - * Returns TRUE if succeeded or if not supported, FALSE if failed */ -static gboolean -update_param_avc (GstOMXH264Enc * self, - OMX_VIDEO_AVCPROFILETYPE profile, OMX_VIDEO_AVCLEVELTYPE level) -{ - OMX_VIDEO_PARAM_AVCTYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - /* On Android the param struct is initialized manually with default - * settings rather than using GetParameter() to retrieve them. - * We should probably do the same when we'll add Android as target. - * See bgo#783862 for details. */ - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoAvc, ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Getting OMX_IndexParamVideoAvc not supported by component"); - return TRUE; - } - - if (profile != OMX_VIDEO_AVCProfileMax) - param.eProfile = profile; - if (level != OMX_VIDEO_AVCLevelMax) - param.eLevel = level; - - /* GOP pattern */ - if (self->interval_intraframes != - GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT) { - param.nPFrames = self->interval_intraframes; - - /* If user specified a specific number of B-frames, reduce the number of - * P-frames by this amount. If not ensure there is no B-frame to have the - * requested GOP length. */ - if (self->b_frames != GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT) { - if (self->b_frames > self->interval_intraframes) { - GST_ERROR_OBJECT (self, - "The interval_intraframes perdiod (%u) needs to be higher than the number of B-frames (%u)", - self->interval_intraframes, self->b_frames); - return FALSE; - } - param.nPFrames -= self->b_frames; - } else { - param.nBFrames = 0; - } - } - - if (self->b_frames != GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT) { - if (profile == OMX_VIDEO_AVCProfileBaseline && self->b_frames > 0) { - GST_ERROR_OBJECT (self, - "Baseline profile doesn't support B-frames (%u requested)", - self->b_frames); - return FALSE; - } - param.nBFrames = self->b_frames; - } - - if (self->ref_frames != GST_OMX_H264_VIDEO_ENC_REF_FRAMES_DEFAULT) - param.nRefFrames = self->ref_frames; - - if (self->entropy_mode != GST_OMX_H264_VIDEO_ENC_ENTROPY_MODE_DEFAULT) { - param.bEntropyCodingCABAC = self->entropy_mode; - } - - param.bconstIpred = self->constrained_intra_prediction; - - if (self->loop_filter_mode != GST_OMX_H264_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT) { - param.eLoopFilterMode = self->loop_filter_mode; - } - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoAvc, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting OMX_IndexParamVideoAvc not supported by component"); - return TRUE; - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting AVC settings (profile %u and level %u): %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -static gboolean -set_avc_intra_period (GstOMXH264Enc * self) -{ - OMX_VIDEO_CONFIG_AVCINTRAPERIOD config_avcintraperiod; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&config_avcintraperiod); - config_avcintraperiod.nPortIndex = - GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexConfigVideoAVCIntraPeriod, &config_avcintraperiod); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "OMX_IndexConfigVideoAVCIntraPeriod not supported by component"); - return TRUE; - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't get OMX_IndexConfigVideoAVCIntraPeriod %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_DEBUG_OBJECT (self, "default nPFrames:%u, nIDRPeriod:%u", - (guint) config_avcintraperiod.nPFrames, - (guint) config_avcintraperiod.nIDRPeriod); - - if (self->periodicty_idr != - GST_OMX_H264_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT) { - config_avcintraperiod.nIDRPeriod = self->periodicty_idr; - } - - if (self->interval_intraframes != - GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT) { - /* This OMX API doesn't allow us to specify the number of B-frames. - * So if user requested one we have to rely on update_param_avc() - * to configure the intraframes interval so it can take the - * B-frames into account. */ - if (self->b_frames == GST_OMX_H264_VIDEO_ENC_B_FRAMES_DEFAULT) - config_avcintraperiod.nPFrames = self->interval_intraframes; - } - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexConfigVideoAVCIntraPeriod, &config_avcintraperiod); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't set OMX_IndexConfigVideoAVCIntraPeriod %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -#ifdef USE_OMX_TARGET_RPI -static gboolean -set_brcm_video_intra_period (GstOMXH264Enc * self) -{ - OMX_PARAM_U32TYPE intra_period; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&intra_period); - - intra_period.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexConfigBrcmVideoIntraPeriod, &intra_period); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't get OMX_IndexConfigBrcmVideoIntraPeriod %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_DEBUG_OBJECT (self, "default OMX_IndexConfigBrcmVideoIntraPeriod: %u", - (guint) intra_period.nU32); - - if (self->interval_intraframes == - GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT) - return TRUE; - - intra_period.nU32 = self->interval_intraframes; - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexConfigBrcmVideoIntraPeriod, &intra_period); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't set OMX_IndexConfigBrcmVideoIntraPeriod %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_DEBUG_OBJECT (self, "OMX_IndexConfigBrcmVideoIntraPeriod set to %u", - (guint) intra_period.nU32); - - return TRUE; -} -#endif - -static gboolean -gst_omx_h264_enc_set_format (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (enc); - GstCaps *peercaps; - OMX_PARAM_PORTDEFINITIONTYPE port_def; -#ifdef USE_OMX_TARGET_RPI - OMX_CONFIG_PORTBOOLEANTYPE config_inline_header; -#endif - OMX_ERRORTYPE err; - const gchar *profile_string, *level_string; - OMX_VIDEO_AVCPROFILETYPE profile = OMX_VIDEO_AVCProfileMax; - OMX_VIDEO_AVCLEVELTYPE level = OMX_VIDEO_AVCLevelMax; - gboolean enable_subframe = FALSE; - -#ifdef USE_OMX_TARGET_RPI - GST_OMX_INIT_STRUCT (&config_inline_header); - config_inline_header.nPortIndex = - GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamBrcmVideoAVCInlineHeaderEnable, &config_inline_header); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't get OMX_IndexParamBrcmVideoAVCInlineHeaderEnable %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - if (self->inline_sps_pps_headers) { - config_inline_header.bEnabled = OMX_TRUE; - } else { - config_inline_header.bEnabled = OMX_FALSE; - } - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamBrcmVideoAVCInlineHeaderEnable, &config_inline_header); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't set OMX_IndexParamBrcmVideoAVCInlineHeaderEnable %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } -#endif - - /* Configure GOP pattern */ - if (self->periodicty_idr != - GST_OMX_H264_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT - || self->interval_intraframes != - GST_OMX_H264_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT) { - set_avc_intra_period (self); - } -#ifdef USE_OMX_TARGET_RPI - /* The Pi uses a specific OMX setting to configure the intra period */ - - if (self->interval_intraframes) - set_brcm_video_intra_period (self); -#endif - - gst_omx_port_get_port_definition (GST_OMX_VIDEO_ENC (self)->enc_out_port, - &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingAVC; - err = - gst_omx_port_update_port_definition (GST_OMX_VIDEO_ENC - (self)->enc_out_port, &port_def); - if (err != OMX_ErrorNone) - return FALSE; - - /* Set profile and level */ - peercaps = gst_pad_peer_query_caps (GST_VIDEO_ENCODER_SRC_PAD (enc), - gst_pad_get_pad_template_caps (GST_VIDEO_ENCODER_SRC_PAD (enc))); - if (peercaps) { - GstStructure *s; - const gchar *alignment_string; - - if (gst_caps_is_empty (peercaps)) { - gst_caps_unref (peercaps); - GST_ERROR_OBJECT (self, "Empty caps"); - return FALSE; - } - - s = gst_caps_get_structure (peercaps, 0); - profile_string = gst_structure_get_string (s, "profile"); - if (profile_string) { - profile = gst_omx_h264_utils_get_profile_from_str (profile_string); - if (profile == OMX_VIDEO_AVCProfileMax) - goto unsupported_profile; - } - level_string = gst_structure_get_string (s, "level"); - if (level_string) { - level = gst_omx_h264_utils_get_level_from_str (level_string); - if (level == OMX_VIDEO_AVCLevelMax) - goto unsupported_level; - } - - alignment_string = gst_structure_get_string (s, "alignment"); - if (alignment_string && g_str_equal (alignment_string, "nal")) - enable_subframe = TRUE; - - gst_caps_unref (peercaps); - } - - if (profile != OMX_VIDEO_AVCProfileMax || level != OMX_VIDEO_AVCLevelMax) { - /* OMX provides 2 API to set the profile and level. We try using the - * generic one here and the H264 specific when calling - * update_param_avc() */ - if (!update_param_profile_level (self, profile, level)) - return FALSE; - } - - gst_omx_port_set_subframe (GST_OMX_VIDEO_ENC (self)->enc_out_port, - enable_subframe); - - if (!update_param_avc (self, profile, level)) - return FALSE; - - return TRUE; - -unsupported_profile: - GST_ERROR_OBJECT (self, "Unsupported profile %s", profile_string); - gst_caps_unref (peercaps); - return FALSE; - -unsupported_level: - GST_ERROR_OBJECT (self, "Unsupported level %s", level_string); - gst_caps_unref (peercaps); - return FALSE; -} - -static GstCaps * -gst_omx_h264_enc_get_caps (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (enc); - GstCaps *caps; - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - const gchar *profile, *level, *alignment; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone && err != OMX_ErrorUnsupportedIndex) - return NULL; - - if (gst_omx_port_get_subframe (GST_OMX_VIDEO_ENC (self)->enc_out_port)) - alignment = "nal"; - else - alignment = "au"; - - caps = gst_caps_new_simple ("video/x-h264", - "stream-format", G_TYPE_STRING, "byte-stream", - "alignment", G_TYPE_STRING, alignment, NULL); - - if (err == OMX_ErrorNone) { - profile = gst_omx_h264_utils_get_profile_from_enum (param.eProfile); - if (!profile) { - g_assert_not_reached (); - gst_caps_unref (caps); - return NULL; - } - - switch (param.eLevel) { - case OMX_VIDEO_AVCLevel1: - level = "1"; - break; - case OMX_VIDEO_AVCLevel1b: - level = "1b"; - break; - case OMX_VIDEO_AVCLevel11: - level = "1.1"; - break; - case OMX_VIDEO_AVCLevel12: - level = "1.2"; - break; - case OMX_VIDEO_AVCLevel13: - level = "1.3"; - break; - case OMX_VIDEO_AVCLevel2: - level = "2"; - break; - case OMX_VIDEO_AVCLevel21: - level = "2.1"; - break; - case OMX_VIDEO_AVCLevel22: - level = "2.2"; - break; - case OMX_VIDEO_AVCLevel3: - level = "3"; - break; - case OMX_VIDEO_AVCLevel31: - level = "3.1"; - break; - case OMX_VIDEO_AVCLevel32: - level = "3.2"; - break; - case OMX_VIDEO_AVCLevel4: - level = "4"; - break; - case OMX_VIDEO_AVCLevel41: - level = "4.1"; - break; - case OMX_VIDEO_AVCLevel42: - level = "4.2"; - break; - case OMX_VIDEO_AVCLevel5: - level = "5"; - break; - case OMX_VIDEO_AVCLevel51: - level = "5.1"; - break; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case OMX_ALG_VIDEO_AVCLevel52: - level = "5.2"; - break; - case OMX_ALG_VIDEO_AVCLevel60: - level = "6.0"; - break; - case OMX_ALG_VIDEO_AVCLevel61: - level = "6.1"; - break; - case OMX_ALG_VIDEO_AVCLevel62: - level = "6.2"; - break; -#endif - default: - g_assert_not_reached (); - gst_caps_unref (caps); - return NULL; - } - gst_caps_set_simple (caps, - "profile", G_TYPE_STRING, profile, "level", G_TYPE_STRING, level, NULL); - } - - return caps; -} - -static GstFlowReturn -gst_omx_h264_enc_handle_output_frame (GstOMXVideoEnc * enc, GstOMXPort * port, - GstOMXBuffer * buf, GstVideoCodecFrame * frame) -{ - GstOMXH264Enc *self = GST_OMX_H264_ENC (enc); - - if (buf->omx_buf->nFlags & OMX_BUFFERFLAG_CODECCONFIG) { - /* The codec data is SPS/PPS but our output is stream-format=byte-stream. - * For bytestream stream format the SPS/PPS is only in-stream and not - * in the caps! - */ - GstBuffer *hdrs; - GstMapInfo map = GST_MAP_INFO_INIT; - GstFlowReturn flow_ret; - - GST_DEBUG_OBJECT (self, "got codecconfig in byte-stream format"); - - hdrs = gst_buffer_new_and_alloc (buf->omx_buf->nFilledLen); - GST_BUFFER_FLAG_SET (hdrs, GST_BUFFER_FLAG_HEADER); - - gst_buffer_map (hdrs, &map, GST_MAP_WRITE); - memcpy (map.data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - gst_buffer_unmap (hdrs, &map); - self->headers = g_list_append (self->headers, gst_buffer_ref (hdrs)); - frame->output_buffer = hdrs; - flow_ret = - gst_video_encoder_finish_subframe (GST_VIDEO_ENCODER (self), frame); - gst_video_codec_frame_unref (frame); - - return flow_ret; - } else if (self->headers) { - gst_video_encoder_set_headers (GST_VIDEO_ENCODER (self), self->headers); - self->headers = NULL; - } - - return - GST_OMX_VIDEO_ENC_CLASS - (gst_omx_h264_enc_parent_class)->handle_output_frame (enc, port, buf, - frame); -} diff --git a/subprojects/gst-omx/omx/gstomxh264enc.h b/subprojects/gst-omx/omx/gstomxh264enc.h deleted file mode 100644 index 4d67c86b02..0000000000 --- a/subprojects/gst-omx/omx/gstomxh264enc.h +++ /dev/null @@ -1,73 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H264_ENC_H__ -#define __GST_OMX_H264_ENC_H__ - -#include -#include "gstomxvideoenc.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_H264_ENC \ - (gst_omx_h264_enc_get_type()) -#define GST_OMX_H264_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_H264_ENC,GstOMXH264Enc)) -#define GST_OMX_H264_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_H264_ENC,GstOMXH264EncClass)) -#define GST_OMX_H264_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_H264_ENC,GstOMXH264EncClass)) -#define GST_IS_OMX_H264_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_H264_ENC)) -#define GST_IS_OMX_H264_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_H264_ENC)) - -typedef struct _GstOMXH264Enc GstOMXH264Enc; -typedef struct _GstOMXH264EncClass GstOMXH264EncClass; - -struct _GstOMXH264Enc -{ - GstOMXVideoEnc parent; - -#ifdef USE_OMX_TARGET_RPI - gboolean inline_sps_pps_headers; -#endif - guint32 periodicty_idr; - guint32 interval_intraframes; - guint32 b_frames; - guint32 entropy_mode; - gboolean constrained_intra_prediction; - guint32 loop_filter_mode; - guint8 ref_frames; - - GList *headers; -}; - -struct _GstOMXH264EncClass -{ - GstOMXVideoEncClass parent_class; -}; - -GType gst_omx_h264_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_H264_ENC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxh264utils.c b/subprojects/gst-omx/omx/gstomxh264utils.c deleted file mode 100644 index ba292115af..0000000000 --- a/subprojects/gst-omx/omx/gstomxh264utils.c +++ /dev/null @@ -1,131 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "gstomxh264utils.h" - -typedef struct -{ - const gchar *profile; - OMX_VIDEO_AVCPROFILETYPE e; -} H264ProfileMapping; - -static const H264ProfileMapping h264_profiles[] = { - {"baseline", OMX_VIDEO_AVCProfileBaseline}, -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - {"constrained-baseline", - (OMX_VIDEO_AVCPROFILETYPE) OMX_ALG_VIDEO_AVCProfileConstrainedBaseline}, -#else - {"constrained-baseline", OMX_VIDEO_AVCProfileBaseline}, -#endif - {"main", OMX_VIDEO_AVCProfileMain}, - {"high", OMX_VIDEO_AVCProfileHigh}, - {"high-10", OMX_VIDEO_AVCProfileHigh10}, - {"high-4:2:2", OMX_VIDEO_AVCProfileHigh422}, -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - {"progressive-high", - (OMX_VIDEO_AVCPROFILETYPE) OMX_ALG_VIDEO_AVCProfileProgressiveHigh}, - {"constrained-high", - (OMX_VIDEO_AVCPROFILETYPE) OMX_ALG_VIDEO_AVCProfileConstrainedHigh}, - {"high-10-intra", - (OMX_VIDEO_AVCPROFILETYPE) OMX_ALG_VIDEO_AVCProfileHigh10_Intra}, - {"high-4:2:2-intra", - (OMX_VIDEO_AVCPROFILETYPE) OMX_ALG_VIDEO_AVCProfileHigh422_Intra}, -#endif -}; - -OMX_VIDEO_AVCPROFILETYPE -gst_omx_h264_utils_get_profile_from_str (const gchar * profile) -{ - guint i; - - for (i = 0; i < G_N_ELEMENTS (h264_profiles); i++) { - if (g_str_equal (profile, h264_profiles[i].profile)) - return h264_profiles[i].e; - } - - return OMX_VIDEO_AVCProfileMax; -} - -const gchar * -gst_omx_h264_utils_get_profile_from_enum (OMX_VIDEO_AVCPROFILETYPE e) -{ - guint i; - - for (i = 0; i < G_N_ELEMENTS (h264_profiles); i++) { - if (e == h264_profiles[i].e) - return h264_profiles[i].profile; - } - - return NULL; -} - -OMX_VIDEO_AVCLEVELTYPE -gst_omx_h264_utils_get_level_from_str (const gchar * level) -{ - if (g_str_equal (level, "1")) { - return OMX_VIDEO_AVCLevel1; - } else if (g_str_equal (level, "1b")) { - return OMX_VIDEO_AVCLevel1b; - } else if (g_str_equal (level, "1.1")) { - return OMX_VIDEO_AVCLevel11; - } else if (g_str_equal (level, "1.2")) { - return OMX_VIDEO_AVCLevel12; - } else if (g_str_equal (level, "1.3")) { - return OMX_VIDEO_AVCLevel13; - } else if (g_str_equal (level, "2")) { - return OMX_VIDEO_AVCLevel2; - } else if (g_str_equal (level, "2.1")) { - return OMX_VIDEO_AVCLevel21; - } else if (g_str_equal (level, "2.2")) { - return OMX_VIDEO_AVCLevel22; - } else if (g_str_equal (level, "3")) { - return OMX_VIDEO_AVCLevel3; - } else if (g_str_equal (level, "3.1")) { - return OMX_VIDEO_AVCLevel31; - } else if (g_str_equal (level, "3.2")) { - return OMX_VIDEO_AVCLevel32; - } else if (g_str_equal (level, "4")) { - return OMX_VIDEO_AVCLevel4; - } else if (g_str_equal (level, "4.1")) { - return OMX_VIDEO_AVCLevel41; - } else if (g_str_equal (level, "4.2")) { - return OMX_VIDEO_AVCLevel42; - } else if (g_str_equal (level, "5")) { - return OMX_VIDEO_AVCLevel5; - } else if (g_str_equal (level, "5.1")) { - return OMX_VIDEO_AVCLevel51; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - } else if (g_str_equal (level, "5.2")) { - return (OMX_VIDEO_AVCLEVELTYPE) OMX_ALG_VIDEO_AVCLevel52; - } else if (g_str_equal (level, "6.0")) { - return (OMX_VIDEO_AVCLEVELTYPE) OMX_ALG_VIDEO_AVCLevel60; - } else if (g_str_equal (level, "6.1")) { - return (OMX_VIDEO_AVCLEVELTYPE) OMX_ALG_VIDEO_AVCLevel61; - } else if (g_str_equal (level, "6.2")) { - return (OMX_VIDEO_AVCLEVELTYPE) OMX_ALG_VIDEO_AVCLevel62; -#endif - } - - return OMX_VIDEO_AVCLevelMax; -} diff --git a/subprojects/gst-omx/omx/gstomxh264utils.h b/subprojects/gst-omx/omx/gstomxh264utils.h deleted file mode 100644 index e5c35e4f24..0000000000 --- a/subprojects/gst-omx/omx/gstomxh264utils.h +++ /dev/null @@ -1,36 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H264_UTILS_H__ -#define __GST_OMX_H264_UTILS_H__ - -#include "gstomx.h" - -G_BEGIN_DECLS - -OMX_VIDEO_AVCPROFILETYPE gst_omx_h264_utils_get_profile_from_str (const - gchar * profile); -OMX_VIDEO_AVCLEVELTYPE gst_omx_h264_utils_get_level_from_str (const gchar * - level); - -const gchar * gst_omx_h264_utils_get_profile_from_enum (OMX_VIDEO_AVCPROFILETYPE e); - -G_END_DECLS -#endif /* __GST_OMX_H264_UTILS_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxh265dec.c b/subprojects/gst-omx/omx/gstomxh265dec.c deleted file mode 100644 index f8abf419f7..0000000000 --- a/subprojects/gst-omx/omx/gstomxh265dec.c +++ /dev/null @@ -1,224 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Copyright (C) 2017 Xilinx, Inc. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxh265dec.h" -#include "gstomxh265utils.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_h265_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_h265_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_h265_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_h265_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_h265_dec_debug_category, "omxh265dec", 0, \ - "debug category for gst-omx H265 video decoder"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXH265Dec, gst_omx_h265_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -#define MAKE_CAPS(alignment) \ - "video/x-h265, " \ - "alignment=(string) " alignment ", " \ - "stream-format=(string) byte-stream, " \ - "width=(int) [1,MAX], height=(int) [1,MAX]" - -/* The Zynq MPSoC supports decoding subframes though we want "au" to be the - * default, so we keep it prepended. This is the only way that it works with - * rtph265depay. */ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -#define SINK_CAPS MAKE_CAPS ("au") ";" MAKE_CAPS ("nal"); -#else -#define SINK_CAPS MAKE_CAPS ("au") -#endif - -static void -gst_omx_h265_dec_class_init (GstOMXH265DecClass * klass) -{ - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_h265_dec_is_format_change); - videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h265_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = SINK_CAPS; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX H.265 Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode H.265 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.hevc"); -} - -static void -gst_omx_h265_dec_init (GstOMXH265Dec * self) -{ -} - -static gboolean -gst_omx_h265_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - GstCaps *old_caps = NULL; - GstCaps *new_caps = state->caps; - GstStructure *old_structure, *new_structure; - const gchar *old_profile, *old_level, *old_tier, *old_alignment, - *new_profile, *new_level, *new_tier, *new_alignment; - - if (dec->input_state) { - old_caps = dec->input_state->caps; - } - - if (!old_caps) { - return FALSE; - } - - old_structure = gst_caps_get_structure (old_caps, 0); - new_structure = gst_caps_get_structure (new_caps, 0); - old_profile = gst_structure_get_string (old_structure, "profile"); - old_level = gst_structure_get_string (old_structure, "level"); - old_tier = gst_structure_get_string (old_structure, "tier"); - old_alignment = gst_structure_get_string (old_structure, "alignment"); - new_profile = gst_structure_get_string (new_structure, "profile"); - new_level = gst_structure_get_string (new_structure, "level"); - new_tier = gst_structure_get_string (new_structure, "tier"); - new_alignment = gst_structure_get_string (new_structure, "alignment"); - - if (g_strcmp0 (old_profile, new_profile) != 0 - || g_strcmp0 (old_level, new_level) != 0 - || g_strcmp0 (old_tier, new_tier) != 0 - || g_strcmp0 (old_alignment, new_alignment) != 0) { - return TRUE; - } - - return FALSE; -} - -static gboolean -set_profile_and_level (GstOMXH265Dec * self, GstVideoCodecState * state) -{ - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - const gchar *profile_string, *level_string, *tier_string; - GstStructure *s; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_DEC (self)->dec_in_port->index; - - /* Pass profile, level and tier to the decoder if we have all info from the - * caps. */ - s = gst_caps_get_structure (state->caps, 0); - profile_string = gst_structure_get_string (s, "profile"); - if (!profile_string) - return TRUE; - - param.eProfile = gst_omx_h265_utils_get_profile_from_str (profile_string); - if (param.eProfile == OMX_VIDEO_HEVCProfileUnknown) - goto unsupported_profile; - - level_string = gst_structure_get_string (s, "level"); - tier_string = gst_structure_get_string (s, "tier"); - if (!level_string || !tier_string) - return TRUE; - - param.eLevel = - gst_omx_h265_utils_get_level_from_str (level_string, tier_string); - if (param.eLevel == OMX_VIDEO_HEVCLevelUnknown) - goto unsupported_level; - - GST_DEBUG_OBJECT (self, - "Set profile (%s) level (%s) and tier (%s) on decoder", profile_string, - level_string, tier_string); - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_DEC (self)->dec, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting profile/level not supported by component"); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting profile %u and level %u: %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; - -unsupported_profile: - GST_ERROR_OBJECT (self, "Unsupported profile %s", profile_string); - return FALSE; - -unsupported_level: - GST_ERROR_OBJECT (self, "Unsupported level %s", level_string); - return FALSE; -} - -static gboolean -gst_omx_h265_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (dec); - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_ERRORTYPE err; - const GstStructure *s; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = - (OMX_VIDEO_CODINGTYPE) OMX_VIDEO_CodingHEVC; - err = gst_omx_port_update_port_definition (port, &port_def); - if (err != OMX_ErrorNone) - return FALSE; - - if (klass->cdata.hacks & GST_OMX_HACK_PASS_PROFILE_TO_DECODER) { - if (!set_profile_and_level (GST_OMX_H265_DEC (dec), state)) - return FALSE; - } - - /* Enable subframe mode if NAL aligned */ - s = gst_caps_get_structure (state->caps, 0); - if (!g_strcmp0 (gst_structure_get_string (s, "alignment"), "nal") - && gst_omx_port_set_subframe (dec->dec_in_port, TRUE)) { - gst_video_decoder_set_subframe_mode (GST_VIDEO_DECODER (dec), TRUE); - } - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxh265dec.h b/subprojects/gst-omx/omx/gstomxh265dec.h deleted file mode 100644 index f0f1016ae1..0000000000 --- a/subprojects/gst-omx/omx/gstomxh265dec.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Copyright (C) 2017 Xilinx, Inc. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H265_DEC_H__ -#define __GST_OMX_H265_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_H265_DEC \ - (gst_omx_h265_dec_get_type()) -#define GST_OMX_H265_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_H265_DEC,GstOMXH265Dec)) -#define GST_OMX_H265_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_H265_DEC,GstOMXH265DecClass)) -#define GST_OMX_H265_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_H265_DEC,GstOMXH265DecClass)) -#define GST_IS_OMX_H265_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_H265_DEC)) -#define GST_IS_OMX_H265_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_H265_DEC)) - -typedef struct _GstOMXH265Dec GstOMXH265Dec; -typedef struct _GstOMXH265DecClass GstOMXH265DecClass; - -struct _GstOMXH265Dec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXH265DecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_h265_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_H265_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxh265enc.c b/subprojects/gst-omx/omx/gstomxh265enc.c deleted file mode 100644 index 8b31c42414..0000000000 --- a/subprojects/gst-omx/omx/gstomxh265enc.c +++ /dev/null @@ -1,748 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Copyright (C) 2017 Xilinx, Inc. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxh265enc.h" -#include "gstomxh265utils.h" -#include "gstomxvideo.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_h265_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_h265_enc_debug_category - -/* prototypes */ -static gboolean gst_omx_h265_enc_set_format (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); -static GstCaps *gst_omx_h265_enc_get_caps (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); -static void gst_omx_h265_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec); -static void gst_omx_h265_enc_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec); -static GstFlowReturn gst_omx_h265_enc_handle_output_frame (GstOMXVideoEnc * - self, GstOMXPort * port, GstOMXBuffer * buf, GstVideoCodecFrame * frame); - -enum -{ - PROP_0, - PROP_PERIODICITYOFIDRFRAMES, - PROP_INTERVALOFCODINGINTRAFRAMES, - PROP_B_FRAMES, - PROP_CONSTRAINED_INTRA_PREDICTION, - PROP_LOOP_FILTER_MODE, -}; - -#define GST_OMX_H265_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_H265_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_H265_VIDEO_ENC_B_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_H265_VIDEO_ENC_CONSTRAINED_INTRA_PREDICTION_DEFAULT (FALSE) -#define GST_OMX_H265_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT (0xffffffff) - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -/* zynqultrascaleplus's OMX uses a param struct different of Android's one */ -#define INDEX_PARAM_VIDEO_HEVC OMX_ALG_IndexParamVideoHevc -#define ALIGNMENT "{ au, nal }" -#else -#define INDEX_PARAM_VIDEO_HEVC OMX_IndexParamVideoHevc -#define ALIGNMENT "au" -#endif - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_h265_enc_debug_category, "omxh265enc", 0, \ - "debug category for gst-omx H265 video encoder"); - -#define parent_class gst_omx_h265_enc_parent_class -G_DEFINE_TYPE_WITH_CODE (GstOMXH265Enc, gst_omx_h265_enc, - GST_TYPE_OMX_VIDEO_ENC, DEBUG_INIT); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -#define GST_TYPE_OMX_H265_ENC_LOOP_FILTER_MODE (gst_omx_h265_enc_loop_filter_mode_get_type ()) -static GType -gst_omx_h265_enc_loop_filter_mode_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_ALG_VIDEO_HEVCLoopFilterEnable, "Enable deblocking filter", - "enable"}, - {OMX_ALG_VIDEO_HEVCLoopFilterDisable, "Disable deblocking filter", - "disable"}, - {OMX_ALG_VIDEO_HEVCLoopFilterDisableCrossSlice, - "Disable deblocking filter on slice boundary", "disable-cross-slice"}, - {OMX_ALG_VIDEO_HEVCLoopFilterDisableCrossTile, - "Disable deblocking filter on tile boundary", "disable-cross-tile"}, - {OMX_ALG_VIDEO_HEVCLoopFilterDisableCrossSliceAndTile, - "Disable deblocking filter on slice and tile boundary", - "disable-slice-and-tile"}, - {0xffffffff, "Component Default", "default"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXH265EncLoopFilter", values); - } - return qtype; -} -#endif - -static gboolean -gst_omx_h265_enc_flush (GstVideoEncoder * enc) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (enc); - - g_list_free_full (self->headers, (GDestroyNotify) gst_buffer_unref); - self->headers = NULL; - - return GST_VIDEO_ENCODER_CLASS (parent_class)->flush (enc); -} - -static gboolean -gst_omx_h265_enc_stop (GstVideoEncoder * enc) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (enc); - - g_list_free_full (self->headers, (GDestroyNotify) gst_buffer_unref); - self->headers = NULL; - - return GST_VIDEO_ENCODER_CLASS (parent_class)->stop (enc); -} - -static void -gst_omx_h265_enc_class_init (GstOMXH265EncClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstVideoEncoderClass *basevideoenc_class = GST_VIDEO_ENCODER_CLASS (klass); - GstOMXVideoEncClass *videoenc_class = GST_OMX_VIDEO_ENC_CLASS (klass); - - videoenc_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h265_enc_set_format); - videoenc_class->get_caps = GST_DEBUG_FUNCPTR (gst_omx_h265_enc_get_caps); - videoenc_class->handle_output_frame = - GST_DEBUG_FUNCPTR (gst_omx_h265_enc_handle_output_frame); - - basevideoenc_class->flush = gst_omx_h265_enc_flush; - basevideoenc_class->stop = gst_omx_h265_enc_stop; - - gobject_class->set_property = gst_omx_h265_enc_set_property; - gobject_class->get_property = gst_omx_h265_enc_get_property; - - g_object_class_install_property (gobject_class, - PROP_INTERVALOFCODINGINTRAFRAMES, - g_param_spec_uint ("interval-intraframes", - "Interval of coding Intra frames", - "Interval of coding Intra frames (0xffffffff=component default)", 0, - G_MAXUINT, - GST_OMX_H265_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - g_object_class_install_property (gobject_class, PROP_PERIODICITYOFIDRFRAMES, - g_param_spec_uint ("periodicity-idr", "IDR periodicity", - "Periodicity of IDR frames (0xffffffff=component default)", - 0, G_MAXUINT, - GST_OMX_H265_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_B_FRAMES, - g_param_spec_uint ("b-frames", "Number of B-frames", - "Number of B-frames between two consecutive I-frames (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_H265_VIDEO_ENC_B_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, - PROP_CONSTRAINED_INTRA_PREDICTION, - g_param_spec_boolean ("constrained-intra-prediction", - "Constrained Intra Prediction", - "If enabled, prediction only uses residual data and decoded samples " - "from neighbouring coding blocks coded using intra prediction modes", - GST_OMX_H265_VIDEO_ENC_CONSTRAINED_INTRA_PREDICTION_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_LOOP_FILTER_MODE, - g_param_spec_enum ("loop-filter-mode", "Loop Filter mode", - "Enable or disable the deblocking filter (0xffffffff=component default)", - GST_TYPE_OMX_H265_ENC_LOOP_FILTER_MODE, - GST_OMX_H265_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); -#endif - - videoenc_class->cdata.default_sink_template_caps = -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GST_VIDEO_CAPS_MAKE_WITH_FEATURES (GST_CAPS_FEATURE_FORMAT_INTERLACED, - GST_OMX_VIDEO_ENC_SUPPORTED_FORMATS) - ", interlace-mode = (string) alternate ; " -#endif - GST_VIDEO_CAPS_MAKE (GST_OMX_VIDEO_ENC_SUPPORTED_FORMATS); - - videoenc_class->cdata.default_src_template_caps = "video/x-h265, " - "width=(int) [ 1, MAX ], " "height=(int) [ 1, MAX ], " - "framerate = (fraction) [0, MAX], stream-format=(string) byte-stream, " - "aligmment = (string) " ALIGNMENT; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX H.265 Video Encoder", - "Codec/Encoder/Video/Hardware", - "Encode H.265 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videoenc_class->cdata, "video_encoder.hevc"); -} - -static void -gst_omx_h265_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (object); - - switch (prop_id) { - case PROP_INTERVALOFCODINGINTRAFRAMES: - self->interval_intraframes = g_value_get_uint (value); - break; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case PROP_PERIODICITYOFIDRFRAMES: - self->periodicity_idr = g_value_get_uint (value); - break; - case PROP_B_FRAMES: - self->b_frames = g_value_get_uint (value); - break; - case PROP_CONSTRAINED_INTRA_PREDICTION: - self->constrained_intra_prediction = g_value_get_boolean (value); - break; - case PROP_LOOP_FILTER_MODE: - self->loop_filter_mode = g_value_get_enum (value); - break; -#endif - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_h265_enc_get_property (GObject * object, guint prop_id, GValue * value, - GParamSpec * pspec) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (object); - - switch (prop_id) { - case PROP_INTERVALOFCODINGINTRAFRAMES: - g_value_set_uint (value, self->interval_intraframes); - break; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case PROP_PERIODICITYOFIDRFRAMES: - g_value_set_uint (value, self->periodicity_idr); - break; - case PROP_B_FRAMES: - g_value_set_uint (value, self->b_frames); - break; - case PROP_CONSTRAINED_INTRA_PREDICTION: - g_value_set_boolean (value, self->constrained_intra_prediction); - break; - case PROP_LOOP_FILTER_MODE: - g_value_set_enum (value, self->loop_filter_mode); - break; -#endif - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_h265_enc_init (GstOMXH265Enc * self) -{ - self->interval_intraframes = - GST_OMX_H265_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - self->periodicity_idr = - GST_OMX_H265_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT; - self->b_frames = GST_OMX_H265_VIDEO_ENC_B_FRAMES_DEFAULT; - self->constrained_intra_prediction = - GST_OMX_H265_VIDEO_ENC_CONSTRAINED_INTRA_PREDICTION_DEFAULT; - self->loop_filter_mode = GST_OMX_H265_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT; -#endif -} - -/* Update OMX_VIDEO_PARAM_PROFILELEVELTYPE.{eProfile,eLevel} - * - * Returns TRUE if succeeded or if not supported, FALSE if failed */ -static gboolean -update_param_profile_level (GstOMXH265Enc * self, - OMX_VIDEO_HEVCPROFILETYPE profile, OMX_VIDEO_HEVCLEVELTYPE level) -{ - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Getting OMX_IndexParamVideoProfileLevelCurrent not supported by component"); - return TRUE; - } - - if (profile != OMX_VIDEO_HEVCProfileUnknown) - param.eProfile = profile; - if (level != OMX_VIDEO_HEVCLevelUnknown) - param.eLevel = level; - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting OMX_IndexParamVideoProfileLevelCurrent not supported by component"); - return TRUE; - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting profile %u and level %u: %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -/* Update OMX_ALG_VIDEO_PARAM_HEVCTYPE - * - * Returns TRUE if succeeded or if not supported, FALSE if failed */ -static gboolean -update_param_hevc (GstOMXH265Enc * self, - OMX_VIDEO_HEVCPROFILETYPE profile, OMX_VIDEO_HEVCLEVELTYPE level) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - OMX_ALG_VIDEO_PARAM_HEVCTYPE param; -#else - OMX_VIDEO_PARAM_HEVCTYPE param; -#endif - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - /* On Android the param struct is initialized manually with default - * settings rather than using GetParameter() to retrieve them. - * We should probably do the same when we'll add Android as target. - * See bgo#783862 for details. */ - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - param.bConstIpred = self->constrained_intra_prediction; - - if (self->loop_filter_mode != GST_OMX_H265_VIDEO_ENC_LOOP_FILTER_MODE_DEFAULT) - param.eLoopFilterMode = self->loop_filter_mode; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoHevc, ¶m); -#else - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - (OMX_INDEXTYPE) OMX_IndexParamVideoHevc, ¶m); -#endif - - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Getting OMX_ALG_IndexParamVideoHevc not supported by component"); - return TRUE; - } - - if (profile != OMX_VIDEO_HEVCProfileUnknown) -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - param.eProfile = (OMX_ALG_VIDEO_HEVCPROFILETYPE) profile; -#else - param.eProfile = profile; -#endif - - if (level != OMX_VIDEO_HEVCLevelUnknown) -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - param.eLevel = (OMX_ALG_VIDEO_HEVCLEVELTYPE) level; -#else - param.eLevel = level; -#endif - - /* GOP pattern */ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - /* The zynqultrascaleplus uses another PARAM_HEVCTYPE API allowing users to - * define the number of P and B frames while Android's API only expose the - * former. */ - if (self->interval_intraframes != - GST_OMX_H265_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT) { - param.nPFrames = self->interval_intraframes; - - /* If user specified a specific number of B-frames, reduce the number of - * P-frames by this amount. If not ensure there is no B-frame to have the - * requested GOP length. */ - if (self->b_frames != GST_OMX_H265_VIDEO_ENC_B_FRAMES_DEFAULT) { - if (self->b_frames > self->interval_intraframes) { - GST_ERROR_OBJECT (self, - "The interval_intraframes perdiod (%u) needs to be higher than the number of B-frames (%u)", - self->interval_intraframes, self->b_frames); - return FALSE; - } - param.nPFrames -= self->b_frames; - } else { - param.nBFrames = 0; - } - } - - if (self->b_frames != GST_OMX_H265_VIDEO_ENC_B_FRAMES_DEFAULT) - param.nBFrames = self->b_frames; -#else - if (self->interval_intraframes != - GST_OMX_H265_VIDEO_ENC_INTERVAL_OF_CODING_INTRA_FRAMES_DEFAULT) - param.nKeyFrameInterval = self->interval_intraframes; -#endif - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - (OMX_INDEXTYPE) INDEX_PARAM_VIDEO_HEVC, ¶m); - - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting IndexParamVideoHevc not supported by component"); - return TRUE; - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting HEVC settings (profile %u and level %u): %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static gboolean -set_intra_period (GstOMXH265Enc * self) -{ - OMX_ALG_VIDEO_PARAM_INSTANTANEOUS_DECODING_REFRESH config_idr; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&config_idr); - config_idr.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - GST_DEBUG_OBJECT (self, "nIDRPeriod:%u", - (guint) config_idr.nInstantaneousDecodingRefreshFrequency); - - config_idr.nInstantaneousDecodingRefreshFrequency = self->periodicity_idr; - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoInstantaneousDecodingRefresh, - &config_idr); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "can't set OMX_IndexConfigVideoAVCIntraPeriod %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} -#endif - -static gboolean -gst_omx_h265_enc_set_format (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (enc); - GstCaps *peercaps; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_ERRORTYPE err; - const gchar *profile_string, *level_string, *tier_string; - OMX_VIDEO_HEVCPROFILETYPE profile = OMX_VIDEO_HEVCProfileUnknown; - OMX_VIDEO_HEVCLEVELTYPE level = OMX_VIDEO_HEVCLevelUnknown; - gboolean enable_subframe = FALSE; - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (self->periodicity_idr != - GST_OMX_H265_VIDEO_ENC_PERIODICITY_OF_IDR_FRAMES_DEFAULT) - set_intra_period (self); -#endif - - gst_omx_port_get_port_definition (GST_OMX_VIDEO_ENC (self)->enc_out_port, - &port_def); - port_def.format.video.eCompressionFormat = - (OMX_VIDEO_CODINGTYPE) OMX_VIDEO_CodingHEVC; - err = - gst_omx_port_update_port_definition (GST_OMX_VIDEO_ENC - (self)->enc_out_port, &port_def); - if (err != OMX_ErrorNone) - return FALSE; - - /* Set profile and level */ - peercaps = gst_pad_peer_query_caps (GST_VIDEO_ENCODER_SRC_PAD (enc), - gst_pad_get_pad_template_caps (GST_VIDEO_ENCODER_SRC_PAD (enc))); - if (peercaps) { - GstStructure *s; - const gchar *alignment_string; - - if (gst_caps_is_empty (peercaps)) { - gst_caps_unref (peercaps); - GST_ERROR_OBJECT (self, "Empty caps"); - return FALSE; - } - - s = gst_caps_get_structure (peercaps, 0); - profile_string = gst_structure_get_string (s, "profile"); - if (profile_string) { - profile = gst_omx_h265_utils_get_profile_from_str (profile_string); - if (profile == OMX_VIDEO_HEVCProfileUnknown) - goto unsupported_profile; - } - - level_string = gst_structure_get_string (s, "level"); - tier_string = gst_structure_get_string (s, "tier"); - if (level_string && tier_string) { - level = gst_omx_h265_utils_get_level_from_str (level_string, tier_string); - if (level == OMX_VIDEO_HEVCLevelUnknown) - goto unsupported_level; - } - - alignment_string = gst_structure_get_string (s, "alignment"); - if (alignment_string && g_str_equal (alignment_string, "nal")) - enable_subframe = TRUE; - - gst_caps_unref (peercaps); - } - - if (profile != OMX_VIDEO_HEVCProfileUnknown - || level != OMX_VIDEO_HEVCLevelUnknown) { - /* OMX provides 2 API to set the profile and level. We try using the - * generic one here and the H265 specific when calling - * update_param_hevc() */ - if (!update_param_profile_level (self, profile, level)) - return FALSE; - } - - if (!update_param_hevc (self, profile, level)) - return FALSE; - - gst_omx_port_set_subframe (GST_OMX_VIDEO_ENC (self)->enc_out_port, - enable_subframe); - - return TRUE; - -unsupported_profile: - GST_ERROR_OBJECT (self, "Unsupported profile %s", profile_string); - gst_caps_unref (peercaps); - return FALSE; - -unsupported_level: - GST_ERROR_OBJECT (self, "Unsupported level %s", level_string); - gst_caps_unref (peercaps); - return FALSE; -} - -static GstCaps * -gst_omx_h265_enc_get_caps (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (enc); - GstCaps *caps; - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - const gchar *profile, *level, *tier, *alignment; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone && err != OMX_ErrorUnsupportedIndex) - return NULL; - - if (gst_omx_port_get_subframe (GST_OMX_VIDEO_ENC (self)->enc_out_port)) - alignment = "nal"; - else - alignment = "au"; - - caps = gst_caps_new_simple ("video/x-h265", - "stream-format", G_TYPE_STRING, "byte-stream", - "alignment", G_TYPE_STRING, alignment, NULL); - - if (err == OMX_ErrorNone) { - profile = gst_omx_h265_utils_get_profile_from_enum (param.eProfile); - if (!profile) { - g_assert_not_reached (); - gst_caps_unref (caps); - return NULL; - } - - switch (param.eLevel) { - case OMX_VIDEO_HEVCMainTierLevel1: - tier = "main"; - level = "1"; - break; - case OMX_VIDEO_HEVCMainTierLevel2: - tier = "main"; - level = "2"; - break; - case OMX_VIDEO_HEVCMainTierLevel21: - tier = "main"; - level = "2.1"; - break; - case OMX_VIDEO_HEVCMainTierLevel3: - tier = "main"; - level = "3"; - break; - case OMX_VIDEO_HEVCMainTierLevel31: - tier = "main"; - level = "3.1"; - break; - case OMX_VIDEO_HEVCMainTierLevel4: - tier = "main"; - level = "4"; - break; - case OMX_VIDEO_HEVCMainTierLevel41: - tier = "main"; - level = "4.1"; - break; - case OMX_VIDEO_HEVCMainTierLevel5: - tier = "main"; - level = "5"; - break; - case OMX_VIDEO_HEVCMainTierLevel51: - tier = "main"; - level = "5.1"; - break; - case OMX_VIDEO_HEVCMainTierLevel52: - tier = "main"; - level = "5.2"; - break; - case OMX_VIDEO_HEVCMainTierLevel6: - tier = "main"; - level = "6"; - break; - case OMX_VIDEO_HEVCMainTierLevel61: - tier = "main"; - level = "6.1"; - break; - case OMX_VIDEO_HEVCMainTierLevel62: - tier = "main"; - level = "6.2"; - break; - case OMX_VIDEO_HEVCHighTierLevel4: - tier = "high"; - level = "4"; - break; - case OMX_VIDEO_HEVCHighTierLevel41: - tier = "high"; - level = "4.1"; - break; - case OMX_VIDEO_HEVCHighTierLevel5: - tier = "high"; - level = "5"; - break; - case OMX_VIDEO_HEVCHighTierLevel51: - tier = "high"; - level = "5.1"; - break; - case OMX_VIDEO_HEVCHighTierLevel52: - tier = "high"; - level = "5.2"; - break; - case OMX_VIDEO_HEVCHighTierLevel6: - tier = "high"; - level = "6"; - break; - case OMX_VIDEO_HEVCHighTierLevel61: - tier = "high"; - level = "6.1"; - break; - case OMX_VIDEO_HEVCHighTierLevel62: - tier = "high"; - level = "6.2"; - break; - default: - g_assert_not_reached (); - gst_caps_unref (caps); - return NULL; - } - - gst_caps_set_simple (caps, - "profile", G_TYPE_STRING, profile, "level", G_TYPE_STRING, level, - "tier", G_TYPE_STRING, tier, NULL); - } - - return caps; -} - -static GstFlowReturn -gst_omx_h265_enc_handle_output_frame (GstOMXVideoEnc * enc, GstOMXPort * port, - GstOMXBuffer * buf, GstVideoCodecFrame * frame) -{ - GstOMXH265Enc *self = GST_OMX_H265_ENC (enc); - - if (buf->omx_buf->nFlags & OMX_BUFFERFLAG_CODECCONFIG) { - /* The codec data is SPS/PPS but our output is stream-format=byte-stream. - * For bytestream stream format the SPS/PPS is only in-stream and not - * in the caps! - */ - GstBuffer *hdrs; - GstMapInfo map = GST_MAP_INFO_INIT; - GstFlowReturn flow_ret; - - GST_DEBUG_OBJECT (self, "got codecconfig in byte-stream format"); - - hdrs = gst_buffer_new_and_alloc (buf->omx_buf->nFilledLen); - GST_BUFFER_FLAG_SET (hdrs, GST_BUFFER_FLAG_HEADER); - - gst_buffer_map (hdrs, &map, GST_MAP_WRITE); - memcpy (map.data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - gst_buffer_unmap (hdrs, &map); - self->headers = g_list_append (self->headers, gst_buffer_ref (hdrs)); - frame->output_buffer = hdrs; - flow_ret = - gst_video_encoder_finish_subframe (GST_VIDEO_ENCODER (self), frame); - gst_video_codec_frame_unref (frame); - - return flow_ret; - } else if (self->headers) { - gst_video_encoder_set_headers (GST_VIDEO_ENCODER (self), self->headers); - self->headers = NULL; - } - - return - GST_OMX_VIDEO_ENC_CLASS - (gst_omx_h265_enc_parent_class)->handle_output_frame (enc, port, buf, - frame); -} diff --git a/subprojects/gst-omx/omx/gstomxh265enc.h b/subprojects/gst-omx/omx/gstomxh265enc.h deleted file mode 100644 index b67fa1f0fb..0000000000 --- a/subprojects/gst-omx/omx/gstomxh265enc.h +++ /dev/null @@ -1,72 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Copyright (C) 2017 Xilinx, Inc. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H265_ENC_H__ -#define __GST_OMX_H265_ENC_H__ - -#include -#include "gstomxvideoenc.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_H265_ENC \ - (gst_omx_h265_enc_get_type()) -#define GST_OMX_H265_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_H265_ENC,GstOMXH265Enc)) -#define GST_OMX_H265_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_H265_ENC,GstOMXH265EncClass)) -#define GST_OMX_H265_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_H265_ENC,GstOMXH265EncClass)) -#define GST_IS_OMX_H265_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_H265_ENC)) -#define GST_IS_OMX_H265_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_H265_ENC)) - -typedef struct _GstOMXH265Enc GstOMXH265Enc; -typedef struct _GstOMXH265EncClass GstOMXH265EncClass; - -struct _GstOMXH265Enc -{ - GstOMXVideoEnc parent; - - /* properties */ - guint32 interval_intraframes; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - guint32 periodicity_idr; - guint32 b_frames; - gboolean constrained_intra_prediction; - guint32 loop_filter_mode; -#endif - - GList *headers; -}; - -struct _GstOMXH265EncClass -{ - GstOMXVideoEncClass parent_class; -}; - -GType gst_omx_h265_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_H265_ENC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxh265utils.c b/subprojects/gst-omx/omx/gstomxh265utils.c deleted file mode 100644 index 8bf81da06d..0000000000 --- a/subprojects/gst-omx/omx/gstomxh265utils.c +++ /dev/null @@ -1,138 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Copyright (C) 2017 Xilinx, Inc. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "gstomxh265utils.h" - -typedef struct -{ - const gchar *profile; - OMX_VIDEO_HEVCPROFILETYPE e; -} H265ProfileMapping; - -static const H265ProfileMapping h265_profiles[] = { - {"main", OMX_VIDEO_HEVCProfileMain}, - {"main-10", OMX_VIDEO_HEVCProfileMain10}, -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - {"main-still-picture", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMainStill}, - /* Format range extensions profiles (A.3.5) */ - {"monochrome", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMonochrome}, - /* Not standard: 10 bits variation of monochrome-12 */ - {"monochrome-10", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMonochrome10}, - /* Not standard: 8 bits variation of main-422-10 */ - {"main-422", (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMain422}, - {"main-422-10", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMain422_10}, - {"main-intra", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMain_Intra}, - {"main-10-intra", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMain10_Intra}, - /* Not standard: intra variation of main-422 */ - {"main-422-intra", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMain422_Intra}, - {"main-422-10-intra", - (OMX_VIDEO_HEVCPROFILETYPE) OMX_ALG_VIDEO_HEVCProfileMain422_10_Intra}, -#endif -}; - -OMX_VIDEO_HEVCPROFILETYPE -gst_omx_h265_utils_get_profile_from_str (const gchar * profile) -{ - guint i; - - for (i = 0; i < G_N_ELEMENTS (h265_profiles); i++) { - if (g_str_equal (profile, h265_profiles[i].profile)) - return h265_profiles[i].e; - } - - return OMX_VIDEO_HEVCProfileUnknown; -} - -const gchar * -gst_omx_h265_utils_get_profile_from_enum (OMX_VIDEO_HEVCPROFILETYPE e) -{ - guint i; - - for (i = 0; i < G_N_ELEMENTS (h265_profiles); i++) { - if (e == h265_profiles[i].e) - return h265_profiles[i].profile; - } - - return NULL; -} - -OMX_VIDEO_HEVCLEVELTYPE -gst_omx_h265_utils_get_level_from_str (const gchar * level, const gchar * tier) -{ - if (g_str_equal (tier, "main")) { - if (g_str_equal (level, "1")) - return OMX_VIDEO_HEVCMainTierLevel1; - else if (g_str_equal (level, "2")) - return OMX_VIDEO_HEVCMainTierLevel2; - else if (g_str_equal (level, "2.1")) - return OMX_VIDEO_HEVCMainTierLevel21; - else if (g_str_equal (level, "3")) - return OMX_VIDEO_HEVCMainTierLevel3; - else if (g_str_equal (level, "3.1")) - return OMX_VIDEO_HEVCMainTierLevel31; - else if (g_str_equal (level, "4")) - return OMX_VIDEO_HEVCMainTierLevel4; - else if (g_str_equal (level, "4.1")) - return OMX_VIDEO_HEVCMainTierLevel41; - else if (g_str_equal (level, "5")) - return OMX_VIDEO_HEVCMainTierLevel5; - else if (g_str_equal (level, "5.1")) - return OMX_VIDEO_HEVCMainTierLevel51; - else if (g_str_equal (level, "5.2")) - return OMX_VIDEO_HEVCMainTierLevel52; - else if (g_str_equal (level, "6")) - return OMX_VIDEO_HEVCMainTierLevel6; - else if (g_str_equal (level, "6.1")) - return OMX_VIDEO_HEVCMainTierLevel61; - else if (g_str_equal (level, "6.2")) - return OMX_VIDEO_HEVCMainTierLevel62; - } else if (g_str_equal (tier, "high")) { - if (g_str_equal (level, "4")) - return OMX_VIDEO_HEVCHighTierLevel4; - else if (g_str_equal (level, "4.1")) - return OMX_VIDEO_HEVCHighTierLevel41; - else if (g_str_equal (level, "5")) - return OMX_VIDEO_HEVCHighTierLevel5; - else if (g_str_equal (level, "5.1")) - return OMX_VIDEO_HEVCHighTierLevel51; - else if (g_str_equal (level, "5.2")) - return OMX_VIDEO_HEVCHighTierLevel52; - else if (g_str_equal (level, "6")) - return OMX_VIDEO_HEVCHighTierLevel6; - else if (g_str_equal (level, "6.1")) - return OMX_VIDEO_HEVCHighTierLevel61; - else if (g_str_equal (level, "6.2")) - return OMX_VIDEO_HEVCHighTierLevel62; - } - - return OMX_VIDEO_HEVCLevelUnknown; -} diff --git a/subprojects/gst-omx/omx/gstomxh265utils.h b/subprojects/gst-omx/omx/gstomxh265utils.h deleted file mode 100644 index 1987a326aa..0000000000 --- a/subprojects/gst-omx/omx/gstomxh265utils.h +++ /dev/null @@ -1,37 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Copyright (C) 2017 Xilinx, Inc. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_H265_UTILS_H__ -#define __GST_OMX_H265_UTILS_H__ - -#include "gstomx.h" - -G_BEGIN_DECLS - -OMX_VIDEO_HEVCPROFILETYPE gst_omx_h265_utils_get_profile_from_str (const - gchar * profile); -OMX_VIDEO_HEVCLEVELTYPE gst_omx_h265_utils_get_level_from_str (const gchar * - level, const gchar * tier); - -const gchar * gst_omx_h265_utils_get_profile_from_enum (OMX_VIDEO_HEVCPROFILETYPE e); - -G_END_DECLS -#endif /* __GST_OMX_H265_UTILS_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxhdmiaudiosink.c b/subprojects/gst-omx/omx/gstomxhdmiaudiosink.c deleted file mode 100644 index 211b719343..0000000000 --- a/subprojects/gst-omx/omx/gstomxhdmiaudiosink.c +++ /dev/null @@ -1,66 +0,0 @@ -/* - * Copyright (C) 2014, Fluendo, S.A. - * Copyright (C) 2014, Metrological Media Innovations B.V. - * Author: Josep Torra - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxhdmiaudiosink.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_hdmi_audio_sink_debug_category); -#define GST_CAT_DEFAULT gst_omx_hdmi_audio_sink_debug_category - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_hdmi_audio_sink_debug_category, \ - "omxhdmiaudiosink", 0, "debug category for gst-omx hdmi audio sink"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXHdmiAudioSink, gst_omx_hdmi_audio_sink, - GST_TYPE_OMX_AUDIO_SINK, DEBUG_INIT); - -static void -gst_omx_hdmi_audio_sink_class_init (GstOMXHdmiAudioSinkClass * klass) -{ - GstOMXAudioSinkClass *audiosink_class = GST_OMX_AUDIO_SINK_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - audiosink_class->cdata.default_sink_template_caps = "audio/x-raw, " - "format = (string) " GST_AUDIO_FORMATS_ALL ", " - "layout = (string) interleaved, " - "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, MAX ]; " - PASSTHROUGH_CAPS; - audiosink_class->destination = "hdmi"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX HDMI Audio Sink", - "Sink/Audio", - "Output audio through HDMI", "Josep Torra "); - - gst_omx_set_default_role (&audiosink_class->cdata, "audio_render.hdmi"); -} - -static void -gst_omx_hdmi_audio_sink_init (GstOMXHdmiAudioSink * self) -{ -} diff --git a/subprojects/gst-omx/omx/gstomxhdmiaudiosink.h b/subprojects/gst-omx/omx/gstomxhdmiaudiosink.h deleted file mode 100644 index e45e56b3ce..0000000000 --- a/subprojects/gst-omx/omx/gstomxhdmiaudiosink.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (C) 2014, Fluendo, S.A. - * Copyright (C) 2014, Metrological Media Innovations B.V. - * Author: Josep Torra - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_HDMI_AUDIO_SINK_H__ -#define __GST_OMX_HDMI_AUDIO_SINK_H__ - -#include -#include "gstomxaudiosink.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_HDMI_AUDIO_SINK \ - (gst_omx_hdmi_audio_sink_get_type()) -#define GST_OMX_HDMI_AUDIO_SINK(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_HDMI_AUDIO_SINK,GstOMXHdmiAudioSink)) -#define GST_OMX_HDMI_AUDIO_SINK_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_HDMI_AUDIO_SINK,GstOMXHdmiAudioSinkClass)) -#define GST_OMX_HDMI_AUDIO_SINK_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_HDMI_AUDIO_SINK,GstOMXHdmiAudioSinkClass)) -#define GST_IS_OMX_HDMI_AUDIO_SINK(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_HDMI_AUDIO_SINK)) -#define GST_IS_OMX_HDMI_AUDIO_SINK_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_HDMI_AUDIO_SINK)) - -typedef struct _GstOMXHdmiAudioSink GstOMXHdmiAudioSink; -typedef struct _GstOMXHdmiAudioSinkClass GstOMXHdmiAudioSinkClass; - -struct _GstOMXHdmiAudioSink -{ - GstOMXAudioSink parent; -}; - -struct _GstOMXHdmiAudioSinkClass -{ - GstOMXAudioSinkClass parent_class; -}; - -GType gst_omx_hdmi_audio_sink_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_HDMI_AUDIO_SINK_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxmjpegdec.c b/subprojects/gst-omx/omx/gstomxmjpegdec.c deleted file mode 100644 index 6ca34f2d56..0000000000 --- a/subprojects/gst-omx/omx/gstomxmjpegdec.c +++ /dev/null @@ -1,98 +0,0 @@ -/* - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxmjpegdec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_mjpeg_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_mjpeg_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_mjpeg_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_mjpeg_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_mjpeg_dec_debug_category, "omxmjpegdec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXMJPEGDec, gst_omx_mjpeg_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -static void -gst_omx_mjpeg_dec_class_init (GstOMXMJPEGDecClass * klass) -{ - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_mjpeg_dec_is_format_change); - videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_mjpeg_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "image/jpeg, " - "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX MJPEG Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode MJPEG video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.mjpeg"); -} - -static void -gst_omx_mjpeg_dec_init (GstOMXMJPEGDec * self) -{ -} - -static gboolean -gst_omx_mjpeg_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_mjpeg_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingMJPEG; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} diff --git a/subprojects/gst-omx/omx/gstomxmjpegdec.h b/subprojects/gst-omx/omx/gstomxmjpegdec.h deleted file mode 100644 index 8802c8d7ea..0000000000 --- a/subprojects/gst-omx/omx/gstomxmjpegdec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_MJPEG_DEC_H__ -#define __GST_OMX_MJPEG_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_MJPEG_DEC \ - (gst_omx_mjpeg_dec_get_type()) -#define GST_OMX_MJPEG_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_MJPEG_DEC,GstOMXMJPEGDec)) -#define GST_OMX_MJPEG_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_MJPEG_DEC,GstOMXMJPEGDecClass)) -#define GST_OMX_MJPEG_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_MJPEG_DEC,GstOMXMJPEGDecClass)) -#define GST_IS_OMX_MJPEG_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_MJPEG_DEC)) -#define GST_IS_OMX_MJPEG_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_MJPEG_DEC)) - -typedef struct _GstOMXMJPEGDec GstOMXMJPEGDec; -typedef struct _GstOMXMJPEGDecClass GstOMXMJPEGDecClass; - -struct _GstOMXMJPEGDec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXMJPEGDecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_mjpeg_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_MJPEG_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxmp3dec.c b/subprojects/gst-omx/omx/gstomxmp3dec.c deleted file mode 100644 index aa22e80fb0..0000000000 --- a/subprojects/gst-omx/omx/gstomxmp3dec.c +++ /dev/null @@ -1,246 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxmp3dec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_mp3_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_mp3_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_mp3_dec_set_format (GstOMXAudioDec * dec, - GstOMXPort * port, GstCaps * caps); -static gboolean gst_omx_mp3_dec_is_format_change (GstOMXAudioDec * dec, - GstOMXPort * port, GstCaps * caps); -static gint gst_omx_mp3_dec_get_samples_per_frame (GstOMXAudioDec * dec, - GstOMXPort * port); -static gboolean gst_omx_mp3_dec_get_channel_positions (GstOMXAudioDec * dec, - GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]); - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_mp3_dec_debug_category, "omxmp3dec", 0, \ - "debug category for gst-omx mp3 audio decoder"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXMP3Dec, gst_omx_mp3_dec, - GST_TYPE_OMX_AUDIO_DEC, DEBUG_INIT); - - -static void -gst_omx_mp3_dec_class_init (GstOMXMP3DecClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXAudioDecClass *audiodec_class = GST_OMX_AUDIO_DEC_CLASS (klass); - - audiodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_mp3_dec_set_format); - audiodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_mp3_dec_is_format_change); - audiodec_class->get_samples_per_frame = - GST_DEBUG_FUNCPTR (gst_omx_mp3_dec_get_samples_per_frame); - audiodec_class->get_channel_positions = - GST_DEBUG_FUNCPTR (gst_omx_mp3_dec_get_channel_positions); - - audiodec_class->cdata.default_sink_template_caps = "audio/mpeg, " - "mpegversion=(int)1, " - "layer=(int)3, " - "mpegaudioversion=(int)[1,3], " - "rate=(int)[8000,48000], " - "channels=(int)[1,2], " "parsed=(boolean) true"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX MP3 Audio Decoder", - "Codec/Decoder/Audio/Hardware", - "Decode MP3 audio streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&audiodec_class->cdata, "audio_decoder.mp3"); -} - -static void -gst_omx_mp3_dec_init (GstOMXMP3Dec * self) -{ - self->spf = -1; -} - -static gboolean -gst_omx_mp3_dec_set_format (GstOMXAudioDec * dec, GstOMXPort * port, - GstCaps * caps) -{ - GstOMXMP3Dec *self = GST_OMX_MP3_DEC (dec); - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_AUDIO_PARAM_MP3TYPE mp3_param; - OMX_ERRORTYPE err; - GstStructure *s; - gint rate, channels, layer, mpegaudioversion; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.audio.eEncoding = OMX_AUDIO_CodingMP3; - err = gst_omx_port_update_port_definition (port, &port_def); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set MP3 format on component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - GST_OMX_INIT_STRUCT (&mp3_param); - mp3_param.nPortIndex = port->index; - - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioMp3, - &mp3_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get MP3 parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - s = gst_caps_get_structure (caps, 0); - - if (!gst_structure_get_int (s, "mpegaudioversion", &mpegaudioversion) || - !gst_structure_get_int (s, "layer", &layer) || - !gst_structure_get_int (s, "rate", &rate) || - !gst_structure_get_int (s, "channels", &channels)) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - self->spf = (mpegaudioversion == 1 ? 1152 : 576); - - mp3_param.nChannels = channels; - mp3_param.nBitRate = 0; /* unknown */ - mp3_param.nSampleRate = rate; - mp3_param.nAudioBandWidth = 0; /* decoder decision */ - mp3_param.eChannelMode = 0; /* FIXME */ - if (mpegaudioversion == 1) - mp3_param.eFormat = OMX_AUDIO_MP3StreamFormatMP1Layer3; - else if (mpegaudioversion == 2) - mp3_param.eFormat = OMX_AUDIO_MP3StreamFormatMP2Layer3; - else - mp3_param.eFormat = OMX_AUDIO_MP3StreamFormatMP2_5Layer3; - - err = - gst_omx_component_set_parameter (dec->dec, OMX_IndexParamAudioMp3, - &mp3_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Error setting MP3 parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -static gboolean -gst_omx_mp3_dec_is_format_change (GstOMXAudioDec * dec, GstOMXPort * port, - GstCaps * caps) -{ - GstOMXMP3Dec *self = GST_OMX_MP3_DEC (dec); - OMX_AUDIO_PARAM_MP3TYPE mp3_param; - OMX_ERRORTYPE err; - GstStructure *s; - gint rate, channels, layer, mpegaudioversion; - - GST_OMX_INIT_STRUCT (&mp3_param); - mp3_param.nPortIndex = port->index; - - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioMp3, - &mp3_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get MP3 parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - s = gst_caps_get_structure (caps, 0); - - if (!gst_structure_get_int (s, "mpegaudioversion", &mpegaudioversion) || - !gst_structure_get_int (s, "layer", &layer) || - !gst_structure_get_int (s, "rate", &rate) || - !gst_structure_get_int (s, "channels", &channels)) { - GST_ERROR_OBJECT (self, "Incomplete caps"); - return FALSE; - } - - if (mp3_param.nChannels != channels) - return TRUE; - - if (mp3_param.nSampleRate != rate) - return TRUE; - - if (mpegaudioversion == 1 - && mp3_param.eFormat != OMX_AUDIO_MP3StreamFormatMP1Layer3) - return TRUE; - if (mpegaudioversion == 2 - && mp3_param.eFormat != OMX_AUDIO_MP3StreamFormatMP2Layer3) - return TRUE; - if (mpegaudioversion == 3 - && mp3_param.eFormat != OMX_AUDIO_MP3StreamFormatMP2_5Layer3) - return TRUE; - - return FALSE; -} - -static gint -gst_omx_mp3_dec_get_samples_per_frame (GstOMXAudioDec * dec, GstOMXPort * port) -{ - return GST_OMX_MP3_DEC (dec)->spf; -} - -static gboolean -gst_omx_mp3_dec_get_channel_positions (GstOMXAudioDec * dec, - GstOMXPort * port, GstAudioChannelPosition position[OMX_AUDIO_MAXCHANNELS]) -{ - OMX_AUDIO_PARAM_PCMMODETYPE pcm_param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&pcm_param); - pcm_param.nPortIndex = port->index; - err = - gst_omx_component_get_parameter (dec->dec, OMX_IndexParamAudioPcm, - &pcm_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (dec, "Failed to get PCM parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - switch (pcm_param.nChannels) { - case 1: - position[0] = GST_AUDIO_CHANNEL_POSITION_MONO; - break; - case 2: - position[0] = GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT; - position[1] = GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT; - break; - default: - return FALSE; - } - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxmp3dec.h b/subprojects/gst-omx/omx/gstomxmp3dec.h deleted file mode 100644 index 4f07659783..0000000000 --- a/subprojects/gst-omx/omx/gstomxmp3dec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2014, Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_MP3_DEC_H__ -#define __GST_OMX_MP3_DEC_H__ - -#include -#include "gstomxaudiodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_MP3_DEC \ - (gst_omx_mp3_dec_get_type()) -#define GST_OMX_MP3_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_MP3_DEC,GstOMXMP3Dec)) -#define GST_OMX_MP3_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_MP3_DEC,GstOMXMP3DecClass)) -#define GST_OMX_MP3_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_MP3_DEC,GstOMXMP3DecClass)) -#define GST_IS_OMX_MP3_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_MP3_DEC)) -#define GST_IS_OMX_MP3_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_MP3_DEC)) - -typedef struct _GstOMXMP3Dec GstOMXMP3Dec; -typedef struct _GstOMXMP3DecClass GstOMXMP3DecClass; - -struct _GstOMXMP3Dec -{ - GstOMXAudioDec parent; - gint spf; -}; - -struct _GstOMXMP3DecClass -{ - GstOMXAudioDecClass parent_class; -}; - -GType gst_omx_mp3_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_MP3_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxmp3enc.c b/subprojects/gst-omx/omx/gstomxmp3enc.c deleted file mode 100644 index 1296564f31..0000000000 --- a/subprojects/gst-omx/omx/gstomxmp3enc.c +++ /dev/null @@ -1,278 +0,0 @@ -/* - * Copyright (C) 2017 - * Author: Julien Isorce - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxmp3enc.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_mp3_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_mp3_enc_debug_category - -/* prototypes */ -static void gst_omx_mp3_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec); -static void gst_omx_mp3_enc_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec); -static gboolean gst_omx_mp3_enc_set_format (GstOMXAudioEnc * enc, - GstOMXPort * port, GstAudioInfo * info); -static GstCaps *gst_omx_mp3_enc_get_caps (GstOMXAudioEnc * enc, - GstOMXPort * port, GstAudioInfo * info); -static guint gst_omx_mp3_enc_get_num_samples (GstOMXAudioEnc * enc, - GstOMXPort * port, GstAudioInfo * info, GstOMXBuffer * buf); - -enum -{ - PROP_0, - PROP_BITRATE -}; - -#define DEFAULT_BITRATE (128) - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_mp3_enc_debug_category, "omxmp3enc", 0, \ - "debug category for gst-omx audio encoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXMP3Enc, gst_omx_mp3_enc, - GST_TYPE_OMX_AUDIO_ENC, DEBUG_INIT); - - -static void -gst_omx_mp3_enc_class_init (GstOMXMP3EncClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXAudioEncClass *audioenc_class = GST_OMX_AUDIO_ENC_CLASS (klass); - - gobject_class->set_property = gst_omx_mp3_enc_set_property; - gobject_class->get_property = gst_omx_mp3_enc_get_property; - - g_object_class_install_property (gobject_class, PROP_BITRATE, - g_param_spec_uint ("bitrate", "Bitrate (kb/s)", - "Bitrate in kbit/sec", - 0, G_MAXUINT, DEFAULT_BITRATE, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - audioenc_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_mp3_enc_set_format); - audioenc_class->get_caps = GST_DEBUG_FUNCPTR (gst_omx_mp3_enc_get_caps); - audioenc_class->get_num_samples = - GST_DEBUG_FUNCPTR (gst_omx_mp3_enc_get_num_samples); - - audioenc_class->cdata.default_src_template_caps = "audio/mpeg, " - "mpegversion=(int)1, " - "layer=(int)3, " - "mpegaudioversion=(int)[1,3], " - "rate=(int)[8000,48000], " "channels=(int)[1,2]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX MP3 Audio Encoder", - "Codec/Encoder/Audio/Hardware", - "Encode AAC audio streams", "Julien Isorce "); - - gst_omx_set_default_role (&audioenc_class->cdata, "audio_encoder.mp3"); -} - -static void -gst_omx_mp3_enc_init (GstOMXMP3Enc * self) -{ - self->mpegaudioversion = 1; - self->bitrate = DEFAULT_BITRATE; -} - -static void -gst_omx_mp3_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ - GstOMXMP3Enc *self = GST_OMX_MP3_ENC (object); - - switch (prop_id) { - case PROP_BITRATE: - self->bitrate = g_value_get_uint (value); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_mp3_enc_get_property (GObject * object, guint prop_id, GValue * value, - GParamSpec * pspec) -{ - GstOMXMP3Enc *self = GST_OMX_MP3_ENC (object); - - switch (prop_id) { - case PROP_BITRATE: - g_value_set_uint (value, self->bitrate); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static gboolean -gst_omx_mp3_enc_set_format (GstOMXAudioEnc * enc, GstOMXPort * port, - GstAudioInfo * info) -{ - GstOMXMP3Enc *self = GST_OMX_MP3_ENC (enc); - OMX_AUDIO_PARAM_MP3TYPE mp3_param; - GstCaps *peercaps; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&mp3_param); - mp3_param.nPortIndex = enc->enc_out_port->index; - - err = - gst_omx_component_get_parameter (enc->enc, OMX_IndexParamAudioMp3, - &mp3_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get MP# parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - peercaps = gst_pad_peer_query_caps (GST_AUDIO_ENCODER_SRC_PAD (self), - gst_pad_get_pad_template_caps (GST_AUDIO_ENCODER_SRC_PAD (self))); - if (peercaps) { - GstStructure *s; - gint mpegaudioversion = 0; - - if (gst_caps_is_empty (peercaps)) { - gst_caps_unref (peercaps); - GST_ERROR_OBJECT (self, "Empty caps"); - return FALSE; - } - - s = gst_caps_get_structure (peercaps, 0); - - if (gst_structure_get_int (s, "mpegaudioversion", &mpegaudioversion)) { - switch (mpegaudioversion) { - case 1: - mp3_param.eFormat = OMX_AUDIO_MP3StreamFormatMP1Layer3; - break; - case 2: - mp3_param.eFormat = OMX_AUDIO_MP3StreamFormatMP2Layer3; - break; - case 3: - mp3_param.eFormat = OMX_AUDIO_MP3StreamFormatMP2_5Layer3; - break; - default: - GST_ERROR_OBJECT (self, "Unsupported mpegaudioversion '%d'", - mpegaudioversion); - gst_caps_unref (peercaps); - return FALSE; - } - self->mpegaudioversion = mpegaudioversion; - } - - gst_caps_unref (peercaps); - - mp3_param.nSampleRate = info->rate; - mp3_param.nChannels = info->channels; - - mp3_param.eChannelMode = - info->channels == - 1 ? OMX_AUDIO_ChannelModeMono : OMX_AUDIO_ChannelModeStereo; - } - - mp3_param.nBitRate = self->bitrate; - - err = - gst_omx_component_set_parameter (enc->enc, OMX_IndexParamAudioMp3, - &mp3_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Error setting MP3 parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; -} - -static GstCaps * -gst_omx_mp3_enc_get_caps (GstOMXAudioEnc * enc, GstOMXPort * port, - GstAudioInfo * info) -{ - GstCaps *caps; - OMX_ERRORTYPE err; - OMX_AUDIO_PARAM_MP3TYPE mp3_param; - gint mpegaudioversion = 0; - - GST_OMX_INIT_STRUCT (&mp3_param); - mp3_param.nPortIndex = enc->enc_out_port->index; - - err = - gst_omx_component_get_parameter (enc->enc, OMX_IndexParamAudioMp3, - &mp3_param); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (enc, - "Failed to get MP3 parameters from component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return NULL; - } - - switch (mp3_param.eFormat) { - case OMX_AUDIO_MP3StreamFormatMP1Layer3: - mpegaudioversion = 1; - break; - case OMX_AUDIO_MP3StreamFormatMP2Layer3: - mpegaudioversion = 2; - break; - case OMX_AUDIO_MP3StreamFormatMP2_5Layer3: - mpegaudioversion = 3; - break; - default: - GST_ERROR_OBJECT (enc, "Unsupported mpegaudioversion %d", - mp3_param.eFormat); - break; - } - - caps = - gst_caps_new_simple ("audio/mpeg", "mpegversion", G_TYPE_INT, 1, "layer", - G_TYPE_INT, 3, NULL); - - if (mpegaudioversion != 0) - gst_caps_set_simple (caps, "mpegaudioversion", G_TYPE_INT, mpegaudioversion, - NULL); - if (mp3_param.nChannels != 0) - gst_caps_set_simple (caps, "channels", G_TYPE_INT, mp3_param.nChannels, - NULL); - if (mp3_param.nSampleRate != 0) - gst_caps_set_simple (caps, "rate", G_TYPE_INT, mp3_param.nSampleRate, NULL); - - return caps; - -} - -static guint -gst_omx_mp3_enc_get_num_samples (GstOMXAudioEnc * enc, GstOMXPort * port, - GstAudioInfo * info, GstOMXBuffer * buf) -{ - GstOMXMP3Enc *self = GST_OMX_MP3_ENC (enc); - return (self->mpegaudioversion == 1) ? 1152 : 576; -} diff --git a/subprojects/gst-omx/omx/gstomxmp3enc.h b/subprojects/gst-omx/omx/gstomxmp3enc.h deleted file mode 100644 index 74e115e6c6..0000000000 --- a/subprojects/gst-omx/omx/gstomxmp3enc.h +++ /dev/null @@ -1,65 +0,0 @@ -/* - * Copyright (C) 2017 - * Author: Julien Isorce - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_MP3_ENC_H__ -#define __GST_OMX_MP3_ENC_H__ - -#include -#include "gstomxaudioenc.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_MP3_ENC \ - (gst_omx_mp3_enc_get_type()) -#define GST_OMX_MP3_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_MP3_ENC,GstOMXMP3Enc)) -#define GST_OMX_MP3_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_MP3_ENC,GstOMXMP3EncClass)) -#define GST_OMX_MP3_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_MP3_ENC,GstOMXMP3EncClass)) -#define GST_IS_OMX_MP3_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_MP3_ENC)) -#define GST_IS_OMX_MP3_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_MP3_ENC)) - -typedef struct _GstOMXMP3Enc GstOMXMP3Enc; -typedef struct _GstOMXMP3EncClass GstOMXMP3EncClass; - -struct _GstOMXMP3Enc -{ - GstOMXAudioEnc parent; - - guint mpegaudioversion; - - /* properties */ - guint bitrate; -}; - -struct _GstOMXMP3EncClass -{ - GstOMXAudioEncClass parent_class; -}; - -GType gst_omx_mp3_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_MP3_ENC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxmpeg2videodec.c b/subprojects/gst-omx/omx/gstomxmpeg2videodec.c deleted file mode 100644 index 144845060d..0000000000 --- a/subprojects/gst-omx/omx/gstomxmpeg2videodec.c +++ /dev/null @@ -1,101 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxmpeg2videodec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_mpeg2_video_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_mpeg2_video_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_mpeg2_video_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_mpeg2_video_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_mpeg2_video_dec_debug_category, "omxmpeg2dec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXMPEG2VideoDec, gst_omx_mpeg2_video_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -static void -gst_omx_mpeg2_video_dec_class_init (GstOMXMPEG2VideoDecClass * klass) -{ - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_mpeg2_video_dec_is_format_change); - videodec_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_mpeg2_video_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "video/mpeg, " - "mpegversion=(int) [1, 2], " - "systemstream=(boolean) false, " - "parsed=(boolean) true, " "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX MPEG2 Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode MPEG2 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.mpeg2"); -} - -static void -gst_omx_mpeg2_video_dec_init (GstOMXMPEG2VideoDec * self) -{ -} - -static gboolean -gst_omx_mpeg2_video_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_mpeg2_video_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingMPEG2; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} diff --git a/subprojects/gst-omx/omx/gstomxmpeg2videodec.h b/subprojects/gst-omx/omx/gstomxmpeg2videodec.h deleted file mode 100644 index ff86bcdee5..0000000000 --- a/subprojects/gst-omx/omx/gstomxmpeg2videodec.h +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_MPEG2_VIDEO_DEC_H__ -#define __GST_OMX_MPEG2_VIDEO_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_MPEG2_VIDEO_DEC \ - (gst_omx_mpeg2_video_get_type()) -#define GST_OMX_MPEG2_VIDEO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_MPEG2_VIDEO_DEC,GstOMXMPEG2VideoDec)) -#define GST_OMX_MPEG2_VIDEO_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_MPEG2_VIDEO_DEC,GstOMXMPEG2VideoDecClass)) -#define GST_OMX_MPEG2_VIDEO_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_MPEG2_VIDEO_DEC,GstOMXMPEG2VideoDecClass)) -#define GST_IS_OMX_MPEG2_VIDEO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_MPEG2_VIDEO_DEC)) -#define GST_IS_OMX_MPEG2_VIDEO_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_MPEG2_VIDEO_DEC)) - -typedef struct _GstOMXMPEG2VideoDec GstOMXMPEG2VideoDec; -typedef struct _GstOMXMPEG2VideoDecClass GstOMXMPEG2VideoDecClass; - -struct _GstOMXMPEG2VideoDec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXMPEG2VideoDecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_mpeg2_video_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_MPEG2_VIDEO_DEC_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxmpeg4videodec.c b/subprojects/gst-omx/omx/gstomxmpeg4videodec.c deleted file mode 100644 index 8cebef82d6..0000000000 --- a/subprojects/gst-omx/omx/gstomxmpeg4videodec.c +++ /dev/null @@ -1,102 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxmpeg4videodec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_mpeg4_video_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_mpeg4_video_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_mpeg4_video_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_mpeg4_video_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_mpeg4_video_dec_debug_category, "omxmpeg4videodec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXMPEG4VideoDec, gst_omx_mpeg4_video_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - - -static void -gst_omx_mpeg4_video_dec_class_init (GstOMXMPEG4VideoDecClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_mpeg4_video_dec_is_format_change); - videodec_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_mpeg4_video_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "video/mpeg, " - "mpegversion=(int) 4, " - "systemstream=(boolean) false, " - "parsed=(boolean) true, " "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX MPEG4 Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode MPEG4 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.mpeg4"); -} - -static void -gst_omx_mpeg4_video_dec_init (GstOMXMPEG4VideoDec * self) -{ -} - -static gboolean -gst_omx_mpeg4_video_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_mpeg4_video_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingMPEG4; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} diff --git a/subprojects/gst-omx/omx/gstomxmpeg4videodec.h b/subprojects/gst-omx/omx/gstomxmpeg4videodec.h deleted file mode 100644 index 73a68d5d70..0000000000 --- a/subprojects/gst-omx/omx/gstomxmpeg4videodec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_MPEG4_VIDEO_DEC_H__ -#define __GST_OMX_MPEG4_VIDEO_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_MPEG4_VIDEO_DEC \ - (gst_omx_mpeg4_video_dec_get_type()) -#define GST_OMX_MPEG4_VIDEO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_MPEG4_VIDEO_DEC,GstOMXMPEG4VideoDec)) -#define GST_OMX_MPEG4_VIDEO_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_MPEG4_VIDEO_DEC,GstOMXMPEG4VideoDecClass)) -#define GST_OMX_MPEG4_VIDEO_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_MPEG4_VIDEO_DEC,GstOMXMPEG4VideoDecClass)) -#define GST_IS_OMX_MPEG4_VIDEO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_MPEG4_VIDEO_DEC)) -#define GST_IS_OMX_MPEG4_VIDEO_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_MPEG4_VIDEO_DEC)) - -typedef struct _GstOMXMPEG4VideoDec GstOMXMPEG4VideoDec; -typedef struct _GstOMXMPEG4VideoDecClass GstOMXMPEG4VideoDecClass; - -struct _GstOMXMPEG4VideoDec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXMPEG4VideoDecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_mpeg4_video_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_MPEG4_VIDEO_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxmpeg4videoenc.c b/subprojects/gst-omx/omx/gstomxmpeg4videoenc.c deleted file mode 100644 index c928171c33..0000000000 --- a/subprojects/gst-omx/omx/gstomxmpeg4videoenc.c +++ /dev/null @@ -1,336 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxmpeg4videoenc.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_mpeg4_video_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_mpeg4_video_enc_debug_category - -/* prototypes */ -static gboolean gst_omx_mpeg4_video_enc_set_format (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); -static GstCaps *gst_omx_mpeg4_video_enc_get_caps (GstOMXVideoEnc * enc, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_mpeg4_video_enc_debug_category, "omxmpeg4videoenc", 0, \ - "debug category for gst-omx video encoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXMPEG4VideoEnc, gst_omx_mpeg4_video_enc, - GST_TYPE_OMX_VIDEO_ENC, DEBUG_INIT); - -static void -gst_omx_mpeg4_video_enc_class_init (GstOMXMPEG4VideoEncClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXVideoEncClass *videoenc_class = GST_OMX_VIDEO_ENC_CLASS (klass); - - videoenc_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_mpeg4_video_enc_set_format); - videoenc_class->get_caps = - GST_DEBUG_FUNCPTR (gst_omx_mpeg4_video_enc_get_caps); - - videoenc_class->cdata.default_src_template_caps = "video/mpeg, " - "mpegversion=(int) 4, " - "systemstream=(boolean) false, " - "width=(int) [ 16, 4096 ], " "height=(int) [ 16, 4096 ]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX MPEG4 Video Encoder", - "Codec/Encoder/Video/Hardware", - "Encode MPEG4 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videoenc_class->cdata, "video_encoder.mpeg4"); -} - -static void -gst_omx_mpeg4_video_enc_init (GstOMXMPEG4VideoEnc * self) -{ -} - -static gboolean -gst_omx_mpeg4_video_enc_set_format (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXMPEG4VideoEnc *self = GST_OMX_MPEG4_VIDEO_ENC (enc); - GstCaps *peercaps, *intersection; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - OMX_ERRORTYPE err; - const gchar *profile_string, *level_string; - - gst_omx_port_get_port_definition (GST_OMX_VIDEO_ENC (self)->enc_out_port, - &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingMPEG4; - err = - gst_omx_port_update_port_definition (GST_OMX_VIDEO_ENC - (self)->enc_out_port, &port_def); - if (err != OMX_ErrorNone) - return FALSE; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Getting profile/level not supported by component"); - return FALSE; - } - - peercaps = gst_pad_peer_query_caps (GST_VIDEO_ENCODER_SRC_PAD (enc), NULL); - if (peercaps) { - GstStructure *s; - - intersection = - gst_caps_intersect (peercaps, - gst_pad_get_pad_template_caps (GST_VIDEO_ENCODER_SRC_PAD (enc))); - - gst_caps_unref (peercaps); - if (gst_caps_is_empty (intersection)) { - gst_caps_unref (intersection); - GST_ERROR_OBJECT (self, "Empty caps"); - return FALSE; - } - - s = gst_caps_get_structure (intersection, 0); - profile_string = gst_structure_get_string (s, "profile"); - if (profile_string) { - if (g_str_equal (profile_string, "simple")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileSimple; - } else if (g_str_equal (profile_string, "simple-scalable")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileSimpleScalable; - } else if (g_str_equal (profile_string, "core")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileCore; - } else if (g_str_equal (profile_string, "main")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileMain; - } else if (g_str_equal (profile_string, "n-bit")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileNbit; - } else if (g_str_equal (profile_string, "scalable")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileScalableTexture; - } else if (g_str_equal (profile_string, "simple-face")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileSimpleFace; - } else if (g_str_equal (profile_string, "simple-fba")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileSimpleFBA; - } else if (g_str_equal (profile_string, "basic-animated-texture")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileBasicAnimated; - } else if (g_str_equal (profile_string, "hybrid")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileHybrid; - } else if (g_str_equal (profile_string, "advanced-real-time-simple")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileAdvancedRealTime; - } else if (g_str_equal (profile_string, "core-scalable")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileCoreScalable; - } else if (g_str_equal (profile_string, "advanced-coding-efficiency")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileAdvancedCoding; - } else if (g_str_equal (profile_string, "advanced-core")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileAdvancedCore; - } else if (g_str_equal (profile_string, "advanced-scalable-texture")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileAdvancedScalable; - } else if (g_str_equal (profile_string, "advanced-simple")) { - param.eProfile = OMX_VIDEO_MPEG4ProfileAdvancedSimple; - } else { - goto unsupported_profile; - } - } - level_string = gst_structure_get_string (s, "level"); - if (level_string) { - if (g_str_equal (level_string, "0")) { - param.eLevel = OMX_VIDEO_MPEG4Level0; - } else if (g_str_equal (level_string, "0b")) { - param.eLevel = OMX_VIDEO_MPEG4Level0b; - } else if (g_str_equal (level_string, "1")) { - param.eLevel = OMX_VIDEO_MPEG4Level1; - } else if (g_str_equal (level_string, "2")) { - param.eLevel = OMX_VIDEO_MPEG4Level2; - } else if (g_str_equal (level_string, "3")) { - param.eLevel = OMX_VIDEO_MPEG4Level3; - } else if (g_str_equal (level_string, "4")) { - param.eLevel = OMX_VIDEO_MPEG4Level4; - } else if (g_str_equal (level_string, "4a")) { - param.eLevel = OMX_VIDEO_MPEG4Level4a; - } else if (g_str_equal (level_string, "5")) { - param.eLevel = OMX_VIDEO_MPEG4Level5; - } else { - goto unsupported_level; - } - } - - gst_caps_unref (intersection); - } - - err = - gst_omx_component_set_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting profile/level not supported by component"); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Error setting profile %u and level %u: %s (0x%08x)", - (guint) param.eProfile, (guint) param.eLevel, - gst_omx_error_to_string (err), err); - return FALSE; - } - - return TRUE; - -unsupported_profile: - GST_ERROR_OBJECT (self, "Unsupported profile %s", profile_string); - gst_caps_unref (intersection); - return FALSE; - -unsupported_level: - GST_ERROR_OBJECT (self, "Unsupported level %s", level_string); - gst_caps_unref (intersection); - return FALSE; -} - -static GstCaps * -gst_omx_mpeg4_video_enc_get_caps (GstOMXVideoEnc * enc, GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXMPEG4VideoEnc *self = GST_OMX_MPEG4_VIDEO_ENC (enc); - GstCaps *caps; - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_PROFILELEVELTYPE param; - const gchar *profile, *level; - - caps = - gst_caps_new_simple ("video/mpeg", "mpegversion", G_TYPE_INT, 4, - "systemstream", G_TYPE_BOOLEAN, FALSE, NULL); - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = GST_OMX_VIDEO_ENC (self)->enc_out_port->index; - - err = - gst_omx_component_get_parameter (GST_OMX_VIDEO_ENC (self)->enc, - OMX_IndexParamVideoProfileLevelCurrent, ¶m); - if (err != OMX_ErrorNone && err != OMX_ErrorUnsupportedIndex) { - gst_caps_unref (caps); - return NULL; - } - - if (err == OMX_ErrorNone) { - switch (param.eProfile) { - case OMX_VIDEO_MPEG4ProfileSimple: - profile = "simple"; - break; - case OMX_VIDEO_MPEG4ProfileSimpleScalable: - profile = "simple-scalable"; - break; - case OMX_VIDEO_MPEG4ProfileCore: - profile = "core"; - break; - case OMX_VIDEO_MPEG4ProfileMain: - profile = "main"; - break; - case OMX_VIDEO_MPEG4ProfileNbit: - profile = "n-bit"; - break; - case OMX_VIDEO_MPEG4ProfileScalableTexture: - profile = "scalable"; - break; - case OMX_VIDEO_MPEG4ProfileSimpleFace: - profile = "simple-face"; - break; - case OMX_VIDEO_MPEG4ProfileSimpleFBA: - profile = "simple-fba"; - break; - case OMX_VIDEO_MPEG4ProfileBasicAnimated: - profile = "basic-animated-texture"; - break; - case OMX_VIDEO_MPEG4ProfileHybrid: - profile = "hybrid"; - break; - case OMX_VIDEO_MPEG4ProfileAdvancedRealTime: - profile = "advanced-real-time-simple"; - break; - case OMX_VIDEO_MPEG4ProfileCoreScalable: - profile = "core-scalable"; - break; - case OMX_VIDEO_MPEG4ProfileAdvancedCoding: - profile = "advanced-coding-efficiency"; - break; - case OMX_VIDEO_MPEG4ProfileAdvancedCore: - profile = "advanced-core"; - break; - case OMX_VIDEO_MPEG4ProfileAdvancedScalable: - profile = "advanced-scalable-texture"; - break; - case OMX_VIDEO_MPEG4ProfileAdvancedSimple: - profile = "advanced-simple"; - break; - default: - g_assert_not_reached (); - return NULL; - } - - switch (param.eLevel) { - case OMX_VIDEO_MPEG4Level0: - level = "0"; - break; - case OMX_VIDEO_MPEG4Level0b: - level = "0b"; - break; - case OMX_VIDEO_MPEG4Level1: - level = "1"; - break; - case OMX_VIDEO_MPEG4Level2: - level = "2"; - break; - case OMX_VIDEO_MPEG4Level3: - level = "3"; - break; - case OMX_VIDEO_MPEG4Level4: - level = "4"; - break; - case OMX_VIDEO_MPEG4Level4a: - level = "4a"; - break; - case OMX_VIDEO_MPEG4Level5: - level = "5"; - break; - default: - g_assert_not_reached (); - return NULL; - } - - gst_caps_set_simple (caps, - "profile", G_TYPE_STRING, profile, "level", G_TYPE_STRING, level, NULL); - } - - return caps; -} diff --git a/subprojects/gst-omx/omx/gstomxmpeg4videoenc.h b/subprojects/gst-omx/omx/gstomxmpeg4videoenc.h deleted file mode 100644 index 01d6698c87..0000000000 --- a/subprojects/gst-omx/omx/gstomxmpeg4videoenc.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_MPEG4_VIDEO_ENC_H__ -#define __GST_OMX_MPEG4_VIDEO_ENC_H__ - -#include -#include "gstomxvideoenc.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_MPEG4_VIDEO_ENC \ - (gst_omx_mpeg4_video_enc_get_type()) -#define GST_OMX_MPEG4_VIDEO_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_MPEG4_VIDEO_ENC,GstOMXMPEG4VideoEnc)) -#define GST_OMX_MPEG4_VIDEO_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_MPEG4_VIDEO_ENC,GstOMXMPEG4VideoEncClass)) -#define GST_OMX_MPEG4_VIDEO_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_MPEG4_VIDEO_ENC,GstOMXMPEG4VideoEncClass)) -#define GST_IS_OMX_MPEG4_VIDEO_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_MPEG4_VIDEO_ENC)) -#define GST_IS_OMX_MPEG4_VIDEO_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_MPEG4_VIDEO_ENC)) - -typedef struct _GstOMXMPEG4VideoEnc GstOMXMPEG4VideoEnc; -typedef struct _GstOMXMPEG4VideoEncClass GstOMXMPEG4VideoEncClass; - -struct _GstOMXMPEG4VideoEnc -{ - GstOMXVideoEnc parent; -}; - -struct _GstOMXMPEG4VideoEncClass -{ - GstOMXVideoEncClass parent_class; -}; - -GType gst_omx_mpeg4_video_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_MPEG4_VIDEO_ENC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxtheoradec.c b/subprojects/gst-omx/omx/gstomxtheoradec.c deleted file mode 100644 index b17419e41f..0000000000 --- a/subprojects/gst-omx/omx/gstomxtheoradec.c +++ /dev/null @@ -1,157 +0,0 @@ -/* - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxtheoradec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_theora_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_theora_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_theora_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_theora_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static GstFlowReturn gst_omx_theora_dec_handle_frame (GstVideoDecoder * decoder, - GstVideoCodecFrame * frame); -static gboolean gst_omx_theora_dec_stop (GstVideoDecoder * decoder); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_theora_dec_debug_category, "omxtheoradec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXTheoraDec, gst_omx_theora_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -static void -gst_omx_theora_dec_class_init (GstOMXTheoraDecClass * klass) -{ - GstVideoDecoderClass *gstvideodec_class = GST_VIDEO_DECODER_CLASS (klass); - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_theora_dec_is_format_change); - videodec_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_theora_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "video/x-theora, " - "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gstvideodec_class->handle_frame = gst_omx_theora_dec_handle_frame; - gstvideodec_class->stop = gst_omx_theora_dec_stop; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX Theora Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode Theora video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.theora"); -} - -static void -gst_omx_theora_dec_init (GstOMXTheoraDec * self) -{ -} - -static gboolean -gst_omx_theora_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_theora_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingTheora; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} - -static GstFlowReturn -gst_omx_theora_dec_handle_frame (GstVideoDecoder * decoder, - GstVideoCodecFrame * frame) -{ - GstOMXTheoraDec *self = GST_OMX_THEORA_DEC (decoder); - - if (GST_BUFFER_FLAG_IS_SET (frame->input_buffer, GST_BUFFER_FLAG_HEADER)) { - guint16 size; - GstBuffer *sbuf; - - if (!self->header) { - self->header = gst_buffer_new (); - gst_buffer_copy_into (self->header, frame->input_buffer, - GST_BUFFER_COPY_FLAGS | GST_BUFFER_COPY_TIMESTAMPS, 0, -1); - } - - size = gst_buffer_get_size (frame->input_buffer); - size = GUINT16_TO_BE (size); - sbuf = gst_buffer_new_and_alloc (2); - gst_buffer_fill (sbuf, 0, &size, 2); - self->header = gst_buffer_append (self->header, sbuf); - - self->header = - gst_buffer_append (self->header, gst_buffer_ref (frame->input_buffer)); - - gst_video_decoder_drop_frame (GST_VIDEO_DECODER (self), frame); - - return GST_FLOW_OK; - } - - if (self->header) { - gst_buffer_replace (&GST_OMX_VIDEO_DEC (self)->codec_data, self->header); - gst_buffer_unref (self->header); - self->header = NULL; - } - - return - GST_VIDEO_DECODER_CLASS (gst_omx_theora_dec_parent_class)->handle_frame - (GST_VIDEO_DECODER (self), frame); -} - -static gboolean -gst_omx_theora_dec_stop (GstVideoDecoder * decoder) -{ - GstOMXTheoraDec *self = GST_OMX_THEORA_DEC (decoder); - - gst_buffer_replace (&self->header, NULL); - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxtheoradec.h b/subprojects/gst-omx/omx/gstomxtheoradec.h deleted file mode 100644 index 4b5a2fa2fa..0000000000 --- a/subprojects/gst-omx/omx/gstomxtheoradec.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_THEORA_DEC_H__ -#define __GST_OMX_THEORA_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_THEORA_DEC \ - (gst_omx_theora_dec_get_type()) -#define GST_OMX_THEORA_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_THEORA_DEC,GstOMXTheoraDec)) -#define GST_OMX_THEORA_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_THEORA_DEC,GstOMXTheoraDecClass)) -#define GST_OMX_THEORA_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_THEORA_DEC,GstOMXTheoraDecClass)) -#define GST_IS_OMX_THEORA_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_THEORA_DEC)) -#define GST_IS_OMX_THEORA_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_THEORA_DEC)) - -typedef struct _GstOMXTheoraDec GstOMXTheoraDec; -typedef struct _GstOMXTheoraDecClass GstOMXTheoraDecClass; - -struct _GstOMXTheoraDec -{ - GstOMXVideoDec parent; - GstBuffer *header; -}; - -struct _GstOMXTheoraDecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_theora_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_THEORA_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxvideo.c b/subprojects/gst-omx/omx/gstomxvideo.c deleted file mode 100644 index 71963fb64b..0000000000 --- a/subprojects/gst-omx/omx/gstomxvideo.c +++ /dev/null @@ -1,356 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge * - * Copyright 2014 Advanced Micro Devices, Inc. - * Author: Christian König - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "gstomxvideo.h" - -#include - -GST_DEBUG_CATEGORY (gst_omx_video_debug_category); -#define GST_CAT_DEFAULT gst_omx_video_debug_category - -/* Keep synced with GST_OMX_VIDEO_DEC_SUPPORTED_FORMATS */ -GstVideoFormat -gst_omx_video_get_format_from_omx (OMX_COLOR_FORMATTYPE omx_colorformat) -{ - GstVideoFormat format; - - switch (omx_colorformat) { - case OMX_COLOR_FormatL8: - format = GST_VIDEO_FORMAT_GRAY8; - break; - case OMX_COLOR_FormatYUV420Planar: - case OMX_COLOR_FormatYUV420PackedPlanar: - format = GST_VIDEO_FORMAT_I420; - break; - case OMX_COLOR_FormatYUV420SemiPlanar: - case OMX_COLOR_FormatYUV420PackedSemiPlanar: - format = GST_VIDEO_FORMAT_NV12; - break; - case OMX_COLOR_FormatYUV422SemiPlanar: - format = GST_VIDEO_FORMAT_NV16; - break; - case OMX_COLOR_FormatYCbYCr: - format = GST_VIDEO_FORMAT_YUY2; - break; - case OMX_COLOR_FormatYCrYCb: - format = GST_VIDEO_FORMAT_YVYU; - break; - case OMX_COLOR_FormatCbYCrY: - format = GST_VIDEO_FORMAT_UYVY; - break; - case OMX_COLOR_Format32bitARGB8888: - /* There is a mismatch in omxil specification 4.2.1 between - * OMX_COLOR_Format32bitARGB8888 and its description - * Follow the description */ - format = GST_VIDEO_FORMAT_ABGR; - break; - case OMX_COLOR_Format32bitBGRA8888: - /* Same issue as OMX_COLOR_Format32bitARGB8888 */ - format = GST_VIDEO_FORMAT_ARGB; - break; - case OMX_COLOR_Format16bitRGB565: - format = GST_VIDEO_FORMAT_RGB16; - break; - case OMX_COLOR_Format16bitBGR565: - format = GST_VIDEO_FORMAT_BGR16; - break; - case OMX_COLOR_Format24bitBGR888: - format = GST_VIDEO_FORMAT_BGR; - break; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - /* Formats defined in extensions have their own enum so disable to -Wswitch warning */ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wswitch" - case OMX_ALG_COLOR_FormatYUV420SemiPlanar10bitPacked: - format = GST_VIDEO_FORMAT_NV12_10LE32; - break; - case OMX_ALG_COLOR_FormatYUV422SemiPlanar10bitPacked: - format = GST_VIDEO_FORMAT_NV16_10LE32; - break; -#pragma GCC diagnostic pop -#endif - default: - format = GST_VIDEO_FORMAT_UNKNOWN; - break; - } - - return format; -} - -GList * -gst_omx_video_get_supported_colorformats (GstOMXPort * port, - GstVideoCodecState * state) -{ - GstOMXComponent *comp = port->comp; - OMX_VIDEO_PARAM_PORTFORMATTYPE param; - OMX_ERRORTYPE err; - GList *negotiation_map = NULL; - gint old_index; - GstOMXVideoNegotiationMap *m; - GstVideoFormat f; - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = port->index; - param.nIndex = 0; - param.xFramerate = - state ? gst_omx_video_calculate_framerate_q16 (&state->info) : 0; - - old_index = -1; - do { - err = - gst_omx_component_get_parameter (comp, - OMX_IndexParamVideoPortFormat, ¶m); - - /* FIXME: Workaround for Bellagio that simply always - * returns the same value regardless of nIndex and - * never returns OMX_ErrorNoMore - */ - if (old_index == param.nIndex) - break; - - if (err == OMX_ErrorNone || err == OMX_ErrorNoMore) { - f = gst_omx_video_get_format_from_omx (param.eColorFormat); - - if (f != GST_VIDEO_FORMAT_UNKNOWN) { - m = g_new (GstOMXVideoNegotiationMap, 1); - m->format = f; - m->type = param.eColorFormat; - negotiation_map = g_list_append (negotiation_map, m); - GST_DEBUG_OBJECT (comp->parent, - "Component port %d supports %s (%d) at index %u", port->index, - gst_video_format_to_string (f), param.eColorFormat, - (guint) param.nIndex); - } else { - GST_DEBUG_OBJECT (comp->parent, - "Component port %d supports unsupported color format %d at index %u", - port->index, param.eColorFormat, (guint) param.nIndex); - } - } - old_index = param.nIndex++; - } while (err == OMX_ErrorNone); - - return negotiation_map; -} - -GstCaps * -gst_omx_video_get_caps_for_map (GList * map) -{ - GstCaps *caps = gst_caps_new_empty (); - GList *l; - - for (l = map; l; l = l->next) { - GstOMXVideoNegotiationMap *entry = l->data; - - gst_caps_append_structure (caps, - gst_structure_new ("video/x-raw", - "format", G_TYPE_STRING, - gst_video_format_to_string (entry->format), NULL)); - } - return caps; -} - -void -gst_omx_video_negotiation_map_free (GstOMXVideoNegotiationMap * m) -{ - g_free (m); -} - -GstVideoCodecFrame * -gst_omx_video_find_nearest_frame (GstElement * element, GstOMXBuffer * buf, - GList * frames) -{ - GstVideoCodecFrame *best = NULL; - GstClockTimeDiff best_diff = G_MAXINT64; - GstClockTime timestamp; - GList *l; - - timestamp = - gst_util_uint64_scale (GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp), - GST_SECOND, OMX_TICKS_PER_SECOND); - - GST_LOG_OBJECT (element, "look for ts %" GST_TIME_FORMAT, - GST_TIME_ARGS (timestamp)); - - for (l = frames; l; l = l->next) { - GstVideoCodecFrame *tmp = l->data; - GstClockTimeDiff diff = ABS (GST_CLOCK_DIFF (timestamp, tmp->pts)); - - GST_LOG_OBJECT (element, - " frame %u diff %" G_GINT64_FORMAT " ts %" GST_TIME_FORMAT, - tmp->system_frame_number, diff, GST_TIME_ARGS (tmp->pts)); - - if (diff < best_diff) { - best = tmp; - best_diff = diff; - - if (diff == 0) - break; - } - } - - if (best) { - gst_video_codec_frame_ref (best); - - /* OMX timestamps are in microseconds while gst ones are in nanoseconds. - * So if the difference between them is higher than 1 microsecond we likely - * picked the wrong frame. */ - if (best_diff >= GST_USECOND) - GST_WARNING_OBJECT (element, - "Difference between ts (%" GST_TIME_FORMAT ") and frame %u (%" - GST_TIME_FORMAT ") seems too high (%" GST_TIME_FORMAT ")", - GST_TIME_ARGS (timestamp), best->system_frame_number, - GST_TIME_ARGS (best->pts), GST_TIME_ARGS (best_diff)); - } else - GST_WARNING_OBJECT (element, "No best frame has been found"); - - g_list_foreach (frames, (GFunc) gst_video_codec_frame_unref, NULL); - g_list_free (frames); - - return best; -} - -OMX_U32 -gst_omx_video_calculate_framerate_q16 (GstVideoInfo * info) -{ - g_assert (info); - - if (!info->fps_d) - return 0; - - /* OMX API expects frame rate to actually be the field rate, so twice - * the frame rate in interlace mode. */ - return gst_util_uint64_scale_int (1 << 16, GST_VIDEO_INFO_FIELD_RATE_N (info), - info->fps_d); -} - -gboolean -gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b) -{ - /* If one of them is 0 use the classic comparison. The value 0 has a special - meaning and is used to indicate the frame rate is unknown, variable, or - is not needed. */ - if (!q16_a || !q16_b) - return q16_a == q16_b; - - /* If the 'percentage change' is less than 1% then consider it equal to avoid - * an unnecessary re-negotiation. */ - return fabs (((gdouble) q16_a) - ((gdouble) q16_b)) / (gdouble) q16_b < 0.01; -} - -gboolean -gst_omx_video_get_port_padding (GstOMXPort * port, GstVideoInfo * info_orig, - GstVideoAlignment * align) -{ - guint nstride; - guint nslice_height; - GstVideoInfo info; - gsize plane_size[GST_VIDEO_MAX_PLANES]; - - gst_video_alignment_reset (align); - - /* Create a copy of @info_orig without any offset/stride as we need a - * 'standard' version to compute the paddings. */ - gst_video_info_init (&info); - gst_video_info_set_interlaced_format (&info, - GST_VIDEO_INFO_FORMAT (info_orig), - GST_VIDEO_INFO_INTERLACE_MODE (info_orig), - GST_VIDEO_INFO_WIDTH (info_orig), GST_VIDEO_INFO_HEIGHT (info_orig)); - - /* Retrieve the plane sizes */ - if (!gst_video_info_align_full (&info, align, plane_size)) { - GST_WARNING_OBJECT (port->comp->parent, "Failed to retrieve plane sizes"); - return FALSE; - } - - nstride = port->port_def.format.video.nStride; - nslice_height = port->port_def.format.video.nSliceHeight; - - if (nstride > GST_VIDEO_INFO_PLANE_STRIDE (&info, 0)) { - align->padding_right = nstride - GST_VIDEO_INFO_PLANE_STRIDE (&info, 0); - - if (GST_VIDEO_FORMAT_INFO_IS_COMPLEX (info.finfo)) { - /* Stride is in bytes while padding is in pixels so we need to do manual - * conversions for complex formats. */ - switch (GST_VIDEO_INFO_FORMAT (&info)) { - case GST_VIDEO_FORMAT_NV12_10LE32: - case GST_VIDEO_FORMAT_NV16_10LE32: - /* Need ((width + 2) / 3) 32-bits words to store one row, - * see unpack_NV12_10LE32 in -base. - * - * So let's say: - * - W = the width, in pixels - * - S = the stride, in bytes - * - P = the padding, in bytes - * - Δ = the padding, in pixels - * - * we then have: - * S = ((W+2)/3) * 4 - * S+P = ((W+2+Δ)/3) * 4 - * - * By solving this system we get: - * Δ = (3/4) * P - */ - align->padding_right *= 0.75; - break; - default: - GST_FIXME_OBJECT (port->comp->parent, - "Stride conversion is not supported for format %s", - GST_VIDEO_INFO_NAME (&info)); - return FALSE; - } - } - - GST_LOG_OBJECT (port->comp->parent, - "OMX stride (%d) is higher than standard (%d) for port %u; right padding: %d", - nstride, GST_VIDEO_INFO_PLANE_STRIDE (&info, 0), port->index, - align->padding_right); - } - - if (nslice_height > GST_VIDEO_INFO_PLANE_HEIGHT (&info, 0, plane_size)) { - align->padding_bottom = - nslice_height - GST_VIDEO_INFO_PLANE_HEIGHT (&info, 0, plane_size); - - if (GST_VIDEO_INFO_INTERLACE_MODE (&info) == - GST_VIDEO_INTERLACE_MODE_ALTERNATE) { - /* GstVideoAlignment defines the alignment for the full frame while - * OMX gives us the slice height for a single field, so we have to - * double the vertical padding. */ - GST_DEBUG_OBJECT (port->comp->parent, - "Double bottom padding because of alternate stream"); - align->padding_bottom *= 2; - } - - GST_LOG_OBJECT (port->comp->parent, - "OMX slice height (%d) is higher than standard (%" G_GSIZE_FORMAT - ") for port %u; vertical padding: %d", nslice_height, - GST_VIDEO_INFO_PLANE_HEIGHT (&info, 0, plane_size), port->index, - align->padding_bottom); - } - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxvideo.h b/subprojects/gst-omx/omx/gstomxvideo.h deleted file mode 100644 index 8664345f21..0000000000 --- a/subprojects/gst-omx/omx/gstomxvideo.h +++ /dev/null @@ -1,74 +0,0 @@ -/* - * Copyright 2014 Advanced Micro Devices, Inc. - * Author: Christian König - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_VIDEO_H__ -#define __GST_OMX_VIDEO_H__ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -/* Keep synced with gst_omx_video_get_format_from_omx(). Sort by decreasing quality */ -#define GST_OMX_VIDEO_DEC_SUPPORTED_FORMATS "{ NV16_10LE32, NV12_10LE32, " \ - "NV16, YUY2, YVYU, UYVY, NV12, I420, RGB16, BGR16, ABGR, ARGB, GRAY8 }" - -#define GST_OMX_VIDEO_ENC_SUPPORTED_FORMATS "{ NV16_10LE32, NV12_10LE32, " \ - "NV16, NV12, I420, GRAY8 }" - -typedef struct -{ - GstVideoFormat format; - OMX_COLOR_FORMATTYPE type; -} GstOMXVideoNegotiationMap; - -GstVideoFormat -gst_omx_video_get_format_from_omx (OMX_COLOR_FORMATTYPE omx_colorformat); - -GList * -gst_omx_video_get_supported_colorformats (GstOMXPort * port, - GstVideoCodecState * state); - -GstCaps * gst_omx_video_get_caps_for_map(GList * map); - -void -gst_omx_video_negotiation_map_free (GstOMXVideoNegotiationMap * m); - -GstVideoCodecFrame * -gst_omx_video_find_nearest_frame (GstElement * element, GstOMXBuffer * buf, GList * frames); - -OMX_U32 gst_omx_video_calculate_framerate_q16 (GstVideoInfo * info); - -gboolean gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b); - -gboolean gst_omx_video_get_port_padding (GstOMXPort * port, GstVideoInfo * info_orig, - GstVideoAlignment * align); - -G_END_DECLS - -#endif /* __GST_OMX_VIDEO_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxvideodec.c b/subprojects/gst-omx/omx/gstomxvideodec.c deleted file mode 100644 index 28cc24417f..0000000000 --- a/subprojects/gst-omx/omx/gstomxvideodec.c +++ /dev/null @@ -1,3524 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include - -#if defined (USE_OMX_TARGET_RPI) && defined(__GNUC__) -#ifndef __VCCOREVER__ -#define __VCCOREVER__ 0x04000000 -#endif - -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wredundant-decls" -#pragma GCC optimize ("gnu89-inline") -#endif - -#if defined (HAVE_GST_GL) -#include -#endif - -#if defined (USE_OMX_TARGET_RPI) && defined(__GNUC__) -#pragma GCC reset_options -#pragma GCC diagnostic pop -#endif - -#include - -#include "gstomxbufferpool.h" -#include "gstomxvideo.h" -#include "gstomxvideodec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_video_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_video_dec_debug_category - -/* prototypes */ -static void gst_omx_video_dec_finalize (GObject * object); - -static GstStateChangeReturn -gst_omx_video_dec_change_state (GstElement * element, - GstStateChange transition); - -static gboolean gst_omx_video_dec_open (GstVideoDecoder * decoder); -static gboolean gst_omx_video_dec_close (GstVideoDecoder * decoder); -static gboolean gst_omx_video_dec_start (GstVideoDecoder * decoder); -static gboolean gst_omx_video_dec_stop (GstVideoDecoder * decoder); -static gboolean gst_omx_video_dec_set_format (GstVideoDecoder * decoder, - GstVideoCodecState * state); -static gboolean gst_omx_video_dec_flush (GstVideoDecoder * decoder); -static GstFlowReturn gst_omx_video_dec_handle_frame (GstVideoDecoder * decoder, - GstVideoCodecFrame * frame); -static GstFlowReturn gst_omx_video_dec_finish (GstVideoDecoder * decoder); -static gboolean gst_omx_video_dec_decide_allocation (GstVideoDecoder * bdec, - GstQuery * query); -static gboolean gst_omx_video_dec_propose_allocation (GstVideoDecoder * bdec, - GstQuery * query); - -static GstFlowReturn gst_omx_video_dec_drain (GstVideoDecoder * decoder); - -static OMX_ERRORTYPE gst_omx_video_dec_allocate_output_buffers (GstOMXVideoDec * - self); -static gboolean gst_omx_video_dec_deallocate_output_buffers (GstOMXVideoDec - * self); - -enum -{ - PROP_0, - PROP_INTERNAL_ENTROPY_BUFFERS, -}; - -#define GST_OMX_VIDEO_DEC_INTERNAL_ENTROPY_BUFFERS_DEFAULT (5) - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_video_dec_debug_category, "omxvideodec", 0, \ - "debug category for gst-omx video decoder base class"); - - -G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GstOMXVideoDec, gst_omx_video_dec, - GST_TYPE_VIDEO_DECODER, DEBUG_INIT); - -static void -gst_omx_video_dec_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (object); -#endif - - switch (prop_id) { -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case PROP_INTERNAL_ENTROPY_BUFFERS: - self->internal_entropy_buffers = g_value_get_uint (value); - break; -#endif - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_video_dec_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (object); -#endif - - switch (prop_id) { -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case PROP_INTERNAL_ENTROPY_BUFFERS: - g_value_set_uint (value, self->internal_entropy_buffers); - break; -#endif - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_video_dec_class_init (GstOMXVideoDecClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstVideoDecoderClass *video_decoder_class = GST_VIDEO_DECODER_CLASS (klass); - - gobject_class->finalize = gst_omx_video_dec_finalize; - gobject_class->set_property = gst_omx_video_dec_set_property; - gobject_class->get_property = gst_omx_video_dec_get_property; - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - g_object_class_install_property (gobject_class, PROP_INTERNAL_ENTROPY_BUFFERS, - g_param_spec_uint ("internal-entropy-buffers", "Internal entropy buffers", - "Number of internal buffers used by the decoder to smooth out entropy decoding performance. " - "Increasing it may improve the frame rate when decoding high bitrate streams. " - "Decreasing it reduces the memory footprint", - 2, 16, GST_OMX_VIDEO_DEC_INTERNAL_ENTROPY_BUFFERS_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); -#endif - - element_class->change_state = - GST_DEBUG_FUNCPTR (gst_omx_video_dec_change_state); - - video_decoder_class->open = GST_DEBUG_FUNCPTR (gst_omx_video_dec_open); - video_decoder_class->close = GST_DEBUG_FUNCPTR (gst_omx_video_dec_close); - video_decoder_class->start = GST_DEBUG_FUNCPTR (gst_omx_video_dec_start); - video_decoder_class->stop = GST_DEBUG_FUNCPTR (gst_omx_video_dec_stop); - video_decoder_class->flush = GST_DEBUG_FUNCPTR (gst_omx_video_dec_flush); - video_decoder_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_video_dec_set_format); - video_decoder_class->handle_frame = - GST_DEBUG_FUNCPTR (gst_omx_video_dec_handle_frame); - video_decoder_class->finish = GST_DEBUG_FUNCPTR (gst_omx_video_dec_finish); - video_decoder_class->drain = GST_DEBUG_FUNCPTR (gst_omx_video_dec_drain); - video_decoder_class->decide_allocation = - GST_DEBUG_FUNCPTR (gst_omx_video_dec_decide_allocation); - video_decoder_class->propose_allocation = - GST_DEBUG_FUNCPTR (gst_omx_video_dec_propose_allocation); - - klass->cdata.type = GST_OMX_COMPONENT_TYPE_FILTER; - klass->cdata.default_src_template_caps = -#if defined (HAVE_GST_GL) - GST_VIDEO_CAPS_MAKE_WITH_FEATURES (GST_CAPS_FEATURE_MEMORY_GL_MEMORY, - "RGBA") "; " -#endif -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GST_VIDEO_CAPS_MAKE_WITH_FEATURES (GST_CAPS_FEATURE_FORMAT_INTERLACED, - GST_OMX_VIDEO_DEC_SUPPORTED_FORMATS) - ", interlace-mode = (string) alternate ; " -#endif - GST_VIDEO_CAPS_MAKE (GST_OMX_VIDEO_DEC_SUPPORTED_FORMATS); -} - -static void -gst_omx_video_dec_init (GstOMXVideoDec * self) -{ - self->dmabuf = FALSE; - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - self->internal_entropy_buffers = - GST_OMX_VIDEO_DEC_INTERNAL_ENTROPY_BUFFERS_DEFAULT; -#endif - - gst_video_decoder_set_packetized (GST_VIDEO_DECODER (self), TRUE); - gst_video_decoder_set_use_default_pad_acceptcaps (GST_VIDEO_DECODER_CAST - (self), TRUE); - GST_PAD_SET_ACCEPT_TEMPLATE (GST_VIDEO_DECODER_SINK_PAD (self)); - - g_mutex_init (&self->drain_lock); - g_cond_init (&self->drain_cond); -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - -#define CHECK_ERR(setting) \ - if (err == OMX_ErrorUnsupportedIndex || err == OMX_ErrorUnsupportedSetting) { \ - GST_WARNING_OBJECT (self, \ - "Setting " setting " parameters not supported by the component"); \ - } else if (err != OMX_ErrorNone) { \ - GST_ERROR_OBJECT (self, \ - "Failed to set " setting " parameters: %s (0x%08x)", \ - gst_omx_error_to_string (err), err); \ - return FALSE; \ - } - -static gboolean -set_zynqultrascaleplus_props (GstOMXVideoDec * self) -{ - OMX_ERRORTYPE err; - - { - OMX_ALG_VIDEO_PARAM_INTERNAL_ENTROPY_BUFFERS entropy_buffers; - - GST_OMX_INIT_STRUCT (&entropy_buffers); - entropy_buffers.nPortIndex = self->dec_in_port->index; - entropy_buffers.nNumInternalEntropyBuffers = self->internal_entropy_buffers; - - GST_DEBUG_OBJECT (self, "setting number of internal entropy buffers to %d", - self->internal_entropy_buffers); - - err = - gst_omx_component_set_parameter (self->dec, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoInternalEntropyBuffers, - &entropy_buffers); - CHECK_ERR ("internal entropy buffers"); - } - - return TRUE; -} -#endif - -static gboolean -gst_omx_video_dec_open (GstVideoDecoder * decoder) -{ - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (decoder); - GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (self); - gint in_port_index, out_port_index; - - GST_DEBUG_OBJECT (self, "Opening decoder"); - - self->dec = - gst_omx_component_new (GST_OBJECT_CAST (self), klass->cdata.core_name, - klass->cdata.component_name, klass->cdata.component_role, - klass->cdata.hacks); - self->started = FALSE; - - if (!self->dec) - return FALSE; - - if (gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded) - return FALSE; - - in_port_index = klass->cdata.in_port_index; - out_port_index = klass->cdata.out_port_index; - - if (in_port_index == -1 || out_port_index == -1) { - OMX_PORT_PARAM_TYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->dec, OMX_IndexParamVideoInit, - ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - in_port_index = 0; - out_port_index = 1; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", - (guint) param.nPorts, (guint) param.nStartPortNumber); - in_port_index = param.nStartPortNumber + 0; - out_port_index = param.nStartPortNumber + 1; - } - } - self->dec_in_port = gst_omx_component_add_port (self->dec, in_port_index); - self->dec_out_port = gst_omx_component_add_port (self->dec, out_port_index); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GST_DEBUG_OBJECT (self, "Configure decoder output to export dmabuf"); - self->dmabuf = gst_omx_port_set_dmabuf (self->dec_out_port, TRUE); -#endif - - if (!self->dec_in_port || !self->dec_out_port) - return FALSE; - - GST_DEBUG_OBJECT (self, "Opened decoder"); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - GST_DEBUG_OBJECT (self, "Opening EGL renderer"); - self->egl_render = - gst_omx_component_new (GST_OBJECT_CAST (self), klass->cdata.core_name, - "OMX.broadcom.egl_render", NULL, klass->cdata.hacks); - - if (!self->egl_render) - return FALSE; - - if (gst_omx_component_get_state (self->egl_render, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded) - return FALSE; - - { - OMX_PORT_PARAM_TYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->egl_render, - OMX_IndexParamVideoInit, ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - in_port_index = 0; - out_port_index = 1; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", param.nPorts, - param.nStartPortNumber); - in_port_index = param.nStartPortNumber + 0; - out_port_index = param.nStartPortNumber + 1; - } - } - - self->egl_in_port = - gst_omx_component_add_port (self->egl_render, in_port_index); - self->egl_out_port = - gst_omx_component_add_port (self->egl_render, out_port_index); - - if (!self->egl_in_port || !self->egl_out_port) - return FALSE; - - GST_DEBUG_OBJECT (self, "Opened EGL renderer"); -#endif - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (!set_zynqultrascaleplus_props (self)) - return FALSE; -#endif - - return TRUE; -} - -static gboolean -gst_omx_video_dec_shutdown (GstOMXVideoDec * self) -{ - OMX_STATETYPE state; - - GST_DEBUG_OBJECT (self, "Shutting down decoder"); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - state = gst_omx_component_get_state (self->egl_render, 0); - if (state > OMX_StateLoaded || state == OMX_StateInvalid) { - if (state > OMX_StateIdle) { - gst_omx_component_set_state (self->egl_render, OMX_StateIdle); - gst_omx_component_set_state (self->dec, OMX_StateIdle); - gst_omx_component_get_state (self->egl_render, 5 * GST_SECOND); - gst_omx_component_get_state (self->dec, 1 * GST_SECOND); - } - gst_omx_component_set_state (self->egl_render, OMX_StateLoaded); - gst_omx_component_set_state (self->dec, OMX_StateLoaded); - - gst_omx_port_deallocate_buffers (self->dec_in_port); - gst_omx_video_dec_deallocate_output_buffers (self); - gst_omx_close_tunnel (self->dec_out_port, self->egl_in_port); - if (state > OMX_StateLoaded) { - gst_omx_component_get_state (self->egl_render, 5 * GST_SECOND); - gst_omx_component_get_state (self->dec, 1 * GST_SECOND); - } - } - - /* Otherwise we didn't use EGL and just fall back to - * shutting down the decoder */ -#endif - - state = gst_omx_component_get_state (self->dec, 0); - if (state > OMX_StateLoaded || state == OMX_StateInvalid) { - if (state > OMX_StateIdle) { - gst_omx_component_set_state (self->dec, OMX_StateIdle); - gst_omx_component_get_state (self->dec, 5 * GST_SECOND); - } - gst_omx_component_set_state (self->dec, OMX_StateLoaded); - gst_omx_port_deallocate_buffers (self->dec_in_port); - gst_omx_video_dec_deallocate_output_buffers (self); - if (state > OMX_StateLoaded) { - if (self->dec_out_port->buffers) - /* Don't wait for the state transition if the pool still has outstanding - * buffers as it will timeout anyway */ - GST_WARNING_OBJECT (self, - "Output buffers haven't been freed; still owned downstream?"); - else - gst_omx_component_get_state (self->dec, 5 * GST_SECOND); - } - } - - return TRUE; -} - -static gboolean -gst_omx_video_dec_close (GstVideoDecoder * decoder) -{ - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (decoder); - - GST_DEBUG_OBJECT (self, "Closing decoder"); - - if (!gst_omx_video_dec_shutdown (self)) - return FALSE; - - self->dec_in_port = NULL; - self->dec_out_port = NULL; - if (self->dec) - gst_omx_component_unref (self->dec); - self->dec = NULL; - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - self->egl_in_port = NULL; - self->egl_out_port = NULL; - if (self->egl_render) - gst_omx_component_unref (self->egl_render); - self->egl_render = NULL; -#endif - - self->started = FALSE; - - GST_DEBUG_OBJECT (self, "Closed decoder"); - - return TRUE; -} - -static void -gst_omx_video_dec_finalize (GObject * object) -{ - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (object); - - g_mutex_clear (&self->drain_lock); - g_cond_clear (&self->drain_cond); - - G_OBJECT_CLASS (gst_omx_video_dec_parent_class)->finalize (object); -} - -static GstStateChangeReturn -gst_omx_video_dec_change_state (GstElement * element, GstStateChange transition) -{ - GstOMXVideoDec *self; - GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; - - g_return_val_if_fail (GST_IS_OMX_VIDEO_DEC (element), - GST_STATE_CHANGE_FAILURE); - self = GST_OMX_VIDEO_DEC (element); - - switch (transition) { - case GST_STATE_CHANGE_NULL_TO_READY: - break; - case GST_STATE_CHANGE_READY_TO_PAUSED: - self->downstream_flow_ret = GST_FLOW_OK; - self->draining = FALSE; - self->started = FALSE; - self->use_buffers = FALSE; - break; - case GST_STATE_CHANGE_PAUSED_TO_PLAYING: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - if (self->dec_in_port) - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - if (self->dec_out_port) - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->egl_in_port) - gst_omx_port_set_flushing (self->egl_in_port, 5 * GST_SECOND, TRUE); - if (self->egl_out_port) - gst_omx_port_set_flushing (self->egl_out_port, 5 * GST_SECOND, TRUE); -#endif - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - break; - default: - break; - } - - ret = - GST_ELEMENT_CLASS (gst_omx_video_dec_parent_class)->change_state - (element, transition); - - if (ret == GST_STATE_CHANGE_FAILURE) - return ret; - - switch (transition) { - case GST_STATE_CHANGE_PLAYING_TO_PAUSED: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - break; - case GST_STATE_CHANGE_READY_TO_NULL: - break; - default: - break; - } - - return ret; -} - -static gboolean -gst_omx_video_dec_fill_buffer (GstOMXVideoDec * self, - GstOMXBuffer * inbuf, GstBuffer * outbuf) -{ - GstVideoCodecState *state = - gst_video_decoder_get_output_state (GST_VIDEO_DECODER (self)); - GstVideoInfo *vinfo = &state->info; - OMX_PARAM_PORTDEFINITIONTYPE *port_def = &self->dec_out_port->port_def; - gboolean ret = FALSE; - GstVideoFrame frame; - - if (vinfo->width != port_def->format.video.nFrameWidth || - GST_VIDEO_INFO_FIELD_HEIGHT (vinfo) != - port_def->format.video.nFrameHeight) { - GST_ERROR_OBJECT (self, "Resolution do not match: port=%ux%u vinfo=%dx%d", - (guint) port_def->format.video.nFrameWidth, - (guint) port_def->format.video.nFrameHeight, - vinfo->width, GST_VIDEO_INFO_FIELD_HEIGHT (vinfo)); - goto done; - } - - /* Same strides and everything */ - if (gst_buffer_get_size (outbuf) == inbuf->omx_buf->nFilledLen) { - GstMapInfo map = GST_MAP_INFO_INIT; - - if (!gst_buffer_map (outbuf, &map, GST_MAP_WRITE)) { - GST_ERROR_OBJECT (self, "Failed to map output buffer"); - goto done; - } - - memcpy (map.data, - inbuf->omx_buf->pBuffer + inbuf->omx_buf->nOffset, - inbuf->omx_buf->nFilledLen); - gst_buffer_unmap (outbuf, &map); - ret = TRUE; - goto done; - } - - /* Different strides */ - if (gst_video_frame_map (&frame, vinfo, outbuf, GST_MAP_WRITE)) { - const guint nstride = port_def->format.video.nStride; - const guint nslice = port_def->format.video.nSliceHeight; - guint src_stride[GST_VIDEO_MAX_PLANES] = { nstride, 0, }; - guint src_size[GST_VIDEO_MAX_PLANES] = { nstride * nslice, 0, }; - gint dst_width[GST_VIDEO_MAX_PLANES] = { 0, }; - gint dst_height[GST_VIDEO_MAX_PLANES] = - { GST_VIDEO_INFO_FIELD_HEIGHT (vinfo), 0, }; - const guint8 *src; - guint p; - - switch (GST_VIDEO_INFO_FORMAT (vinfo)) { - case GST_VIDEO_FORMAT_ABGR: - case GST_VIDEO_FORMAT_ARGB: - dst_width[0] = GST_VIDEO_INFO_WIDTH (vinfo) * 4; - break; - case GST_VIDEO_FORMAT_RGB16: - case GST_VIDEO_FORMAT_BGR16: - case GST_VIDEO_FORMAT_YUY2: - case GST_VIDEO_FORMAT_UYVY: - case GST_VIDEO_FORMAT_YVYU: - dst_width[0] = GST_VIDEO_INFO_WIDTH (vinfo) * 2; - break; - case GST_VIDEO_FORMAT_GRAY8: - dst_width[0] = GST_VIDEO_INFO_WIDTH (vinfo); - break; - case GST_VIDEO_FORMAT_I420: - dst_width[0] = GST_VIDEO_INFO_WIDTH (vinfo); - src_stride[1] = nstride / 2; - src_size[1] = (src_stride[1] * nslice) / 2; - dst_width[1] = GST_VIDEO_INFO_WIDTH (vinfo) / 2; - dst_height[1] = GST_VIDEO_INFO_FIELD_HEIGHT (vinfo) / 2; - src_stride[2] = nstride / 2; - src_size[2] = (src_stride[1] * nslice) / 2; - dst_width[2] = GST_VIDEO_INFO_WIDTH (vinfo) / 2; - dst_height[2] = GST_VIDEO_INFO_FIELD_HEIGHT (vinfo) / 2; - break; - case GST_VIDEO_FORMAT_NV12: - dst_width[0] = GST_VIDEO_INFO_WIDTH (vinfo); - src_stride[1] = nstride; - src_size[1] = src_stride[1] * nslice / 2; - dst_width[1] = GST_VIDEO_INFO_WIDTH (vinfo); - dst_height[1] = GST_VIDEO_INFO_FIELD_HEIGHT (vinfo) / 2; - break; - case GST_VIDEO_FORMAT_NV16: - dst_width[0] = GST_VIDEO_INFO_WIDTH (vinfo); - src_stride[1] = nstride; - src_size[1] = src_stride[1] * nslice; - dst_width[1] = GST_VIDEO_INFO_WIDTH (vinfo); - dst_height[1] = GST_VIDEO_INFO_FIELD_HEIGHT (vinfo); - break; - case GST_VIDEO_FORMAT_NV12_10LE32: - /* Need ((width + 2) / 3) 32-bits words */ - dst_width[0] = (GST_VIDEO_INFO_WIDTH (vinfo) + 2) / 3 * 4; - dst_width[1] = dst_width[0]; - src_stride[1] = nstride; - src_size[1] = src_stride[1] * nslice / 2; - dst_height[1] = GST_VIDEO_INFO_FIELD_HEIGHT (vinfo) / 2; - break; - case GST_VIDEO_FORMAT_NV16_10LE32: - /* Need ((width + 2) / 3) 32-bits words */ - dst_width[0] = (GST_VIDEO_INFO_WIDTH (vinfo) + 2) / 3 * 4; - dst_width[1] = dst_width[0]; - src_stride[1] = nstride; - src_size[1] = src_stride[1] * nslice; - dst_height[1] = GST_VIDEO_INFO_FIELD_HEIGHT (vinfo); - break; - default: - g_assert_not_reached (); - break; - } - - src = inbuf->omx_buf->pBuffer + inbuf->omx_buf->nOffset; - for (p = 0; p < GST_VIDEO_INFO_N_PLANES (vinfo); p++) { - const guint8 *data; - guint8 *dst; - guint h; - - dst = GST_VIDEO_FRAME_PLANE_DATA (&frame, p); - data = src; - for (h = 0; h < dst_height[p]; h++) { - memcpy (dst, data, dst_width[p]); - dst += GST_VIDEO_FRAME_PLANE_STRIDE (&frame, p); - data += src_stride[p]; - } - src += src_size[p]; - } - - gst_video_frame_unmap (&frame); - ret = TRUE; - } else { - GST_ERROR_OBJECT (self, "Can't map output buffer to frame"); - goto done; - } - -done: - if (ret) { - GST_BUFFER_PTS (outbuf) = - gst_util_uint64_scale (GST_OMX_GET_TICKS (inbuf->omx_buf->nTimeStamp), - GST_SECOND, OMX_TICKS_PER_SECOND); - if (inbuf->omx_buf->nTickCount != 0) - GST_BUFFER_DURATION (outbuf) = - gst_util_uint64_scale (inbuf->omx_buf->nTickCount, GST_SECOND, - OMX_TICKS_PER_SECOND); - } - - gst_video_codec_state_unref (state); - - return ret; -} - -static GstBuffer * -gst_omx_try_importing_buffer (GstOMXVideoDec * self, GstBufferPool * pool, - GstOMXPort * port, GstVideoInfo * v_info, guint i, GstVideoFrame ** frame) -{ - GstBufferPoolAcquireParams params = { 0, }; - GstBuffer *buffer = NULL; - GstMemory *mem; - GstMapFlags flags = GST_MAP_WRITE | GST_VIDEO_FRAME_MAP_FLAG_NO_REF; - gboolean is_mapped = FALSE; - - *frame = NULL; - - if (gst_buffer_pool_acquire_buffer (pool, &buffer, ¶ms) != GST_FLOW_OK) { - GST_INFO_OBJECT (self, "Failed to acquire %d-th buffer", i); - return NULL; - } - - if (gst_buffer_n_memory (buffer) != 1) { - GST_INFO_OBJECT (self, "%d-th buffer has more than one memory (%d)", i, - gst_buffer_n_memory (buffer)); - goto out; - } - - mem = gst_buffer_peek_memory (buffer, 0); - if (!mem) { - GST_INFO_OBJECT (self, "Failed to acquire memory of %d-th buffer", i); - goto out; - } - - if (self->dmabuf && !gst_is_dmabuf_memory (mem)) { - GST_INFO_OBJECT (self, - "%d-th buffer doesn't contain dmabuf while the decoder is in dmabuf mode", - i); - goto out; - } - - *frame = g_new0 (GstVideoFrame, 1); - - is_mapped = gst_video_frame_map (*frame, v_info, buffer, flags); - if (!is_mapped) { - GST_INFO_OBJECT (self, "Failed to map %d-th buffer", i); - goto out; - } - - if (GST_VIDEO_FRAME_SIZE (*frame) < port->port_def.nBufferSize) { - GST_INFO_OBJECT (self, - "Frame size of %d-th buffer (%" G_GSIZE_FORMAT - ") is too small for port buffer size (%d)", i, - GST_VIDEO_FRAME_SIZE (*frame), (guint32) port->port_def.nBufferSize); - goto out; - } - - return buffer; - -out: - if (*frame) { - if (is_mapped) - gst_video_frame_unmap (*frame); - g_free (*frame); - *frame = NULL; - } - gst_buffer_unref (buffer); - return NULL; -} - -static OMX_ERRORTYPE -gst_omx_video_dec_allocate_output_buffers (GstOMXVideoDec * self) -{ - OMX_ERRORTYPE err = OMX_ErrorNone; - GstOMXPort *port; - GstBufferPool *pool; - GstStructure *config; - gboolean eglimage = FALSE, add_videometa = FALSE; - GstCaps *caps = NULL; - guint min = 0, max = 0; - GstVideoCodecState *state = - gst_video_decoder_get_output_state (GST_VIDEO_DECODER (self)); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - port = self->eglimage ? self->egl_out_port : self->dec_out_port; -#else - port = self->dec_out_port; -#endif - - pool = gst_video_decoder_get_buffer_pool (GST_VIDEO_DECODER (self)); - if (pool) { - GstAllocator *allocator; - - config = gst_buffer_pool_get_config (pool); - if (!gst_buffer_pool_config_get_params (config, &caps, NULL, &min, &max)) { - GST_ERROR_OBJECT (self, "Can't get buffer pool params"); - gst_structure_free (config); - err = OMX_ErrorUndefined; - goto done; - } - if (!gst_buffer_pool_config_get_allocator (config, &allocator, NULL)) { - GST_ERROR_OBJECT (self, "Can't get buffer pool allocator"); - gst_structure_free (config); - err = OMX_ErrorUndefined; - goto done; - } - - /* Need at least 4 buffers for anything meaningful */ - min = MAX (min + port->port_def.nBufferCountMin, 4); - if (max == 0) { - max = min; - } else if (max < min) { - /* Can't use pool because can't have enough buffers */ - GST_DEBUG_OBJECT (self, - "pool can only provide %d buffers but %d are required", max, min); - caps = NULL; - } else { - min = max; - } - - add_videometa = gst_buffer_pool_config_has_option (config, - GST_BUFFER_POOL_OPTION_VIDEO_META); - gst_structure_free (config); - -#if defined (HAVE_GST_GL) - eglimage = self->eglimage - && (allocator && GST_IS_GL_MEMORY_EGL_ALLOCATOR (allocator)); -#else - eglimage = FALSE; -#endif - caps = caps ? gst_caps_ref (caps) : NULL; - - GST_DEBUG_OBJECT (self, "Trying to use pool %p with caps %" GST_PTR_FORMAT - " and memory type %s", pool, caps, - (allocator ? allocator->mem_type : "(null)")); - } else { - gst_caps_replace (&caps, NULL); - min = max = port->port_def.nBufferCountMin; - GST_DEBUG_OBJECT (self, "No pool available, not negotiated yet"); - } - -#if defined (HAVE_GST_GL) - /* Will retry without EGLImage */ - if (self->eglimage && !eglimage) { - GST_DEBUG_OBJECT (self, - "Wanted to use EGLImage but downstream doesn't support it"); - err = OMX_ErrorUndefined; - goto done; - } -#endif - - if (caps) - self->out_port_pool = - gst_omx_buffer_pool_new (GST_ELEMENT_CAST (self), self->dec, port, - self->dmabuf ? GST_OMX_BUFFER_MODE_DMABUF : - GST_OMX_BUFFER_MODE_SYSTEM_MEMORY); - -#if defined (HAVE_GST_GL) - if (eglimage) { - GList *buffers = NULL; - GList *images = NULL; - gint i; - GstBufferPoolAcquireParams params = { 0, }; - gpointer egl_display = 0; - - GST_DEBUG_OBJECT (self, "Trying to allocate %d EGLImages", min); - - for (i = 0; i < min; i++) { - GstBuffer *buffer = NULL; - GstMemory *mem; - GstGLMemoryEGL *gl_mem; - - if (gst_buffer_pool_acquire_buffer (pool, &buffer, ¶ms) != GST_FLOW_OK - || gst_buffer_n_memory (buffer) != 1 - || !(mem = gst_buffer_peek_memory (buffer, 0)) - || !GST_IS_GL_MEMORY_EGL_ALLOCATOR (mem->allocator)) { - GST_INFO_OBJECT (self, "Failed to allocated %d-th EGLImage", i); - gst_buffer_replace (&buffer, NULL); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - g_list_free (images); - buffers = NULL; - images = NULL; - err = OMX_ErrorUndefined; - goto done; - } - gl_mem = (GstGLMemoryEGL *) mem; - buffers = g_list_append (buffers, buffer); - images = g_list_append (images, gst_gl_memory_egl_get_image (gl_mem)); - if (!egl_display) - egl_display = gst_gl_memory_egl_get_display (gl_mem); - } - - GST_DEBUG_OBJECT (self, "Allocated %d EGLImages successfully", min); - - /* Everything went fine? */ - if (eglimage) { - GST_DEBUG_OBJECT (self, "Setting EGLDisplay"); - port->port_def.format.video.pNativeWindow = egl_display; - err = gst_omx_port_update_port_definition (port, &port->port_def); - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to set EGLDisplay on port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - g_list_free (images); - goto done; - } else { - GList *l; - - if (min != port->port_def.nBufferCountActual) { - err = gst_omx_port_update_port_definition (port, NULL); - if (err == OMX_ErrorNone) { - port->port_def.nBufferCountActual = min; - err = gst_omx_port_update_port_definition (port, &port->port_def); - } - - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to configure %u output buffers: %s (0x%08x)", min, - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - g_list_free (images); - goto done; - } -#if OMX_VERSION_MINOR == 2 - /* In OMX-IL 1.2.0, the nBufferCountActual change is propagated to the - * the input port upon call to the SetParameter on out port above. This - * propagation triggers a SettingsChanged event. It is up to the client - * to decide if this event should lead to reconfigure the port. Here - * this is clearly informal so lets just acknowledge the event to avoid - * input port reconfiguration. Note that the SettingsChanged event will - * be sent in-context of the SetParameter call above. So the event is - * garantie to be proceeded in the handle_message call below. */ - err = gst_omx_port_mark_reconfigured (self->dec_in_port); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to acknowledge port settings changed: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - g_list_free (images); - goto done; - } -#endif - } - - if (!gst_omx_port_is_enabled (port)) { - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to enable port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - g_list_free (images); - goto done; - } - } - - err = gst_omx_port_use_eglimages (port, images); - g_list_free (images); - - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to pass EGLImages to port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - goto done; - } - - err = gst_omx_port_wait_enabled (port, 2 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to wait until port is enabled: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - goto done; - } - - GST_DEBUG_OBJECT (self, "Populating internal buffer pool"); - GST_OMX_BUFFER_POOL (self->out_port_pool)->other_pool = - GST_BUFFER_POOL (gst_object_ref (pool)); - for (l = buffers; l; l = l->next) { - g_ptr_array_add (GST_OMX_BUFFER_POOL (self->out_port_pool)->buffers, - l->data); - } - g_list_free (buffers); - /* All good and done, set caps below */ - } - } - } -#endif /* defined (HAVE_GST_GL) */ - - /* If not using EGLImage or trying to use EGLImage failed */ - if (!eglimage) { - gboolean was_enabled = TRUE; - GList *buffers = NULL; - GList *l = NULL; - - if (min != port->port_def.nBufferCountActual) { - err = gst_omx_port_update_port_definition (port, NULL); - if (err == OMX_ErrorNone) { - port->port_def.nBufferCountActual = min; - err = gst_omx_port_update_port_definition (port, &port->port_def); - } - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to configure %u output buffers: %s (0x%08x)", min, - gst_omx_error_to_string (err), err); - goto done; - } -#if OMX_VERSION_MINOR == 2 - /* In OMX-IL 1.2.0, the nBufferCountActual change is propagated to the - * the input port upon call to the SetParameter on out port above. This - * propagation triggers a SettingsChanged event. It is up to the client - * to decide if this event should lead to reconfigure the port. Here - * this is clearly informal so lets just acknowledge the event to avoid - * input port reconfiguration. Note that the SettingsChanged event will - * be sent in-context of the SetParameter call above. So the event is - * garantie to be proceeded in the handle_message call below. */ - err = gst_omx_port_mark_reconfigured (self->dec_in_port); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to acknowledge port settings changed: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto done; - } -#endif - } - - if (!gst_omx_port_is_enabled (port)) { - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to enable port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto done; - } - was_enabled = FALSE; - } - - if (!caps) - self->use_buffers = FALSE; - - if (self->use_buffers) { - GList *images = NULL; - GList *frames = NULL; - GstVideoInfo v_info; - gint i; - - if (!gst_video_info_from_caps (&v_info, caps)) { - GST_INFO_OBJECT (self, - "Failed to get video info from caps %" GST_PTR_FORMAT, caps); - err = OMX_ErrorUndefined; - self->use_buffers = FALSE; - } - - GST_DEBUG_OBJECT (self, "Trying to use %d buffers", min); - - for (i = 0; i < min && self->use_buffers; i++) { - GstBuffer *buffer = NULL; - GstVideoFrame *frame = NULL; - - buffer = - gst_omx_try_importing_buffer (self, pool, port, &v_info, i, &frame); - if (!buffer) { - /* buffer does not match minimal requirement to try OMX_UseBuffer */ - GST_DEBUG_OBJECT (self, "Failed to import %d-th buffer", i); - g_list_free (images); - g_list_free_full (frames, (GDestroyNotify) gst_video_frame_unmap); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - buffers = NULL; - images = NULL; - err = OMX_ErrorUndefined; - self->use_buffers = FALSE; - break; - } else { - /* if downstream pool is 1 n_mem then always try to use buffers - * and retry without using them if it fails */ - GstMemory *mem; - - buffers = g_list_append (buffers, buffer); - frames = g_list_append (frames, frame); - - mem = gst_buffer_peek_memory (buffer, 0); - if (self->dmabuf && gst_is_dmabuf_memory (mem)) - /* Use the imported fd rather than mapped address in dmabuf mode */ - images = - g_list_append (images, - GUINT_TO_POINTER (gst_dmabuf_memory_get_fd (mem))); - else - images = - g_list_append (images, GST_VIDEO_FRAME_PLANE_DATA (frame, 0)); - } - } - - /* buffers match minimal requirements then - * now try to actually use them */ - if (images) { - err = gst_omx_port_use_buffers (port, images); - g_list_free (images); - g_list_free_full (frames, (GDestroyNotify) gst_video_frame_unmap); - - if (err == OMX_ErrorNone) { - GST_DEBUG_OBJECT (self, "Using %d buffers", min); - } else { - GST_INFO_OBJECT (self, - "Failed to OMX_UseBuffer on port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_list_free_full (buffers, (GDestroyNotify) gst_buffer_unref); - self->use_buffers = FALSE; - } - } - } - - if (!self->use_buffers) - err = gst_omx_port_allocate_buffers (port); - - if (err != OMX_ErrorNone && min > port->port_def.nBufferCountMin) { - GST_ERROR_OBJECT (self, - "Failed to allocate required number of buffers %d, trying less and copying", - min); - min = port->port_def.nBufferCountMin; - - if (!was_enabled) { - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) { - GST_INFO_OBJECT (self, - "Failed to disable port again: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto done; - } - } - - if (min != port->port_def.nBufferCountActual) { - err = gst_omx_port_update_port_definition (port, NULL); - if (err == OMX_ErrorNone) { - port->port_def.nBufferCountActual = min; - err = gst_omx_port_update_port_definition (port, &port->port_def); - } - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to configure %u output buffers: %s (0x%08x)", min, - gst_omx_error_to_string (err), err); - goto done; - } - } - - err = gst_omx_port_allocate_buffers (port); - - /* Can't provide buffers downstream in this case */ - gst_caps_replace (&caps, NULL); - } - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to allocate %d buffers: %s (0x%08x)", min, - gst_omx_error_to_string (err), err); - goto done; - } - - if (!was_enabled) { - err = gst_omx_port_wait_enabled (port, 2 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to wait until port is enabled: %s (0x%08x)", - gst_omx_error_to_string (err), err); - goto done; - } - } - - if (self->use_buffers) { - GST_DEBUG_OBJECT (self, "Populating internal buffer pool"); - GST_OMX_BUFFER_POOL (self->out_port_pool)->other_pool = - GST_BUFFER_POOL (gst_object_ref (pool)); - for (l = buffers; l; l = l->next) { - g_ptr_array_add (GST_OMX_BUFFER_POOL (self->out_port_pool)->buffers, - l->data); - } - g_list_free (buffers); - } - - } - - err = OMX_ErrorNone; - - if (caps) { - config = gst_buffer_pool_get_config (self->out_port_pool); - - if (add_videometa) - gst_buffer_pool_config_add_option (config, - GST_BUFFER_POOL_OPTION_VIDEO_META); - - gst_buffer_pool_config_set_params (config, caps, - self->dec_out_port->port_def.nBufferSize, min, max); - - if (!gst_buffer_pool_set_config (self->out_port_pool, config)) { - GST_INFO_OBJECT (self, "Failed to set config on internal pool"); - gst_object_unref (self->out_port_pool); - self->out_port_pool = NULL; - goto done; - } - - /* This now allocates all the buffers */ - if (!gst_buffer_pool_set_active (self->out_port_pool, TRUE)) { - GST_INFO_OBJECT (self, "Failed to activate internal pool"); - gst_object_unref (self->out_port_pool); - self->out_port_pool = NULL; - } else if (!self->use_buffers) { - gst_buffer_pool_set_active (pool, FALSE); - } - } else if (self->out_port_pool) { - gst_object_unref (self->out_port_pool); - self->out_port_pool = NULL; - } - -done: - if (!self->out_port_pool && err == OMX_ErrorNone) - GST_DEBUG_OBJECT (self, - "Not using our internal pool and copying buffers for downstream"); - - if (caps) - gst_caps_unref (caps); - if (pool) - gst_object_unref (pool); - if (state) - gst_video_codec_state_unref (state); - - return err; -} - -static gboolean -gst_omx_video_dec_deallocate_output_buffers (GstOMXVideoDec * self) -{ - if (self->out_port_pool) { - /* Pool will free buffers when stopping */ - gst_buffer_pool_set_active (self->out_port_pool, FALSE); -#if 0 - gst_buffer_pool_wait_released (self->out_port_pool); -#endif - GST_OMX_BUFFER_POOL (self->out_port_pool)->deactivated = TRUE; - gst_object_unref (self->out_port_pool); - self->out_port_pool = NULL; - } else { - OMX_ERRORTYPE err; - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - err = - gst_omx_port_deallocate_buffers (self->eglimage ? self-> - egl_out_port : self->dec_out_port); -#else - err = gst_omx_port_deallocate_buffers (self->dec_out_port); -#endif - - return err == OMX_ErrorNone; - } - - return TRUE; -} - -static GstVideoInterlaceMode -gst_omx_video_dec_get_output_interlace_info (GstOMXVideoDec * self) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - OMX_ERRORTYPE err; - OMX_ALG_COMMON_PARAM_SEQUENCE_PICTURE_MODE seq_pic_mode; - - GST_OMX_INIT_STRUCT (&seq_pic_mode); - seq_pic_mode.nPortIndex = self->dec_out_port->index; - - err = gst_omx_component_get_parameter (self->dec, - (OMX_INDEXTYPE) OMX_ALG_IndexParamCommonSequencePictureModeCurrent, - &seq_pic_mode); - - if (err != OMX_ErrorNone) { - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Picture sequence mode not supported by the component"); - } else { - GST_DEBUG_OBJECT (self, - "Failed to get picture sequence mode: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - return GST_VIDEO_INTERLACE_MODE_PROGRESSIVE; - } - - if (seq_pic_mode.eMode == OMX_ALG_SEQUENCE_PICTURE_FIELD) { - GST_DEBUG_OBJECT (self, "Decoding interlaced video frames"); - return GST_VIDEO_INTERLACE_MODE_ALTERNATE; - } else if (seq_pic_mode.eMode == OMX_ALG_SEQUENCE_PICTURE_FRAME) { - GST_DEBUG_OBJECT (self, "Decoding progressive video frames"); - return GST_VIDEO_INTERLACE_MODE_PROGRESSIVE; - } else { - GST_ERROR_OBJECT (self, "Unsupported interlace format: (0x%08x)", - seq_pic_mode.eMode); - return GST_VIDEO_INTERLACE_MODE_PROGRESSIVE; - } - -#endif - return GST_VIDEO_INTERLACE_MODE_PROGRESSIVE; -} - -#if defined (HAVE_GST_GL) -static void -add_caps_gl_memory_feature (GstCaps * caps) -{ - GstCapsFeatures *old, *features; - - features = gst_caps_features_new_empty (); - old = gst_caps_get_features (caps, 0); - - if (old) { - guint i; - - /* Copy the existing features ignoring memory ones as we are changing - * it to GL. */ - for (i = 0; i < gst_caps_features_get_size (old); i++) { - const gchar *f = gst_caps_features_get_nth (old, i); - - if (!g_str_has_prefix (f, "memory:")) - gst_caps_features_add (features, f); - } - } - - gst_caps_features_add (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY); - gst_caps_set_features (caps, 0, features); -} -#endif - -static OMX_ERRORTYPE -gst_omx_video_dec_reconfigure_output_port (GstOMXVideoDec * self) -{ - GstOMXPort *port; - OMX_ERRORTYPE err; - GstVideoCodecState *state; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - GstVideoFormat format; - GstVideoInterlaceMode interlace_mode; - guint frame_height; - - /* At this point the decoder output port is disabled */ - interlace_mode = gst_omx_video_dec_get_output_interlace_info (self); - -#if defined (HAVE_GST_GL) - { -#if defined (USE_OMX_TARGET_RPI) - OMX_STATETYPE egl_state; -#endif - - if (self->eglimage) { - /* Nothing to do here, we could however fall back to non-EGLImage in theory */ -#if defined (USE_OMX_TARGET_RPI) - port = self->egl_out_port; -#else - port = self->dec_out_port; -#endif - err = OMX_ErrorNone; - goto enable_port; - } else { - /* Set up egl_render */ - - self->eglimage = TRUE; - - gst_omx_port_get_port_definition (self->dec_out_port, &port_def); - GST_VIDEO_DECODER_STREAM_LOCK (self); - - frame_height = port_def.format.video.nFrameHeight; - /* OMX's frame height is actually the field height in alternate mode - * while it's always the full frame height in gst. */ - if (interlace_mode == GST_VIDEO_INTERLACE_MODE_ALTERNATE || - interlace_mode == GST_VIDEO_INTERLACE_MODE_INTERLEAVED) { - frame_height *= 2; - /* Decoder outputs interlaced content using the alternate mode */ - interlace_mode = GST_VIDEO_INTERLACE_MODE_ALTERNATE; - } - - state = - gst_video_decoder_set_interlaced_output_state (GST_VIDEO_DECODER - (self), GST_VIDEO_FORMAT_RGBA, interlace_mode, - port_def.format.video.nFrameWidth, frame_height, self->input_state); - - /* at this point state->caps is NULL */ - if (state->caps) - gst_caps_unref (state->caps); - state->caps = gst_video_info_to_caps (&state->info); - add_caps_gl_memory_feature (state->caps); - - /* try to negotiate with caps feature */ - if (!gst_video_decoder_negotiate (GST_VIDEO_DECODER (self))) { - - GST_DEBUG_OBJECT (self, - "Failed to negotiate with feature %s", - GST_CAPS_FEATURE_MEMORY_GL_MEMORY); - - if (state->caps) - gst_caps_replace (&state->caps, NULL); - -#if defined (USE_OMX_TARGET_RPI) - /* fallback: try to use EGLImage even if it is not in the caps feature */ - if (!gst_video_decoder_negotiate (GST_VIDEO_DECODER (self))) { - gst_video_codec_state_unref (state); - GST_DEBUG_OBJECT (self, "Failed to negotiate RGBA for EGLImage"); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - goto no_egl; - } -#else - gst_video_codec_state_unref (state); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - goto no_egl; -#endif - } - - gst_video_codec_state_unref (state); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - -#if defined (USE_OMX_TARGET_RPI) - /* Now link it all together */ - - err = gst_omx_port_set_enabled (self->egl_in_port, FALSE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_wait_enabled (self->egl_in_port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_set_enabled (self->egl_out_port, FALSE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_wait_enabled (self->egl_out_port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto no_egl; - - { -#define OMX_IndexParamBrcmVideoEGLRenderDiscardMode 0x7f0000db - OMX_CONFIG_PORTBOOLEANTYPE discardMode; - memset (&discardMode, 0, sizeof (discardMode)); - discardMode.nSize = sizeof (discardMode); - discardMode.nPortIndex = 220; - discardMode.nVersion.nVersion = OMX_VERSION; - discardMode.bEnabled = OMX_FALSE; - if (gst_omx_component_set_parameter (self->egl_render, - OMX_IndexParamBrcmVideoEGLRenderDiscardMode, - &discardMode) != OMX_ErrorNone) - goto no_egl; -#undef OMX_IndexParamBrcmVideoEGLRenderDiscardMode - } - - err = gst_omx_setup_tunnel (self->dec_out_port, self->egl_in_port); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_set_enabled (self->egl_in_port, TRUE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_component_set_state (self->egl_render, OMX_StateIdle); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_wait_enabled (self->egl_in_port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto no_egl; - - if (gst_omx_component_get_state (self->egl_render, - GST_CLOCK_TIME_NONE) != OMX_StateIdle) - goto no_egl; - - err = gst_omx_video_dec_allocate_output_buffers (self); - if (err != OMX_ErrorNone) - goto no_egl; - - if (gst_omx_component_set_state (self->egl_render, - OMX_StateExecuting) != OMX_ErrorNone) - goto no_egl; - - if (gst_omx_component_get_state (self->egl_render, - GST_CLOCK_TIME_NONE) != OMX_StateExecuting) - goto no_egl; - - err = - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, FALSE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = - gst_omx_port_set_flushing (self->egl_in_port, 5 * GST_SECOND, FALSE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = - gst_omx_port_set_flushing (self->egl_out_port, 5 * GST_SECOND, FALSE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_populate (self->egl_out_port); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_set_enabled (self->dec_out_port, TRUE); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_wait_enabled (self->dec_out_port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto no_egl; - - - err = gst_omx_port_mark_reconfigured (self->dec_out_port); - if (err != OMX_ErrorNone) - goto no_egl; - - err = gst_omx_port_mark_reconfigured (self->egl_out_port); - if (err != OMX_ErrorNone) - goto no_egl; - - goto done; -#else - port = self->dec_out_port; - err = OMX_ErrorNone; - goto enable_port; -#endif /* defined (USE_OMX_TARGET_RPI) */ - } - - no_egl: - -#if defined (USE_OMX_TARGET_RPI) - gst_omx_port_set_enabled (self->dec_out_port, FALSE); - gst_omx_port_wait_enabled (self->dec_out_port, 1 * GST_SECOND); - egl_state = gst_omx_component_get_state (self->egl_render, 0); - if (egl_state > OMX_StateLoaded || egl_state == OMX_StateInvalid) { - if (egl_state > OMX_StateIdle) { - gst_omx_component_set_state (self->egl_render, OMX_StateIdle); - gst_omx_component_get_state (self->egl_render, 5 * GST_SECOND); - } - gst_omx_component_set_state (self->egl_render, OMX_StateLoaded); - - gst_omx_video_dec_deallocate_output_buffers (self); - gst_omx_close_tunnel (self->dec_out_port, self->egl_in_port); - - if (egl_state > OMX_StateLoaded) { - gst_omx_component_get_state (self->egl_render, 5 * GST_SECOND); - } - } -#endif - - /* After this egl_render should be deactivated - * and the decoder's output port disabled */ - self->eglimage = FALSE; - } -#endif /* defined (HAVE_GST_GL) */ - - port = self->dec_out_port; - - /* Update caps */ - GST_VIDEO_DECODER_STREAM_LOCK (self); - - gst_omx_port_get_port_definition (port, &port_def); - g_assert (port_def.format.video.eCompressionFormat == OMX_VIDEO_CodingUnused); - - format = - gst_omx_video_get_format_from_omx (port_def.format.video.eColorFormat); - - if (format == GST_VIDEO_FORMAT_UNKNOWN) { - GST_ERROR_OBJECT (self, "Unsupported color format: %d", - port_def.format.video.eColorFormat); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - err = OMX_ErrorUndefined; - goto done; - } - - frame_height = port_def.format.video.nFrameHeight; - /* OMX's frame height is actually the field height in alternate mode - * while it's always the full frame height in gst. */ - if (interlace_mode == GST_VIDEO_INTERLACE_MODE_ALTERNATE || - interlace_mode == GST_VIDEO_INTERLACE_MODE_INTERLEAVED) { - frame_height *= 2; - /* Decoder outputs interlaced content using the alternate mode */ - interlace_mode = GST_VIDEO_INTERLACE_MODE_ALTERNATE; - } - - GST_DEBUG_OBJECT (self, - "Setting output state: format %s (%d), width %u, height %u", - gst_video_format_to_string (format), - port_def.format.video.eColorFormat, - (guint) port_def.format.video.nFrameWidth, frame_height); - - state = - gst_video_decoder_set_interlaced_output_state (GST_VIDEO_DECODER (self), - format, interlace_mode, port_def.format.video.nFrameWidth, - frame_height, self->input_state); - - if (!gst_video_decoder_negotiate (GST_VIDEO_DECODER (self))) { - gst_video_codec_state_unref (state); - GST_ERROR_OBJECT (self, "Failed to negotiate"); - err = OMX_ErrorUndefined; - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - goto done; - } - - gst_video_codec_state_unref (state); - - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - -#if defined (HAVE_GST_GL) -enable_port: -#endif - - err = gst_omx_video_dec_allocate_output_buffers (self); - if (err != OMX_ErrorNone) { -#if defined (HAVE_GST_GL) - /* TODO: works on desktop but need to try on RPI. */ -#if !defined (USE_OMX_TARGET_RPI) - if (self->eglimage) { - GST_INFO_OBJECT (self, "Fallback to non eglimage"); - goto no_egl; - } -#endif -#endif - goto done; - } - - err = gst_omx_port_populate (port); - if (err != OMX_ErrorNone) - goto done; - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) - goto done; - -done: - - return err; -} - -static void -gst_omx_video_dec_clean_older_frames (GstOMXVideoDec * self, - GstOMXBuffer * buf, GList * frames) -{ - GList *l; - GstClockTime timestamp; - - timestamp = - gst_util_uint64_scale (GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp), - GST_SECOND, OMX_TICKS_PER_SECOND); - - if (GST_CLOCK_TIME_IS_VALID (timestamp)) { - /* We could release all frames stored with pts < timestamp since the - * decoder will likely output frames in display order */ - for (l = frames; l; l = l->next) { - GstVideoCodecFrame *tmp = l->data; - - if (tmp->pts < timestamp) { - GST_LOG_OBJECT (self, - "discarding ghost frame %p (#%d) PTS:%" GST_TIME_FORMAT " DTS:%" - GST_TIME_FORMAT, tmp, tmp->system_frame_number, - GST_TIME_ARGS (tmp->pts), GST_TIME_ARGS (tmp->dts)); - gst_video_decoder_release_frame (GST_VIDEO_DECODER (self), tmp); - } else { - gst_video_codec_frame_unref (tmp); - } - } - } else { - /* We will release all frames with invalid timestamp because we don't even - * know if they will be output some day. */ - for (l = frames; l; l = l->next) { - GstVideoCodecFrame *tmp = l->data; - - if (!GST_CLOCK_TIME_IS_VALID (tmp->pts)) { - GST_LOG_OBJECT (self, - "discarding frame %p (#%d) with invalid PTS:%" GST_TIME_FORMAT - " DTS:%" GST_TIME_FORMAT, tmp, tmp->system_frame_number, - GST_TIME_ARGS (tmp->pts), GST_TIME_ARGS (tmp->dts)); - gst_video_decoder_release_frame (GST_VIDEO_DECODER (self), tmp); - } else { - gst_video_codec_frame_unref (tmp); - } - } - } - - g_list_free (frames); -} - -/* copy_frame() will consume @outpuf resulting in the buffer being released to - * the pool and so reset fields such as outbuf->omx_buf->nFlags. - * Make sure to handle them all before. */ -static GstBuffer * -copy_frame (const GstVideoInfo * info, GstBuffer * outbuf) -{ - GstVideoInfo out_info, tmp_info; - GstBuffer *tmpbuf; - GstVideoFrame out_frame, tmp_frame; - - out_info = *info; - tmp_info = *info; - - tmpbuf = gst_buffer_new_and_alloc (out_info.size); - - gst_video_frame_map (&out_frame, &out_info, outbuf, GST_MAP_READ); - gst_video_frame_map (&tmp_frame, &tmp_info, tmpbuf, GST_MAP_WRITE); - gst_video_frame_copy (&tmp_frame, &out_frame); - gst_video_frame_unmap (&out_frame); - gst_video_frame_unmap (&tmp_frame); - - /* Use gst_video_frame_copy() to copy the content of the buffer so it - * will handle the stride/offset/etc from the source buffer. - * It doesn't copy buffer flags so do it manually. */ - gst_buffer_copy_into (tmpbuf, outbuf, GST_BUFFER_COPY_FLAGS, 0, -1); - - gst_buffer_unref (outbuf); - - return tmpbuf; -} - -static void -gst_omx_video_dec_pause_loop (GstOMXVideoDec * self, GstFlowReturn flow_ret) -{ - g_mutex_lock (&self->drain_lock); - if (self->draining) { - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - } - gst_pad_pause_task (GST_VIDEO_DECODER_SRC_PAD (self)); - self->downstream_flow_ret = flow_ret; - self->started = FALSE; - g_mutex_unlock (&self->drain_lock); -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static void -set_outbuffer_interlace_flags (GstOMXBuffer * buf, GstBuffer * outbuf) -{ - if (buf->omx_buf->nFlags & OMX_ALG_BUFFERFLAG_TOP_FIELD) { - GST_BUFFER_FLAG_SET (outbuf, GST_VIDEO_BUFFER_FLAG_TOP_FIELD); - } else if (buf->omx_buf->nFlags & OMX_ALG_BUFFERFLAG_BOT_FIELD) { - GST_BUFFER_FLAG_SET (outbuf, GST_VIDEO_BUFFER_FLAG_BOTTOM_FIELD); - } -} -#endif // USE_OMX_TARGET_ZYNQ_USCALE_PLUS - -static void -gst_omx_video_dec_loop (GstOMXVideoDec * self) -{ - GstOMXPort *port; - GstOMXBuffer *buf = NULL; - GstVideoCodecFrame *frame; - GstFlowReturn flow_ret = GST_FLOW_OK; - GstOMXAcquireBufferReturn acq_return; - OMX_ERRORTYPE err; - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - port = self->eglimage ? self->egl_out_port : self->dec_out_port; -#else - port = self->dec_out_port; -#endif - - acq_return = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - if (acq_return == GST_OMX_ACQUIRE_BUFFER_ERROR) { - goto component_error; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - goto flushing; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_EOS) { - goto eos; - } - - if (!gst_pad_has_current_caps (GST_VIDEO_DECODER_SRC_PAD (self)) || - acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - GstVideoCodecState *state; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - GstVideoFormat format; - - GST_DEBUG_OBJECT (self, "Port settings have changed, updating caps"); - - /* Reallocate all buffers */ - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE - && gst_omx_port_is_enabled (port)) { - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - if (!gst_omx_video_dec_deallocate_output_buffers (self)) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } - - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - /* We have the possibility to reconfigure everything now */ - err = gst_omx_video_dec_reconfigure_output_port (self); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } else { - GstVideoInterlaceMode interlace_mode; - - /* Just update caps */ - GST_VIDEO_DECODER_STREAM_LOCK (self); - - gst_omx_port_get_port_definition (port, &port_def); - g_assert (port_def.format.video.eCompressionFormat == - OMX_VIDEO_CodingUnused); - - format = - gst_omx_video_get_format_from_omx (port_def.format.video. - eColorFormat); - - if (format == GST_VIDEO_FORMAT_UNKNOWN) { - GST_ERROR_OBJECT (self, "Unsupported color format: %d", - port_def.format.video.eColorFormat); - if (buf) - gst_omx_port_release_buffer (port, buf); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - goto caps_failed; - } - - GST_DEBUG_OBJECT (self, - "Setting output state: format %s (%d), width %u, height %u", - gst_video_format_to_string (format), - port_def.format.video.eColorFormat, - (guint) port_def.format.video.nFrameWidth, - (guint) port_def.format.video.nFrameHeight); - interlace_mode = gst_omx_video_dec_get_output_interlace_info (self); - - state = - gst_video_decoder_set_interlaced_output_state (GST_VIDEO_DECODER - (self), format, interlace_mode, port_def.format.video.nFrameWidth, - port_def.format.video.nFrameHeight, self->input_state); - - /* Take framerate and pixel-aspect-ratio from sinkpad caps */ - - if (!gst_video_decoder_negotiate (GST_VIDEO_DECODER (self))) { - if (buf) - gst_omx_port_release_buffer (port, buf); - gst_video_codec_state_unref (state); - goto caps_failed; - } - - gst_video_codec_state_unref (state); - - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - } - - /* Now get a buffer */ - if (acq_return != GST_OMX_ACQUIRE_BUFFER_OK) { - return; - } - } - - g_assert (acq_return == GST_OMX_ACQUIRE_BUFFER_OK); - - /* This prevents a deadlock between the srcpad stream - * lock and the videocodec stream lock, if ::reset() - * is called at the wrong time - */ - if (gst_omx_port_is_flushing (port)) { - GST_DEBUG_OBJECT (self, "Flushing"); - gst_omx_port_release_buffer (port, buf); - goto flushing; - } - - GST_DEBUG_OBJECT (self, "Handling buffer: 0x%08x (%s) %" G_GUINT64_FORMAT, - (guint) buf->omx_buf->nFlags, - gst_omx_buffer_flags_to_string (buf->omx_buf->nFlags), - (guint64) GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp)); - - frame = gst_omx_video_find_nearest_frame (GST_ELEMENT_CAST (self), buf, - gst_video_decoder_get_frames (GST_VIDEO_DECODER (self))); - - /* So we have a timestamped OMX buffer and get, or not, corresponding frame. - * Assuming decoder output frames in display order, frames preceding this - * frame could be discarded as they seems useless due to e.g interlaced - * stream, corrupted input data... - * In any cases, not likely to be seen again. so drop it before they pile up - * and use all the memory. */ - gst_omx_video_dec_clean_older_frames (self, buf, - gst_video_decoder_get_frames (GST_VIDEO_DECODER (self))); - - if (!frame && (buf->omx_buf->nFilledLen > 0 || buf->eglimage)) { - GstBuffer *outbuf = NULL; - - /* This sometimes happens at EOS or if the input is not properly framed, - * let's handle it gracefully by allocating a new buffer for the current - * caps and filling it - */ - - GST_ERROR_OBJECT (self, "No corresponding frame found"); - - if (self->out_port_pool) { - gint i, n; - GstBufferPoolAcquireParams params = { 0, }; - - n = port->buffers->len; - for (i = 0; i < n; i++) { - GstOMXBuffer *tmp = g_ptr_array_index (port->buffers, i); - - if (tmp == buf) - break; - } - g_assert (i != n); - - GST_OMX_BUFFER_POOL (self->out_port_pool)->current_buffer_index = i; - flow_ret = - gst_buffer_pool_acquire_buffer (self->out_port_pool, &outbuf, - ¶ms); - if (flow_ret != GST_FLOW_OK) { - gst_omx_port_release_buffer (port, buf); - goto invalid_buffer; - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - set_outbuffer_interlace_flags (buf, outbuf); -#endif - - if (GST_OMX_BUFFER_POOL (self->out_port_pool)->need_copy) - outbuf = - copy_frame (&GST_OMX_BUFFER_POOL (self->out_port_pool)->video_info, - outbuf); - - buf = NULL; - } else { - outbuf = - gst_video_decoder_allocate_output_buffer (GST_VIDEO_DECODER (self)); - if (!gst_omx_video_dec_fill_buffer (self, buf, outbuf)) { - gst_buffer_unref (outbuf); - gst_omx_port_release_buffer (port, buf); - goto invalid_buffer; - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - set_outbuffer_interlace_flags (buf, outbuf); -#endif - } - - flow_ret = gst_pad_push (GST_VIDEO_DECODER_SRC_PAD (self), outbuf); - } else if (buf->omx_buf->nFilledLen > 0 || buf->eglimage) { - if (self->out_port_pool) { - gint i, n; - GstBuffer *outbuf; - GstBufferPoolAcquireParams params = { 0, }; - - n = port->buffers->len; - for (i = 0; i < n; i++) { - GstOMXBuffer *tmp = g_ptr_array_index (port->buffers, i); - - if (tmp == buf) - break; - } - g_assert (i != n); - - GST_OMX_BUFFER_POOL (self->out_port_pool)->current_buffer_index = i; - flow_ret = - gst_buffer_pool_acquire_buffer (self->out_port_pool, - &outbuf, ¶ms); - if (flow_ret != GST_FLOW_OK) { - flow_ret = - gst_video_decoder_drop_frame (GST_VIDEO_DECODER (self), frame); - frame = NULL; - gst_omx_port_release_buffer (port, buf); - goto invalid_buffer; - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - set_outbuffer_interlace_flags (buf, outbuf); -#endif - - if (GST_OMX_BUFFER_POOL (self->out_port_pool)->need_copy) - outbuf = - copy_frame (&GST_OMX_BUFFER_POOL (self->out_port_pool)->video_info, - outbuf); - - frame->output_buffer = outbuf; - - flow_ret = - gst_video_decoder_finish_frame (GST_VIDEO_DECODER (self), frame); - frame = NULL; - buf = NULL; - } else { - if ((flow_ret = - gst_video_decoder_allocate_output_frame (GST_VIDEO_DECODER - (self), frame)) == GST_FLOW_OK) { - /* FIXME: This currently happens because of a race condition too. - * We first need to reconfigure the output port and then the input - * port if both need reconfiguration. - */ - if (!gst_omx_video_dec_fill_buffer (self, buf, frame->output_buffer)) { - gst_buffer_replace (&frame->output_buffer, NULL); - flow_ret = - gst_video_decoder_drop_frame (GST_VIDEO_DECODER (self), frame); - frame = NULL; - gst_omx_port_release_buffer (port, buf); - goto invalid_buffer; - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - set_outbuffer_interlace_flags (buf, frame->output_buffer); -#endif - - flow_ret = - gst_video_decoder_finish_frame (GST_VIDEO_DECODER (self), frame); - frame = NULL; - } - } - } else if (frame != NULL) { - /* Just ignore empty buffers, don't drop a frame for that */ - flow_ret = GST_FLOW_OK; - gst_video_codec_frame_unref (frame); - frame = NULL; - } - - GST_DEBUG_OBJECT (self, "Finished frame: %s", gst_flow_get_name (flow_ret)); - - if (buf) { - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - } - - GST_VIDEO_DECODER_STREAM_LOCK (self); - self->downstream_flow_ret = flow_ret; - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - return; - -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec))); - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_dec_pause_loop (self, GST_FLOW_ERROR); - return; - } - -flushing: - { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - gst_omx_video_dec_pause_loop (self, GST_FLOW_FLUSHING); - return; - } - -eos: - { - g_mutex_lock (&self->drain_lock); - if (self->draining) { - GstQuery *query = gst_query_new_drain (); - - /* Drain the pipeline to reclaim all memories back to the pool */ - if (!gst_pad_peer_query (GST_VIDEO_DECODER_SRC_PAD (self), query)) - GST_DEBUG_OBJECT (self, "drain query failed"); - gst_query_unref (query); - - GST_DEBUG_OBJECT (self, "Drained"); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - flow_ret = GST_FLOW_OK; - gst_pad_pause_task (GST_VIDEO_DECODER_SRC_PAD (self)); - } else { - GST_DEBUG_OBJECT (self, "Component signalled EOS"); - flow_ret = GST_FLOW_EOS; - } - g_mutex_unlock (&self->drain_lock); - - GST_VIDEO_DECODER_STREAM_LOCK (self); - self->downstream_flow_ret = flow_ret; - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - - /* Here we fallback and pause the task for the EOS case */ - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - return; - } - -flow_error: - { - if (flow_ret == GST_FLOW_EOS) { - GST_DEBUG_OBJECT (self, "EOS"); - - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), - gst_event_new_eos ()); - } else if (flow_ret < GST_FLOW_EOS) { - GST_ELEMENT_ERROR (self, STREAM, FAILED, - ("Internal data stream error."), ("stream stopped, reason %s", - gst_flow_get_name (flow_ret))); - - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), - gst_event_new_eos ()); - } else if (flow_ret == GST_FLOW_FLUSHING) { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - } - gst_omx_video_dec_pause_loop (self, flow_ret); - return; - } - -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure output port")); - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_dec_pause_loop (self, GST_FLOW_ERROR); - return; - } - -invalid_buffer: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Invalid sized input buffer")); - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_dec_pause_loop (self, GST_FLOW_NOT_NEGOTIATED); - return; - } - -caps_failed: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), ("Failed to set caps")); - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_dec_pause_loop (self, GST_FLOW_NOT_NEGOTIATED); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - return; - } -release_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase output buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - gst_pad_push_event (GST_VIDEO_DECODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_dec_pause_loop (self, GST_FLOW_ERROR); - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - return; - } -} - -static gboolean -gst_omx_video_dec_start (GstVideoDecoder * decoder) -{ - GstOMXVideoDec *self; - - self = GST_OMX_VIDEO_DEC (decoder); - - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - self->use_buffers = FALSE; - - return TRUE; -} - -static gboolean -gst_omx_video_dec_stop (GstVideoDecoder * decoder) -{ - GstOMXVideoDec *self; - - self = GST_OMX_VIDEO_DEC (decoder); - - GST_DEBUG_OBJECT (self, "Stopping decoder"); - - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - gst_omx_port_set_flushing (self->egl_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->egl_out_port, 5 * GST_SECOND, TRUE); -#endif - - gst_pad_stop_task (GST_VIDEO_DECODER_SRC_PAD (decoder)); - - if (gst_omx_component_get_state (self->dec, 0) > OMX_StateIdle) - gst_omx_component_set_state (self->dec, OMX_StateIdle); -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (gst_omx_component_get_state (self->egl_render, 0) > OMX_StateIdle) - gst_omx_component_set_state (self->egl_render, OMX_StateIdle); -#endif - - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - - gst_omx_component_get_state (self->dec, 5 * GST_SECOND); -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - gst_omx_component_get_state (self->egl_render, 1 * GST_SECOND); -#endif - - gst_buffer_replace (&self->codec_data, NULL); - - if (self->input_state) - gst_video_codec_state_unref (self->input_state); - self->input_state = NULL; - - GST_DEBUG_OBJECT (self, "Stopped decoder"); - - return TRUE; -} - -static gboolean -gst_omx_video_dec_negotiate (GstOMXVideoDec * self) -{ - OMX_VIDEO_PARAM_PORTFORMATTYPE param; - OMX_ERRORTYPE err; - GstCaps *comp_supported_caps; - GList *negotiation_map = NULL, *l; - GstCaps *templ_caps, *intersection; - GstVideoFormat format; - GstStructure *s; - const gchar *format_str; - - GST_DEBUG_OBJECT (self, "Trying to negotiate a video format with downstream"); - - templ_caps = gst_pad_get_pad_template_caps (GST_VIDEO_DECODER_SRC_PAD (self)); - intersection = - gst_pad_peer_query_caps (GST_VIDEO_DECODER_SRC_PAD (self), templ_caps); - gst_caps_unref (templ_caps); - - GST_DEBUG_OBJECT (self, "Allowed downstream caps: %" GST_PTR_FORMAT, - intersection); - - negotiation_map = - gst_omx_video_get_supported_colorformats (self->dec_out_port, - self->input_state); - - comp_supported_caps = gst_omx_video_get_caps_for_map (negotiation_map); - - GST_DEBUG_OBJECT (self, "Decoder supported caps: %" GST_PTR_FORMAT, - comp_supported_caps); - - if (!gst_caps_is_empty (comp_supported_caps)) { - GstCaps *tmp; - - tmp = gst_caps_intersect (comp_supported_caps, intersection); - gst_caps_unref (intersection); - intersection = tmp; - } - gst_caps_unref (comp_supported_caps); - - if (gst_caps_is_empty (intersection)) { - gst_caps_unref (intersection); - GST_ERROR_OBJECT (self, "Empty caps"); - g_list_free_full (negotiation_map, - (GDestroyNotify) gst_omx_video_negotiation_map_free); - return FALSE; - } - - intersection = gst_caps_truncate (intersection); - intersection = gst_caps_fixate (intersection); - - s = gst_caps_get_structure (intersection, 0); - format_str = gst_structure_get_string (s, "format"); - if (!format_str || - (format = - gst_video_format_from_string (format_str)) == - GST_VIDEO_FORMAT_UNKNOWN) { - GST_ERROR_OBJECT (self, "Invalid caps: %" GST_PTR_FORMAT, intersection); - gst_caps_unref (intersection); - g_list_free_full (negotiation_map, - (GDestroyNotify) gst_omx_video_negotiation_map_free); - return FALSE; - } - - GST_OMX_INIT_STRUCT (¶m); - param.nPortIndex = self->dec_out_port->index; - - err = gst_omx_component_get_parameter (self->dec, - OMX_IndexParamVideoPortFormat, ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to get video port format: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - for (l = negotiation_map; l; l = l->next) { - GstOMXVideoNegotiationMap *m = l->data; - - if (m->format == format) { - param.eColorFormat = m->type; - break; - } - } - - GST_DEBUG_OBJECT (self, "Negotiating color format %s (%d)", format_str, - param.eColorFormat); - - /* We must find something here */ - g_assert (l != NULL); - g_list_free_full (negotiation_map, - (GDestroyNotify) gst_omx_video_negotiation_map_free); - - err = - gst_omx_component_set_parameter (self->dec, - OMX_IndexParamVideoPortFormat, ¶m); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to set video port format: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - gst_caps_unref (intersection); - return (err == OMX_ErrorNone); -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static void -gst_omx_video_dec_set_latency (GstOMXVideoDec * self) -{ - GstClockTime latency; - OMX_ALG_PARAM_REPORTED_LATENCY param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - err = - gst_omx_component_get_parameter (self->dec, - (OMX_INDEXTYPE) OMX_ALG_IndexParamReportedLatency, ¶m); - - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't retrieve latency: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return; - } - - GST_DEBUG_OBJECT (self, "retrieved latency of %d ms", - (guint32) param.nLatency); - - /* Convert to ns */ - latency = param.nLatency * GST_MSECOND; - - gst_video_decoder_set_latency (GST_VIDEO_DECODER (self), latency, latency); -} -#endif - -static gboolean -gst_omx_video_dec_disable (GstOMXVideoDec * self) -{ - GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (self); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - GstOMXPort *out_port = - self->eglimage ? self->egl_out_port : self->dec_out_port; -#else - GstOMXPort *out_port = self->dec_out_port; -#endif - - GST_DEBUG_OBJECT (self, "Need to disable and drain decoder"); - - gst_omx_video_dec_drain (GST_VIDEO_DECODER (self)); - gst_omx_port_set_flushing (out_port, 5 * GST_SECOND, TRUE); - - if (klass->cdata.hacks & GST_OMX_HACK_NO_COMPONENT_RECONFIGURE) { - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - gst_omx_video_dec_stop (GST_VIDEO_DECODER (self)); - gst_omx_video_dec_close (GST_VIDEO_DECODER (self)); - GST_VIDEO_DECODER_STREAM_LOCK (self); - - if (!gst_omx_video_dec_open (GST_VIDEO_DECODER (self))) - return FALSE; - - self->disabled = FALSE; - } else { -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->eglimage) { - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->egl_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->egl_out_port, 5 * GST_SECOND, TRUE); - } -#endif - - /* Disabling at the same time input port and output port is only - * required when a buffer is shared between the ports. This cannot - * be the case for a decoder because its input and output buffers - * are of different nature. So let's disable ports sequencially. - * Starting from IL 1.2.0, this point has been clarified. - * OMX_SendCommand will return an error if the IL client attempts to - * call it when there is already an on-going command being processed. - * The exception is for buffer sharing above and the event - * OMX_EventPortNeedsDisable will be sent to request disabling the - * other port at the same time. */ - if (gst_omx_port_set_enabled (self->dec_in_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (self->dec_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_deallocate_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_enabled (self->dec_in_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_set_enabled (out_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (!gst_omx_video_dec_deallocate_output_buffers (self)) - return FALSE; - if (gst_omx_port_wait_enabled (out_port, 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->eglimage) { - OMX_STATETYPE egl_state; - - egl_state = gst_omx_component_get_state (self->egl_render, 0); - if (egl_state > OMX_StateLoaded || egl_state == OMX_StateInvalid) { - - if (egl_state > OMX_StateIdle) { - gst_omx_component_set_state (self->egl_render, OMX_StateIdle); - gst_omx_component_set_state (self->dec, OMX_StateIdle); - egl_state = gst_omx_component_get_state (self->egl_render, - 5 * GST_SECOND); - gst_omx_component_get_state (self->dec, 1 * GST_SECOND); - } - gst_omx_component_set_state (self->egl_render, OMX_StateLoaded); - gst_omx_component_set_state (self->dec, OMX_StateLoaded); - - gst_omx_close_tunnel (self->dec_out_port, self->egl_in_port); - - if (egl_state > OMX_StateLoaded) { - gst_omx_component_get_state (self->egl_render, 5 * GST_SECOND); - } - - gst_omx_component_set_state (self->dec, OMX_StateIdle); - - gst_omx_component_set_state (self->dec, OMX_StateExecuting); - gst_omx_component_get_state (self->dec, GST_CLOCK_TIME_NONE); - } - self->eglimage = FALSE; - } -#endif - - self->disabled = TRUE; - } - if (self->input_state) - gst_video_codec_state_unref (self->input_state); - self->input_state = NULL; - - GST_DEBUG_OBJECT (self, "Decoder drained and disabled"); - return TRUE; -} - -static gboolean -gst_omx_video_dec_allocate_in_buffers (GstOMXVideoDec * self) -{ - switch (self->input_allocation) { - case GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER: - if (gst_omx_port_allocate_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - break; - case GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC: - if (gst_omx_port_use_dynamic_buffers (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - break; - case GST_OMX_BUFFER_ALLOCATION_USE_BUFFER: - default: - /* Not supported */ - g_return_val_if_reached (FALSE); - } - - return TRUE; -} - -static gboolean -check_input_alignment (GstOMXVideoDec * self, GstMapInfo * map) -{ - OMX_PARAM_PORTDEFINITIONTYPE *port_def = &self->dec_in_port->port_def; - - if (port_def->nBufferAlignment && - (GPOINTER_TO_UINT (map->data) & (port_def->nBufferAlignment - 1)) != 0) { - GST_DEBUG_OBJECT (self, - "input buffer is not properly aligned (address: %p alignment: %u bytes), can't use dynamic allocation", - map->data, (guint32) port_def->nBufferAlignment); - return FALSE; - } - - return TRUE; -} - -/* Check if @inbuf's alignment matches the requirements to use the - * dynamic buffer mode. */ -static gboolean -can_use_dynamic_buffer_mode (GstOMXVideoDec * self, GstBuffer * inbuf) -{ - gboolean result = TRUE; - guint i; - - for (i = 0; i < gst_buffer_n_memory (inbuf) && result; i++) { - GstMemory *mem = gst_buffer_peek_memory (inbuf, i); - GstMapInfo map; - - if (!gst_memory_map (mem, &map, GST_MAP_READ)) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("failed to map input buffer")); - return FALSE; - } - - result = check_input_alignment (self, &map); - - gst_memory_unmap (mem, &map); - } - - return result; -} - -/* Choose the allocation mode for input buffers depending of what's supported by - * the component and the size/alignment of the input buffer. */ -static GstOMXBufferAllocation -gst_omx_video_dec_pick_input_allocation_mode (GstOMXVideoDec * self, - GstBuffer * inbuf) -{ - if (!gst_omx_is_dynamic_allocation_supported ()) - return GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER; - - if (can_use_dynamic_buffer_mode (self, inbuf)) { - GST_DEBUG_OBJECT (self, - "input buffer is properly aligned, use dynamic allocation"); - return GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC; - } - - GST_DEBUG_OBJECT (self, "let input buffer allocate its buffers"); - return GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER; -} - -static gboolean -gst_omx_video_dec_ensure_nb_in_buffers (GstOMXVideoDec * self) -{ - GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (self); - - if ((klass->cdata.hacks & GST_OMX_HACK_ENSURE_BUFFER_COUNT_ACTUAL)) { - if (!gst_omx_port_ensure_buffer_count_actual (self->dec_in_port, 0)) - return FALSE; - } - - return TRUE; -} - -static gboolean -gst_omx_video_dec_enable (GstOMXVideoDec * self, GstBuffer * input) -{ - GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (self); - - GST_DEBUG_OBJECT (self, "Enabling component"); - - self->input_allocation = gst_omx_video_dec_pick_input_allocation_mode (self, - input); - - if (self->disabled) { - if (!gst_omx_video_dec_ensure_nb_in_buffers (self)) - return FALSE; - if (gst_omx_port_set_enabled (self->dec_in_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (!gst_omx_video_dec_allocate_in_buffers (self)) - return FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - if (gst_omx_port_set_enabled (self->dec_out_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_allocate_buffers (self->dec_out_port) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->dec_out_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_port_wait_enabled (self->dec_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_mark_reconfigured (self->dec_in_port) != OMX_ErrorNone) - return FALSE; - } else { - if (!gst_omx_video_dec_negotiate (self)) - GST_LOG_OBJECT (self, "Negotiation failed, will get output format later"); - - if (!gst_omx_video_dec_ensure_nb_in_buffers (self)) - return FALSE; - - if (!(klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - /* Disable output port */ - if (gst_omx_port_set_enabled (self->dec_out_port, FALSE) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->dec_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_set_state (self->dec, - OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (!gst_omx_video_dec_allocate_in_buffers (self)) - return FALSE; - } else { - if (gst_omx_component_set_state (self->dec, - OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (!gst_omx_video_dec_allocate_in_buffers (self)) - return FALSE; - if (gst_omx_port_allocate_buffers (self->dec_out_port) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateIdle) - return FALSE; - - if (gst_omx_component_set_state (self->dec, - OMX_StateExecuting) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateExecuting) - return FALSE; - } - - /* Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, FALSE); - - if (gst_omx_component_get_last_error (self->dec) != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Component in error state: %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec)); - return FALSE; - } - - self->disabled = FALSE; - - return TRUE; -} - -static OMX_COLOR_FORMATTYPE -get_color_format_from_chroma (const gchar * chroma_format, - guint bit_depth_luma, guint bit_depth_chroma) -{ - if (chroma_format == NULL) - goto out; - - if (!g_strcmp0 (chroma_format, "4:0:0") && bit_depth_chroma == 0) { - switch (bit_depth_luma) { - case 1: - return OMX_COLOR_FormatMonochrome; - case 2: - return OMX_COLOR_FormatL2; - case 4: - return OMX_COLOR_FormatL4; - case 8: - return OMX_COLOR_FormatL8; - case 16: - return OMX_COLOR_FormatL16; - case 24: - return OMX_COLOR_FormatL24; - case 32: - return OMX_COLOR_FormatL32; - } - goto out; - } - - if (bit_depth_luma == 8 && bit_depth_chroma == 8) { - if (!g_strcmp0 (chroma_format, "4:2:0")) - return OMX_COLOR_FormatYUV420SemiPlanar; - else if (!g_strcmp0 (chroma_format, "4:2:2")) - return OMX_COLOR_FormatYUV422SemiPlanar; - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (bit_depth_luma == 10 && bit_depth_chroma == 10) { - if (!g_strcmp0 (chroma_format, "4:2:0")) - return (OMX_COLOR_FORMATTYPE) - OMX_ALG_COLOR_FormatYUV420SemiPlanar10bitPacked; - else if (!g_strcmp0 (chroma_format, "4:2:2")) - return (OMX_COLOR_FORMATTYPE) - OMX_ALG_COLOR_FormatYUV422SemiPlanar10bitPacked; - } -#endif - -out: - return OMX_COLOR_FormatUnused; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static gboolean -gst_omx_video_dec_set_interlacing_parameters (GstOMXVideoDec * self, - GstVideoInfo * info) -{ - OMX_ERRORTYPE err; - OMX_ALG_COMMON_PARAM_SEQUENCE_PICTURE_MODE seq_pic_mode; - - GST_OMX_INIT_STRUCT (&seq_pic_mode); - seq_pic_mode.nPortIndex = self->dec_in_port->index; - - err = gst_omx_component_get_parameter (self->dec, - (OMX_INDEXTYPE) OMX_ALG_IndexParamCommonSequencePictureModeCurrent, - &seq_pic_mode); - - if (err != OMX_ErrorNone) { - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Picture sequence mode not supported by the component"); - } else { - GST_DEBUG_OBJECT (self, - "Failed to get picture sequence mode: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - return FALSE; - } - - if (info->interlace_mode == GST_VIDEO_INTERLACE_MODE_ALTERNATE || - info->interlace_mode == GST_VIDEO_INTERLACE_MODE_INTERLEAVED) - seq_pic_mode.eMode = OMX_ALG_SEQUENCE_PICTURE_FIELD; - else if (info->interlace_mode == GST_VIDEO_INTERLACE_MODE_PROGRESSIVE) - seq_pic_mode.eMode = OMX_ALG_SEQUENCE_PICTURE_FRAME; - else { - /* Caps templates should ensure this doesn't happen but just to be safe.. */ - GST_ERROR_OBJECT (self, "Video interlacing mode %s not supported", - gst_video_interlace_mode_to_string (info->interlace_mode)); - return FALSE; - } - - err = gst_omx_component_set_parameter (self->dec, - (OMX_INDEXTYPE) OMX_ALG_IndexParamCommonSequencePictureModeCurrent, - &seq_pic_mode); - - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting picture sequence mode not supported by the component"); - } else if (err == OMX_ErrorUnsupportedSetting) { - GST_WARNING_OBJECT (self, - "Interlaced picture sequence mode not supported by the component"); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set picture sequence mode: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } else { - GST_DEBUG_OBJECT (self, "Video interlacing mode %s set on component", - gst_video_interlace_mode_to_string (info->interlace_mode)); - } - - return TRUE; -} -#endif // USE_OMX_TARGET_ZYNQ_USCALE_PLUS - -static gboolean -gst_omx_video_dec_set_format (GstVideoDecoder * decoder, - GstVideoCodecState * state) -{ - GstOMXVideoDec *self; - GstOMXVideoDecClass *klass; - GstVideoInfo *info = &state->info; - gboolean is_format_change = FALSE; - gboolean needs_disable = FALSE; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - OMX_U32 framerate_q16 = gst_omx_video_calculate_framerate_q16 (info); - - self = GST_OMX_VIDEO_DEC (decoder); - klass = GST_OMX_VIDEO_DEC_GET_CLASS (decoder); - - GST_DEBUG_OBJECT (self, "Setting new caps %" GST_PTR_FORMAT, state->caps); - - if (!self->dmabuf - && gst_caps_features_contains (gst_caps_get_features (state->caps, 0), - GST_CAPS_FEATURE_MEMORY_DMABUF)) { - GST_WARNING_OBJECT (self, - "caps has the 'memory:DMABuf' feature but decoder cannot produce dmabuf"); - return FALSE; - } - - gst_omx_port_get_port_definition (self->dec_in_port, &port_def); - - /* Check if the caps change is a real format change or if only irrelevant - * parts of the caps have changed or nothing at all. - */ - is_format_change |= port_def.format.video.nFrameWidth != info->width; - is_format_change |= - port_def.format.video.nFrameHeight != GST_VIDEO_INFO_FIELD_HEIGHT (info); - is_format_change |= (port_def.format.video.xFramerate == 0 - && info->fps_n != 0) - || !gst_omx_video_is_equal_framerate_q16 (port_def.format. - video.xFramerate, framerate_q16); - is_format_change |= (self->codec_data != state->codec_data); - if (klass->is_format_change) - is_format_change |= - klass->is_format_change (self, self->dec_in_port, state); - - needs_disable = - gst_omx_component_get_state (self->dec, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded; - /* If the component is not in Loaded state and a real format change happens - * we have to disable the port and re-allocate all buffers. If no real - * format change happened we can just exit here. - */ - if (needs_disable && !is_format_change) { - GST_DEBUG_OBJECT (self, - "Already running and caps did not change the format"); - if (self->input_state) - gst_video_codec_state_unref (self->input_state); - self->input_state = gst_video_codec_state_ref (state); - return TRUE; - } - - if (needs_disable && is_format_change) { - if (!gst_omx_video_dec_disable (self)) - return FALSE; - - if (!self->disabled) { - /* The local port_def is now obsolete so get it again. */ - gst_omx_port_get_port_definition (self->dec_in_port, &port_def); - } - } - - port_def.format.video.nFrameWidth = info->width; - port_def.format.video.nFrameHeight = GST_VIDEO_INFO_HEIGHT (info); - /*We cannot use GST_VIDEO_INFO_FIELD_HEIGHT() as encoded content may use either - * interlace-mode=interleaved or alternate. In both case we'll output alternate - * so the OMX frame height needs to be halfed. */ - if (GST_VIDEO_INFO_IS_INTERLACED (info)) - port_def.format.video.nFrameHeight = - GST_ROUND_UP_2 (port_def.format.video.nFrameHeight / 2); - port_def.format.video.xFramerate = framerate_q16; - - if (klass->cdata.hacks & GST_OMX_HACK_PASS_COLOR_FORMAT_TO_DECODER) { - /* Let the decoder know the colar format of the encoded input stream. - * It may use it to pre-allocate its internal buffers and so save time when - * it will actually start to decode. */ - GstStructure *s; - const gchar *chroma_format; - guint bit_depth_luma, bit_depth_chroma; - - s = gst_caps_get_structure (state->caps, 0); - chroma_format = gst_structure_get_string (s, "chroma-format"); - if (s && gst_structure_get_uint (s, "bit-depth-luma", &bit_depth_luma) && - gst_structure_get_uint (s, "bit-depth-chroma", &bit_depth_chroma)) { - OMX_COLOR_FORMATTYPE color_format; - - color_format = - get_color_format_from_chroma (chroma_format, - bit_depth_luma, bit_depth_chroma); - if (color_format != OMX_COLOR_FormatUnused) { - GST_DEBUG_OBJECT (self, "Setting input eColorFormat to %d", - color_format); - port_def.format.video.eColorFormat = color_format; - } else { - GST_WARNING_OBJECT (self, - "Unsupported input color format: %s (luma %d bits, chroma %d bits)", - chroma_format, bit_depth_luma, bit_depth_chroma); - } - } else { - GST_DEBUG_OBJECT (self, - "Input color format info not present in caps, can't pass them to decoder"); - } - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (!gst_omx_video_dec_set_interlacing_parameters (self, info)) - return FALSE; -#endif - - GST_DEBUG_OBJECT (self, "Setting inport port definition"); - - if (gst_omx_port_update_port_definition (self->dec_in_port, - &port_def) != OMX_ErrorNone) - return FALSE; - - if (klass->set_format) { - if (!klass->set_format (self, self->dec_in_port, state)) { - GST_ERROR_OBJECT (self, "Subclass failed to set the new format"); - return FALSE; - } - } - - GST_DEBUG_OBJECT (self, "Updating ports definition"); - if (gst_omx_port_update_port_definition (self->dec_out_port, - NULL) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_update_port_definition (self->dec_in_port, - NULL) != OMX_ErrorNone) - return FALSE; - - gst_buffer_replace (&self->codec_data, state->codec_data); - self->input_state = gst_video_codec_state_ref (state); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - gst_omx_video_dec_set_latency (self); -#endif - - self->downstream_flow_ret = GST_FLOW_OK; - return TRUE; -} - -static gboolean -gst_omx_video_dec_flush (GstVideoDecoder * decoder) -{ - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (decoder); - OMX_ERRORTYPE err = OMX_ErrorNone; - - GST_DEBUG_OBJECT (self, "Flushing decoder"); - - if (gst_omx_component_get_state (self->dec, 0) == OMX_StateLoaded) - return TRUE; - - /* 0) Pause the components */ - if (gst_omx_component_get_state (self->dec, 0) == OMX_StateExecuting) { - gst_omx_component_set_state (self->dec, OMX_StatePause); - gst_omx_component_get_state (self->dec, GST_CLOCK_TIME_NONE); - } -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->eglimage) { - if (gst_omx_component_get_state (self->egl_render, 0) == OMX_StateExecuting) { - gst_omx_component_set_state (self->egl_render, OMX_StatePause); - gst_omx_component_get_state (self->egl_render, GST_CLOCK_TIME_NONE); - } - } -#endif - - /* 1) Flush the ports */ - GST_DEBUG_OBJECT (self, "flushing ports"); - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, TRUE); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->eglimage) { - gst_omx_port_set_flushing (self->egl_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->egl_out_port, 5 * GST_SECOND, TRUE); - } -#endif - - /* 2) Wait until the srcpad loop is stopped, - * unlock GST_VIDEO_DECODER_STREAM_LOCK to prevent deadlocks - * caused by using this lock from inside the loop function */ - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - gst_pad_stop_task (GST_VIDEO_DECODER_SRC_PAD (decoder)); - GST_DEBUG_OBJECT (self, "Flushing -- task stopped"); - GST_VIDEO_DECODER_STREAM_LOCK (self); - - /* 3) Resume components */ - gst_omx_component_set_state (self->dec, OMX_StateExecuting); - gst_omx_component_get_state (self->dec, GST_CLOCK_TIME_NONE); -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->eglimage) { - gst_omx_component_set_state (self->egl_render, OMX_StateExecuting); - gst_omx_component_get_state (self->egl_render, GST_CLOCK_TIME_NONE); - } -#endif - - /* 4) Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->dec_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->dec_out_port, 5 * GST_SECOND, FALSE); - -#if defined (USE_OMX_TARGET_RPI) && defined (HAVE_GST_GL) - if (self->eglimage) { - gst_omx_port_set_flushing (self->egl_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->egl_out_port, 5 * GST_SECOND, FALSE); - err = gst_omx_port_populate (self->egl_out_port); - gst_omx_port_mark_reconfigured (self->egl_out_port); - } else { - err = gst_omx_port_populate (self->dec_out_port); - } -#else - err = gst_omx_port_populate (self->dec_out_port); -#endif - - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Failed to populate output port: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - /* Reset our state */ - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - self->started = FALSE; - GST_DEBUG_OBJECT (self, "Flush finished"); - - return TRUE; -} - -static GstFlowReturn -gst_omx_video_dec_handle_frame (GstVideoDecoder * decoder, - GstVideoCodecFrame * frame) -{ - GstOMXAcquireBufferReturn acq_ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - GstOMXVideoDec *self; - GstOMXPort *port; - GstOMXBuffer *buf; - GstBuffer *codec_data = NULL; - guint offset = 0, size; - GstClockTime timestamp, duration; - OMX_ERRORTYPE err; - gboolean done = FALSE; - gboolean first_ouput_buffer = TRUE; - guint memory_idx = 0; /* only used in dynamic buffer mode */ - gboolean last_subframe = GST_BUFFER_FLAG_IS_SET (frame->input_buffer, - GST_VIDEO_BUFFER_FLAG_MARKER); - gboolean header = - GST_BUFFER_FLAG_IS_SET (frame->input_buffer, GST_BUFFER_FLAG_HEADER); - gboolean subframe_mode = gst_video_decoder_get_subframe_mode (decoder); - - self = GST_OMX_VIDEO_DEC (decoder); - - GST_DEBUG_OBJECT (self, - "Handling frame %p last_subframe=%d header %d subframes %d", frame, - last_subframe, header, frame->abidata.ABI.num_subframes); - - if (self->downstream_flow_ret != GST_FLOW_OK) { - gst_video_codec_frame_unref (frame); - return self->downstream_flow_ret; - } - - if (!self->started) { - if (!GST_VIDEO_CODEC_FRAME_IS_SYNC_POINT (frame) && !header) { - gst_video_decoder_drop_frame (GST_VIDEO_DECODER (self), frame); - return GST_FLOW_OK; - } - - if (gst_omx_port_is_flushing (self->dec_out_port)) { - if (!gst_omx_video_dec_enable (self, frame->input_buffer)) - goto enable_error; - } - - GST_DEBUG_OBJECT (self, "Starting task"); - gst_pad_start_task (GST_VIDEO_DECODER_SRC_PAD (self), - (GstTaskFunction) gst_omx_video_dec_loop, decoder, NULL); - } - - timestamp = frame->pts; - duration = frame->duration; - port = self->dec_in_port; - - size = gst_buffer_get_size (frame->input_buffer); - while (!done) { - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - acq_ret = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - - if (acq_ret == GST_OMX_ACQUIRE_BUFFER_ERROR) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto component_error; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto flushing; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - /* Reallocate all buffers */ - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - if (!gst_omx_video_dec_ensure_nb_in_buffers (self)) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - if (!gst_omx_video_dec_allocate_in_buffers (self)) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - /* Now get a new buffer and fill it */ - GST_VIDEO_DECODER_STREAM_LOCK (self); - continue; - } - GST_VIDEO_DECODER_STREAM_LOCK (self); - - g_assert (acq_ret == GST_OMX_ACQUIRE_BUFFER_OK && buf != NULL); - - if (buf->omx_buf->nAllocLen - buf->omx_buf->nOffset <= 0) { - gst_omx_port_release_buffer (port, buf); - goto full_buffer; - } - - if (self->downstream_flow_ret != GST_FLOW_OK) { - gst_omx_port_release_buffer (port, buf); - goto flow_error; - } - - if (self->codec_data) { - GST_DEBUG_OBJECT (self, "Passing codec data to the component"); - - codec_data = self->codec_data; - - if (self->input_allocation == - GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC) { - /* Map the full buffer, this may lead to copying if for some reason its - * content is split on more than one memory but that seems unlikely and - * the codec data aren't supposed to be that big anyway. */ - if (!gst_omx_buffer_map_buffer (buf, codec_data)) - goto map_failed; - } else { - if (buf->omx_buf->nAllocLen - buf->omx_buf->nOffset < - gst_buffer_get_size (codec_data)) { - gst_omx_port_release_buffer (port, buf); - goto too_large_codec_data; - } - - buf->omx_buf->nFilledLen = gst_buffer_get_size (codec_data);; - gst_buffer_extract (codec_data, 0, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - } - - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_CODECCONFIG; - - if (GST_CLOCK_TIME_IS_VALID (timestamp)) - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (timestamp, OMX_TICKS_PER_SECOND, - GST_SECOND)); - else - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, G_GUINT64_CONSTANT (0)); - buf->omx_buf->nTickCount = 0; - - self->started = TRUE; - err = gst_omx_port_release_buffer (port, buf); - gst_buffer_replace (&self->codec_data, NULL); - if (err != OMX_ErrorNone) - goto release_error; - /* Acquire new buffer for the actual frame */ - continue; - } - - /* Now handle the frame */ - - if (self->input_allocation == GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC) { - /* Transfer the buffer content per memory rather than mapping the full - * buffer to prevent copies. */ - GstMemory *mem = gst_buffer_peek_memory (frame->input_buffer, memory_idx); - - GST_LOG_OBJECT (self, - "Transferring %" G_GSIZE_FORMAT " bytes to the component", - gst_memory_get_sizes (mem, NULL, NULL)); - - if (!gst_omx_buffer_map_memory (buf, mem)) - goto map_failed; - - if (!check_input_alignment (self, &buf->map)) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("input buffer now has wrong alignment/stride, can't use dynamic allocation any more")); - return FALSE; - } - - memory_idx++; - if (memory_idx == gst_buffer_n_memory (frame->input_buffer)) - done = TRUE; - } else { - /* Copy the buffer content in chunks of size as requested - * by the port */ - buf->omx_buf->nFilledLen = - MIN (size - offset, buf->omx_buf->nAllocLen - buf->omx_buf->nOffset); - - GST_LOG_OBJECT (self, - "Copying %d bytes (frame offset %d) to the component", - (guint) buf->omx_buf->nFilledLen, offset); - - gst_buffer_extract (frame->input_buffer, offset, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - - offset += buf->omx_buf->nFilledLen; - if (offset == size) - done = TRUE; - } - - if (timestamp != GST_CLOCK_TIME_NONE) { - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (timestamp, OMX_TICKS_PER_SECOND, GST_SECOND)); - self->last_upstream_ts = timestamp; - } else { - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, G_GUINT64_CONSTANT (0)); - } - - if (duration != GST_CLOCK_TIME_NONE && first_ouput_buffer) { - buf->omx_buf->nTickCount = - gst_util_uint64_scale (duration, OMX_TICKS_PER_SECOND, GST_SECOND); - self->last_upstream_ts += duration; - } else { - buf->omx_buf->nTickCount = 0; - } - - if (first_ouput_buffer && GST_VIDEO_CODEC_FRAME_IS_SYNC_POINT (frame)) - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_SYNCFRAME; - - if (header) - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_CODECCONFIG; - - /* TODO: Set flags - * - OMX_BUFFERFLAG_DECODEONLY for buffers that are outside - * the segment - */ - - if (done) { - /* If the input buffer is a subframe mark the OMX buffer as such */ - if (subframe_mode && !last_subframe) { -#ifdef OMX_BUFFERFLAG_ENDOFSUBFRAME - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_ENDOFSUBFRAME; -#endif - } else { - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_ENDOFFRAME; - if (subframe_mode && last_subframe) - gst_video_decoder_have_last_subframe (decoder, frame); - } - } - - self->started = TRUE; - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - - first_ouput_buffer = FALSE; - } - - gst_video_codec_frame_unref (frame); - - GST_DEBUG_OBJECT (self, "Passed frame to component"); - - return self->downstream_flow_ret; - -full_buffer: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Got OpenMAX buffer with no free space (%p, %u/%u)", buf, - (guint) buf->omx_buf->nOffset, (guint) buf->omx_buf->nAllocLen)); - return GST_FLOW_ERROR; - } - -flow_error: - { - gst_video_codec_frame_unref (frame); - - return self->downstream_flow_ret; - } - -too_large_codec_data: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("codec_data larger than supported by OpenMAX port " - "(%" G_GSIZE_FORMAT " > %u)", gst_buffer_get_size (codec_data), - (guint) self->dec_in_port->port_def.nBufferSize)); - return GST_FLOW_ERROR; - } - -map_failed: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("failed to map input buffer")); - return GST_FLOW_ERROR; - } - -enable_error: - { - /* Report the OMX error, if any */ - if (gst_omx_component_get_last_error (self->dec) != OMX_ErrorNone) - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Failed to enable OMX decoder: %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec))); - else - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Failed to enable OMX decoder")); - gst_video_codec_frame_unref (frame); - return GST_FLOW_ERROR; - } - -component_error: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->dec), - gst_omx_component_get_last_error (self->dec))); - return GST_FLOW_ERROR; - } - -flushing: - { - gst_video_codec_frame_unref (frame); - GST_DEBUG_OBJECT (self, "Flushing -- returning FLUSHING"); - return GST_FLOW_FLUSHING; - } -reconfigure_error: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure input port")); - return GST_FLOW_ERROR; - } -release_error: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase input buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - return GST_FLOW_ERROR; - } -} - -static GstFlowReturn -gst_omx_video_dec_drain (GstVideoDecoder * decoder) -{ - gboolean ret; - ret = gst_omx_video_dec_finish (decoder); - gst_omx_video_dec_flush (decoder); - return ret; -} - -static GstFlowReturn -gst_omx_video_dec_finish (GstVideoDecoder * decoder) -{ - GstOMXVideoDec *self; - GstOMXVideoDecClass *klass; - GstOMXBuffer *buf; - GstOMXAcquireBufferReturn acq_ret; - OMX_ERRORTYPE err; - - self = GST_OMX_VIDEO_DEC (decoder); - - GST_DEBUG_OBJECT (self, "Draining component"); - - klass = GST_OMX_VIDEO_DEC_GET_CLASS (self); - - if (!self->started) { - GST_DEBUG_OBJECT (self, "Component not started yet"); - return GST_FLOW_OK; - } - self->started = FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_EMPTY_EOS_BUFFER)) { - GST_WARNING_OBJECT (self, "Component does not support empty EOS buffers"); - return GST_FLOW_OK; - } - - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_VIDEO_DECODER_STREAM_UNLOCK (self); - - /* Send an EOS buffer to the component and let the base - * class drop the EOS event. We will send it later when - * the EOS buffer arrives on the output port. */ - acq_ret = gst_omx_port_acquire_buffer (self->dec_in_port, &buf, GST_OMX_WAIT); - if (acq_ret != GST_OMX_ACQUIRE_BUFFER_OK) { - GST_VIDEO_DECODER_STREAM_LOCK (self); - GST_ERROR_OBJECT (self, "Failed to acquire buffer for draining: %d", - acq_ret); - return GST_FLOW_ERROR; - } - - g_mutex_lock (&self->drain_lock); - self->draining = TRUE; - buf->omx_buf->nFilledLen = 0; - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (self->last_upstream_ts, OMX_TICKS_PER_SECOND, - GST_SECOND)); - buf->omx_buf->nTickCount = 0; - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_EOS; - err = gst_omx_port_release_buffer (self->dec_in_port, buf); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to drain component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_mutex_unlock (&self->drain_lock); - GST_VIDEO_DECODER_STREAM_LOCK (self); - return GST_FLOW_ERROR; - } - - GST_DEBUG_OBJECT (self, "Waiting until component is drained"); - - if (G_UNLIKELY (self->dec->hacks & GST_OMX_HACK_DRAIN_MAY_NOT_RETURN)) { - gint64 wait_until = g_get_monotonic_time () + G_TIME_SPAN_SECOND / 2; - - if (!g_cond_wait_until (&self->drain_cond, &self->drain_lock, wait_until)) - GST_WARNING_OBJECT (self, "Drain timed out"); - else - GST_DEBUG_OBJECT (self, "Drained component"); - - } else { - g_cond_wait (&self->drain_cond, &self->drain_lock); - GST_DEBUG_OBJECT (self, "Drained component"); - } - - g_mutex_unlock (&self->drain_lock); - GST_VIDEO_DECODER_STREAM_LOCK (self); - - self->started = FALSE; - - return GST_FLOW_OK; -} - -static gboolean -gst_omx_video_dec_decide_allocation (GstVideoDecoder * bdec, GstQuery * query) -{ - GstBufferPool *pool = NULL; - GstStructure *config; - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (bdec); - guint i; - -#if defined (HAVE_GST_GL) - { - GstCaps *caps; - gint i, n; - GstVideoInfo info; - - gst_query_parse_allocation (query, &caps, NULL); - if (caps && gst_video_info_from_caps (&info, caps) - && info.finfo->format == GST_VIDEO_FORMAT_RGBA) { - gboolean found = FALSE; - GstCapsFeatures *feature = gst_caps_get_features (caps, 0); - /* Prefer an EGLImage allocator if available and we want to use it */ - n = gst_query_get_n_allocation_params (query); - for (i = 0; i < n; i++) { - GstAllocator *allocator; - GstAllocationParams params; - - gst_query_parse_nth_allocation_param (query, i, &allocator, ¶ms); - if (allocator) { - if (GST_IS_GL_MEMORY_EGL_ALLOCATOR (allocator)) { - found = TRUE; - gst_query_set_nth_allocation_param (query, 0, allocator, ¶ms); - while (gst_query_get_n_allocation_params (query) > 1) - gst_query_remove_nth_allocation_param (query, 1); - } - - gst_object_unref (allocator); - - if (found) - break; - } - } - - /* if try to negotiate with caps feature memory:EGLImage - * and if allocator is not of type memory EGLImage then fails */ - if (feature - && gst_caps_features_contains (feature, - GST_CAPS_FEATURE_MEMORY_GL_MEMORY) && !found) { - return FALSE; - } - } - } -#endif /* defined (HAVE_GST_GL) */ - - self->use_buffers = FALSE; - - /* Importing OMX buffers from downstream isn't supported. - * That wouldn't bring us much as the dynamic buffer mode already - * prevent copies between OMX components. */ - i = 0; - while (i < gst_query_get_n_allocation_pools (query)) { - gst_query_parse_nth_allocation_pool (query, i, &pool, NULL, NULL, NULL); - if (GST_IS_OMX_BUFFER_POOL (pool)) { - GST_DEBUG_OBJECT (self, "Discard OMX pool from downstream"); - gst_query_remove_nth_allocation_pool (query, i); - } else { - GST_DEBUG_OBJECT (self, - "Try using downstream buffers with OMX_UseBuffer"); - self->use_buffers = TRUE; - i++; - } - - if (pool) - gst_object_unref (pool); - } - - if (!GST_VIDEO_DECODER_CLASS - (gst_omx_video_dec_parent_class)->decide_allocation (bdec, query)) - return FALSE; - - g_assert (gst_query_get_n_allocation_pools (query) > 0); - gst_query_parse_nth_allocation_pool (query, 0, &pool, NULL, NULL, NULL); - g_assert (pool != NULL); - - config = gst_buffer_pool_get_config (pool); - if (gst_query_find_allocation_meta (query, GST_VIDEO_META_API_TYPE, NULL)) { - gst_buffer_pool_config_add_option (config, - GST_BUFFER_POOL_OPTION_VIDEO_META); - } - gst_buffer_pool_set_config (pool, config); - gst_object_unref (pool); - - return TRUE; -} - -static gboolean -gst_omx_video_dec_propose_allocation (GstVideoDecoder * bdec, GstQuery * query) -{ - GstOMXVideoDec *self = GST_OMX_VIDEO_DEC (bdec); - guint size, num_buffers; - - size = self->dec_in_port->port_def.nBufferSize; - num_buffers = self->dec_in_port->port_def.nBufferCountMin + 1; - - GST_DEBUG_OBJECT (self, - "request at least %d buffers of size %d", num_buffers, size); - gst_query_add_allocation_pool (query, NULL, size, num_buffers, 0); - - return - GST_VIDEO_DECODER_CLASS - (gst_omx_video_dec_parent_class)->propose_allocation (bdec, query); -} diff --git a/subprojects/gst-omx/omx/gstomxvideodec.h b/subprojects/gst-omx/omx/gstomxvideodec.h deleted file mode 100644 index df441d9d08..0000000000 --- a/subprojects/gst-omx/omx/gstomxvideodec.h +++ /dev/null @@ -1,119 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_VIDEO_DEC_H__ -#define __GST_OMX_VIDEO_DEC_H__ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_VIDEO_DEC \ - (gst_omx_video_dec_get_type()) -#define GST_OMX_VIDEO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_VIDEO_DEC,GstOMXVideoDec)) -#define GST_OMX_VIDEO_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_VIDEO_DEC,GstOMXVideoDecClass)) -#define GST_OMX_VIDEO_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_VIDEO_DEC,GstOMXVideoDecClass)) -#define GST_IS_OMX_VIDEO_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_VIDEO_DEC)) -#define GST_IS_OMX_VIDEO_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_VIDEO_DEC)) - -typedef struct _GstOMXVideoDec GstOMXVideoDec; -typedef struct _GstOMXVideoDecClass GstOMXVideoDecClass; - -struct _GstOMXVideoDec -{ - GstVideoDecoder parent; - - /* < protected > */ - GstOMXComponent *dec; - GstOMXPort *dec_in_port, *dec_out_port; - - GstBufferPool *in_port_pool, *out_port_pool; - - /* < private > */ - GstVideoCodecState *input_state; - GstBuffer *codec_data; - /* TRUE if the component is configured and saw - * the first buffer */ - gboolean started; - /* TRUE if the ports where disabled after being activated the first time. */ - gboolean disabled; - - GstClockTime last_upstream_ts; - - /* Draining state */ - GMutex drain_lock; - GCond drain_cond; - /* TRUE if EOS buffers shouldn't be forwarded */ - gboolean draining; /* protected by drain_lock */ - - GstFlowReturn downstream_flow_ret; - /* Initially FALSE. Switched to TRUE when all requirements - * are met to try setting up the decoder with OMX_UseBuffer. - * Switched to FALSE if this trial fails so that the decoder - * can fallback to OMX_AllocateBuffer. */ - gboolean use_buffers; - -#if defined (USE_OMX_TARGET_RPI) - GstOMXComponent *egl_render; - GstOMXPort *egl_in_port, *egl_out_port; -#endif - -#if defined (HAVE_GST_GL) - gboolean eglimage; -#endif - - /* TRUE if decoder is producing dmabuf */ - gboolean dmabuf; - GstOMXBufferAllocation input_allocation; - - /* properties */ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - guint32 internal_entropy_buffers; -#endif -}; - -struct _GstOMXVideoDecClass -{ - GstVideoDecoderClass parent_class; - - GstOMXClassData cdata; - - gboolean (*is_format_change) (GstOMXVideoDec * self, GstOMXPort * port, GstVideoCodecState * state); - gboolean (*set_format) (GstOMXVideoDec * self, GstOMXPort * port, GstVideoCodecState * state); -}; - -GType gst_omx_video_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_VIDEO_DEC_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxvideoenc.c b/subprojects/gst-omx/omx/gstomxvideoenc.c deleted file mode 100644 index 6dbfb411ca..0000000000 --- a/subprojects/gst-omx/omx/gstomxvideoenc.c +++ /dev/null @@ -1,3732 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include -#include - -#include - -#include "gstomxbufferpool.h" -#include "gstomxvideo.h" -#include "gstomxvideoenc.h" - -#ifdef USE_OMX_TARGET_RPI -#include -#include -#endif - -GST_DEBUG_CATEGORY_STATIC (gst_omx_video_enc_debug_category); -#define GST_CAT_DEFAULT gst_omx_video_enc_debug_category - -#define GST_TYPE_OMX_VIDEO_ENC_CONTROL_RATE (gst_omx_video_enc_control_rate_get_type ()) -static GType -gst_omx_video_enc_control_rate_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_Video_ControlRateDisable, "Disable", "disable"}, - {OMX_Video_ControlRateVariable, "Variable", "variable"}, - {OMX_Video_ControlRateConstant, "Constant", "constant"}, - {OMX_Video_ControlRateVariableSkipFrames, "Variable Skip Frames", - "variable-skip-frames"}, - {OMX_Video_ControlRateConstantSkipFrames, "Constant Skip Frames", - "constant-skip-frames"}, -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - {OMX_ALG_Video_ControlRateLowLatency, "Low Latency", "low-latency"}, -#endif - {0xffffffff, "Component Default", "default"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncControlRate", values); - } - return qtype; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -#define GST_TYPE_OMX_VIDEO_ENC_QP_MODE (gst_omx_video_enc_qp_mode_get_type ()) -typedef enum -{ - UNIFORM_QP, - ROI_QP, - AUTO_QP, - LOAD_QP_ABSOLUTE, - LOAD_QP_RELATIVE, -} GstOMXVideoEncQpMode; - - -static GType -gst_omx_video_enc_qp_mode_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {UNIFORM_QP, "Use the same QP for all coding units of the frame", - "uniform"}, - {ROI_QP, - "Adjust QP according to the regions of interest defined on each frame. Must be set to handle ROI metadata.", - "roi"}, - {AUTO_QP, - "Let the VCU encoder change the QP for each coding unit according to its content", - "auto"}, - {LOAD_QP_ABSOLUTE, - "Uses absolute QP values set by user. Must be set to use External QP buffer", - "load-qp-absolute"}, - {LOAD_QP_RELATIVE, - "Uses Relative/Delta QP values set by user. Must be set to use External QP buffer", - "load-qp-relative"}, - {0xffffffff, "Component Default", "default"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncQpMode", values); - } - return qtype; -} - -#define GST_TYPE_OMX_VIDEO_ENC_GOP_MODE (gst_omx_video_enc_gop_mode_get_type ()) -static GType -gst_omx_video_enc_gop_mode_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_ALG_GOP_MODE_DEFAULT, "Basic GOP settings", "basic"}, - {OMX_ALG_GOP_MODE_PYRAMIDAL, - "Advanced GOP pattern with hierarchical B-frames", "pyramidal"}, - {OMX_ALG_GOP_MODE_LOW_DELAY_P, "Single I-frame followed by P-frames only", - "low-delay-p"}, - {OMX_ALG_GOP_MODE_LOW_DELAY_B, "Single I-frame followed by B-frames only", - "low-delay-b"}, - {OMX_ALG_GOP_MODE_ADAPTIVE, "Advanced GOP pattern with adaptive B-frames", - "adaptive"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncGopMode", values); - } - return qtype; -} - -#define GST_TYPE_OMX_VIDEO_ENC_GDR_MODE (gst_omx_video_enc_gdr_mode_get_type ()) -static GType -gst_omx_video_enc_gdr_mode_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_ALG_GDR_OFF, "No GDR", "disabled"}, - {OMX_ALG_GDR_VERTICAL, - "Gradual refresh using a vertical bar moving from left to right", - "vertical"}, - {OMX_ALG_GDR_HORIZONTAL, - "Gradual refresh using a horizontal bar moving from top to bottom", - "horizontal"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncGdrMode", values); - } - return qtype; -} - -#define GST_TYPE_OMX_VIDEO_ENC_SCALING_LIST (gst_omx_video_enc_scaling_list_get_type ()) -static GType -gst_omx_video_enc_scaling_list_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_ALG_SCL_DEFAULT, "Default scaling list mode", "default"}, - {OMX_ALG_SCL_FLAT, "Flat scaling list mode", "flat"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncScalingList", values); - } - return qtype; -} - -#define GST_TYPE_OMX_VIDEO_ENC_ASPECT_RATIO (gst_omx_video_enc_aspect_ratio_get_type ()) -static GType -gst_omx_video_enc_aspect_ratio_get_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_ALG_ASPECT_RATIO_AUTO, - "4:3 for SD video,16:9 for HD video,unspecified for unknown format", - "auto"}, - {OMX_ALG_ASPECT_RATIO_4_3, "4:3 aspect ratio", "4-3"}, - {OMX_ALG_ASPECT_RATIO_16_9, "16:9 aspect ratio", "16-9"}, - {OMX_ALG_ASPECT_RATIO_NONE, - "Aspect ratio information is not present in the stream", "none"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncAspectRatio", values); - } - return qtype; -} - -#define GST_TYPE_OMX_VIDEO_ENC_ROI_QUALITY (gst_omx_video_enc_roi_quality_type ()) -static GType -gst_omx_video_enc_roi_quality_type (void) -{ - static GType qtype = 0; - - if (qtype == 0) { - static const GEnumValue values[] = { - {OMX_ALG_ROI_QUALITY_HIGH, "Delta QP of -5", "high"}, - {OMX_ALG_ROI_QUALITY_MEDIUM, "Delta QP of 0", "medium"}, - {OMX_ALG_ROI_QUALITY_LOW, "Delta QP of +5", "low"}, - {OMX_ALG_ROI_QUALITY_DONT_CARE, "Maximum delta QP value", "dont-care"}, - {0, NULL, NULL} - }; - - qtype = g_enum_register_static ("GstOMXVideoEncRoiQuality", values); - } - return qtype; -} -#endif - -/* prototypes */ -static void gst_omx_video_enc_finalize (GObject * object); -static void gst_omx_video_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec); -static void gst_omx_video_enc_get_property (GObject * object, guint prop_id, - GValue * value, GParamSpec * pspec); - - -static GstStateChangeReturn -gst_omx_video_enc_change_state (GstElement * element, - GstStateChange transition); - -static gboolean gst_omx_video_enc_open (GstVideoEncoder * encoder); -static gboolean gst_omx_video_enc_close (GstVideoEncoder * encoder); -static gboolean gst_omx_video_enc_start (GstVideoEncoder * encoder); -static gboolean gst_omx_video_enc_stop (GstVideoEncoder * encoder); -static gboolean gst_omx_video_enc_set_format (GstVideoEncoder * encoder, - GstVideoCodecState * state); -static gboolean gst_omx_video_enc_flush (GstVideoEncoder * encoder); -static GstFlowReturn gst_omx_video_enc_handle_frame (GstVideoEncoder * encoder, - GstVideoCodecFrame * frame); -static gboolean gst_omx_video_enc_finish (GstVideoEncoder * encoder); -static gboolean gst_omx_video_enc_propose_allocation (GstVideoEncoder * encoder, - GstQuery * query); -static GstCaps *gst_omx_video_enc_getcaps (GstVideoEncoder * encoder, - GstCaps * filter); -static gboolean gst_omx_video_enc_decide_allocation (GstVideoEncoder * encoder, - GstQuery * query); - -static GstFlowReturn gst_omx_video_enc_drain (GstOMXVideoEnc * self); - -static GstFlowReturn gst_omx_video_enc_handle_output_frame (GstOMXVideoEnc * - self, GstOMXPort * port, GstOMXBuffer * buf, GstVideoCodecFrame * frame); - -static gboolean gst_omx_video_enc_sink_event (GstVideoEncoder * encoder, - GstEvent * event); - -enum -{ - PROP_0, - PROP_CONTROL_RATE, - PROP_TARGET_BITRATE, - PROP_QUANT_I_FRAMES, - PROP_QUANT_P_FRAMES, - PROP_QUANT_B_FRAMES, - PROP_QP_MODE, - PROP_MIN_QP, - PROP_MAX_QP, - PROP_GOP_MODE, - PROP_GDR_MODE, - PROP_INITIAL_DELAY, - PROP_CPB_SIZE, - PROP_SCALING_LIST, - PROP_LOW_BANDWIDTH, - PROP_MAX_BITRATE, - PROP_ASPECT_RATIO, - PROP_FILLER_DATA, - PROP_NUM_SLICES, - PROP_SLICE_SIZE, - PROP_DEPENDENT_SLICE, - PROP_DEFAULT_ROI_QUALITY, - PROP_LONGTERM_REF, - PROP_LONGTERM_FREQUENCY, - PROP_LOOK_AHEAD, -}; - -/* FIXME: Better defaults */ -#define GST_OMX_VIDEO_ENC_CONTROL_RATE_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_TARGET_BITRATE_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_QUANT_I_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_QUANT_P_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_QUANT_B_FRAMES_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_QP_MODE_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_MIN_QP_DEFAULT (10) -#define GST_OMX_VIDEO_ENC_MAX_QP_DEFAULT (51) -#define GST_OMX_VIDEO_ENC_GOP_MODE_DEFAULT (OMX_ALG_GOP_MODE_DEFAULT) -#define GST_OMX_VIDEO_ENC_GDR_MODE_DEFAULT (OMX_ALG_GDR_OFF) -#define GST_OMX_VIDEO_ENC_INITIAL_DELAY_DEFAULT (1500) -#define GST_OMX_VIDEO_ENC_CPB_SIZE_DEFAULT (3000) -#define GST_OMX_VIDEO_ENC_SCALING_LIST_DEFAULT (OMX_ALG_SCL_DEFAULT) -#define GST_OMX_VIDEO_ENC_LOW_BANDWIDTH_DEFAULT (FALSE) -#define GST_OMX_VIDEO_ENC_MAX_BITRATE_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_ASPECT_RATIO_DEFAULT (OMX_ALG_ASPECT_RATIO_AUTO) -#define GST_OMX_VIDEO_ENC_FILLER_DATA_DEFAULT (TRUE) -#define GST_OMX_VIDEO_ENC_NUM_SLICES_DEFAULT (0xffffffff) -#define GST_OMX_VIDEO_ENC_SLICE_SIZE_DEFAULT (0) -#define GST_OMX_VIDEO_ENC_DEPENDENT_SLICE_DEFAULT (FALSE) -#define GST_OMX_VIDEO_ENC_DEFAULT_ROI_QUALITY OMX_ALG_ROI_QUALITY_HIGH -#define GST_OMX_VIDEO_ENC_LONGTERM_REF_DEFAULT (FALSE) -#define GST_OMX_VIDEO_ENC_LONGTERM_FREQUENCY_DEFAULT (0) -#define GST_OMX_VIDEO_ENC_LOOK_AHEAD_DEFAULT (0) - -/* ZYNQ_USCALE_PLUS encoder custom events */ -#define OMX_ALG_GST_EVENT_INSERT_LONGTERM "omx-alg/insert-longterm" -#define OMX_ALG_GST_EVENT_USE_LONGTERM "omx-alg/use-longterm" - -/* class initialization */ -#define do_init \ -{ \ - GST_DEBUG_CATEGORY_INIT (gst_omx_video_enc_debug_category, "omxvideoenc", 0, \ - "debug category for gst-omx video encoder base class"); \ - G_IMPLEMENT_INTERFACE (GST_TYPE_PRESET, NULL); \ -} - -G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GstOMXVideoEnc, gst_omx_video_enc, - GST_TYPE_VIDEO_ENCODER, do_init); - -static void -gst_omx_video_enc_class_init (GstOMXVideoEncClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstVideoEncoderClass *video_encoder_class = GST_VIDEO_ENCODER_CLASS (klass); - - - gobject_class->finalize = gst_omx_video_enc_finalize; - gobject_class->set_property = gst_omx_video_enc_set_property; - gobject_class->get_property = gst_omx_video_enc_get_property; - - g_object_class_install_property (gobject_class, PROP_CONTROL_RATE, - g_param_spec_enum ("control-rate", "Control Rate", - "Bitrate control method", - GST_TYPE_OMX_VIDEO_ENC_CONTROL_RATE, - GST_OMX_VIDEO_ENC_CONTROL_RATE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_TARGET_BITRATE, - g_param_spec_uint ("target-bitrate", "Target Bitrate", - "Target bitrate in bits per second (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_TARGET_BITRATE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_PLAYING)); - - g_object_class_install_property (gobject_class, PROP_QUANT_I_FRAMES, - g_param_spec_uint ("quant-i-frames", "I-Frame Quantization", - "Quantization parameter for I-frames (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_QUANT_I_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_QUANT_P_FRAMES, - g_param_spec_uint ("quant-p-frames", "P-Frame Quantization", - "Quantization parameter for P-frames (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_QUANT_P_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_QUANT_B_FRAMES, - g_param_spec_uint ("quant-b-frames", "B-Frame Quantization", - "Quantization parameter for B-frames (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_QUANT_B_FRAMES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - g_object_class_install_property (gobject_class, PROP_QP_MODE, - g_param_spec_enum ("qp-mode", "QP mode", - "QP control mode used by the VCU encoder", - GST_TYPE_OMX_VIDEO_ENC_QP_MODE, - GST_OMX_VIDEO_ENC_QP_MODE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_MIN_QP, - g_param_spec_uint ("min-qp", "min Quantization value", - "Minimum QP value allowed for the rate control", - 0, 51, GST_OMX_VIDEO_ENC_MIN_QP_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_MAX_QP, - g_param_spec_uint ("max-qp", "max Quantization value", - "Maximum QP value allowed for the rate control", - 0, 51, GST_OMX_VIDEO_ENC_MAX_QP_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_GOP_MODE, - g_param_spec_enum ("gop-mode", "GOP mode", - "Group Of Pictures mode", - GST_TYPE_OMX_VIDEO_ENC_GOP_MODE, - GST_OMX_VIDEO_ENC_GOP_MODE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_GDR_MODE, - g_param_spec_enum ("gdr-mode", "GDR mode", - "Gradual Decoder Refresh scheme mode. Only used if gop-mode=low-delay-p", - GST_TYPE_OMX_VIDEO_ENC_GDR_MODE, - GST_OMX_VIDEO_ENC_GDR_MODE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_INITIAL_DELAY, - g_param_spec_uint ("initial-delay", "Initial Delay", - "The initial removal delay as specified in the HRD model in msec. " - "Not used when control-rate=disable", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_INITIAL_DELAY_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_CPB_SIZE, - g_param_spec_uint ("cpb-size", "CPB size", - "Coded Picture Buffer as specified in the HRD model in msec. " - "Not used when control-rate=disable", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_CPB_SIZE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_SCALING_LIST, - g_param_spec_enum ("scaling-list", "Scaling List", - "Scaling list mode", - GST_TYPE_OMX_VIDEO_ENC_SCALING_LIST, - GST_OMX_VIDEO_ENC_SCALING_LIST_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_LOW_BANDWIDTH, - g_param_spec_boolean ("low-bandwidth", "Low bandwidth mode", - "If enabled, decrease the vertical search range " - "used for P-frame motion estimation to reduce the bandwidth", - GST_OMX_VIDEO_ENC_LOW_BANDWIDTH_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_MAX_BITRATE, - g_param_spec_uint ("max-bitrate", "Max Bitrate", - "Max bitrate in bits per second, only used if control-rate=variable (0xffffffff=component default)", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_MAX_BITRATE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_ASPECT_RATIO, - g_param_spec_enum ("aspect-ratio", "Aspect ratio", - "Display aspect ratio of the video sequence to be written in SPS/VUI", - GST_TYPE_OMX_VIDEO_ENC_ASPECT_RATIO, - GST_OMX_VIDEO_ENC_ASPECT_RATIO_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_FILLER_DATA, - g_param_spec_boolean ("filler-data", "Filler Data", - "Enable/Disable Filler Data NAL units for CBR rate control", - GST_OMX_VIDEO_ENC_FILLER_DATA_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_NUM_SLICES, - g_param_spec_uint ("num-slices", "Number of slices", - "Number of slices produced for each frame. Each slice contains one or more complete macroblock/CTU row(s). " - "Slices are distributed over the frame as regularly as possible. If slice-size is defined as well more slices " - "may be produced to fit the slice-size requirement (0xffffffff=component default)", - 1, G_MAXUINT, GST_OMX_VIDEO_ENC_NUM_SLICES_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_SLICE_SIZE, - g_param_spec_uint ("slice-size", "Target slice size", - "Target slice size (in bytes) that the encoder uses to " - "automatically split the bitstream into approximately equally-sized slices", - 0, 65535, GST_OMX_VIDEO_ENC_SLICE_SIZE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_DEPENDENT_SLICE, - g_param_spec_boolean ("dependent-slice", "Dependent slice", - "If encoding with multiple slices, specify whether the additional slices are " - "dependent slice segments or regular slices", - GST_OMX_VIDEO_ENC_DEPENDENT_SLICE_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, PROP_DEFAULT_ROI_QUALITY, - g_param_spec_enum ("default-roi-quality", "Default ROI Qualtiy", - "The default quality level to apply to each Region of Interest", - GST_TYPE_OMX_VIDEO_ENC_ROI_QUALITY, - GST_OMX_VIDEO_ENC_DEFAULT_ROI_QUALITY, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, PROP_LONGTERM_REF, - g_param_spec_boolean ("long-term-ref", "LongTerm Reference Pictures", - "If enabled, encoder accepts dynamically inserting and using long-term reference " - "picture events from upstream elements", - GST_OMX_VIDEO_ENC_LONGTERM_REF_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_LONGTERM_FREQUENCY, - g_param_spec_uint ("long-term-freq", "LongTerm reference frequency", - "Periodicity of LongTerm reference picture marking in encoding process " - "Units in frames, distance between two consequtive long-term reference pictures", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_LONGTERM_REF_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); - - g_object_class_install_property (gobject_class, PROP_LOOK_AHEAD, - g_param_spec_uint ("look-ahead", "look ahead size", - "The number of frames processed ahead of second pass encoding. If smaller than 2, dual pass encoding is disabled", - 0, G_MAXUINT, GST_OMX_VIDEO_ENC_LOOK_AHEAD_DEFAULT, - G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | - GST_PARAM_MUTABLE_READY)); -#endif - - element_class->change_state = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_change_state); - - video_encoder_class->open = GST_DEBUG_FUNCPTR (gst_omx_video_enc_open); - video_encoder_class->close = GST_DEBUG_FUNCPTR (gst_omx_video_enc_close); - video_encoder_class->start = GST_DEBUG_FUNCPTR (gst_omx_video_enc_start); - video_encoder_class->stop = GST_DEBUG_FUNCPTR (gst_omx_video_enc_stop); - video_encoder_class->flush = GST_DEBUG_FUNCPTR (gst_omx_video_enc_flush); - video_encoder_class->set_format = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_set_format); - video_encoder_class->handle_frame = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_handle_frame); - video_encoder_class->finish = GST_DEBUG_FUNCPTR (gst_omx_video_enc_finish); - video_encoder_class->propose_allocation = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_propose_allocation); - video_encoder_class->getcaps = GST_DEBUG_FUNCPTR (gst_omx_video_enc_getcaps); - video_encoder_class->sink_event = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_sink_event); - video_encoder_class->decide_allocation = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_decide_allocation); - - klass->cdata.type = GST_OMX_COMPONENT_TYPE_FILTER; - klass->cdata.default_sink_template_caps = - GST_VIDEO_CAPS_MAKE (GST_OMX_VIDEO_ENC_SUPPORTED_FORMATS); - - klass->handle_output_frame = - GST_DEBUG_FUNCPTR (gst_omx_video_enc_handle_output_frame); -} - -static void -gst_omx_video_enc_init (GstOMXVideoEnc * self) -{ - self->control_rate = GST_OMX_VIDEO_ENC_CONTROL_RATE_DEFAULT; - self->target_bitrate = GST_OMX_VIDEO_ENC_TARGET_BITRATE_DEFAULT; - self->quant_i_frames = GST_OMX_VIDEO_ENC_QUANT_I_FRAMES_DEFAULT; - self->quant_p_frames = GST_OMX_VIDEO_ENC_QUANT_P_FRAMES_DEFAULT; - self->quant_b_frames = GST_OMX_VIDEO_ENC_QUANT_B_FRAMES_DEFAULT; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - self->qp_mode = GST_OMX_VIDEO_ENC_QP_MODE_DEFAULT; - self->min_qp = GST_OMX_VIDEO_ENC_MIN_QP_DEFAULT; - self->max_qp = GST_OMX_VIDEO_ENC_MAX_QP_DEFAULT; - self->gop_mode = GST_OMX_VIDEO_ENC_GOP_MODE_DEFAULT; - self->gdr_mode = GST_OMX_VIDEO_ENC_GDR_MODE_DEFAULT; - self->initial_delay = GST_OMX_VIDEO_ENC_INITIAL_DELAY_DEFAULT; - self->cpb_size = GST_OMX_VIDEO_ENC_CPB_SIZE_DEFAULT; - self->scaling_list = GST_OMX_VIDEO_ENC_SCALING_LIST_DEFAULT; - self->low_bandwidth = GST_OMX_VIDEO_ENC_LOW_BANDWIDTH_DEFAULT; - self->max_bitrate = GST_OMX_VIDEO_ENC_MAX_BITRATE_DEFAULT; - self->aspect_ratio = GST_OMX_VIDEO_ENC_ASPECT_RATIO_DEFAULT; - self->filler_data = GST_OMX_VIDEO_ENC_FILLER_DATA_DEFAULT; - self->num_slices = GST_OMX_VIDEO_ENC_NUM_SLICES_DEFAULT; - self->slice_size = GST_OMX_VIDEO_ENC_SLICE_SIZE_DEFAULT; - self->dependent_slice = GST_OMX_VIDEO_ENC_DEPENDENT_SLICE_DEFAULT; - self->default_roi_quality = GST_OMX_VIDEO_ENC_DEFAULT_ROI_QUALITY; - self->long_term_ref = GST_OMX_VIDEO_ENC_LONGTERM_REF_DEFAULT; - self->long_term_freq = GST_OMX_VIDEO_ENC_LONGTERM_FREQUENCY_DEFAULT; - self->look_ahead = GST_OMX_VIDEO_ENC_LOOK_AHEAD_DEFAULT; -#endif - - self->default_target_bitrate = GST_OMX_PROP_OMX_DEFAULT; - - g_mutex_init (&self->drain_lock); - g_cond_init (&self->drain_cond); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - self->alg_roi_quality_enum_class = - g_type_class_ref (GST_TYPE_OMX_VIDEO_ENC_ROI_QUALITY); -#endif -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - -#define CHECK_ERR(setting) \ - if (err == OMX_ErrorUnsupportedIndex || err == OMX_ErrorUnsupportedSetting) { \ - GST_WARNING_OBJECT (self, \ - "Setting " setting " parameters not supported by the component"); \ - } else if (err != OMX_ErrorNone) { \ - GST_ERROR_OBJECT (self, \ - "Failed to set " setting " parameters: %s (0x%08x)", \ - gst_omx_error_to_string (err), err); \ - return FALSE; \ - } - -static gboolean -set_zynqultrascaleplus_props (GstOMXVideoEnc * self) -{ - OMX_ERRORTYPE err; - OMX_ALG_VIDEO_PARAM_QUANTIZATION_CONTROL quant; - OMX_ALG_VIDEO_PARAM_QUANTIZATION_TABLE quant_table; - - if (self->qp_mode != GST_OMX_VIDEO_ENC_QP_MODE_DEFAULT) { - guint32 qp_mode = OMX_ALG_QP_CTRL_NONE; - guint32 qp_table = OMX_ALG_QP_TABLE_NONE; - - /* qp_mode should be mapped to combination QUANTIZATION_CONTROL & QUANTIZATION_TABLE Params */ - switch (self->qp_mode) { - case UNIFORM_QP: - qp_mode = OMX_ALG_QP_CTRL_NONE; - qp_table = OMX_ALG_QP_TABLE_NONE; - break; - case AUTO_QP: - qp_mode = OMX_ALG_QP_CTRL_AUTO; - qp_table = OMX_ALG_QP_TABLE_NONE; - break; - case ROI_QP: - qp_mode = OMX_ALG_QP_CTRL_NONE; - qp_table = OMX_ALG_QP_TABLE_RELATIVE; - break; - case LOAD_QP_ABSOLUTE: - qp_mode = OMX_ALG_QP_CTRL_NONE; - qp_table = OMX_ALG_QP_TABLE_ABSOLUTE; - break; - case LOAD_QP_RELATIVE: - qp_mode = OMX_ALG_QP_CTRL_NONE; - qp_table = OMX_ALG_QP_TABLE_RELATIVE; - break; - default: - GST_WARNING_OBJECT (self, - "Invalid option. Falling back to Uniform mode"); - break; - } - - GST_OMX_INIT_STRUCT (&quant); - quant.nPortIndex = self->enc_out_port->index; - quant.eQpControlMode = qp_mode; - - GST_DEBUG_OBJECT (self, "setting QP mode to %d", qp_mode); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoQuantizationControl, &quant); - CHECK_ERR ("quantization"); - - GST_OMX_INIT_STRUCT (&quant_table); - quant_table.nPortIndex = self->enc_out_port->index; - quant_table.eQpTableMode = qp_table; - - GST_DEBUG_OBJECT (self, "setting QP Table Mode to %d", qp_table); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoQuantizationTable, &quant_table); - CHECK_ERR ("quantization table"); - } - - { - OMX_ALG_VIDEO_PARAM_QUANTIZATION_EXTENSION qp_values; - - GST_OMX_INIT_STRUCT (&qp_values); - qp_values.nPortIndex = self->enc_out_port->index; - qp_values.nQpMin = self->min_qp; - qp_values.nQpMax = self->max_qp; - - GST_DEBUG_OBJECT (self, "setting min QP as %d and max QP as %d", - self->min_qp, self->max_qp); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoQuantizationExtension, - &qp_values); - CHECK_ERR ("min-qp and max-qp"); - } - - { - OMX_ALG_VIDEO_PARAM_GOP_CONTROL gop_mode; - - if (self->gdr_mode != OMX_ALG_GDR_OFF && - self->gop_mode != OMX_ALG_GOP_MODE_LOW_DELAY_P) { - GST_ERROR_OBJECT (self, - "gdr-mode mode only can be set if gop-mode=low-delay-p"); - return FALSE; - } - - GST_OMX_INIT_STRUCT (&gop_mode); - gop_mode.nPortIndex = self->enc_out_port->index; - gop_mode.eGopControlMode = self->gop_mode; - gop_mode.eGdrMode = self->gdr_mode; - - GST_DEBUG_OBJECT (self, "setting GOP mode to %d and GDR mode to %d", - self->gop_mode, self->gdr_mode); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoGopControl, &gop_mode); - CHECK_ERR ("GOP & GDR"); - } - - if (self->control_rate != OMX_Video_ControlRateDisable) { - if (self->cpb_size < self->initial_delay) { - GST_ERROR_OBJECT (self, - "cpb-size (%d) cannot be smaller than initial-delay (%d)", - self->cpb_size, self->initial_delay); - g_critical ("cpb-size (%d) cannot be smaller than initial-delay (%d)", - self->cpb_size, self->initial_delay); - } else { - OMX_ALG_VIDEO_PARAM_CODED_PICTURE_BUFFER cpb; - - GST_OMX_INIT_STRUCT (&cpb); - cpb.nPortIndex = self->enc_out_port->index; - cpb.nCodedPictureBufferSize = self->cpb_size; - cpb.nInitialRemovalDelay = self->initial_delay; - - GST_DEBUG_OBJECT (self, "setting cpb size to %d and initial delay to %d", - self->cpb_size, self->initial_delay); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoCodedPictureBuffer, &cpb); - CHECK_ERR ("cpb size & initial delay"); - } - } - - { - OMX_ALG_VIDEO_PARAM_SCALING_LIST scaling_list; - - GST_OMX_INIT_STRUCT (&scaling_list); - scaling_list.nPortIndex = self->enc_out_port->index; - scaling_list.eScalingListMode = self->scaling_list; - - GST_DEBUG_OBJECT (self, "setting scaling list mode as %d", - self->scaling_list); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoScalingList, &scaling_list); - CHECK_ERR ("scaling-list"); - } - - { - OMX_ALG_VIDEO_PARAM_LOW_BANDWIDTH low_bw; - - GST_OMX_INIT_STRUCT (&low_bw); - low_bw.nPortIndex = self->enc_out_port->index; - low_bw.bEnableLowBandwidth = self->low_bandwidth; - - GST_DEBUG_OBJECT (self, "%s low bandwith moded", - self->low_bandwidth ? "Enable" : "Disable"); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoLowBandwidth, &low_bw); - CHECK_ERR ("low-bandwidth"); - } - - if (self->max_bitrate != GST_OMX_VIDEO_ENC_MAX_BITRATE_DEFAULT) { - OMX_ALG_VIDEO_PARAM_MAX_BITRATE max_bitrate; - - GST_OMX_INIT_STRUCT (&max_bitrate); - max_bitrate.nPortIndex = self->enc_out_port->index; - /* nMaxBitrate is in kbps while max-bitrate is in bps */ - max_bitrate.nMaxBitrate = self->max_bitrate / 1000; - - GST_DEBUG_OBJECT (self, "setting max bitrate to %d", self->max_bitrate); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoMaxBitrate, &max_bitrate); - CHECK_ERR ("max-bitrate"); - } - - { - OMX_ALG_VIDEO_PARAM_ASPECT_RATIO aspect_ratio; - - GST_OMX_INIT_STRUCT (&aspect_ratio); - aspect_ratio.nPortIndex = self->enc_out_port->index; - aspect_ratio.eAspectRatio = self->aspect_ratio; - - GST_DEBUG_OBJECT (self, "setting aspect ratio to %d", self->aspect_ratio); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoAspectRatio, &aspect_ratio); - CHECK_ERR ("aspect-ratio"); - } - - { - OMX_ALG_VIDEO_PARAM_FILLER_DATA filler_data; - - GST_OMX_INIT_STRUCT (&filler_data); - filler_data.nPortIndex = self->enc_out_port->index; - filler_data.bDisableFillerData = !(self->filler_data); - - GST_DEBUG_OBJECT (self, "%s filler data", - self->filler_data ? "Enable" : "Disable"); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoFillerData, &filler_data); - CHECK_ERR ("filler-data"); - } - - if (self->num_slices != GST_OMX_VIDEO_ENC_NUM_SLICES_DEFAULT || - self->slice_size != GST_OMX_VIDEO_ENC_SLICE_SIZE_DEFAULT) { - OMX_ALG_VIDEO_PARAM_SLICES slices; - - GST_OMX_INIT_STRUCT (&slices); - slices.nPortIndex = self->enc_out_port->index; - - err = gst_omx_component_get_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoSlices, &slices); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Error getting slice parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - if (self->num_slices != GST_OMX_VIDEO_ENC_NUM_SLICES_DEFAULT) { - slices.nNumSlices = self->num_slices; - GST_DEBUG_OBJECT (self, - "setting number of slices to %d (dependent slices: %d)", - self->num_slices, self->dependent_slice); - } - - if (self->slice_size != GST_OMX_VIDEO_ENC_SLICE_SIZE_DEFAULT) { - slices.nSlicesSize = self->slice_size; - GST_DEBUG_OBJECT (self, "setting slice size to %d (dependent slices: %d)", - self->slice_size, self->dependent_slice); - } - - slices.bDependentSlices = self->dependent_slice; - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoSlices, &slices); - CHECK_ERR ("slices"); - } - - { - OMX_ALG_VIDEO_PARAM_LONG_TERM longterm; - GST_OMX_INIT_STRUCT (&longterm); - longterm.nPortIndex = self->enc_out_port->index; - longterm.bEnableLongTerm = self->long_term_ref; - longterm.nLongTermFrequency = self->long_term_freq; - - GST_DEBUG_OBJECT (self, "setting long-term ref to %d, long-term-freq to %d", - self->long_term_ref, self->long_term_freq); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoLongTerm, &longterm); - CHECK_ERR ("longterm"); - } - - { - OMX_ALG_VIDEO_PARAM_LOOKAHEAD look_ahead; - - GST_OMX_INIT_STRUCT (&look_ahead); - look_ahead.nPortIndex = self->enc_in_port->index; - look_ahead.nLookAhead = self->look_ahead; - - GST_DEBUG_OBJECT (self, "setting look_ahead to %d", self->look_ahead); - - err = - gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoLookAhead, &look_ahead); - CHECK_ERR ("look-ahead"); - } - - return TRUE; -} -#endif - -static gboolean -gst_omx_video_enc_set_bitrate (GstOMXVideoEnc * self) -{ - OMX_ERRORTYPE err; - OMX_VIDEO_PARAM_BITRATETYPE bitrate_param; - gboolean result = TRUE; - - GST_OBJECT_LOCK (self); - - GST_OMX_INIT_STRUCT (&bitrate_param); - bitrate_param.nPortIndex = self->enc_out_port->index; - - err = gst_omx_component_get_parameter (self->enc, - OMX_IndexParamVideoBitrate, &bitrate_param); - - if (err == OMX_ErrorNone) { -#ifdef USE_OMX_TARGET_RPI - /* FIXME: Workaround for RPi returning garbage for this parameter */ - if (bitrate_param.nVersion.nVersion == 0) { - GST_OMX_INIT_STRUCT (&bitrate_param); - bitrate_param.nPortIndex = self->enc_out_port->index; - } -#endif - if (self->default_target_bitrate == GST_OMX_PROP_OMX_DEFAULT) - /* Save the actual OMX default so we can restore it if needed */ - self->default_target_bitrate = bitrate_param.nTargetBitrate; - - if (self->control_rate != 0xffffffff) - bitrate_param.eControlRate = self->control_rate; - if (self->target_bitrate != 0xffffffff) - bitrate_param.nTargetBitrate = self->target_bitrate; - else - bitrate_param.nTargetBitrate = self->default_target_bitrate; - - err = - gst_omx_component_set_parameter (self->enc, - OMX_IndexParamVideoBitrate, &bitrate_param); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting a bitrate not supported by the component"); - } else if (err == OMX_ErrorUnsupportedSetting) { - GST_WARNING_OBJECT (self, - "Setting bitrate settings %u %u not supported by the component", - self->control_rate, self->target_bitrate); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set bitrate parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - result = FALSE; - } - } else { - GST_ERROR_OBJECT (self, "Failed to get bitrate parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - - GST_OBJECT_UNLOCK (self); - return result; -} - -static gboolean -gst_omx_video_enc_open (GstVideoEncoder * encoder) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (encoder); - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - gint in_port_index, out_port_index; - - self->enc = - gst_omx_component_new (GST_OBJECT_CAST (self), klass->cdata.core_name, - klass->cdata.component_name, klass->cdata.component_role, - klass->cdata.hacks); - self->started = FALSE; - - if (!self->enc) - return FALSE; - - if (gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded) - return FALSE; - - in_port_index = klass->cdata.in_port_index; - out_port_index = klass->cdata.out_port_index; - - if (in_port_index == -1 || out_port_index == -1) { - OMX_PORT_PARAM_TYPE param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - - err = - gst_omx_component_get_parameter (self->enc, OMX_IndexParamVideoInit, - ¶m); - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't get port information: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* Fallback */ - in_port_index = 0; - out_port_index = 1; - } else { - GST_DEBUG_OBJECT (self, "Detected %u ports, starting at %u", - (guint) param.nPorts, (guint) param.nStartPortNumber); - in_port_index = param.nStartPortNumber + 0; - out_port_index = param.nStartPortNumber + 1; - } - } - - self->enc_in_port = gst_omx_component_add_port (self->enc, in_port_index); - self->enc_out_port = gst_omx_component_add_port (self->enc, out_port_index); - - if (!self->enc_in_port || !self->enc_out_port) - return FALSE; - - /* Set properties */ - { - OMX_ERRORTYPE err; - - if (!gst_omx_video_enc_set_bitrate (self)) - return FALSE; - - if (self->quant_i_frames != 0xffffffff || - self->quant_p_frames != 0xffffffff || - self->quant_b_frames != 0xffffffff) { - OMX_VIDEO_PARAM_QUANTIZATIONTYPE quant_param; - - GST_OMX_INIT_STRUCT (&quant_param); - quant_param.nPortIndex = self->enc_out_port->index; - - err = gst_omx_component_get_parameter (self->enc, - OMX_IndexParamVideoQuantization, &quant_param); - - if (err == OMX_ErrorNone) { - - if (self->quant_i_frames != 0xffffffff) - quant_param.nQpI = self->quant_i_frames; - if (self->quant_p_frames != 0xffffffff) - quant_param.nQpP = self->quant_p_frames; - if (self->quant_b_frames != 0xffffffff) - quant_param.nQpB = self->quant_b_frames; - - err = - gst_omx_component_set_parameter (self->enc, - OMX_IndexParamVideoQuantization, &quant_param); - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting quantization parameters not supported by the component"); - } else if (err == OMX_ErrorUnsupportedSetting) { - GST_WARNING_OBJECT (self, - "Setting quantization parameters %u %u %u not supported by the component", - self->quant_i_frames, self->quant_p_frames, self->quant_b_frames); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set quantization parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - } else { - GST_ERROR_OBJECT (self, - "Failed to get quantization parameters: %s (0x%08x)", - gst_omx_error_to_string (err), err); - - } - } - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (!set_zynqultrascaleplus_props (self)) - return FALSE; -#endif - - return TRUE; -} - -static gboolean -gst_omx_video_enc_deallocate_in_buffers (GstOMXVideoEnc * self) -{ - /* Pool will take care of deallocating buffers when deactivated upstream */ - if (!self->in_pool_used - && gst_omx_port_deallocate_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - - return TRUE; -} - -static gboolean -gst_omx_video_enc_shutdown (GstOMXVideoEnc * self) -{ - OMX_STATETYPE state; - - GST_DEBUG_OBJECT (self, "Shutting down encoder"); - - state = gst_omx_component_get_state (self->enc, 0); - if (state > OMX_StateLoaded || state == OMX_StateInvalid) { - if (state > OMX_StateIdle) { - gst_omx_component_set_state (self->enc, OMX_StateIdle); - gst_omx_component_get_state (self->enc, 5 * GST_SECOND); - } - gst_omx_component_set_state (self->enc, OMX_StateLoaded); - gst_omx_video_enc_deallocate_in_buffers (self); - gst_omx_port_deallocate_buffers (self->enc_out_port); - if (state > OMX_StateLoaded) - gst_omx_component_get_state (self->enc, 5 * GST_SECOND); - } - - return TRUE; -} - -static gboolean -gst_omx_video_enc_close (GstVideoEncoder * encoder) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Closing encoder"); - - if (!gst_omx_video_enc_shutdown (self)) - return FALSE; - - self->enc_in_port = NULL; - self->enc_out_port = NULL; - if (self->enc) - gst_omx_component_unref (self->enc); - self->enc = NULL; - - self->started = FALSE; - - return TRUE; -} - -static void -gst_omx_video_enc_finalize (GObject * object) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (object); - - g_mutex_clear (&self->drain_lock); - g_cond_clear (&self->drain_cond); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - g_clear_pointer (&self->alg_roi_quality_enum_class, g_type_class_unref); -#endif - - G_OBJECT_CLASS (gst_omx_video_enc_parent_class)->finalize (object); -} - -static void -gst_omx_video_enc_set_property (GObject * object, guint prop_id, - const GValue * value, GParamSpec * pspec) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (object); - - switch (prop_id) { - case PROP_CONTROL_RATE: - self->control_rate = g_value_get_enum (value); - break; - case PROP_TARGET_BITRATE: - GST_OBJECT_LOCK (self); - self->target_bitrate = g_value_get_uint (value); - if (self->enc) { - OMX_VIDEO_CONFIG_BITRATETYPE config; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (&config); - config.nPortIndex = self->enc_out_port->index; - config.nEncodeBitrate = self->target_bitrate; - err = - gst_omx_component_set_config (self->enc, - OMX_IndexConfigVideoBitrate, &config); - if (err != OMX_ErrorNone) - GST_ERROR_OBJECT (self, - "Failed to set bitrate parameter: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } - GST_OBJECT_UNLOCK (self); - break; - case PROP_QUANT_I_FRAMES: - self->quant_i_frames = g_value_get_uint (value); - break; - case PROP_QUANT_P_FRAMES: - self->quant_p_frames = g_value_get_uint (value); - break; - case PROP_QUANT_B_FRAMES: - self->quant_b_frames = g_value_get_uint (value); - break; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case PROP_QP_MODE: - self->qp_mode = g_value_get_enum (value); - break; - case PROP_MIN_QP: - self->min_qp = g_value_get_uint (value); - break; - case PROP_MAX_QP: - self->max_qp = g_value_get_uint (value); - break; - case PROP_GOP_MODE: - self->gop_mode = g_value_get_enum (value); - break; - case PROP_GDR_MODE: - self->gdr_mode = g_value_get_enum (value); - break; - case PROP_INITIAL_DELAY: - self->initial_delay = g_value_get_uint (value); - break; - case PROP_CPB_SIZE: - self->cpb_size = g_value_get_uint (value); - break; - case PROP_SCALING_LIST: - self->scaling_list = g_value_get_enum (value); - break; - case PROP_LOW_BANDWIDTH: - self->low_bandwidth = g_value_get_boolean (value); - break; - case PROP_MAX_BITRATE: - self->max_bitrate = g_value_get_uint (value); - break; - case PROP_ASPECT_RATIO: - self->aspect_ratio = g_value_get_enum (value); - break; - case PROP_FILLER_DATA: - self->filler_data = g_value_get_boolean (value); - break; - case PROP_NUM_SLICES: - self->num_slices = g_value_get_uint (value); - break; - case PROP_SLICE_SIZE: - self->slice_size = g_value_get_uint (value); - break; - case PROP_DEPENDENT_SLICE: - self->dependent_slice = g_value_get_boolean (value); - break; - case PROP_DEFAULT_ROI_QUALITY: - self->default_roi_quality = g_value_get_enum (value); - break; - case PROP_LONGTERM_REF: - self->long_term_ref = g_value_get_boolean (value); - break; - case PROP_LONGTERM_FREQUENCY: - self->long_term_freq = g_value_get_uint (value); - break; - case PROP_LOOK_AHEAD: - self->look_ahead = g_value_get_uint (value); - break; -#endif - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static void -gst_omx_video_enc_get_property (GObject * object, guint prop_id, GValue * value, - GParamSpec * pspec) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (object); - - switch (prop_id) { - case PROP_CONTROL_RATE: - g_value_set_enum (value, self->control_rate); - break; - case PROP_TARGET_BITRATE: - GST_OBJECT_LOCK (self); - g_value_set_uint (value, self->target_bitrate); - GST_OBJECT_UNLOCK (self); - break; - case PROP_QUANT_I_FRAMES: - g_value_set_uint (value, self->quant_i_frames); - break; - case PROP_QUANT_P_FRAMES: - g_value_set_uint (value, self->quant_p_frames); - break; - case PROP_QUANT_B_FRAMES: - g_value_set_uint (value, self->quant_b_frames); - break; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - case PROP_QP_MODE: - g_value_set_enum (value, self->qp_mode); - break; - case PROP_MIN_QP: - g_value_set_uint (value, self->min_qp); - break; - case PROP_MAX_QP: - g_value_set_uint (value, self->max_qp); - break; - case PROP_GOP_MODE: - g_value_set_enum (value, self->gop_mode); - break; - case PROP_GDR_MODE: - g_value_set_enum (value, self->gdr_mode); - break; - case PROP_INITIAL_DELAY: - g_value_set_uint (value, self->initial_delay); - break; - case PROP_CPB_SIZE: - g_value_set_uint (value, self->cpb_size); - break; - case PROP_SCALING_LIST: - g_value_set_enum (value, self->scaling_list); - break; - case PROP_LOW_BANDWIDTH: - g_value_set_boolean (value, self->low_bandwidth); - break; - case PROP_MAX_BITRATE: - g_value_set_uint (value, self->max_bitrate); - break; - case PROP_ASPECT_RATIO: - g_value_set_enum (value, self->aspect_ratio); - break; - case PROP_FILLER_DATA: - g_value_set_boolean (value, self->filler_data); - break; - case PROP_NUM_SLICES: - g_value_set_uint (value, self->num_slices); - break; - case PROP_SLICE_SIZE: - g_value_set_uint (value, self->slice_size); - break; - case PROP_DEPENDENT_SLICE: - g_value_set_boolean (value, self->dependent_slice); - break; - case PROP_DEFAULT_ROI_QUALITY: - g_value_set_enum (value, self->default_roi_quality); - break; - case PROP_LONGTERM_REF: - g_value_set_boolean (value, self->long_term_ref); - break; - case PROP_LONGTERM_FREQUENCY: - g_value_set_uint (value, self->long_term_freq); - break; - case PROP_LOOK_AHEAD: - g_value_set_uint (value, self->look_ahead); - break; -#endif - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); - break; - } -} - -static GstStateChangeReturn -gst_omx_video_enc_change_state (GstElement * element, GstStateChange transition) -{ - GstOMXVideoEnc *self; - GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS; - - g_return_val_if_fail (GST_IS_OMX_VIDEO_ENC (element), - GST_STATE_CHANGE_FAILURE); - self = GST_OMX_VIDEO_ENC (element); - - switch (transition) { - case GST_STATE_CHANGE_NULL_TO_READY: - break; - case GST_STATE_CHANGE_READY_TO_PAUSED: - self->downstream_flow_ret = GST_FLOW_OK; - - self->draining = FALSE; - self->started = FALSE; - break; - case GST_STATE_CHANGE_PAUSED_TO_PLAYING: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - if (self->enc_in_port) - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, TRUE); - if (self->enc_out_port) - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - break; - default: - break; - } - - if (ret == GST_STATE_CHANGE_FAILURE) - return ret; - - ret = - GST_ELEMENT_CLASS (gst_omx_video_enc_parent_class)->change_state (element, - transition); - - if (ret == GST_STATE_CHANGE_FAILURE) - return ret; - - switch (transition) { - case GST_STATE_CHANGE_PLAYING_TO_PAUSED: - break; - case GST_STATE_CHANGE_PAUSED_TO_READY: - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - break; - case GST_STATE_CHANGE_READY_TO_NULL: - break; - default: - break; - } - - return ret; -} - -static gboolean -get_chroma_info_from_input (GstOMXVideoEnc * self, const gchar ** chroma_format, - guint * bit_depth_luma, guint * bit_depth_chroma) -{ - switch (self->input_state->info.finfo->format) { - case GST_VIDEO_FORMAT_GRAY8: - *chroma_format = "4:0:0"; - *bit_depth_luma = 8; - *bit_depth_chroma = 0; - break; - case GST_VIDEO_FORMAT_I420: - case GST_VIDEO_FORMAT_NV12: - *chroma_format = "4:2:0"; - *bit_depth_luma = *bit_depth_chroma = 8; - break; - case GST_VIDEO_FORMAT_NV16: - case GST_VIDEO_FORMAT_YUY2: - case GST_VIDEO_FORMAT_YVYU: - case GST_VIDEO_FORMAT_UYVY: - *chroma_format = "4:2:2"; - *bit_depth_luma = *bit_depth_chroma = 8; - break; - case GST_VIDEO_FORMAT_GRAY10_LE32: - *chroma_format = "4:0:0"; - *bit_depth_luma = 10; - *bit_depth_chroma = 0; - break; - case GST_VIDEO_FORMAT_NV12_10LE32: - *chroma_format = "4:2:0"; - *bit_depth_luma = *bit_depth_chroma = 10; - break; - case GST_VIDEO_FORMAT_NV16_10LE32: - *chroma_format = "4:2:2"; - *bit_depth_luma = *bit_depth_chroma = 10; - break; - default: - return FALSE; - } - - return TRUE; -} - -static GstCaps * -get_output_caps (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - GstCaps *caps; - const gchar *chroma_format; - guint bit_depth_luma, bit_depth_chroma; - - caps = klass->get_caps (self, self->enc_out_port, self->input_state); - - /* Add chroma info about the encoded stream inferred from the format of the input */ - if (get_chroma_info_from_input (self, &chroma_format, &bit_depth_luma, - &bit_depth_chroma)) { - GST_DEBUG_OBJECT (self, - "adding chroma info to output caps: %s (luma %d bits) (chroma %d bits)", - chroma_format, bit_depth_luma, bit_depth_chroma); - - gst_caps_set_simple (caps, "chroma-format", G_TYPE_STRING, chroma_format, - "bit-depth-luma", G_TYPE_UINT, bit_depth_luma, - "bit-depth-chroma", G_TYPE_UINT, bit_depth_chroma, NULL); - } - - return caps; -} - -static GstFlowReturn -gst_omx_video_enc_handle_output_frame (GstOMXVideoEnc * self, GstOMXPort * port, - GstOMXBuffer * buf, GstVideoCodecFrame * frame) -{ - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - GstFlowReturn flow_ret = GST_FLOW_OK; - - if ((buf->omx_buf->nFlags & OMX_BUFFERFLAG_CODECCONFIG) - && buf->omx_buf->nFilledLen > 0) { - GstVideoCodecState *state; - GstBuffer *codec_data; - GstMapInfo map = GST_MAP_INFO_INIT; - GstCaps *caps; - - GST_DEBUG_OBJECT (self, "Handling codec data"); - - caps = get_output_caps (self); - codec_data = gst_buffer_new_and_alloc (buf->omx_buf->nFilledLen); - - gst_buffer_map (codec_data, &map, GST_MAP_WRITE); - memcpy (map.data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - gst_buffer_unmap (codec_data, &map); - state = - gst_video_encoder_set_output_state (GST_VIDEO_ENCODER (self), caps, - self->input_state); - state->codec_data = codec_data; - gst_video_codec_state_unref (state); - if (!gst_video_encoder_negotiate (GST_VIDEO_ENCODER (self))) { - gst_video_codec_frame_unref (frame); - GST_ERROR_OBJECT (self, - "Downstream element refused to negotiate codec_data in the caps"); - return GST_FLOW_NOT_NEGOTIATED; - } - gst_video_codec_frame_unref (frame); - flow_ret = GST_FLOW_OK; - } else if (buf->omx_buf->nFilledLen > 0) { - GstBuffer *outbuf; - GstMapInfo map = GST_MAP_INFO_INIT; - - GST_DEBUG_OBJECT (self, "Handling output data"); - - outbuf = gst_buffer_new_and_alloc (buf->omx_buf->nFilledLen); - - gst_buffer_map (outbuf, &map, GST_MAP_WRITE); - memcpy (map.data, - buf->omx_buf->pBuffer + buf->omx_buf->nOffset, - buf->omx_buf->nFilledLen); - gst_buffer_unmap (outbuf, &map); - - GST_BUFFER_TIMESTAMP (outbuf) = - gst_util_uint64_scale (GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp), - GST_SECOND, OMX_TICKS_PER_SECOND); - if (buf->omx_buf->nTickCount != 0) - GST_BUFFER_DURATION (outbuf) = - gst_util_uint64_scale (buf->omx_buf->nTickCount, GST_SECOND, - OMX_TICKS_PER_SECOND); - - if ((klass->cdata.hacks & GST_OMX_HACK_SYNCFRAME_FLAG_NOT_USED) - || (buf->omx_buf->nFlags & OMX_BUFFERFLAG_SYNCFRAME)) { - if (frame) - GST_VIDEO_CODEC_FRAME_SET_SYNC_POINT (frame); - else - GST_BUFFER_FLAG_UNSET (outbuf, GST_BUFFER_FLAG_DELTA_UNIT); - } else { - if (frame) - GST_VIDEO_CODEC_FRAME_UNSET_SYNC_POINT (frame); - else - GST_BUFFER_FLAG_SET (outbuf, GST_BUFFER_FLAG_DELTA_UNIT); - } - - if (frame) { - frame->output_buffer = outbuf; - if ((buf->omx_buf->nFlags & OMX_BUFFERFLAG_ENDOFFRAME) - || !gst_omx_port_get_subframe (self->enc_out_port)) { - flow_ret = - gst_video_encoder_finish_frame (GST_VIDEO_ENCODER (self), frame); - if (!(buf->omx_buf->nFlags & OMX_BUFFERFLAG_ENDOFFRAME)) - GST_WARNING_OBJECT (self, - "OMX_BUFFERFLAG_ENDOFFRAME is missing in flags 0x%x", - (guint) buf->omx_buf->nFlags); - } else { - flow_ret = - gst_video_encoder_finish_subframe (GST_VIDEO_ENCODER (self), frame); - gst_video_codec_frame_unref (frame); - } - } else { - GST_ERROR_OBJECT (self, "No corresponding frame found"); - flow_ret = gst_pad_push (GST_VIDEO_ENCODER_SRC_PAD (self), outbuf); - } - } else if (frame != NULL) { - /* Just ignore empty buffers, don't drop a frame for that */ - flow_ret = GST_FLOW_OK; - gst_video_codec_frame_unref (frame); - } - - return flow_ret; -} - -static gboolean -gst_omx_video_enc_ensure_nb_out_buffers (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - guint extra = 0; - - if (!(klass->cdata.hacks & GST_OMX_HACK_ENSURE_BUFFER_COUNT_ACTUAL)) - return TRUE; - - /* If dowstream tell us how many buffers it needs allocate as many extra buffers so we won't starve - * if it keeps them downstream (like when using dynamic mode). */ - if (self->nb_downstream_buffers) - extra = self->nb_downstream_buffers; - - if (!gst_omx_port_ensure_buffer_count_actual (self->enc_out_port, extra)) - return FALSE; - - return TRUE; -} - -static gboolean -gst_omx_video_enc_allocate_out_buffers (GstOMXVideoEnc * self) -{ - if (gst_omx_port_allocate_buffers (self->enc_out_port) != OMX_ErrorNone) - return FALSE; - - return TRUE; -} - -static void -gst_omx_video_enc_pause_loop (GstOMXVideoEnc * self, GstFlowReturn flow_ret) -{ - g_mutex_lock (&self->drain_lock); - if (self->draining) { - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - } - gst_pad_pause_task (GST_VIDEO_ENCODER_SRC_PAD (self)); - self->downstream_flow_ret = flow_ret; - self->started = FALSE; - g_mutex_unlock (&self->drain_lock); -} - -static void -gst_omx_video_enc_loop (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass; - GstOMXPort *port = self->enc_out_port; - GstOMXBuffer *buf = NULL; - GstVideoCodecFrame *frame; - GstFlowReturn flow_ret = GST_FLOW_OK; - GstOMXAcquireBufferReturn acq_return; - OMX_ERRORTYPE err; - - klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - - acq_return = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - if (acq_return == GST_OMX_ACQUIRE_BUFFER_ERROR) { - goto component_error; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - goto flushing; - } else if (acq_return == GST_OMX_ACQUIRE_BUFFER_EOS) { - goto eos; - } - - if (!gst_pad_has_current_caps (GST_VIDEO_ENCODER_SRC_PAD (self)) - || acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - GstCaps *caps; - GstVideoCodecState *state; - - GST_DEBUG_OBJECT (self, "Port settings have changed, updating caps"); - - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE - && gst_omx_port_is_enabled (port)) { - /* Reallocate all buffers */ - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } - - GST_VIDEO_ENCODER_STREAM_LOCK (self); - - caps = get_output_caps (self); - if (!caps) { - if (buf) - gst_omx_port_release_buffer (self->enc_out_port, buf); - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - goto caps_failed; - } - - GST_DEBUG_OBJECT (self, "Setting output state: %" GST_PTR_FORMAT, caps); - - state = - gst_video_encoder_set_output_state (GST_VIDEO_ENCODER (self), caps, - self->input_state); - gst_video_codec_state_unref (state); - - if (!gst_video_encoder_negotiate (GST_VIDEO_ENCODER (self))) { - if (buf) - gst_omx_port_release_buffer (self->enc_out_port, buf); - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - goto caps_failed; - } - - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - - if (acq_return == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - if (!gst_omx_video_enc_ensure_nb_out_buffers (self)) - goto reconfigure_error; - - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - if (!gst_omx_video_enc_allocate_out_buffers (self)) - goto reconfigure_error; - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_populate (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) - goto reconfigure_error; - } - - /* Now get a buffer */ - if (acq_return != GST_OMX_ACQUIRE_BUFFER_OK) { - return; - } - } - - g_assert (acq_return == GST_OMX_ACQUIRE_BUFFER_OK); - - /* This prevents a deadlock between the srcpad stream - * lock and the videocodec stream lock, if ::flush() - * is called at the wrong time - */ - if (gst_omx_port_is_flushing (self->enc_out_port)) { - GST_DEBUG_OBJECT (self, "Flushing"); - gst_omx_port_release_buffer (self->enc_out_port, buf); - goto flushing; - } - - GST_DEBUG_OBJECT (self, "Handling buffer: 0x%08x (%s) %" G_GUINT64_FORMAT, - (guint) buf->omx_buf->nFlags, - gst_omx_buffer_flags_to_string (buf->omx_buf->nFlags), - (guint64) GST_OMX_GET_TICKS (buf->omx_buf->nTimeStamp)); - - frame = gst_omx_video_find_nearest_frame (GST_ELEMENT_CAST (self), buf, - gst_video_encoder_get_frames (GST_VIDEO_ENCODER (self))); - - g_assert (klass->handle_output_frame); - - if (frame) - flow_ret = - klass->handle_output_frame (self, self->enc_out_port, buf, frame); - else { - gst_omx_port_release_buffer (self->enc_out_port, buf); - goto flow_error; - } - - - GST_DEBUG_OBJECT (self, "Finished frame: %s", gst_flow_get_name (flow_ret)); - - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - - GST_VIDEO_ENCODER_STREAM_LOCK (self); - self->downstream_flow_ret = flow_ret; - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - - GST_DEBUG_OBJECT (self, "Read frame from component"); - - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - return; - -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc))); - gst_pad_push_event (GST_VIDEO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_enc_pause_loop (self, GST_FLOW_ERROR); - return; - } -flushing: - { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - gst_omx_video_enc_pause_loop (self, GST_FLOW_FLUSHING); - return; - } - -eos: - { - g_mutex_lock (&self->drain_lock); - if (self->draining) { - GST_DEBUG_OBJECT (self, "Drained"); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - flow_ret = GST_FLOW_OK; - gst_pad_pause_task (GST_VIDEO_ENCODER_SRC_PAD (self)); - } else { - GST_DEBUG_OBJECT (self, "Component signalled EOS"); - flow_ret = GST_FLOW_EOS; - } - g_mutex_unlock (&self->drain_lock); - - GST_VIDEO_ENCODER_STREAM_LOCK (self); - self->downstream_flow_ret = flow_ret; - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - - /* Here we fallback and pause the task for the EOS case */ - if (flow_ret != GST_FLOW_OK) - goto flow_error; - - return; - } -flow_error: - { - if (flow_ret == GST_FLOW_EOS) { - GST_DEBUG_OBJECT (self, "EOS"); - - gst_pad_push_event (GST_VIDEO_ENCODER_SRC_PAD (self), - gst_event_new_eos ()); - } else if (flow_ret < GST_FLOW_EOS) { - GST_ELEMENT_ERROR (self, STREAM, FAILED, ("Internal data stream error."), - ("stream stopped, reason %s", gst_flow_get_name (flow_ret))); - - gst_pad_push_event (GST_VIDEO_ENCODER_SRC_PAD (self), - gst_event_new_eos ()); - } else if (flow_ret == GST_FLOW_FLUSHING) { - GST_DEBUG_OBJECT (self, "Flushing -- stopping task"); - } - gst_omx_video_enc_pause_loop (self, flow_ret); - return; - } -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure output port")); - gst_pad_push_event (GST_VIDEO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_enc_pause_loop (self, GST_FLOW_NOT_NEGOTIATED); - return; - } -caps_failed: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), ("Failed to set caps")); - gst_pad_push_event (GST_VIDEO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_enc_pause_loop (self, GST_FLOW_NOT_NEGOTIATED); - return; - } -release_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase output buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - gst_pad_push_event (GST_VIDEO_ENCODER_SRC_PAD (self), gst_event_new_eos ()); - gst_omx_video_enc_pause_loop (self, GST_FLOW_ERROR); - return; - } -} - -static gboolean -gst_omx_video_enc_start (GstVideoEncoder * encoder) -{ - GstOMXVideoEnc *self; - - self = GST_OMX_VIDEO_ENC (encoder); - - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - self->nb_downstream_buffers = 0; - self->in_pool_used = FALSE; - - return TRUE; -} - -static gboolean -gst_omx_video_enc_stop (GstVideoEncoder * encoder) -{ - GstOMXVideoEnc *self; - - self = GST_OMX_VIDEO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Stopping encoder"); - - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - gst_pad_stop_task (GST_VIDEO_ENCODER_SRC_PAD (encoder)); - - if (gst_omx_component_get_state (self->enc, 0) > OMX_StateIdle) - gst_omx_component_set_state (self->enc, OMX_StateIdle); - - self->downstream_flow_ret = GST_FLOW_FLUSHING; - self->started = FALSE; - - if (self->input_state) - gst_video_codec_state_unref (self->input_state); - self->input_state = NULL; - - g_mutex_lock (&self->drain_lock); - self->draining = FALSE; - g_cond_broadcast (&self->drain_cond); - g_mutex_unlock (&self->drain_lock); - - self->default_target_bitrate = GST_OMX_PROP_OMX_DEFAULT; - - gst_omx_component_get_state (self->enc, 5 * GST_SECOND); - - return TRUE; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static void -gst_omx_video_enc_set_latency (GstOMXVideoEnc * self) -{ - GstClockTime latency; - OMX_ALG_PARAM_REPORTED_LATENCY param; - OMX_ERRORTYPE err; - - GST_OMX_INIT_STRUCT (¶m); - err = - gst_omx_component_get_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamReportedLatency, ¶m); - - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, "Couldn't retrieve latency: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return; - } - - GST_DEBUG_OBJECT (self, "retrieved latency of %d ms", - (guint32) param.nLatency); - - /* Convert to ns */ - latency = param.nLatency * GST_MSECOND; - - gst_video_encoder_set_latency (GST_VIDEO_ENCODER (self), latency, latency); -} -#endif - -static gboolean -gst_omx_video_enc_disable (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass; - - klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - - GST_DEBUG_OBJECT (self, "Need to disable and drain encoder"); - gst_omx_video_enc_drain (self); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - /* Wait until the srcpad loop is finished, - * unlock GST_VIDEO_ENCODER_STREAM_LOCK to prevent deadlocks - * caused by using this lock from inside the loop function */ - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - gst_pad_stop_task (GST_VIDEO_ENCODER_SRC_PAD (self)); - GST_VIDEO_ENCODER_STREAM_LOCK (self); - - if (klass->cdata.hacks & GST_OMX_HACK_NO_COMPONENT_RECONFIGURE) { - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - gst_omx_video_enc_stop (GST_VIDEO_ENCODER (self)); - gst_omx_video_enc_close (GST_VIDEO_ENCODER (self)); - GST_VIDEO_ENCODER_STREAM_LOCK (self); - - if (!gst_omx_video_enc_open (GST_VIDEO_ENCODER (self))) - return FALSE; - - /* The decoder is returned to initial state */ - self->disabled = FALSE; - } else { - /* Disabling at the same time input port and output port is only - * required when a buffer is shared between the ports. This cannot - * be the case for a encoder because its input and output buffers - * are of different nature. So let's disable ports sequencially. - * Starting from IL 1.2.0, this point has been clarified. - * OMX_SendCommand will return an error if the IL client attempts to - * call it when there is already an on-going command being processed. - * The exception is for buffer sharing above and the event - * OMX_EventPortNeedsDisable will be sent to request disabling the - * other port at the same time. */ - if (gst_omx_port_set_enabled (self->enc_in_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (self->enc_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (!gst_omx_video_enc_deallocate_in_buffers (self)) - return FALSE; - if (gst_omx_port_wait_enabled (self->enc_in_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_set_enabled (self->enc_out_port, FALSE) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_buffers_released (self->enc_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_deallocate_buffers (self->enc_out_port) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_wait_enabled (self->enc_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - - self->disabled = TRUE; - } - - GST_DEBUG_OBJECT (self, "Encoder drained and disabled"); - return TRUE; -} - -static gboolean -gst_omx_video_enc_configure_input_buffer (GstOMXVideoEnc * self, - GstBuffer * input) -{ - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - GstVideoInfo *info = &self->input_state->info; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - GstVideoMeta *meta; - guint stride, slice_height; - - gst_omx_port_get_port_definition (self->enc_in_port, &port_def); - - meta = gst_buffer_get_video_meta (input); - if (meta) { - guint plane_height[GST_VIDEO_MAX_PLANES]; - - /* Use the stride and slice height of the first plane */ - if (!gst_video_meta_get_plane_height (meta, plane_height)) { - GST_WARNING_OBJECT (self, "Failed to retrieve plane height from meta"); - slice_height = GST_VIDEO_INFO_FIELD_HEIGHT (info); - } else { - slice_height = plane_height[0]; - } - - stride = meta->stride[0]; - g_assert (stride != 0); - - GST_DEBUG_OBJECT (self, - "adjusting stride (%d) and slice-height (%d) using input buffer meta", - stride, slice_height); - } else { - GST_WARNING_OBJECT (self, - "input buffer doesn't provide video meta, can't adjust stride and slice height"); - - stride = info->stride[0]; - slice_height = GST_VIDEO_INFO_FIELD_HEIGHT (info); - } - - if (port_def.nBufferAlignment) - port_def.format.video.nStride = - GST_ROUND_UP_N (stride, port_def.nBufferAlignment); - else - port_def.format.video.nStride = GST_ROUND_UP_4 (stride); /* safe (?) default */ - - if (klass->cdata.hacks & GST_OMX_HACK_HEIGHT_MULTIPLE_16) - port_def.format.video.nSliceHeight = GST_ROUND_UP_16 (slice_height); - else - port_def.format.video.nSliceHeight = slice_height; - - switch (port_def.format.video.eColorFormat) { - case OMX_COLOR_FormatYUV420Planar: - case OMX_COLOR_FormatYUV420PackedPlanar: -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - /* Formats defined in extensions have their own enum so disable to -Wswitch warning */ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wswitch" - case OMX_ALG_COLOR_FormatYUV420SemiPlanar10bitPacked: -#pragma GCC diagnostic pop -#endif - port_def.nBufferSize = - (port_def.format.video.nStride * port_def.format.video.nFrameHeight) + - 2 * ((port_def.format.video.nStride / 2) * - ((port_def.format.video.nFrameHeight + 1) / 2)); - break; - - case OMX_COLOR_FormatYUV420PackedSemiPlanar: - case OMX_COLOR_FormatYUV420SemiPlanar: - port_def.nBufferSize = - (port_def.format.video.nStride * port_def.format.video.nFrameHeight) + - (port_def.format.video.nStride * - ((port_def.format.video.nFrameHeight + 1) / 2)); - break; - - case OMX_COLOR_FormatL8: - port_def.nBufferSize = - port_def.format.video.nStride * port_def.format.video.nFrameHeight; - break; - - case OMX_COLOR_FormatYUV422SemiPlanar: -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - /* Formats defined in extensions have their own enum so disable to -Wswitch warning */ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wswitch" - case OMX_ALG_COLOR_FormatYUV422SemiPlanar10bitPacked: -#pragma GCC diagnostic pop -#endif - port_def.nBufferSize = - (port_def.format.video.nStride * port_def.format.video.nFrameHeight) + - 2 * (port_def.format.video.nStride * - ((port_def.format.video.nFrameHeight + 1) / 2)); - break; - - default: - GST_ERROR_OBJECT (self, "Unsupported port format %x", - port_def.format.video.eColorFormat); - g_assert_not_reached (); - } - - GST_DEBUG_OBJECT (self, - "setting input nStride=%d nSliceHeight=%d nBufferSize=%d (nBufferAlignment=%d)", - (guint) port_def.format.video.nStride, - (guint) port_def.format.video.nSliceHeight, - (guint) port_def.nBufferSize, (guint) port_def.nBufferAlignment); - - if (gst_omx_port_update_port_definition (self->enc_in_port, - &port_def) != OMX_ErrorNone) - return FALSE; - - return TRUE; -} - -static gboolean -gst_omx_video_enc_ensure_nb_in_buffers (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - - if ((klass->cdata.hacks & GST_OMX_HACK_ENSURE_BUFFER_COUNT_ACTUAL)) { - if (!gst_omx_port_ensure_buffer_count_actual (self->enc_in_port, 0)) - return FALSE; - } - - return TRUE; -} - -static gboolean -gst_omx_video_enc_allocate_in_buffers (GstOMXVideoEnc * self) -{ - switch (self->input_allocation) { - case GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER: - if (gst_omx_port_allocate_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - break; - case GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC: - if (gst_omx_port_use_dynamic_buffers (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - break; - case GST_OMX_BUFFER_ALLOCATION_USE_BUFFER: - default: - /* Not supported */ - g_return_val_if_reached (FALSE); - } - - return TRUE; -} - -static gboolean -check_input_alignment (GstOMXVideoEnc * self, GstMapInfo * map) -{ - OMX_PARAM_PORTDEFINITIONTYPE *port_def = &self->enc_in_port->port_def; - - if (map->size != port_def->nBufferSize) { - GST_DEBUG_OBJECT (self, - "input buffer has wrong size/stride (%" G_GSIZE_FORMAT - " expected: %u), can't use dynamic allocation", - map->size, (guint32) port_def->nBufferSize); - return FALSE; - } - - if (port_def->nBufferAlignment && - (GPOINTER_TO_UINT (map->data) & (port_def->nBufferAlignment - 1)) != 0) { - GST_DEBUG_OBJECT (self, - "input buffer is not properly aligned (address: %p alignment: %u bytes), can't use dynamic allocation", - map->data, (guint32) port_def->nBufferAlignment); - return FALSE; - } - - return TRUE; -} - -/* Check if @inbuf's alignment and stride matches the requirements to use the - * dynamic buffer mode. */ -static gboolean -can_use_dynamic_buffer_mode (GstOMXVideoEnc * self, GstBuffer * inbuf) -{ - GstMapInfo map; - gboolean result = FALSE; - - if (gst_buffer_n_memory (inbuf) > 1) { - GST_DEBUG_OBJECT (self, - "input buffer contains more than one memory, can't use dynamic allocation"); - return FALSE; - } - - if (!gst_buffer_map (inbuf, &map, GST_MAP_READ)) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("failed to map input buffer")); - return FALSE; - } - - result = check_input_alignment (self, &map); - - gst_buffer_unmap (inbuf, &map); - return result; -} - -/* Choose the allocation mode for input buffers depending of what's supported by - * the component and the size/alignment of the input buffer. */ -static GstOMXBufferAllocation -gst_omx_video_enc_pick_input_allocation_mode (GstOMXVideoEnc * self, - GstBuffer * inbuf) -{ - if (!gst_omx_is_dynamic_allocation_supported ()) - return GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER; - - if (can_use_dynamic_buffer_mode (self, inbuf)) { - GST_DEBUG_OBJECT (self, - "input buffer is properly aligned, use dynamic allocation"); - return GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC; - } - - GST_DEBUG_OBJECT (self, "let input buffer allocate its buffers"); - return GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER; -} - -static gboolean -gst_omx_video_enc_set_to_idle (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - gboolean no_disable_outport; - - no_disable_outport = klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT; - - if (!no_disable_outport) { - /* Disable output port */ - if (gst_omx_port_set_enabled (self->enc_out_port, FALSE) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_port_wait_enabled (self->enc_out_port, - 1 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_component_set_state (self->enc, OMX_StateIdle) != OMX_ErrorNone) - return FALSE; - - /* Need to allocate buffers to reach Idle state */ - if (!gst_omx_video_enc_allocate_in_buffers (self)) - return FALSE; - - if (no_disable_outport) { - if (!gst_omx_video_enc_allocate_out_buffers (self)) - return FALSE; - } - - if (gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateIdle) - return FALSE; - - return TRUE; -} - -static GstOMXBuffer * -get_omx_buf (GstBuffer * buffer) -{ - GstMemory *mem; - - mem = gst_buffer_peek_memory (buffer, 0); - return gst_omx_memory_get_omx_buf (mem); -} - -static gboolean -buffer_is_from_input_pool (GstOMXVideoEnc * self, GstBuffer * buffer) -{ - /* Buffer from our input pool will already have a GstOMXBuffer associated - * with our input port. */ - GstOMXBuffer *buf; - - buf = get_omx_buf (buffer); - if (!buf) - return FALSE; - - return buf->port == self->enc_in_port; -} - -static gboolean -gst_omx_video_enc_enable (GstOMXVideoEnc * self, GstBuffer * input) -{ - GstOMXVideoEncClass *klass; - - klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - - /* Is downstream using our buffer pool? */ - if (buffer_is_from_input_pool (self, input)) { - self->in_pool_used = TRUE; - } - - if (!self->in_pool_used) { - if (!gst_omx_video_enc_configure_input_buffer (self, input)) - return FALSE; - - self->input_allocation = gst_omx_video_enc_pick_input_allocation_mode (self, - input); - self->input_dmabuf = FALSE; - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (gst_is_dmabuf_memory (gst_buffer_peek_memory (input, 0))) { - if (self->input_allocation == - GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC) { - GST_DEBUG_OBJECT (self, "Configure encoder input to import dmabuf"); - gst_omx_port_set_dmabuf (self->enc_in_port, TRUE); - } else { - GST_DEBUG_OBJECT (self, - "Wrong input allocation mode (%d); dynamic buffers are required to use dmabuf import", - self->input_allocation); - } - - self->input_dmabuf = TRUE; - } -#endif - } - - GST_DEBUG_OBJECT (self, "Enabling component"); - - if (!self->in_pool_used) { - if (!gst_omx_video_enc_ensure_nb_in_buffers (self)) - return FALSE; - if (!gst_omx_video_enc_ensure_nb_out_buffers (self)) - return FALSE; - } - - if (self->disabled) { - if (gst_omx_port_set_enabled (self->enc_in_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (!gst_omx_video_enc_allocate_in_buffers (self)) - return FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_DISABLE_OUTPORT)) { - if (gst_omx_port_set_enabled (self->enc_out_port, TRUE) != OMX_ErrorNone) - return FALSE; - if (!gst_omx_video_enc_allocate_out_buffers (self)) - return FALSE; - - if (gst_omx_port_wait_enabled (self->enc_out_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - } - - if (gst_omx_port_wait_enabled (self->enc_in_port, - 5 * GST_SECOND) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_mark_reconfigured (self->enc_in_port) != OMX_ErrorNone) - return FALSE; - } else { - /* If the input pool is active we already allocated buffers and set the component to Idle. */ - if (!self->in_pool_used) { - if (!gst_omx_video_enc_set_to_idle (self)) - return FALSE; - } - - if (gst_omx_component_set_state (self->enc, - OMX_StateExecuting) != OMX_ErrorNone) - return FALSE; - - if (gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateExecuting) - return FALSE; - } - - /* Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, FALSE); - - if (gst_omx_component_get_last_error (self->enc) != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Component in error state: %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc)); - return FALSE; - } - - self->disabled = FALSE; - - return TRUE; -} - -/* returns TRUE if only the framerate changed and that framerate could be - * updated using OMX_IndexConfigVideoFramerate */ -static gboolean -gst_omx_video_enc_framerate_changed (GstOMXVideoEnc * self, - GstVideoCodecState * state) -{ - GstVideoInfo prev_info = self->input_state->info; - GstVideoInfo *info = &state->info; - GstOMXVideoEncClass *klass; - - klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - - prev_info.fps_n = info->fps_n; - prev_info.fps_d = info->fps_d; - - /* if only the framerate changed, try and set the framerate parameter */ - if (gst_video_info_is_equal (info, &prev_info)) { - OMX_CONFIG_FRAMERATETYPE config; - OMX_ERRORTYPE err; - - GST_DEBUG_OBJECT (self, "Framerate change detected: %d/%d -> %d/%d", - self->input_state->info.fps_n, self->input_state->info.fps_d, - info->fps_n, info->fps_d); - - GST_OMX_INIT_STRUCT (&config); - config.nPortIndex = self->enc_in_port->index; - if (klass->cdata.hacks & GST_OMX_HACK_VIDEO_FRAMERATE_INTEGER) { - config.xEncodeFramerate = - info->fps_d ? GST_VIDEO_INFO_FIELD_RATE_N (info) / (info->fps_d) : 0; - } else { - config.xEncodeFramerate = gst_omx_video_calculate_framerate_q16 (info); - } - - err = gst_omx_component_set_config (self->enc, - OMX_IndexConfigVideoFramerate, &config); - if (err == OMX_ErrorNone) { - gst_video_codec_state_unref (self->input_state); - self->input_state = gst_video_codec_state_ref (state); - return TRUE; - } else { - GST_WARNING_OBJECT (self, - "Failed to set framerate configuration: %s (0x%08x)", - gst_omx_error_to_string (err), err); - /* if changing the rate dynamically didn't work, keep going with a full - * encoder reset */ - } - } - - return FALSE; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static gboolean -gst_omx_video_enc_set_interlacing_parameters (GstOMXVideoEnc * self, - GstVideoInfo * info) -{ - OMX_ERRORTYPE err; - OMX_INTERLACEFORMATTYPE interlace_format_param; - - GST_OMX_INIT_STRUCT (&interlace_format_param); - interlace_format_param.nPortIndex = self->enc_in_port->index; - - err = gst_omx_component_get_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoInterlaceFormatCurrent, - &interlace_format_param); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to get interlace format: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - - if (info->interlace_mode == GST_VIDEO_INTERLACE_MODE_PROGRESSIVE) - interlace_format_param.nFormat = OMX_InterlaceFrameProgressive; - else if (info->interlace_mode == GST_VIDEO_INTERLACE_MODE_ALTERNATE) { - if (GST_VIDEO_INFO_FIELD_ORDER (info) == - GST_VIDEO_FIELD_ORDER_BOTTOM_FIELD_FIRST) - interlace_format_param.nFormat = - OMX_ALG_InterlaceAlternateBottomFieldFirst; - else if (GST_VIDEO_INFO_FIELD_ORDER (info) == - GST_VIDEO_FIELD_ORDER_BOTTOM_FIELD_FIRST) - interlace_format_param.nFormat = OMX_ALG_InterlaceAlternateTopFieldFirst; - else { - GST_INFO_OBJECT (self, - "input field-order unspecified, assume top-field-first"); - interlace_format_param.nFormat = OMX_ALG_InterlaceAlternateTopFieldFirst; - } - } else { - /* Caps templates should ensure this doesn't happen but just to be safe.. */ - GST_ERROR_OBJECT (self, "Video interlacing mode %s not supported", - gst_video_interlace_mode_to_string (info->interlace_mode)); - return FALSE; - } - - err = gst_omx_component_set_parameter (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexParamVideoInterlaceFormatCurrent, - &interlace_format_param); - - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set interlacing mode %s (%s) format: %s (0x%08x)", - gst_video_interlace_mode_to_string (info->interlace_mode), - interlace_format_param.nFormat == - OMX_ALG_InterlaceAlternateTopFieldFirst ? "top-field-first" : - "bottom-field-first", gst_omx_error_to_string (err), err); - return FALSE; - } else { - GST_DEBUG_OBJECT (self, - "Video interlacing mode %s (%s) set on component", - gst_video_interlace_mode_to_string (info->interlace_mode), - interlace_format_param.nFormat == - OMX_ALG_InterlaceAlternateTopFieldFirst ? "top-field-first" : - "bottom-field-first"); - } - - return TRUE; -} -#endif // USE_OMX_TARGET_ZYNQ_USCALE_PLUS - -static gboolean -gst_omx_video_enc_set_format (GstVideoEncoder * encoder, - GstVideoCodecState * state) -{ - GstOMXVideoEnc *self; - GstOMXVideoEncClass *klass; - gboolean needs_disable = FALSE; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - GstVideoInfo *info = &state->info; - GList *negotiation_map = NULL, *l; - GstCaps *caps; - - self = GST_OMX_VIDEO_ENC (encoder); - klass = GST_OMX_VIDEO_ENC_GET_CLASS (encoder); - - caps = gst_video_info_to_caps (info); - GST_DEBUG_OBJECT (self, "Setting new input format: %" GST_PTR_FORMAT, caps); - gst_caps_unref (caps); - - gst_omx_port_get_port_definition (self->enc_in_port, &port_def); - - needs_disable = - gst_omx_component_get_state (self->enc, - GST_CLOCK_TIME_NONE) != OMX_StateLoaded; - /* If the component is not in Loaded state and a real format change happens - * we have to disable the port and re-allocate all buffers. If no real - * format change happened we can just exit here. - */ - if (needs_disable) { - if (gst_omx_video_enc_framerate_changed (self, state)) - return TRUE; - - if (!gst_omx_video_enc_disable (self)) - return FALSE; - - if (!self->disabled) { - /* The local port_def is now obsolete so get it again. */ - gst_omx_port_get_port_definition (self->enc_in_port, &port_def); - } - } - - negotiation_map = - gst_omx_video_get_supported_colorformats (self->enc_in_port, - self->input_state); - if (!negotiation_map) { - /* Fallback */ - switch (info->finfo->format) { - case GST_VIDEO_FORMAT_I420: - port_def.format.video.eColorFormat = OMX_COLOR_FormatYUV420Planar; - break; - case GST_VIDEO_FORMAT_NV12: - port_def.format.video.eColorFormat = OMX_COLOR_FormatYUV420SemiPlanar; - break; - case GST_VIDEO_FORMAT_NV16: - port_def.format.video.eColorFormat = OMX_COLOR_FormatYUV422SemiPlanar; - break; - case GST_VIDEO_FORMAT_ABGR: - port_def.format.video.eColorFormat = OMX_COLOR_Format32bitARGB8888; - break; - case GST_VIDEO_FORMAT_ARGB: - port_def.format.video.eColorFormat = OMX_COLOR_Format32bitBGRA8888; - break; - default: - GST_ERROR_OBJECT (self, "Unsupported format %s", - gst_video_format_to_string (info->finfo->format)); - return FALSE; - break; - } - } else { - for (l = negotiation_map; l; l = l->next) { - GstOMXVideoNegotiationMap *m = l->data; - - if (m->format == info->finfo->format) { - port_def.format.video.eColorFormat = m->type; - break; - } - } - g_list_free_full (negotiation_map, - (GDestroyNotify) gst_omx_video_negotiation_map_free); - } - - port_def.format.video.nFrameWidth = info->width; - port_def.format.video.nFrameHeight = GST_VIDEO_INFO_FIELD_HEIGHT (info); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (!gst_omx_video_enc_set_interlacing_parameters (self, info)) - return FALSE; -#endif - - if (G_UNLIKELY (klass->cdata.hacks & GST_OMX_HACK_VIDEO_FRAMERATE_INTEGER)) { - port_def.format.video.xFramerate = - info->fps_d ? GST_VIDEO_INFO_FIELD_RATE_N (info) / (info->fps_d) : 0; - } else { - port_def.format.video.xFramerate = - gst_omx_video_calculate_framerate_q16 (info); - } - - GST_DEBUG_OBJECT (self, "Setting inport port definition"); - if (gst_omx_port_update_port_definition (self->enc_in_port, - &port_def) != OMX_ErrorNone) - return FALSE; - -#ifdef USE_OMX_TARGET_RPI - /* aspect ratio */ - { - OMX_ERRORTYPE err; - OMX_CONFIG_POINTTYPE aspect_ratio_param; - - GST_OMX_INIT_STRUCT (&aspect_ratio_param); - aspect_ratio_param.nPortIndex = self->enc_out_port->index; - - err = gst_omx_component_get_parameter (self->enc, - OMX_IndexParamBrcmPixelAspectRatio, &aspect_ratio_param); - - if (err == OMX_ErrorNone) { - - aspect_ratio_param.nX = info->par_n; - aspect_ratio_param.nY = info->par_d; - - err = - gst_omx_component_set_parameter (self->enc, - OMX_IndexParamBrcmPixelAspectRatio, &aspect_ratio_param); - - if (err == OMX_ErrorUnsupportedIndex) { - GST_WARNING_OBJECT (self, - "Setting aspect ratio parameters not supported by the component"); - } else if (err == OMX_ErrorUnsupportedSetting) { - GST_WARNING_OBJECT (self, - "Setting aspect ratio %u %u not supported by the component", - aspect_ratio_param.nX, aspect_ratio_param.nY); - } else if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, - "Failed to set aspect ratio: %s (0x%08x)", - gst_omx_error_to_string (err), err); - return FALSE; - } - } - } -#endif // USE_OMX_TARGET_RPI - - if (klass->set_format) { - if (!klass->set_format (self, self->enc_in_port, state)) { - GST_ERROR_OBJECT (self, "Subclass failed to set the new format"); - return FALSE; - } - } - - GST_DEBUG_OBJECT (self, "Updating ports definition"); - if (gst_omx_port_update_port_definition (self->enc_out_port, - NULL) != OMX_ErrorNone) - return FALSE; - if (gst_omx_port_update_port_definition (self->enc_in_port, - NULL) != OMX_ErrorNone) - return FALSE; - - /* Some OMX implementations reset the bitrate after setting the compression - * format, see bgo#698049, so re-set it */ - gst_omx_video_enc_set_bitrate (self); - - if (self->input_state) - gst_video_codec_state_unref (self->input_state); - self->input_state = gst_video_codec_state_ref (state); - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - gst_omx_video_enc_set_latency (self); -#endif - - self->downstream_flow_ret = GST_FLOW_OK; - return TRUE; -} - -static gboolean -gst_omx_video_enc_flush (GstVideoEncoder * encoder) -{ - GstOMXVideoEnc *self; - - self = GST_OMX_VIDEO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Flushing encoder"); - - if (gst_omx_component_get_state (self->enc, 0) == OMX_StateLoaded) - return TRUE; - - /* 0) Pause the components */ - if (gst_omx_component_get_state (self->enc, 0) == OMX_StateExecuting) { - gst_omx_component_set_state (self->enc, OMX_StatePause); - gst_omx_component_get_state (self->enc, GST_CLOCK_TIME_NONE); - } - - /* 1) Flush the ports */ - GST_DEBUG_OBJECT (self, "flushing ports"); - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, TRUE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, TRUE); - - /* Wait until the srcpad loop is finished, - * unlock GST_VIDEO_ENCODER_STREAM_LOCK to prevent deadlocks - * caused by using this lock from inside the loop function */ - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - GST_PAD_STREAM_LOCK (GST_VIDEO_ENCODER_SRC_PAD (self)); - GST_PAD_STREAM_UNLOCK (GST_VIDEO_ENCODER_SRC_PAD (self)); - GST_VIDEO_ENCODER_STREAM_LOCK (self); - - /* 3) Resume components */ - gst_omx_component_set_state (self->enc, OMX_StateExecuting); - gst_omx_component_get_state (self->enc, GST_CLOCK_TIME_NONE); - - /* 4) Unset flushing to allow ports to accept data again */ - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, FALSE); - gst_omx_port_set_flushing (self->enc_out_port, 5 * GST_SECOND, FALSE); - gst_omx_port_populate (self->enc_out_port); - - /* Start the srcpad loop again */ - self->last_upstream_ts = 0; - self->downstream_flow_ret = GST_FLOW_OK; - self->started = FALSE; - GST_DEBUG_OBJECT (self, "Flush finished"); - - return TRUE; -} - -static gboolean -gst_omx_video_enc_copy_plane (GstOMXVideoEnc * self, guint i, - GstVideoFrame * frame, GstOMXBuffer * outbuf, - const GstVideoFormatInfo * finfo) -{ - OMX_PARAM_PORTDEFINITIONTYPE *port_def = &self->enc_in_port->port_def; - guint8 *src, *dest; - gint src_stride, dest_stride; - gint j, height, width; - - src_stride = GST_VIDEO_FRAME_COMP_STRIDE (frame, i); - dest_stride = port_def->format.video.nStride; - /* XXX: Try this if no stride was set */ - if (dest_stride == 0) - dest_stride = src_stride; - - dest = outbuf->omx_buf->pBuffer + outbuf->omx_buf->nOffset; - if (i == 1) - dest += - port_def->format.video.nSliceHeight * port_def->format.video.nStride; - - src = GST_VIDEO_FRAME_COMP_DATA (frame, i); - height = GST_VIDEO_FRAME_COMP_HEIGHT (frame, i); - width = GST_VIDEO_FRAME_COMP_WIDTH (frame, i) * (i == 0 ? 1 : 2); - - if (GST_VIDEO_FORMAT_INFO_BITS (finfo) == 10) - /* Need ((width + 2) / 3) 32-bits words */ - width = (width + 2) / 3 * 4; - - if (dest + dest_stride * height > - outbuf->omx_buf->pBuffer + outbuf->omx_buf->nAllocLen) { - GST_ERROR_OBJECT (self, "Invalid output buffer size"); - return FALSE; - } - - for (j = 0; j < height; j++) { - memcpy (dest, src, width); - src += src_stride; - dest += dest_stride; - } - - /* nFilledLen should include the vertical padding in each slice (spec 3.1.3.7.1) */ - outbuf->omx_buf->nFilledLen += - GST_VIDEO_FORMAT_INFO_SCALE_HEIGHT (finfo, i, - port_def->format.video.nSliceHeight) * port_def->format.video.nStride; - return TRUE; -} - -static gboolean -gst_omx_video_enc_semi_planar_manual_copy (GstOMXVideoEnc * self, - GstBuffer * inbuf, GstOMXBuffer * outbuf, const GstVideoFormatInfo * finfo) -{ - GstVideoInfo *info = &self->input_state->info; - GstVideoFrame frame; - gint i; - - outbuf->omx_buf->nFilledLen = 0; - - if (!gst_video_frame_map (&frame, info, inbuf, GST_MAP_READ)) { - GST_ERROR_OBJECT (self, "Invalid input buffer size"); - return FALSE; - } - - for (i = 0; i < 2; i++) { - if (!gst_omx_video_enc_copy_plane (self, i, &frame, outbuf, finfo)) { - gst_video_frame_unmap (&frame); - return FALSE; - } - } - - gst_video_frame_unmap (&frame); - return TRUE; -} - -static gboolean -gst_omx_video_enc_fill_buffer (GstOMXVideoEnc * self, GstBuffer * inbuf, - GstOMXBuffer * outbuf) -{ - GstVideoCodecState *state = gst_video_codec_state_ref (self->input_state); - GstVideoInfo *info = &state->info; - OMX_PARAM_PORTDEFINITIONTYPE *port_def = &self->enc_in_port->port_def; - gboolean ret = FALSE; - GstVideoFrame frame; - GstVideoMeta *meta = gst_buffer_get_video_meta (inbuf); - gint stride = meta ? meta->stride[0] : info->stride[0]; - - if (info->width != port_def->format.video.nFrameWidth || - GST_VIDEO_INFO_FIELD_HEIGHT (info) != - port_def->format.video.nFrameHeight) { - GST_ERROR_OBJECT (self, "Width or height do not match"); - goto done; - } - - if (self->enc_in_port->allocation == - GST_OMX_BUFFER_ALLOCATION_USE_BUFFER_DYNAMIC) { - if (gst_buffer_n_memory (inbuf) > 1) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("input buffer now has more than one memory, can't use dynamic allocation any more")); - return FALSE; - } - - if (!self->input_dmabuf) { - /* Map and keep a ref on the buffer while it's being processed - * by the OMX component. */ - if (!gst_omx_buffer_map_frame (outbuf, inbuf, info)) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("failed to map input buffer")); - return FALSE; - } - - if (!check_input_alignment (self, &outbuf->input_frame.map[0])) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("input buffer now has wrong alignment/stride, can't use dynamic allocation any more")); - return FALSE; - } - - GST_LOG_OBJECT (self, "Transfer buffer of %" G_GSIZE_FORMAT " bytes", - gst_buffer_get_size (inbuf)); - } else { - /* dmabuf input */ - if (!gst_omx_buffer_import_fd (outbuf, inbuf)) { - GST_ELEMENT_ERROR (self, STREAM, FORMAT, (NULL), - ("failed to import dmabuf")); - return FALSE; - } - - GST_LOG_OBJECT (self, "Import dmabuf of %" G_GSIZE_FORMAT " bytes", - gst_buffer_get_size (inbuf)); - } - - ret = TRUE; - goto done; - } - - /* Same strides and everything */ - if ((gst_buffer_get_size (inbuf) == - outbuf->omx_buf->nAllocLen - outbuf->omx_buf->nOffset) && - (stride == port_def->format.video.nStride)) { - outbuf->omx_buf->nFilledLen = gst_buffer_get_size (inbuf); - - GST_LOG_OBJECT (self, "Matched strides - direct copy %u bytes", - (guint) outbuf->omx_buf->nFilledLen); - - gst_buffer_extract (inbuf, 0, - outbuf->omx_buf->pBuffer + outbuf->omx_buf->nOffset, - outbuf->omx_buf->nFilledLen); - ret = TRUE; - goto done; - } - - /* Different strides */ - GST_LOG_OBJECT (self, "Mismatched strides - copying line-by-line"); - - switch (info->finfo->format) { - case GST_VIDEO_FORMAT_I420:{ - gint i, j, height, width; - guint8 *src, *dest; - gint src_stride, dest_stride; - - outbuf->omx_buf->nFilledLen = 0; - - if (!gst_video_frame_map (&frame, info, inbuf, GST_MAP_READ)) { - GST_ERROR_OBJECT (self, "Invalid input buffer size"); - ret = FALSE; - goto done; - } - - for (i = 0; i < 3; i++) { - if (i == 0) { - dest_stride = port_def->format.video.nStride; - } else { - dest_stride = port_def->format.video.nStride / 2; - } - - src_stride = GST_VIDEO_FRAME_COMP_STRIDE (&frame, i); - /* XXX: Try this if no stride was set */ - if (dest_stride == 0) - dest_stride = src_stride; - - dest = outbuf->omx_buf->pBuffer + outbuf->omx_buf->nOffset; - if (i > 0) - dest += - port_def->format.video.nSliceHeight * - port_def->format.video.nStride; - if (i == 2) - dest += - (port_def->format.video.nSliceHeight / 2) * - (port_def->format.video.nStride / 2); - - src = GST_VIDEO_FRAME_COMP_DATA (&frame, i); - height = GST_VIDEO_FRAME_COMP_HEIGHT (&frame, i); - width = GST_VIDEO_FRAME_COMP_WIDTH (&frame, i); - - if (dest + dest_stride * height > - outbuf->omx_buf->pBuffer + outbuf->omx_buf->nAllocLen) { - gst_video_frame_unmap (&frame); - GST_ERROR_OBJECT (self, "Invalid output buffer size"); - ret = FALSE; - goto done; - } - - for (j = 0; j < height; j++) { - memcpy (dest, src, width); - src += src_stride; - dest += dest_stride; - } - - /* nFilledLen should include the vertical padding in each slice (spec 3.1.3.7.1) */ - if (i == 0) - outbuf->omx_buf->nFilledLen += - port_def->format.video.nSliceHeight * - port_def->format.video.nStride; - else - outbuf->omx_buf->nFilledLen += - (port_def->format.video.nSliceHeight / 2) * - (port_def->format.video.nStride / 2); - } - gst_video_frame_unmap (&frame); - ret = TRUE; - break; - } - case GST_VIDEO_FORMAT_NV12: - case GST_VIDEO_FORMAT_NV16: - case GST_VIDEO_FORMAT_NV12_10LE32: - case GST_VIDEO_FORMAT_NV16_10LE32: - ret = - gst_omx_video_enc_semi_planar_manual_copy (self, inbuf, outbuf, - info->finfo); - break; - case GST_VIDEO_FORMAT_GRAY8: - { - if (!gst_video_frame_map (&frame, info, inbuf, GST_MAP_READ)) { - GST_ERROR_OBJECT (self, "Failed to map input buffer"); - ret = FALSE; - goto done; - } - - ret = gst_omx_video_enc_copy_plane (self, 0, &frame, outbuf, info->finfo); - gst_video_frame_unmap (&frame); - } - break; - default: - GST_ERROR_OBJECT (self, "Unsupported format"); - goto done; - break; - } - -done: - - gst_video_codec_state_unref (state); - - return ret; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static void -handle_roi_metadata (GstOMXVideoEnc * self, GstBuffer * input) -{ - GstMeta *meta; - gpointer state = NULL; - - while ((meta = - gst_buffer_iterate_meta_filtered (input, &state, - GST_VIDEO_REGION_OF_INTEREST_META_API_TYPE))) { - GstVideoRegionOfInterestMeta *roi = (GstVideoRegionOfInterestMeta *) meta; - OMX_ALG_VIDEO_CONFIG_REGION_OF_INTEREST roi_param; - GstStructure *s; - - GST_LOG_OBJECT (self, "Input buffer ROI: type=%s id=%d (%d, %d) %dx%d", - g_quark_to_string (roi->roi_type), roi->id, roi->x, roi->y, roi->w, - roi->h); - - if (self->qp_mode != ROI_QP) { - GST_WARNING_OBJECT (self, - "Need qp-mode=roi to handle ROI metadata (current: %d); ignoring", - self->qp_mode); - continue; - } - - GST_OMX_INIT_STRUCT (&roi_param); - roi_param.nPortIndex = self->enc_in_port->index; - roi_param.nLeft = roi->x; - roi_param.nTop = roi->y; - roi_param.nWidth = roi->w; - roi_param.nHeight = roi->h; - - s = gst_video_region_of_interest_meta_get_param (roi, "roi/omx-alg"); - if (s) { - const gchar *quality; - GEnumValue *evalue; - - quality = gst_structure_get_string (s, "quality"); - - evalue = - g_enum_get_value_by_nick (self->alg_roi_quality_enum_class, quality); - if (!evalue) { - roi_param.eQuality = self->default_roi_quality; - - GST_WARNING_OBJECT (self, - "Unknown ROI encoding quality '%s', use default (%d)", - quality, self->default_roi_quality); - } else { - roi_param.eQuality = evalue->value; - - GST_LOG_OBJECT (self, "Use encoding quality '%s' from upstream", - quality); - } - } else { - roi_param.eQuality = self->default_roi_quality; - - GST_LOG_OBJECT (self, "No quality specified upstream, use default (%d)", - self->default_roi_quality); - } - - gst_omx_component_set_config (self->enc, - (OMX_INDEXTYPE) OMX_ALG_IndexConfigVideoRegionOfInterest, &roi_param); - } -} -#endif - -static GstFlowReturn -gst_omx_video_enc_handle_frame (GstVideoEncoder * encoder, - GstVideoCodecFrame * frame) -{ - GstOMXAcquireBufferReturn acq_ret = GST_OMX_ACQUIRE_BUFFER_ERROR; - GstOMXVideoEnc *self; - GstOMXPort *port; - GstOMXBuffer *buf; - OMX_ERRORTYPE err; - GstClockTimeDiff deadline; - - self = GST_OMX_VIDEO_ENC (encoder); - - GST_DEBUG_OBJECT (self, "Handling frame"); - - if (self->downstream_flow_ret != GST_FLOW_OK) { - gst_video_codec_frame_unref (frame); - return self->downstream_flow_ret; - } - - deadline = gst_video_encoder_get_max_encode_time (encoder, frame); - if (deadline < 0) { - GST_WARNING_OBJECT (self, - "Input frame is too late, dropping (deadline %" GST_TIME_FORMAT ")", - GST_TIME_ARGS (-deadline)); - - /* Calling finish_frame with frame->output_buffer == NULL will drop it */ - return gst_video_encoder_finish_frame (GST_VIDEO_ENCODER (self), frame); - } - - if (!self->started) { - if (gst_omx_port_is_flushing (self->enc_out_port)) { - if (!gst_omx_video_enc_enable (self, frame->input_buffer)) - goto enable_error; - } - - GST_DEBUG_OBJECT (self, "Starting task"); - gst_pad_start_task (GST_VIDEO_ENCODER_SRC_PAD (self), - (GstTaskFunction) gst_omx_video_enc_loop, self, NULL); - } - - port = self->enc_in_port; - - while (acq_ret != GST_OMX_ACQUIRE_BUFFER_OK) { - GstClockTime timestamp, duration; - gboolean fill_buffer = TRUE; - - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - - if (buffer_is_from_input_pool (self, frame->input_buffer)) { - /* Receiving a buffer from our input pool */ - buf = get_omx_buf (frame->input_buffer); - - GST_LOG_OBJECT (self, - "Input buffer %p already has a OMX buffer associated: %p", - frame->input_buffer, buf); - - g_assert (!buf->input_buffer); - /* Prevent the buffer to be released to the pool while it's being - * processed by OMX. The reference will be dropped in EmptyBufferDone() */ - buf->input_buffer = gst_buffer_ref (frame->input_buffer); - - acq_ret = GST_OMX_ACQUIRE_BUFFER_OK; - fill_buffer = FALSE; - buf->omx_buf->nFilledLen = gst_buffer_get_size (frame->input_buffer); - } else { - acq_ret = gst_omx_port_acquire_buffer (port, &buf, GST_OMX_WAIT); - } - - if (acq_ret == GST_OMX_ACQUIRE_BUFFER_ERROR) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto component_error; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_FLUSHING) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto flushing; - } else if (acq_ret == GST_OMX_ACQUIRE_BUFFER_RECONFIGURE) { - /* Reallocate all buffers */ - err = gst_omx_port_set_enabled (port, FALSE); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_buffers_released (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_deallocate_buffers (port); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 1 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - if (!gst_omx_video_enc_ensure_nb_in_buffers (self)) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_set_enabled (port, TRUE); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - if (!gst_omx_video_enc_allocate_in_buffers (self)) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_wait_enabled (port, 5 * GST_SECOND); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - err = gst_omx_port_mark_reconfigured (port); - if (err != OMX_ErrorNone) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - goto reconfigure_error; - } - - /* Now get a new buffer and fill it */ - GST_VIDEO_ENCODER_STREAM_LOCK (self); - continue; - } - GST_VIDEO_ENCODER_STREAM_LOCK (self); - - g_assert (acq_ret == GST_OMX_ACQUIRE_BUFFER_OK && buf != NULL); - - if (buf->omx_buf->nAllocLen - buf->omx_buf->nOffset <= 0) { - gst_omx_port_release_buffer (port, buf); - goto full_buffer; - } - - if (self->downstream_flow_ret != GST_FLOW_OK) { - gst_omx_port_release_buffer (port, buf); - goto flow_error; - } - - /* Now handle the frame */ - - if (GST_VIDEO_CODEC_FRAME_IS_FORCE_KEYFRAME (frame)) { -#ifdef USE_OMX_TARGET_RPI - OMX_CONFIG_BOOLEANTYPE config; - - GST_OMX_INIT_STRUCT (&config); - config.bEnabled = OMX_TRUE; - - GST_DEBUG_OBJECT (self, "Forcing a keyframe (iframe on the RPi)"); - - err = - gst_omx_component_set_config (self->enc, - OMX_IndexConfigBrcmVideoRequestIFrame, &config); -#elif defined(USE_OMX_TARGET_ZYNQ_USCALE_PLUS) - OMX_ALG_VIDEO_CONFIG_INSERT config; - - GST_OMX_INIT_STRUCT (&config); - config.nPortIndex = self->enc_out_port->index; - - GST_DEBUG_OBJECT (self, "Forcing a keyframe"); - err = gst_omx_component_set_config (self->enc, (OMX_INDEXTYPE) - OMX_ALG_IndexConfigVideoInsertInstantaneousDecodingRefresh, &config); -#else - OMX_CONFIG_INTRAREFRESHVOPTYPE config; - - GST_OMX_INIT_STRUCT (&config); - config.nPortIndex = port->index; - config.IntraRefreshVOP = OMX_TRUE; - - GST_DEBUG_OBJECT (self, "Forcing a keyframe"); - err = - gst_omx_component_set_config (self->enc, - OMX_IndexConfigVideoIntraVOPRefresh, &config); -#endif - if (err != OMX_ErrorNone) - GST_ERROR_OBJECT (self, "Failed to force a keyframe: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - handle_roi_metadata (self, frame->input_buffer); -#endif - - /* Copy the buffer content in chunks of size as requested - * by the port */ - if (fill_buffer - && !gst_omx_video_enc_fill_buffer (self, frame->input_buffer, buf)) { - gst_omx_port_release_buffer (port, buf); - goto buffer_fill_error; - } - - timestamp = frame->pts; - if (timestamp != GST_CLOCK_TIME_NONE) { - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (timestamp, OMX_TICKS_PER_SECOND, GST_SECOND)); - self->last_upstream_ts = timestamp; - } - - duration = frame->duration; - if (duration != GST_CLOCK_TIME_NONE) { - buf->omx_buf->nTickCount = - gst_util_uint64_scale (duration, OMX_TICKS_PER_SECOND, GST_SECOND); - self->last_upstream_ts += duration; - } else { - buf->omx_buf->nTickCount = 0; - } - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - if (GST_VIDEO_BUFFER_IS_TOP_FIELD (frame->input_buffer)) - buf->omx_buf->nFlags |= OMX_ALG_BUFFERFLAG_TOP_FIELD; - else if (GST_VIDEO_BUFFER_IS_BOTTOM_FIELD (frame->input_buffer)) - buf->omx_buf->nFlags |= OMX_ALG_BUFFERFLAG_BOT_FIELD; -#endif - - self->started = TRUE; - err = gst_omx_port_release_buffer (port, buf); - if (err != OMX_ErrorNone) - goto release_error; - - GST_DEBUG_OBJECT (self, "Passed frame to component"); - } - - gst_video_codec_frame_unref (frame); - - return self->downstream_flow_ret; - -full_buffer: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Got OpenMAX buffer with no free space (%p, %u/%u)", buf, - (guint) buf->omx_buf->nOffset, (guint) buf->omx_buf->nAllocLen)); - gst_video_codec_frame_unref (frame); - return GST_FLOW_ERROR; - } - -flow_error: - { - gst_video_codec_frame_unref (frame); - return self->downstream_flow_ret; - } - -enable_error: - { - /* Report the OMX error, if any */ - if (gst_omx_component_get_last_error (self->enc) != OMX_ErrorNone) - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Failed to enable OMX encoder: %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc))); - else - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("Failed to enable OMX encoder")); - gst_video_codec_frame_unref (frame); - return GST_FLOW_ERROR; - } - -component_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, FAILED, (NULL), - ("OpenMAX component in error state %s (0x%08x)", - gst_omx_component_get_last_error_string (self->enc), - gst_omx_component_get_last_error (self->enc))); - gst_video_codec_frame_unref (frame); - return GST_FLOW_ERROR; - } - -flushing: - { - GST_DEBUG_OBJECT (self, "Flushing -- returning FLUSHING"); - gst_video_codec_frame_unref (frame); - return GST_FLOW_FLUSHING; - } -reconfigure_error: - { - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Unable to reconfigure input port")); - gst_video_codec_frame_unref (frame); - return GST_FLOW_ERROR; - } -buffer_fill_error: - { - GST_ELEMENT_ERROR (self, RESOURCE, WRITE, (NULL), - ("Failed to write input into the OpenMAX buffer")); - gst_video_codec_frame_unref (frame); - return GST_FLOW_ERROR; - } -release_error: - { - gst_video_codec_frame_unref (frame); - GST_ELEMENT_ERROR (self, LIBRARY, SETTINGS, (NULL), - ("Failed to relase input buffer to component: %s (0x%08x)", - gst_omx_error_to_string (err), err)); - return GST_FLOW_ERROR; - } -} - -static GstFlowReturn -gst_omx_video_enc_finish (GstVideoEncoder * encoder) -{ - GstOMXVideoEnc *self; - - self = GST_OMX_VIDEO_ENC (encoder); - - return gst_omx_video_enc_drain (self); -} - -static GstFlowReturn -gst_omx_video_enc_drain (GstOMXVideoEnc * self) -{ - GstOMXVideoEncClass *klass; - GstOMXBuffer *buf; - GstOMXAcquireBufferReturn acq_ret; - OMX_ERRORTYPE err; - - GST_DEBUG_OBJECT (self, "Draining component"); - - klass = GST_OMX_VIDEO_ENC_GET_CLASS (self); - - if (!self->started) { - GST_DEBUG_OBJECT (self, "Component not started yet"); - return GST_FLOW_OK; - } - self->started = FALSE; - - if ((klass->cdata.hacks & GST_OMX_HACK_NO_EMPTY_EOS_BUFFER)) { - GST_WARNING_OBJECT (self, "Component does not support empty EOS buffers"); - return GST_FLOW_OK; - } - - /* Make sure to release the base class stream lock, otherwise - * _loop() can't call _finish_frame() and we might block forever - * because no input buffers are released */ - GST_VIDEO_ENCODER_STREAM_UNLOCK (self); - - /* Send an EOS buffer to the component and let the base - * class drop the EOS event. We will send it later when - * the EOS buffer arrives on the output port. */ - acq_ret = gst_omx_port_acquire_buffer (self->enc_in_port, &buf, GST_OMX_WAIT); - if (acq_ret != GST_OMX_ACQUIRE_BUFFER_OK) { - GST_VIDEO_ENCODER_STREAM_LOCK (self); - GST_ERROR_OBJECT (self, "Failed to acquire buffer for draining: %d", - acq_ret); - return GST_FLOW_ERROR; - } - - g_mutex_lock (&self->drain_lock); - self->draining = TRUE; - buf->omx_buf->nFilledLen = 0; - GST_OMX_SET_TICKS (buf->omx_buf->nTimeStamp, - gst_util_uint64_scale (self->last_upstream_ts, OMX_TICKS_PER_SECOND, - GST_SECOND)); - buf->omx_buf->nTickCount = 0; - buf->omx_buf->nFlags |= OMX_BUFFERFLAG_EOS; - err = gst_omx_port_release_buffer (self->enc_in_port, buf); - if (err != OMX_ErrorNone) { - GST_ERROR_OBJECT (self, "Failed to drain component: %s (0x%08x)", - gst_omx_error_to_string (err), err); - g_mutex_unlock (&self->drain_lock); - GST_VIDEO_ENCODER_STREAM_LOCK (self); - return GST_FLOW_ERROR; - } - GST_DEBUG_OBJECT (self, "Waiting until component is drained"); - g_cond_wait (&self->drain_cond, &self->drain_lock); - GST_DEBUG_OBJECT (self, "Drained component"); - g_mutex_unlock (&self->drain_lock); - GST_VIDEO_ENCODER_STREAM_LOCK (self); - - self->started = FALSE; - - return GST_FLOW_OK; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static gboolean -pool_request_allocate_cb (GstBufferPool * pool, GstOMXVideoEnc * self) -{ - GstStructure *config; - guint min; - - gst_omx_port_set_dmabuf (self->enc_in_port, TRUE); - - config = gst_buffer_pool_get_config (pool); - - if (!gst_buffer_pool_config_get_params (config, NULL, NULL, &min, NULL)) { - gst_structure_free (config); - return FALSE; - } - gst_structure_free (config); - - GST_DEBUG_OBJECT (self, - "input pool configured for %d buffers, adjust nBufferCountActual", min); - - if (!gst_omx_port_update_buffer_count_actual (self->enc_in_port, min)) - return FALSE; - - if (!gst_omx_video_enc_set_to_idle (self)) - return FALSE; - - self->input_allocation = GST_OMX_BUFFER_ALLOCATION_ALLOCATE_BUFFER; - self->input_dmabuf = TRUE; - - /* gst_omx_port_acquire_buffer() will fail if the input port is stil flushing - * which will prevent upstream from acquiring buffers. */ - gst_omx_port_set_flushing (self->enc_in_port, 5 * GST_SECOND, FALSE); - - return TRUE; -} - -static GstBufferPool * -create_input_pool (GstOMXVideoEnc * self, GstCaps * caps, guint num_buffers) -{ - GstBufferPool *pool; - GstStructure *config; - - pool = - gst_omx_buffer_pool_new (GST_ELEMENT_CAST (self), self->enc, - self->enc_in_port, GST_OMX_BUFFER_MODE_DMABUF); - - g_signal_connect_object (pool, "allocate", - G_CALLBACK (pool_request_allocate_cb), self, 0); - - config = gst_buffer_pool_get_config (pool); - - gst_buffer_pool_config_set_params (config, caps, - self->enc_in_port->port_def.nBufferSize, num_buffers, 0); - - if (!gst_buffer_pool_set_config (pool, config)) { - GST_INFO_OBJECT (self, "Failed to set config on input pool"); - gst_object_unref (pool); - return NULL; - } - - return pool; -} -#endif - -static GstStructure * -get_allocation_video_meta (GstOMXVideoEnc * self, GstVideoInfo * info) -{ - GstStructure *result; - GstVideoAlignment align; - - gst_omx_video_get_port_padding (self->enc_in_port, info, &align); - - result = gst_structure_new_empty ("video-meta"); - - gst_structure_set (result, "padding-top", G_TYPE_UINT, align.padding_top, - "padding-bottom", G_TYPE_UINT, align.padding_bottom, - "padding-left", G_TYPE_UINT, align.padding_left, - "padding-right", G_TYPE_UINT, align.padding_right, NULL); - - GST_LOG_OBJECT (self, "Request buffer layout to producer: %" GST_PTR_FORMAT, - result); - - return result; -} - -static gboolean -gst_omx_video_enc_propose_allocation (GstVideoEncoder * encoder, - GstQuery * query) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (encoder); - guint num_buffers; - GstCaps *caps; - GstVideoInfo info; - GstBufferPool *pool = NULL; - GstStructure *params; - - gst_query_parse_allocation (query, &caps, NULL); - - if (!caps) { - GST_WARNING_OBJECT (self, "allocation query does not contain caps"); - return FALSE; - } - - if (!gst_video_info_from_caps (&info, caps)) { - GST_WARNING_OBJECT (self, "Failed to parse caps %" GST_PTR_FORMAT, caps); - return FALSE; - } - - params = get_allocation_video_meta (self, &info); - gst_query_add_allocation_meta (query, GST_VIDEO_META_API_TYPE, params); - gst_structure_free (params); - - num_buffers = self->enc_in_port->port_def.nBufferCountMin + 1; - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - /* dmabuf export is currently only supported on Zynqultrascaleplus */ - pool = create_input_pool (self, caps, num_buffers); - if (!pool) { - GST_WARNING_OBJECT (self, "Failed to create and configure pool"); - return FALSE; - } -#endif - - GST_DEBUG_OBJECT (self, - "request at least %d buffers of size %d", num_buffers, - (guint) self->enc_in_port->port_def.nBufferSize); - gst_query_add_allocation_pool (query, pool, - self->enc_in_port->port_def.nBufferSize, num_buffers, 0); - - self->in_pool_used = FALSE; - - g_clear_object (&pool); - - return - GST_VIDEO_ENCODER_CLASS - (gst_omx_video_enc_parent_class)->propose_allocation (encoder, query); -} - -static GList * -filter_supported_formats (GList * negotiation_map) -{ - GList *cur; - - for (cur = negotiation_map; cur != NULL;) { - GstOMXVideoNegotiationMap *nmap = (GstOMXVideoNegotiationMap *) (cur->data); - GList *next; - - switch (nmap->format) { - case GST_VIDEO_FORMAT_I420: - case GST_VIDEO_FORMAT_NV12: - case GST_VIDEO_FORMAT_NV12_10LE32: - case GST_VIDEO_FORMAT_NV16: - case GST_VIDEO_FORMAT_NV16_10LE32: - case GST_VIDEO_FORMAT_GRAY8: - cur = g_list_next (cur); - continue; - default: - gst_omx_video_negotiation_map_free (nmap); - next = g_list_next (cur); - negotiation_map = g_list_delete_link (negotiation_map, cur); - cur = next; - } - } - - return negotiation_map; -} - -static GstCaps * -add_interlace_to_caps (GstOMXVideoEnc * self, GstCaps * caps) -{ -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - OMX_ERRORTYPE err; - OMX_INTERLACEFORMATTYPE interlace_format_param; - GstCaps *caps_alternate; - - if (gst_caps_is_empty (caps)) - /* No caps to add to */ - return caps; - - GST_OMX_INIT_STRUCT (&interlace_format_param); - interlace_format_param.nPortIndex = self->enc_in_port->index; - - err = gst_omx_component_get_parameter (self->enc, - OMX_ALG_IndexParamVideoInterlaceFormatSupported, &interlace_format_param); - - if (err != OMX_ErrorNone) { - GST_WARNING_OBJECT (self, - "Failed to get OMX_ALG_IndexParamVideoInterlaceFormatSupported %s (0x%08x)", - gst_omx_error_to_string (err), err); - return caps; - } - - if (!(interlace_format_param.nFormat & - OMX_ALG_InterlaceAlternateTopFieldFirst) - && !(interlace_format_param.nFormat & - OMX_ALG_InterlaceAlternateBottomFieldFirst)) - return caps; - - /* Alternate mode is supported, create an 'alternate' variant of the caps - * with the caps feature. */ - caps_alternate = gst_caps_copy (caps); - - gst_caps_set_features_simple (caps_alternate, - gst_caps_features_new (GST_CAPS_FEATURE_FORMAT_INTERLACED, NULL)); - - caps = gst_caps_merge (caps, caps_alternate); -#endif // USE_OMX_TARGET_ZYNQ_USCALE_PLUS - - return caps; -} - -static GstCaps * -gst_omx_video_enc_getcaps (GstVideoEncoder * encoder, GstCaps * filter) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (encoder); - GList *negotiation_map = NULL; - GstCaps *comp_supported_caps; - GstCaps *ret; - - if (!self->enc) - return gst_video_encoder_proxy_getcaps (encoder, NULL, filter); - - negotiation_map = - gst_omx_video_get_supported_colorformats (self->enc_in_port, - self->input_state); - negotiation_map = filter_supported_formats (negotiation_map); - - comp_supported_caps = gst_omx_video_get_caps_for_map (negotiation_map); - g_list_free_full (negotiation_map, - (GDestroyNotify) gst_omx_video_negotiation_map_free); - - comp_supported_caps = add_interlace_to_caps (self, comp_supported_caps); - - if (!gst_caps_is_empty (comp_supported_caps)) { - ret = - gst_video_encoder_proxy_getcaps (encoder, comp_supported_caps, filter); - gst_caps_unref (comp_supported_caps); - } else { - gst_caps_unref (comp_supported_caps); - ret = gst_video_encoder_proxy_getcaps (encoder, NULL, filter); - } - - GST_LOG_OBJECT (encoder, "Supported caps %" GST_PTR_FORMAT, ret); - - return ret; -} - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS -static gboolean -handle_longterm_event (GstOMXVideoEnc * self, GstEvent * event) -{ - OMX_ALG_VIDEO_CONFIG_INSERT longterm; - OMX_ERRORTYPE err; - OMX_INDEXTYPE omx_index_long_term; - - GST_OMX_INIT_STRUCT (&longterm); - longterm.nPortIndex = self->enc_in_port->index; - - /* If long-term-ref is enabled then "omx-alg/insert-longterm" event - * marks the encoding picture as long term reference picture and - * "omx-alg/use-longterm" event informs the encoder that encoding picture - * should use existing long term picture in the dpb as reference for encoding process */ - - if (self->long_term_ref) { - if (gst_event_has_name (event, OMX_ALG_GST_EVENT_INSERT_LONGTERM)) { - GST_LOG_OBJECT (self, "received omx-alg/insert-longterm event"); - omx_index_long_term = - (OMX_INDEXTYPE) OMX_ALG_IndexConfigVideoInsertLongTerm; - } else { - GST_LOG_OBJECT (self, "received omx-alg/use-longterm event"); - omx_index_long_term = (OMX_INDEXTYPE) OMX_ALG_IndexConfigVideoUseLongTerm; - } - - err = - gst_omx_component_set_config (self->enc, omx_index_long_term, - &longterm); - - if (err != OMX_ErrorNone) - GST_ERROR_OBJECT (self, - "Failed to longterm events: %s (0x%08x)", - gst_omx_error_to_string (err), err); - } else { - GST_WARNING_OBJECT (self, - "LongTerm events are not handled because long_term_ref is disabled"); - } - - return TRUE; -} -#endif - -static gboolean -gst_omx_video_enc_sink_event (GstVideoEncoder * encoder, GstEvent * event) -{ - switch (GST_EVENT_TYPE (event)) { - case GST_EVENT_CUSTOM_DOWNSTREAM: - { -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (encoder); - if (gst_event_has_name (event, OMX_ALG_GST_EVENT_INSERT_LONGTERM) - || gst_event_has_name (event, OMX_ALG_GST_EVENT_USE_LONGTERM)) - return handle_longterm_event (self, event); -#endif - } - default: - break; - } - - return - GST_VIDEO_ENCODER_CLASS (gst_omx_video_enc_parent_class)->sink_event - (encoder, event); -} - -static gboolean -gst_omx_video_enc_decide_allocation (GstVideoEncoder * encoder, - GstQuery * query) -{ - GstOMXVideoEnc *self = GST_OMX_VIDEO_ENC (encoder); - guint min = 1; - - if (!GST_VIDEO_ENCODER_CLASS - (gst_omx_video_enc_parent_class)->decide_allocation (encoder, query)) - return FALSE; - - if (gst_query_get_n_allocation_pools (query)) { - gst_query_parse_nth_allocation_pool (query, 0, NULL, NULL, &min, NULL); - GST_DEBUG_OBJECT (self, - "Downstream requested %d buffers, adjust number of output buffers accordingly", - min); - } else { - GST_DEBUG_OBJECT (self, "Downstream didn't set any allocation pool info"); - } - - self->nb_downstream_buffers = min; - - return TRUE; -} diff --git a/subprojects/gst-omx/omx/gstomxvideoenc.h b/subprojects/gst-omx/omx/gstomxvideoenc.h deleted file mode 100644 index 51e2baf4f8..0000000000 --- a/subprojects/gst-omx/omx/gstomxvideoenc.h +++ /dev/null @@ -1,133 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_VIDEO_ENC_H__ -#define __GST_OMX_VIDEO_ENC_H__ - -#include -#include -#include - -#include "gstomx.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_VIDEO_ENC \ - (gst_omx_video_enc_get_type()) -#define GST_OMX_VIDEO_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_VIDEO_ENC,GstOMXVideoEnc)) -#define GST_OMX_VIDEO_ENC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_VIDEO_ENC,GstOMXVideoEncClass)) -#define GST_OMX_VIDEO_ENC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_VIDEO_ENC,GstOMXVideoEncClass)) -#define GST_IS_OMX_VIDEO_ENC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_VIDEO_ENC)) -#define GST_IS_OMX_VIDEO_ENC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_VIDEO_ENC)) - -typedef struct _GstOMXVideoEnc GstOMXVideoEnc; -typedef struct _GstOMXVideoEncClass GstOMXVideoEncClass; - -struct _GstOMXVideoEnc -{ - GstVideoEncoder parent; - - /* < protected > */ - GstOMXComponent *enc; - GstOMXPort *enc_in_port, *enc_out_port; - - /* < private > */ - GstVideoCodecState *input_state; - /* TRUE if the component is configured and saw - * the first buffer */ - gboolean started; - /* TRUE if the ports where disabled after being activated the first time. */ - gboolean disabled; - - GstClockTime last_upstream_ts; - - /* Draining state */ - GMutex drain_lock; - GCond drain_cond; - /* TRUE if EOS buffers shouldn't be forwarded */ - gboolean draining; /* protected by drain_lock */ - - /* properties */ - guint32 control_rate; - guint32 target_bitrate; /* protected by object lock */ - guint32 quant_i_frames; - guint32 quant_p_frames; - guint32 quant_b_frames; -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - guint32 qp_mode; - guint32 min_qp; - guint32 max_qp; - guint32 gop_mode; - guint32 gdr_mode; - guint32 initial_delay; - guint32 cpb_size; - guint32 scaling_list; - gboolean low_bandwidth; - guint32 max_bitrate; - guint32 aspect_ratio; - gboolean filler_data; - guint32 num_slices; - guint32 slice_size; - gboolean dependent_slice; - gint default_roi_quality; - gboolean long_term_ref; - guint32 long_term_freq; - guint32 look_ahead; -#endif - - guint32 default_target_bitrate; - - GstFlowReturn downstream_flow_ret; - - GstOMXBufferAllocation input_allocation; - /* TRUE if encoder is passing dmabuf's fd directly to the OMX component */ - gboolean input_dmabuf; - /* Number of buffers requested downstream */ - guint nb_downstream_buffers; - - /* TRUE if input buffers are from the pool we proposed to upstream */ - gboolean in_pool_used; - -#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS - GEnumClass *alg_roi_quality_enum_class; -#endif -}; - -struct _GstOMXVideoEncClass -{ - GstVideoEncoderClass parent_class; - - GstOMXClassData cdata; - - gboolean (*set_format) (GstOMXVideoEnc * self, GstOMXPort * port, GstVideoCodecState * state); - GstCaps *(*get_caps) (GstOMXVideoEnc * self, GstOMXPort * port, GstVideoCodecState * state); - GstFlowReturn (*handle_output_frame) (GstOMXVideoEnc * self, GstOMXPort * port, GstOMXBuffer * buffer, GstVideoCodecFrame * frame); -}; - -GType gst_omx_video_enc_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_VIDEO_ENC_H__ */ diff --git a/subprojects/gst-omx/omx/gstomxvp8dec.c b/subprojects/gst-omx/omx/gstomxvp8dec.c deleted file mode 100644 index fd2e5acddf..0000000000 --- a/subprojects/gst-omx/omx/gstomxvp8dec.c +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxvp8dec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_vp8_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_vp8_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_vp8_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_vp8_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_vp8_dec_debug_category, "omxvp8dec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXVP8Dec, gst_omx_vp8_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -static void -gst_omx_vp8_dec_class_init (GstOMXVP8DecClass * klass) -{ - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_vp8_dec_is_format_change); - videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_vp8_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "video/x-vp8, " - "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX VP8 Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode VP8 video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.vp8"); -} - -static void -gst_omx_vp8_dec_init (GstOMXVP8Dec * self) -{ -} - -static gboolean -gst_omx_vp8_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_vp8_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = - (OMX_VIDEO_CODINGTYPE) OMX_VIDEO_CodingVP8; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} diff --git a/subprojects/gst-omx/omx/gstomxvp8dec.h b/subprojects/gst-omx/omx/gstomxvp8dec.h deleted file mode 100644 index f99f4cebcb..0000000000 --- a/subprojects/gst-omx/omx/gstomxvp8dec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2013, Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_VP8_DEC_H__ -#define __GST_OMX_VP8_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_VP8_DEC \ - (gst_omx_vp8_dec_get_type()) -#define GST_OMX_VP8_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_VP8_DEC,GstOMXVP8Dec)) -#define GST_OMX_VP8_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_VP8_DEC,GstOMXVP8DecClass)) -#define GST_OMX_VP8_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_VP8_DEC,GstOMXVP8DecClass)) -#define GST_IS_OMX_VP8_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_VP8_DEC)) -#define GST_IS_OMX_VP8_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_VP8_DEC)) - -typedef struct _GstOMXVP8Dec GstOMXVP8Dec; -typedef struct _GstOMXVP8DecClass GstOMXVP8DecClass; - -struct _GstOMXVP8Dec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXVP8DecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_vp8_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_VP8_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/gstomxwmvdec.c b/subprojects/gst-omx/omx/gstomxwmvdec.c deleted file mode 100644 index 14758275f4..0000000000 --- a/subprojects/gst-omx/omx/gstomxwmvdec.c +++ /dev/null @@ -1,98 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include "gstomxwmvdec.h" - -GST_DEBUG_CATEGORY_STATIC (gst_omx_wmv_dec_debug_category); -#define GST_CAT_DEFAULT gst_omx_wmv_dec_debug_category - -/* prototypes */ -static gboolean gst_omx_wmv_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); -static gboolean gst_omx_wmv_dec_set_format (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state); - -enum -{ - PROP_0 -}; - -/* class initialization */ - -#define DEBUG_INIT \ - GST_DEBUG_CATEGORY_INIT (gst_omx_wmv_dec_debug_category, "omxwmvdec", 0, \ - "debug category for gst-omx video decoder base class"); - -G_DEFINE_TYPE_WITH_CODE (GstOMXWMVDec, gst_omx_wmv_dec, - GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT); - -static void -gst_omx_wmv_dec_class_init (GstOMXWMVDecClass * klass) -{ - GstElementClass *element_class = GST_ELEMENT_CLASS (klass); - GstOMXVideoDecClass *videodec_class = GST_OMX_VIDEO_DEC_CLASS (klass); - - videodec_class->is_format_change = - GST_DEBUG_FUNCPTR (gst_omx_wmv_dec_is_format_change); - videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_wmv_dec_set_format); - - videodec_class->cdata.default_sink_template_caps = "video/x-wmv, " - "width=(int) [1,MAX], " "height=(int) [1,MAX]"; - - gst_element_class_set_static_metadata (element_class, - "OpenMAX WMV Video Decoder", - "Codec/Decoder/Video/Hardware", - "Decode WMV video streams", - "Sebastian Dröge "); - - gst_omx_set_default_role (&videodec_class->cdata, "video_decoder.wmv"); -} - -static void -gst_omx_wmv_dec_init (GstOMXWMVDec * self) -{ -} - -static gboolean -gst_omx_wmv_dec_is_format_change (GstOMXVideoDec * dec, - GstOMXPort * port, GstVideoCodecState * state) -{ - return FALSE; -} - -static gboolean -gst_omx_wmv_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port, - GstVideoCodecState * state) -{ - gboolean ret; - OMX_PARAM_PORTDEFINITIONTYPE port_def; - - gst_omx_port_get_port_definition (port, &port_def); - port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingWMV; - ret = gst_omx_port_update_port_definition (port, &port_def) == OMX_ErrorNone; - - return ret; -} diff --git a/subprojects/gst-omx/omx/gstomxwmvdec.h b/subprojects/gst-omx/omx/gstomxwmvdec.h deleted file mode 100644 index 9375dc5dfa..0000000000 --- a/subprojects/gst-omx/omx/gstomxwmvdec.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011, Hewlett-Packard Development Company, L.P. - * Author: Sebastian Dröge , Collabora Ltd. - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifndef __GST_OMX_WMV_DEC_H__ -#define __GST_OMX_WMV_DEC_H__ - -#include -#include "gstomxvideodec.h" - -G_BEGIN_DECLS - -#define GST_TYPE_OMX_WMV_DEC \ - (gst_omx_wmv_dec_get_type()) -#define GST_OMX_WMV_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_OMX_WMV_DEC,GstOMXWMVDec)) -#define GST_OMX_WMV_DEC_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_OMX_WMV_DEC,GstOMXWMVDecClass)) -#define GST_OMX_WMV_DEC_GET_CLASS(obj) \ - (G_TYPE_INSTANCE_GET_CLASS((obj),GST_TYPE_OMX_WMV_DEC,GstOMXWMVDecClass)) -#define GST_IS_OMX_WMV_DEC(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_OMX_WMV_DEC)) -#define GST_IS_OMX_WMV_DEC_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_OMX_WMV_DEC)) - -typedef struct _GstOMXWMVDec GstOMXWMVDec; -typedef struct _GstOMXWMVDecClass GstOMXWMVDecClass; - -struct _GstOMXWMVDec -{ - GstOMXVideoDec parent; -}; - -struct _GstOMXWMVDecClass -{ - GstOMXVideoDecClass parent_class; -}; - -GType gst_omx_wmv_dec_get_type (void); - -G_END_DECLS - -#endif /* __GST_OMX_WMV_DEC_H__ */ - diff --git a/subprojects/gst-omx/omx/meson.build b/subprojects/gst-omx/omx/meson.build deleted file mode 100644 index 8c074a9238..0000000000 --- a/subprojects/gst-omx/omx/meson.build +++ /dev/null @@ -1,63 +0,0 @@ -omx_sources = [ - 'gstomx.c', - 'gstomxallocator.c', - 'gstomxbufferpool.c', - 'gstomxvideo.c', - 'gstomxvideodec.c', - 'gstomxvideoenc.c', - 'gstomxaudiodec.c', - 'gstomxaudioenc.c', - 'gstomxmjpegdec.c', - 'gstomxmpeg4videodec.c', - 'gstomxmpeg2videodec.c', - 'gstomxh264dec.c', - 'gstomxh264utils.c', - 'gstomxh263dec.c', - 'gstomxwmvdec.c', - 'gstomxmpeg4videoenc.c', - 'gstomxh264enc.c', - 'gstomxh263enc.c', - 'gstomxaacdec.c', - 'gstomxmp3dec.c', - 'gstomxaacenc.c', - 'gstomxamrdec.c', - 'gstomxaudiosink.c', - 'gstomxanalogaudiosink.c', - 'gstomxhdmiaudiosink.c', - 'gstomxmp3enc.c', -] - -extra_c_args = [] - -if have_omx_vp8 - omx_sources += 'gstomxvp8dec.c' -endif - -if have_omx_theora - omx_sources += 'gstomxtheoradec.c' -endif - -if have_omx_hevc - omx_sources += 'gstomxh265utils.c' - omx_sources += 'gstomxh265enc.c' - omx_sources += 'gstomxh265dec.c' -endif - -optional_deps = [] -if gstgl_dep.found() - optional_deps += gstgl_dep - extra_c_args += ['-DGST_USE_UNSTABLE_API'] -endif - -gstomx = library('gstomx', - omx_sources, - c_args : gst_omx_args + extra_c_args, -# link_args : noseh_link_args, - include_directories : [configinc, omx_inc], - dependencies : [gstvideo_dep, gstaudio_dep, gstbase_dep, gstcontroller_dep, - libm, gmodule_dep, gstallocators_dep] + optional_deps, - install : true, - install_dir : plugins_install_dir, -) - -plugins = [gstomx] diff --git a/subprojects/gst-omx/omx/openmax/OMX_Audio.h b/subprojects/gst-omx/omx/openmax/OMX_Audio.h deleted file mode 100644 index 04f1a9997b..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Audio.h +++ /dev/null @@ -1,1311 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** @file OMX_Audio.h - OpenMax IL version 1.1.2 - * The structures needed by Audio components to exchange - * parameters and configuration data with the componenmilts. - */ - -#ifndef OMX_Audio_h -#define OMX_Audio_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - -/* Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ - -#include - -/** @defgroup midi MIDI - * @ingroup audio - */ - -/** @defgroup effects Audio effects - * @ingroup audio - */ - -/** @defgroup audio OpenMAX IL Audio Domain - * Structures for OpenMAX IL Audio domain - * @{ - */ - -/** Enumeration used to define the possible audio codings. - * If "OMX_AUDIO_CodingUnused" is selected, the coding selection must - * be done in a vendor specific way. Since this is for an audio - * processing element this enum is relevant. However, for another - * type of component other enums would be in this area. - */ -typedef enum OMX_AUDIO_CODINGTYPE { - OMX_AUDIO_CodingUnused = 0, /**< Placeholder value when coding is N/A */ - OMX_AUDIO_CodingAutoDetect, /**< auto detection of audio format */ - OMX_AUDIO_CodingPCM, /**< Any variant of PCM coding */ - OMX_AUDIO_CodingADPCM, /**< Any variant of ADPCM encoded data */ - OMX_AUDIO_CodingAMR, /**< Any variant of AMR encoded data */ - OMX_AUDIO_CodingGSMFR, /**< Any variant of GSM fullrate (i.e. GSM610) */ - OMX_AUDIO_CodingGSMEFR, /**< Any variant of GSM Enhanced Fullrate encoded data*/ - OMX_AUDIO_CodingGSMHR, /**< Any variant of GSM Halfrate encoded data */ - OMX_AUDIO_CodingPDCFR, /**< Any variant of PDC Fullrate encoded data */ - OMX_AUDIO_CodingPDCEFR, /**< Any variant of PDC Enhanced Fullrate encoded data */ - OMX_AUDIO_CodingPDCHR, /**< Any variant of PDC Halfrate encoded data */ - OMX_AUDIO_CodingTDMAFR, /**< Any variant of TDMA Fullrate encoded data (TIA/EIA-136-420) */ - OMX_AUDIO_CodingTDMAEFR, /**< Any variant of TDMA Enhanced Fullrate encoded data (TIA/EIA-136-410) */ - OMX_AUDIO_CodingQCELP8, /**< Any variant of QCELP 8kbps encoded data */ - OMX_AUDIO_CodingQCELP13, /**< Any variant of QCELP 13kbps encoded data */ - OMX_AUDIO_CodingEVRC, /**< Any variant of EVRC encoded data */ - OMX_AUDIO_CodingSMV, /**< Any variant of SMV encoded data */ - OMX_AUDIO_CodingG711, /**< Any variant of G.711 encoded data */ - OMX_AUDIO_CodingG723, /**< Any variant of G.723 dot 1 encoded data */ - OMX_AUDIO_CodingG726, /**< Any variant of G.726 encoded data */ - OMX_AUDIO_CodingG729, /**< Any variant of G.729 encoded data */ - OMX_AUDIO_CodingAAC, /**< Any variant of AAC encoded data */ - OMX_AUDIO_CodingMP3, /**< Any variant of MP3 encoded data */ - OMX_AUDIO_CodingSBC, /**< Any variant of SBC encoded data */ - OMX_AUDIO_CodingVORBIS, /**< Any variant of VORBIS encoded data */ - OMX_AUDIO_CodingWMA, /**< Any variant of WMA encoded data */ - OMX_AUDIO_CodingRA, /**< Any variant of RA encoded data */ - OMX_AUDIO_CodingMIDI, /**< Any variant of MIDI encoded data */ - OMX_AUDIO_CodingKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_CodingVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_CodingMax = 0x7FFFFFFF -} OMX_AUDIO_CODINGTYPE; - - -/** The PortDefinition structure is used to define all of the parameters - * necessary for the compliant component to setup an input or an output audio - * path. If additional information is needed to define the parameters of the - * port (such as frequency), additional structures must be sent such as the - * OMX_AUDIO_PARAM_PCMMODETYPE structure to supply the extra parameters for the port. - */ -typedef struct OMX_AUDIO_PORTDEFINITIONTYPE { - OMX_STRING cMIMEType; /**< MIME type of data for the port */ - OMX_NATIVE_DEVICETYPE pNativeRender; /** < platform specific reference - for an output device, - otherwise this field is 0 */ - OMX_BOOL bFlagErrorConcealment; /**< Turns on error concealment if it is - supported by the OMX component */ - OMX_AUDIO_CODINGTYPE eEncoding; /**< Type of data expected for this - port (e.g. PCM, AMR, MP3, etc) */ -} OMX_AUDIO_PORTDEFINITIONTYPE; - - -/** Port format parameter. This structure is used to enumerate - * the various data input/output format supported by the port. - */ -typedef struct OMX_AUDIO_PARAM_PORTFORMATTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Indicates which port to set */ - OMX_U32 nIndex; /**< Indicates the enumeration index for the format from 0x0 to N-1 */ - OMX_AUDIO_CODINGTYPE eEncoding; /**< Type of data expected for this port (e.g. PCM, AMR, MP3, etc) */ -} OMX_AUDIO_PARAM_PORTFORMATTYPE; - - -/** PCM mode type */ -typedef enum OMX_AUDIO_PCMMODETYPE { - OMX_AUDIO_PCMModeLinear = 0, /**< Linear PCM encoded data */ - OMX_AUDIO_PCMModeALaw, /**< A law PCM encoded data (G.711) */ - OMX_AUDIO_PCMModeMULaw, /**< Mu law PCM encoded data (G.711) */ - OMX_AUDIO_PCMModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_PCMModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_PCMModeMax = 0x7FFFFFFF -} OMX_AUDIO_PCMMODETYPE; - - -typedef enum OMX_AUDIO_CHANNELTYPE { - OMX_AUDIO_ChannelNone = 0x0, /**< Unused or empty */ - OMX_AUDIO_ChannelLF = 0x1, /**< Left front */ - OMX_AUDIO_ChannelRF = 0x2, /**< Right front */ - OMX_AUDIO_ChannelCF = 0x3, /**< Center front */ - OMX_AUDIO_ChannelLS = 0x4, /**< Left surround */ - OMX_AUDIO_ChannelRS = 0x5, /**< Right surround */ - OMX_AUDIO_ChannelLFE = 0x6, /**< Low frequency effects */ - OMX_AUDIO_ChannelCS = 0x7, /**< Back surround */ - OMX_AUDIO_ChannelLR = 0x8, /**< Left rear. */ - OMX_AUDIO_ChannelRR = 0x9, /**< Right rear. */ - OMX_AUDIO_ChannelKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_ChannelVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_ChannelMax = 0x7FFFFFFF -} OMX_AUDIO_CHANNELTYPE; - -#define OMX_AUDIO_MAXCHANNELS 16 /**< maximum number distinct audio channels that a buffer may contain */ -#define OMX_MIN_PCMPAYLOAD_MSEC 5 /**< Minimum audio buffer payload size for uncompressed (PCM) audio */ - -/** PCM format description */ -typedef struct OMX_AUDIO_PARAM_PCMMODETYPE { - OMX_U32 nSize; /**< Size of this structure, in Bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels (e.g. 2 for stereo) */ - OMX_NUMERICALDATATYPE eNumData; /**< indicates PCM data as signed or unsigned */ - OMX_ENDIANTYPE eEndian; /**< indicates PCM data as little or big endian */ - OMX_BOOL bInterleaved; /**< True for normal interleaved data; false for - non-interleaved data (e.g. block data) */ - OMX_U32 nBitPerSample; /**< Bit per sample */ - OMX_U32 nSamplingRate; /**< Sampling rate of the source data. Use 0 for - variable or unknown sampling rate. */ - OMX_AUDIO_PCMMODETYPE ePCMMode; /**< PCM mode enumeration */ - OMX_AUDIO_CHANNELTYPE eChannelMapping[OMX_AUDIO_MAXCHANNELS]; /**< Slot i contains channel defined by eChannelMap[i] */ - -} OMX_AUDIO_PARAM_PCMMODETYPE; - - -/** Audio channel mode. This is used by both AAC and MP3, although the names are more appropriate - * for the MP3. For example, JointStereo for MP3 is CouplingChannels for AAC. - */ -typedef enum OMX_AUDIO_CHANNELMODETYPE { - OMX_AUDIO_ChannelModeStereo = 0, /**< 2 channels, the bitrate allocation between those - two channels changes accordingly to each channel information */ - OMX_AUDIO_ChannelModeJointStereo, /**< mode that takes advantage of what is common between - 2 channels for higher compression gain */ - OMX_AUDIO_ChannelModeDual, /**< 2 mono-channels, each channel is encoded with half - the bitrate of the overall bitrate */ - OMX_AUDIO_ChannelModeMono, /**< Mono channel mode */ - OMX_AUDIO_ChannelModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_ChannelModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_ChannelModeMax = 0x7FFFFFFF -} OMX_AUDIO_CHANNELMODETYPE; - - -typedef enum OMX_AUDIO_MP3STREAMFORMATTYPE { - OMX_AUDIO_MP3StreamFormatMP1Layer3 = 0, /**< MP3 Audio MPEG 1 Layer 3 Stream format */ - OMX_AUDIO_MP3StreamFormatMP2Layer3, /**< MP3 Audio MPEG 2 Layer 3 Stream format */ - OMX_AUDIO_MP3StreamFormatMP2_5Layer3, /**< MP3 Audio MPEG2.5 Layer 3 Stream format */ - OMX_AUDIO_MP3StreamFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_MP3StreamFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_MP3StreamFormatMax = 0x7FFFFFFF -} OMX_AUDIO_MP3STREAMFORMATTYPE; - -/** MP3 params */ -typedef struct OMX_AUDIO_PARAM_MP3TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels */ - OMX_U32 nBitRate; /**< Bit rate of the input data. Use 0 for variable - rate or unknown bit rates */ - OMX_U32 nSampleRate; /**< Sampling rate of the source data. Use 0 for - variable or unknown sampling rate. */ - OMX_U32 nAudioBandWidth; /**< Audio band width (in Hz) to which an encoder should - limit the audio signal. Use 0 to let encoder decide */ - OMX_AUDIO_CHANNELMODETYPE eChannelMode; /**< Channel mode enumeration */ - OMX_AUDIO_MP3STREAMFORMATTYPE eFormat; /**< MP3 stream format */ -} OMX_AUDIO_PARAM_MP3TYPE; - - -typedef enum OMX_AUDIO_AACSTREAMFORMATTYPE { - OMX_AUDIO_AACStreamFormatMP2ADTS = 0, /**< AAC Audio Data Transport Stream 2 format */ - OMX_AUDIO_AACStreamFormatMP4ADTS, /**< AAC Audio Data Transport Stream 4 format */ - OMX_AUDIO_AACStreamFormatMP4LOAS, /**< AAC Low Overhead Audio Stream format */ - OMX_AUDIO_AACStreamFormatMP4LATM, /**< AAC Low overhead Audio Transport Multiplex */ - OMX_AUDIO_AACStreamFormatADIF, /**< AAC Audio Data Interchange Format */ - OMX_AUDIO_AACStreamFormatMP4FF, /**< AAC inside MPEG-4/ISO File Format */ - OMX_AUDIO_AACStreamFormatRAW, /**< AAC Raw Format */ - OMX_AUDIO_AACStreamFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_AACStreamFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_AACStreamFormatMax = 0x7FFFFFFF -} OMX_AUDIO_AACSTREAMFORMATTYPE; - - -/** AAC mode type. Note that the term profile is used with the MPEG-2 - * standard and the term object type and profile is used with MPEG-4 */ -typedef enum OMX_AUDIO_AACPROFILETYPE{ - OMX_AUDIO_AACObjectNull = 0, /**< Null, not used */ - OMX_AUDIO_AACObjectMain = 1, /**< AAC Main object */ - OMX_AUDIO_AACObjectLC, /**< AAC Low Complexity object (AAC profile) */ - OMX_AUDIO_AACObjectSSR, /**< AAC Scalable Sample Rate object */ - OMX_AUDIO_AACObjectLTP, /**< AAC Long Term Prediction object */ - OMX_AUDIO_AACObjectHE, /**< AAC High Efficiency (object type SBR, HE-AAC profile) */ - OMX_AUDIO_AACObjectScalable, /**< AAC Scalable object */ - OMX_AUDIO_AACObjectERLC = 17, /**< ER AAC Low Complexity object (Error Resilient AAC-LC) */ - OMX_AUDIO_AACObjectLD = 23, /**< AAC Low Delay object (Error Resilient) */ - OMX_AUDIO_AACObjectHE_PS = 29, /**< AAC High Efficiency with Parametric Stereo coding (HE-AAC v2, object type PS) */ - OMX_AUDIO_AACObjectKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_AACObjectVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_AACObjectMax = 0x7FFFFFFF -} OMX_AUDIO_AACPROFILETYPE; - - -/** AAC tool usage (for nAACtools in OMX_AUDIO_PARAM_AACPROFILETYPE). - * Required for encoder configuration and optional as decoder info output. - * For MP3, OMX_AUDIO_CHANNELMODETYPE is sufficient. */ -#define OMX_AUDIO_AACToolNone 0x00000000 /**< no AAC tools allowed (encoder config) or active (decoder info output) */ -#define OMX_AUDIO_AACToolMS 0x00000001 /**< MS: Mid/side joint coding tool allowed or active */ -#define OMX_AUDIO_AACToolIS 0x00000002 /**< IS: Intensity stereo tool allowed or active */ -#define OMX_AUDIO_AACToolTNS 0x00000004 /**< TNS: Temporal Noise Shaping tool allowed or active */ -#define OMX_AUDIO_AACToolPNS 0x00000008 /**< PNS: MPEG-4 Perceptual Noise substitution tool allowed or active */ -#define OMX_AUDIO_AACToolLTP 0x00000010 /**< LTP: MPEG-4 Long Term Prediction tool allowed or active */ -#define OMX_AUDIO_AACToolAll 0x7FFFFFFF /**< all AAC tools allowed or active (*/ - -/** MPEG-4 AAC error resilience (ER) tool usage (for nAACERtools in OMX_AUDIO_PARAM_AACPROFILETYPE). - * Required for ER encoder configuration and optional as decoder info output */ -#define OMX_AUDIO_AACERNone 0x00000000 /**< no AAC ER tools allowed/used */ -#define OMX_AUDIO_AACERVCB11 0x00000001 /**< VCB11: Virtual Code Books for AAC section data */ -#define OMX_AUDIO_AACERRVLC 0x00000002 /**< RVLC: Reversible Variable Length Coding */ -#define OMX_AUDIO_AACERHCR 0x00000004 /**< HCR: Huffman Codeword Reordering */ -#define OMX_AUDIO_AACERAll 0x7FFFFFFF /**< all AAC ER tools allowed/used */ - - -/** AAC params */ -typedef struct OMX_AUDIO_PARAM_AACPROFILETYPE { - OMX_U32 nSize; /**< Size of this structure, in Bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels */ - OMX_U32 nSampleRate; /**< Sampling rate of the source data. Use 0 for - variable or unknown sampling rate. */ - OMX_U32 nBitRate; /**< Bit rate of the input data. Use 0 for variable - rate or unknown bit rates */ - OMX_U32 nAudioBandWidth; /**< Audio band width (in Hz) to which an encoder should - limit the audio signal. Use 0 to let encoder decide */ - OMX_U32 nFrameLength; /**< Frame length (in audio samples per channel) of the codec. - Can be 1024 or 960 (AAC-LC), 2048 (HE-AAC), 480 or 512 (AAC-LD). - Use 0 to let encoder decide */ - OMX_U32 nAACtools; /**< AAC tool usage */ - OMX_U32 nAACERtools; /**< MPEG-4 AAC error resilience tool usage */ - OMX_AUDIO_AACPROFILETYPE eAACProfile; /**< AAC profile enumeration */ - OMX_AUDIO_AACSTREAMFORMATTYPE eAACStreamFormat; /**< AAC stream format enumeration */ - OMX_AUDIO_CHANNELMODETYPE eChannelMode; /**< Channel mode enumeration */ -} OMX_AUDIO_PARAM_AACPROFILETYPE; - - -/** VORBIS params */ -typedef struct OMX_AUDIO_PARAM_VORBISTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels */ - OMX_U32 nBitRate; /**< Bit rate of the encoded data data. Use 0 for variable - rate or unknown bit rates. Encoding is set to the - bitrate closest to specified value (in bps) */ - OMX_U32 nMinBitRate; /**< Sets minimum bitrate (in bps). */ - OMX_U32 nMaxBitRate; /**< Sets maximum bitrate (in bps). */ - - OMX_U32 nSampleRate; /**< Sampling rate of the source data. Use 0 for - variable or unknown sampling rate. */ - OMX_U32 nAudioBandWidth; /**< Audio band width (in Hz) to which an encoder should - limit the audio signal. Use 0 to let encoder decide */ - OMX_S32 nQuality; /**< Sets encoding quality to n, between -1 (low) and 10 (high). - In the default mode of operation, teh quality level is 3. - Normal quality range is 0 - 10. */ - OMX_BOOL bManaged; /**< Set bitrate management mode. This turns off the - normal VBR encoding, but allows hard or soft bitrate - constraints to be enforced by the encoder. This mode can - be slower, and may also be lower quality. It is - primarily useful for streaming. */ - OMX_BOOL bDownmix; /**< Downmix input from stereo to mono (has no effect on - non-stereo streams). Useful for lower-bitrate encoding. */ -} OMX_AUDIO_PARAM_VORBISTYPE; - - -/** WMA Version */ -typedef enum OMX_AUDIO_WMAFORMATTYPE { - OMX_AUDIO_WMAFormatUnused = 0, /**< format unused or unknown */ - OMX_AUDIO_WMAFormat7, /**< Windows Media Audio format 7 */ - OMX_AUDIO_WMAFormat8, /**< Windows Media Audio format 8 */ - OMX_AUDIO_WMAFormat9, /**< Windows Media Audio format 9 */ - OMX_AUDIO_WMAFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_WMAFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_WMAFormatMax = 0x7FFFFFFF -} OMX_AUDIO_WMAFORMATTYPE; - - -/** WMA Profile */ -typedef enum OMX_AUDIO_WMAPROFILETYPE { - OMX_AUDIO_WMAProfileUnused = 0, /**< profile unused or unknown */ - OMX_AUDIO_WMAProfileL1, /**< Windows Media audio version 9 profile L1 */ - OMX_AUDIO_WMAProfileL2, /**< Windows Media audio version 9 profile L2 */ - OMX_AUDIO_WMAProfileL3, /**< Windows Media audio version 9 profile L3 */ - OMX_AUDIO_WMAProfileKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_WMAProfileVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_WMAProfileMax = 0x7FFFFFFF -} OMX_AUDIO_WMAPROFILETYPE; - - -/** WMA params */ -typedef struct OMX_AUDIO_PARAM_WMATYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U16 nChannels; /**< Number of channels */ - OMX_U32 nBitRate; /**< Bit rate of the input data. Use 0 for variable - rate or unknown bit rates */ - OMX_AUDIO_WMAFORMATTYPE eFormat; /**< Version of WMA stream / data */ - OMX_AUDIO_WMAPROFILETYPE eProfile; /**< Profile of WMA stream / data */ - OMX_U32 nSamplingRate; /**< Sampling rate of the source data */ - OMX_U16 nBlockAlign; /**< is the block alignment, or block size, in bytes of the audio codec */ - OMX_U16 nEncodeOptions; /**< WMA Type-specific data */ - OMX_U32 nSuperBlockAlign; /**< WMA Type-specific data */ -} OMX_AUDIO_PARAM_WMATYPE; - -/** - * RealAudio format - */ -typedef enum OMX_AUDIO_RAFORMATTYPE { - OMX_AUDIO_RAFormatUnused = 0, /**< Format unused or unknown */ - OMX_AUDIO_RA8, /**< RealAudio 8 codec */ - OMX_AUDIO_RA9, /**< RealAudio 9 codec */ - OMX_AUDIO_RA10_AAC, /**< MPEG-4 AAC codec for bitrates of more than 128kbps */ - OMX_AUDIO_RA10_CODEC, /**< RealAudio codec for bitrates less than 128 kbps */ - OMX_AUDIO_RA10_LOSSLESS, /**< RealAudio Lossless */ - OMX_AUDIO_RA10_MULTICHANNEL, /**< RealAudio Multichannel */ - OMX_AUDIO_RA10_VOICE, /**< RealAudio Voice for bitrates below 15 kbps */ - OMX_AUDIO_RAFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_RAFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_RAFormatMax = 0x7FFFFFFF -} OMX_AUDIO_RAFORMATTYPE; - -/** RA (Real Audio) params */ -typedef struct OMX_AUDIO_PARAM_RATYPE { - OMX_U32 nSize; /**< Size of this structure, in Bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels */ - OMX_U32 nSamplingRate; /**< is the sampling rate of the source data */ - OMX_U32 nBitsPerFrame; /**< is the value for bits per frame */ - OMX_U32 nSamplePerFrame; /**< is the value for samples per frame */ - OMX_U32 nCouplingQuantBits; /**< is the number of coupling quantization bits in the stream */ - OMX_U32 nCouplingStartRegion; /**< is the coupling start region in the stream */ - OMX_U32 nNumRegions; /**< is the number of regions value */ - OMX_AUDIO_RAFORMATTYPE eFormat; /**< is the RealAudio audio format */ -} OMX_AUDIO_PARAM_RATYPE; - - -/** SBC Allocation Method Type */ -typedef enum OMX_AUDIO_SBCALLOCMETHODTYPE { - OMX_AUDIO_SBCAllocMethodLoudness, /**< Loudness allocation method */ - OMX_AUDIO_SBCAllocMethodSNR, /**< SNR allocation method */ - OMX_AUDIO_SBCAllocMethodKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_SBCAllocMethodVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_SBCAllocMethodMax = 0x7FFFFFFF -} OMX_AUDIO_SBCALLOCMETHODTYPE; - - -/** SBC params */ -typedef struct OMX_AUDIO_PARAM_SBCTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels */ - OMX_U32 nBitRate; /**< Bit rate of the input data. Use 0 for variable - rate or unknown bit rates */ - OMX_U32 nSampleRate; /**< Sampling rate of the source data. Use 0 for - variable or unknown sampling rate. */ - OMX_U32 nBlocks; /**< Number of blocks */ - OMX_U32 nSubbands; /**< Number of subbands */ - OMX_U32 nBitPool; /**< Bitpool value */ - OMX_BOOL bEnableBitrate; /**< Use bitrate value instead of bitpool */ - OMX_AUDIO_CHANNELMODETYPE eChannelMode; /**< Channel mode enumeration */ - OMX_AUDIO_SBCALLOCMETHODTYPE eSBCAllocType; /**< SBC Allocation method type */ -} OMX_AUDIO_PARAM_SBCTYPE; - - -/** ADPCM stream format parameters */ -typedef struct OMX_AUDIO_PARAM_ADPCMTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_U32 nBitsPerSample; /**< Number of bits in each sample */ - OMX_U32 nSampleRate; /**< Sampling rate of the source data. Use 0 for - variable or unknown sampling rate. */ -} OMX_AUDIO_PARAM_ADPCMTYPE; - - -/** G723 rate */ -typedef enum OMX_AUDIO_G723RATE { - OMX_AUDIO_G723ModeUnused = 0, /**< AMRNB Mode unused / unknown */ - OMX_AUDIO_G723ModeLow, /**< 5300 bps */ - OMX_AUDIO_G723ModeHigh, /**< 6300 bps */ - OMX_AUDIO_G723ModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_G723ModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_G723ModeMax = 0x7FFFFFFF -} OMX_AUDIO_G723RATE; - - -/** G723 - Sample rate must be 8 KHz */ -typedef struct OMX_AUDIO_PARAM_G723TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_AUDIO_G723RATE eBitRate; /**< todo: Should this be moved to a config? */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ - OMX_BOOL bPostFilter; /**< Enable Post Filter */ -} OMX_AUDIO_PARAM_G723TYPE; - - -/** ITU G726 (ADPCM) rate */ -typedef enum OMX_AUDIO_G726MODE { - OMX_AUDIO_G726ModeUnused = 0, /**< G726 Mode unused / unknown */ - OMX_AUDIO_G726Mode16, /**< 16 kbps */ - OMX_AUDIO_G726Mode24, /**< 24 kbps */ - OMX_AUDIO_G726Mode32, /**< 32 kbps, most common rate, also G721 */ - OMX_AUDIO_G726Mode40, /**< 40 kbps */ - OMX_AUDIO_G726ModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_G726ModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_G726ModeMax = 0x7FFFFFFF -} OMX_AUDIO_G726MODE; - - -/** G.726 stream format parameters - must be at 8KHz */ -typedef struct OMX_AUDIO_PARAM_G726TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_AUDIO_G726MODE eG726Mode; -} OMX_AUDIO_PARAM_G726TYPE; - - -/** G729 coder type */ -typedef enum OMX_AUDIO_G729TYPE { - OMX_AUDIO_G729 = 0, /**< ITU G.729 encoded data */ - OMX_AUDIO_G729A, /**< ITU G.729 annex A encoded data */ - OMX_AUDIO_G729B, /**< ITU G.729 with annex B encoded data */ - OMX_AUDIO_G729AB, /**< ITU G.729 annexes A and B encoded data */ - OMX_AUDIO_G729KhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_G729VendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_G729Max = 0x7FFFFFFF -} OMX_AUDIO_G729TYPE; - - -/** G729 stream format parameters - fixed 6KHz sample rate */ -typedef struct OMX_AUDIO_PARAM_G729TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_AUDIO_G729TYPE eBitType; -} OMX_AUDIO_PARAM_G729TYPE; - - -/** AMR Frame format */ -typedef enum OMX_AUDIO_AMRFRAMEFORMATTYPE { - OMX_AUDIO_AMRFrameFormatConformance = 0, /**< Frame Format is AMR Conformance - (Standard) Format */ - OMX_AUDIO_AMRFrameFormatIF1, /**< Frame Format is AMR Interface - Format 1 */ - OMX_AUDIO_AMRFrameFormatIF2, /**< Frame Format is AMR Interface - Format 2*/ - OMX_AUDIO_AMRFrameFormatFSF, /**< Frame Format is AMR File Storage - Format */ - OMX_AUDIO_AMRFrameFormatRTPPayload, /**< Frame Format is AMR Real-Time - Transport Protocol Payload Format */ - OMX_AUDIO_AMRFrameFormatITU, /**< Frame Format is ITU Format (added at Motorola request) */ - OMX_AUDIO_AMRFrameFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_AMRFrameFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_AMRFrameFormatMax = 0x7FFFFFFF -} OMX_AUDIO_AMRFRAMEFORMATTYPE; - - -/** AMR band mode */ -typedef enum OMX_AUDIO_AMRBANDMODETYPE { - OMX_AUDIO_AMRBandModeUnused = 0, /**< AMRNB Mode unused / unknown */ - OMX_AUDIO_AMRBandModeNB0, /**< AMRNB Mode 0 = 4750 bps */ - OMX_AUDIO_AMRBandModeNB1, /**< AMRNB Mode 1 = 5150 bps */ - OMX_AUDIO_AMRBandModeNB2, /**< AMRNB Mode 2 = 5900 bps */ - OMX_AUDIO_AMRBandModeNB3, /**< AMRNB Mode 3 = 6700 bps */ - OMX_AUDIO_AMRBandModeNB4, /**< AMRNB Mode 4 = 7400 bps */ - OMX_AUDIO_AMRBandModeNB5, /**< AMRNB Mode 5 = 7950 bps */ - OMX_AUDIO_AMRBandModeNB6, /**< AMRNB Mode 6 = 10200 bps */ - OMX_AUDIO_AMRBandModeNB7, /**< AMRNB Mode 7 = 12200 bps */ - OMX_AUDIO_AMRBandModeWB0, /**< AMRWB Mode 0 = 6600 bps */ - OMX_AUDIO_AMRBandModeWB1, /**< AMRWB Mode 1 = 8850 bps */ - OMX_AUDIO_AMRBandModeWB2, /**< AMRWB Mode 2 = 12650 bps */ - OMX_AUDIO_AMRBandModeWB3, /**< AMRWB Mode 3 = 14250 bps */ - OMX_AUDIO_AMRBandModeWB4, /**< AMRWB Mode 4 = 15850 bps */ - OMX_AUDIO_AMRBandModeWB5, /**< AMRWB Mode 5 = 18250 bps */ - OMX_AUDIO_AMRBandModeWB6, /**< AMRWB Mode 6 = 19850 bps */ - OMX_AUDIO_AMRBandModeWB7, /**< AMRWB Mode 7 = 23050 bps */ - OMX_AUDIO_AMRBandModeWB8, /**< AMRWB Mode 8 = 23850 bps */ - OMX_AUDIO_AMRBandModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_AMRBandModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_AMRBandModeMax = 0x7FFFFFFF -} OMX_AUDIO_AMRBANDMODETYPE; - - -/** AMR Discontinuous Transmission mode */ -typedef enum OMX_AUDIO_AMRDTXMODETYPE { - OMX_AUDIO_AMRDTXModeOff = 0, /**< AMR Discontinuous Transmission Mode is disabled */ - OMX_AUDIO_AMRDTXModeOnVAD1, /**< AMR Discontinuous Transmission Mode using - Voice Activity Detector 1 (VAD1) is enabled */ - OMX_AUDIO_AMRDTXModeOnVAD2, /**< AMR Discontinuous Transmission Mode using - Voice Activity Detector 2 (VAD2) is enabled */ - OMX_AUDIO_AMRDTXModeOnAuto, /**< The codec will automatically select between - Off, VAD1 or VAD2 modes */ - - OMX_AUDIO_AMRDTXasEFR, /**< DTX as EFR instead of AMR standard (3GPP 26.101, frame type =8,9,10) */ - - OMX_AUDIO_AMRDTXModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_AMRDTXModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_AMRDTXModeMax = 0x7FFFFFFF -} OMX_AUDIO_AMRDTXMODETYPE; - - -/** AMR params */ -typedef struct OMX_AUDIO_PARAM_AMRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels */ - OMX_U32 nBitRate; /**< Bit rate read only field */ - OMX_AUDIO_AMRBANDMODETYPE eAMRBandMode; /**< AMR Band Mode enumeration */ - OMX_AUDIO_AMRDTXMODETYPE eAMRDTXMode; /**< AMR DTX Mode enumeration */ - OMX_AUDIO_AMRFRAMEFORMATTYPE eAMRFrameFormat; /**< AMR frame format enumeration */ -} OMX_AUDIO_PARAM_AMRTYPE; - - -/** GSM_FR (ETSI 06.10, 3GPP 46.010) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_GSMFRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_GSMFRTYPE; - - -/** GSM-HR (ETSI 06.20, 3GPP 46.020) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_GSMHRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_GSMHRTYPE; - - -/** GSM-EFR (ETSI 06.60, 3GPP 46.060) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_GSMEFRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_GSMEFRTYPE; - - -/** TDMA FR (TIA/EIA-136-420, VSELP 7.95kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_TDMAFRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_TDMAFRTYPE; - - -/** TDMA EFR (TIA/EIA-136-410, ACELP 7.4kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_TDMAEFRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_TDMAEFRTYPE; - - -/** PDC FR ( RCR-27, VSELP 6.7kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_PDCFRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_PDCFRTYPE; - - -/** PDC EFR ( RCR-27, ACELP 6.7kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_PDCEFRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_PDCEFRTYPE; - -/** PDC HR ( RCR-27, PSI-CELP 3.45kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_PDCHRTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_BOOL bDTX; /**< Enable Discontinuous Transmisssion */ - OMX_BOOL bHiPassFilter; /**< Enable High Pass Filter */ -} OMX_AUDIO_PARAM_PDCHRTYPE; - - -/** CDMA Rate types */ -typedef enum OMX_AUDIO_CDMARATETYPE { - OMX_AUDIO_CDMARateBlank = 0, /**< CDMA encoded frame is blank */ - OMX_AUDIO_CDMARateFull, /**< CDMA encoded frame in full rate */ - OMX_AUDIO_CDMARateHalf, /**< CDMA encoded frame in half rate */ - OMX_AUDIO_CDMARateQuarter, /**< CDMA encoded frame in quarter rate */ - OMX_AUDIO_CDMARateEighth, /**< CDMA encoded frame in eighth rate (DTX)*/ - OMX_AUDIO_CDMARateErasure, /**< CDMA erasure frame */ - OMX_AUDIO_CDMARateKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_CDMARateVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_CDMARateMax = 0x7FFFFFFF -} OMX_AUDIO_CDMARATETYPE; - - -/** QCELP8 (TIA/EIA-96, up to 8kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_QCELP8TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_U32 nBitRate; /**< Bit rate of the input data. Use 0 for variable - rate or unknown bit rates */ - OMX_AUDIO_CDMARATETYPE eCDMARate; /**< Frame rate */ - OMX_U32 nMinBitRate; /**< minmal rate for the encoder = 1,2,3,4, default = 1 */ - OMX_U32 nMaxBitRate; /**< maximal rate for the encoder = 1,2,3,4, default = 4 */ -} OMX_AUDIO_PARAM_QCELP8TYPE; - - -/** QCELP13 ( CDMA, EIA/TIA-733, 13.3kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_QCELP13TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_AUDIO_CDMARATETYPE eCDMARate; /**< Frame rate */ - OMX_U32 nMinBitRate; /**< minmal rate for the encoder = 1,2,3,4, default = 1 */ - OMX_U32 nMaxBitRate; /**< maximal rate for the encoder = 1,2,3,4, default = 4 */ -} OMX_AUDIO_PARAM_QCELP13TYPE; - - -/** EVRC ( CDMA, EIA/TIA-127, RCELP up to 8.55kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_EVRCTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_AUDIO_CDMARATETYPE eCDMARate; /**< actual Frame rate */ - OMX_BOOL bRATE_REDUCon; /**< RATE_REDUCtion is requested for this frame */ - OMX_U32 nMinBitRate; /**< minmal rate for the encoder = 1,2,3,4, default = 1 */ - OMX_U32 nMaxBitRate; /**< maximal rate for the encoder = 1,2,3,4, default = 4 */ - OMX_BOOL bHiPassFilter; /**< Enable encoder's High Pass Filter */ - OMX_BOOL bNoiseSuppressor; /**< Enable encoder's noise suppressor pre-processing */ - OMX_BOOL bPostFilter; /**< Enable decoder's post Filter */ -} OMX_AUDIO_PARAM_EVRCTYPE; - - -/** SMV ( up to 8.55kbps coder) stream format parameters */ -typedef struct OMX_AUDIO_PARAM_SMVTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannels; /**< Number of channels in the data stream (not - necessarily the same as the number of channels - to be rendered. */ - OMX_AUDIO_CDMARATETYPE eCDMARate; /**< Frame rate */ - OMX_BOOL bRATE_REDUCon; /**< RATE_REDUCtion is requested for this frame */ - OMX_U32 nMinBitRate; /**< minmal rate for the encoder = 1,2,3,4, default = 1 ??*/ - OMX_U32 nMaxBitRate; /**< maximal rate for the encoder = 1,2,3,4, default = 4 ??*/ - OMX_BOOL bHiPassFilter; /**< Enable encoder's High Pass Filter ??*/ - OMX_BOOL bNoiseSuppressor; /**< Enable encoder's noise suppressor pre-processing */ - OMX_BOOL bPostFilter; /**< Enable decoder's post Filter ??*/ -} OMX_AUDIO_PARAM_SMVTYPE; - - -/** MIDI Format - * @ingroup midi - */ -typedef enum OMX_AUDIO_MIDIFORMATTYPE -{ - OMX_AUDIO_MIDIFormatUnknown = 0, /**< MIDI Format unknown or don't care */ - OMX_AUDIO_MIDIFormatSMF0, /**< Standard MIDI File Type 0 */ - OMX_AUDIO_MIDIFormatSMF1, /**< Standard MIDI File Type 1 */ - OMX_AUDIO_MIDIFormatSMF2, /**< Standard MIDI File Type 2 */ - OMX_AUDIO_MIDIFormatSPMIDI, /**< SP-MIDI */ - OMX_AUDIO_MIDIFormatXMF0, /**< eXtensible Music Format type 0 */ - OMX_AUDIO_MIDIFormatXMF1, /**< eXtensible Music Format type 1 */ - OMX_AUDIO_MIDIFormatMobileXMF, /**< Mobile XMF (eXtensible Music Format type 2) */ - OMX_AUDIO_MIDIFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_MIDIFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_MIDIFormatMax = 0x7FFFFFFF -} OMX_AUDIO_MIDIFORMATTYPE; - - -/** MIDI params - * @ingroup midi - */ -typedef struct OMX_AUDIO_PARAM_MIDITYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nFileSize; /**< size of the MIDI file in bytes, where the entire - MIDI file passed in, otherwise if 0x0, the MIDI data - is merged and streamed (instead of passed as an - entire MIDI file) */ - OMX_BU32 sMaxPolyphony; /**< Specifies the maximum simultaneous polyphonic - voices. A value of zero indicates that the default - polyphony of the device is used */ - OMX_BOOL bLoadDefaultSound; /**< Whether to load default sound - bank at initialization */ - OMX_AUDIO_MIDIFORMATTYPE eMidiFormat; /**< Version of the MIDI file */ -} OMX_AUDIO_PARAM_MIDITYPE; - - -/** Type of the MIDI sound bank - * @ingroup midi - */ -typedef enum OMX_AUDIO_MIDISOUNDBANKTYPE { - OMX_AUDIO_MIDISoundBankUnused = 0, /**< unused/unknown soundbank type */ - OMX_AUDIO_MIDISoundBankDLS1, /**< DLS version 1 */ - OMX_AUDIO_MIDISoundBankDLS2, /**< DLS version 2 */ - OMX_AUDIO_MIDISoundBankMobileDLSBase, /**< Mobile DLS, using the base functionality */ - OMX_AUDIO_MIDISoundBankMobileDLSPlusOptions, /**< Mobile DLS, using the specification-defined optional feature set */ - OMX_AUDIO_MIDISoundBankKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_MIDISoundBankVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_MIDISoundBankMax = 0x7FFFFFFF -} OMX_AUDIO_MIDISOUNDBANKTYPE; - - -/** Bank Layout describes how bank MSB & LSB are used in the DLS instrument definitions sound bank - * @ingroup midi - */ -typedef enum OMX_AUDIO_MIDISOUNDBANKLAYOUTTYPE { - OMX_AUDIO_MIDISoundBankLayoutUnused = 0, /**< unused/unknown soundbank type */ - OMX_AUDIO_MIDISoundBankLayoutGM, /**< GS layout (based on bank MSB 0x00) */ - OMX_AUDIO_MIDISoundBankLayoutGM2, /**< General MIDI 2 layout (using MSB 0x78/0x79, LSB 0x00) */ - OMX_AUDIO_MIDISoundBankLayoutUser, /**< Does not conform to any bank numbering standards */ - OMX_AUDIO_MIDISoundBankLayoutKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_MIDISoundBankLayoutVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_MIDISoundBankLayoutMax = 0x7FFFFFFF -} OMX_AUDIO_MIDISOUNDBANKLAYOUTTYPE; - - -/** MIDI params to load/unload user soundbank - * @ingroup midi - */ -typedef struct OMX_AUDIO_PARAM_MIDILOADUSERSOUNDTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nDLSIndex; /**< DLS file index to be loaded */ - OMX_U32 nDLSSize; /**< Size in bytes */ - OMX_PTR pDLSData; /**< Pointer to DLS file data */ - OMX_AUDIO_MIDISOUNDBANKTYPE eMidiSoundBank; /**< Midi sound bank type enumeration */ - OMX_AUDIO_MIDISOUNDBANKLAYOUTTYPE eMidiSoundBankLayout; /**< Midi sound bank layout enumeration */ -} OMX_AUDIO_PARAM_MIDILOADUSERSOUNDTYPE; - - -/** Structure for Live MIDI events and MIP messages. - * (MIP = Maximum Instantaneous Polyphony; part of the SP-MIDI standard.) - * @ingroup midi - */ -typedef struct OMX_AUDIO_CONFIG_MIDIIMMEDIATEEVENTTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_U32 nMidiEventSize; /**< Size of immediate MIDI events or MIP message in bytes */ - OMX_U8 nMidiEvents[1]; /**< MIDI event array to be rendered immediately, or an - array for the MIP message buffer, where the size is - indicated by nMidiEventSize */ -} OMX_AUDIO_CONFIG_MIDIIMMEDIATEEVENTTYPE; - - -/** MIDI sound bank/ program pair in a given channel - * @ingroup midi - */ -typedef struct OMX_AUDIO_CONFIG_MIDISOUNDBANKPROGRAMTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_U32 nChannel; /**< Valid channel values range from 1 to 16 */ - OMX_U16 nIDProgram; /**< Valid program ID range is 1 to 128 */ - OMX_U16 nIDSoundBank; /**< Sound bank ID */ - OMX_U32 nUserSoundBankIndex;/**< User soundbank index, easier to access soundbanks - by index if multiple banks are present */ -} OMX_AUDIO_CONFIG_MIDISOUNDBANKPROGRAMTYPE; - - -/** MIDI control - * @ingroup midi - */ -typedef struct OMX_AUDIO_CONFIG_MIDICONTROLTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BS32 sPitchTransposition; /**< Pitch transposition in semitones, stored as Q22.10 - format based on JAVA MMAPI (JSR-135) requirement */ - OMX_BU32 sPlayBackRate; /**< Relative playback rate, stored as Q14.17 fixed-point - number based on JSR-135 requirement */ - OMX_BU32 sTempo ; /**< Tempo in beats per minute (BPM), stored as Q22.10 - fixed-point number based on JSR-135 requirement */ - OMX_U32 nMaxPolyphony; /**< Specifies the maximum simultaneous polyphonic - voices. A value of zero indicates that the default - polyphony of the device is used */ - OMX_U32 nNumRepeat; /**< Number of times to repeat playback */ - OMX_U32 nStopTime; /**< Time in milliseconds to indicate when playback - will stop automatically. Set to zero if not used */ - OMX_U16 nChannelMuteMask; /**< 16 bit mask for channel mute status */ - OMX_U16 nChannelSoloMask; /**< 16 bit mask for channel solo status */ - OMX_U32 nTrack0031MuteMask; /**< 32 bit mask for track mute status. Note: This is for tracks 0-31 */ - OMX_U32 nTrack3263MuteMask; /**< 32 bit mask for track mute status. Note: This is for tracks 32-63 */ - OMX_U32 nTrack0031SoloMask; /**< 32 bit mask for track solo status. Note: This is for tracks 0-31 */ - OMX_U32 nTrack3263SoloMask; /**< 32 bit mask for track solo status. Note: This is for tracks 32-63 */ - -} OMX_AUDIO_CONFIG_MIDICONTROLTYPE; - - -/** MIDI Playback States - * @ingroup midi - */ -typedef enum OMX_AUDIO_MIDIPLAYBACKSTATETYPE { - OMX_AUDIO_MIDIPlayBackStateUnknown = 0, /**< Unknown state or state does not map to - other defined states */ - OMX_AUDIO_MIDIPlayBackStateClosedEngaged, /**< No MIDI resource is currently open. - The MIDI engine is currently processing - MIDI events. */ - OMX_AUDIO_MIDIPlayBackStateParsing, /**< A MIDI resource is open and is being - primed. The MIDI engine is currently - processing MIDI events. */ - OMX_AUDIO_MIDIPlayBackStateOpenEngaged, /**< A MIDI resource is open and primed but - not playing. The MIDI engine is currently - processing MIDI events. The transition to - this state is only possible from the - OMX_AUDIO_MIDIPlayBackStatePlaying state, - when the 'playback head' reaches the end - of media data or the playback stops due - to stop time set.*/ - OMX_AUDIO_MIDIPlayBackStatePlaying, /**< A MIDI resource is open and currently - playing. The MIDI engine is currently - processing MIDI events.*/ - OMX_AUDIO_MIDIPlayBackStatePlayingPartially, /**< Best-effort playback due to SP-MIDI/DLS - resource constraints */ - OMX_AUDIO_MIDIPlayBackStatePlayingSilently, /**< Due to system resource constraints and - SP-MIDI content constraints, there is - no audible MIDI content during playback - currently. The situation may change if - resources are freed later.*/ - OMX_AUDIO_MIDIPlayBackStateKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_MIDIPlayBackStateVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_MIDIPlayBackStateMax = 0x7FFFFFFF -} OMX_AUDIO_MIDIPLAYBACKSTATETYPE; - - -/** MIDI status - * @ingroup midi - */ -typedef struct OMX_AUDIO_CONFIG_MIDISTATUSTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U16 nNumTracks; /**< Number of MIDI tracks in the file, read only field. - NOTE: May not return a meaningful value until the entire - file is parsed and buffered. */ - OMX_U32 nDuration; /**< The length of the currently open MIDI resource - in milliseconds. NOTE: May not return a meaningful value - until the entire file is parsed and buffered. */ - OMX_U32 nPosition; /**< Current Position of the MIDI resource being played - in milliseconds */ - OMX_BOOL bVibra; /**< Does Vibra track exist? NOTE: May not return a meaningful - value until the entire file is parsed and buffered. */ - OMX_U32 nNumMetaEvents; /**< Total number of MIDI Meta Events in the currently - open MIDI resource. NOTE: May not return a meaningful value - until the entire file is parsed and buffered. */ - OMX_U32 nNumActiveVoices; /**< Number of active voices in the currently playing - MIDI resource. NOTE: May not return a meaningful value until - the entire file is parsed and buffered. */ - OMX_AUDIO_MIDIPLAYBACKSTATETYPE eMIDIPlayBackState; /**< MIDI playback state enumeration, read only field */ -} OMX_AUDIO_CONFIG_MIDISTATUSTYPE; - - -/** MIDI Meta Event structure one per Meta Event. - * MIDI Meta Events are like audio metadata, except that they are interspersed - * with the MIDI content throughout the file and are not localized in the header. - * As such, it is necessary to retrieve information about these Meta Events from - * the engine, as it encounters these Meta Events within the MIDI content. - * For example, SMF files can have up to 14 types of MIDI Meta Events (copyright, - * author, default tempo, etc.) scattered throughout the file. - * @ingroup midi - */ -typedef struct OMX_AUDIO_CONFIG_MIDIMETAEVENTTYPE{ - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nIndex; /**< Index of Meta Event */ - OMX_U8 nMetaEventType; /**< Meta Event Type, 7bits (i.e. 0 - 127) */ - OMX_U32 nMetaEventSize; /**< size of the Meta Event in bytes */ - OMX_U32 nTrack; /**< track number for the meta event */ - OMX_U32 nPosition; /**< Position of the meta-event in milliseconds */ -} OMX_AUDIO_CONFIG_MIDIMETAEVENTTYPE; - - -/** MIDI Meta Event Data structure - one per Meta Event. - * @ingroup midi - */ -typedef struct OMX_AUDIO_CONFIG_MIDIMETAEVENTDATATYPE{ - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nIndex; /**< Index of Meta Event */ - OMX_U32 nMetaEventSize; /**< size of the Meta Event in bytes */ - OMX_U8 nData[1]; /**< array of one or more bytes of meta data - as indicated by the nMetaEventSize field */ -} OMX_AUDIO_CONFIG__MIDIMETAEVENTDATATYPE; - - -/** Audio Volume adjustment for a port */ -typedef struct OMX_AUDIO_CONFIG_VOLUMETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port index indicating which port to - set. Select the input port to set - just that port's volume. Select the - output port to adjust the master - volume. */ - OMX_BOOL bLinear; /**< Is the volume to be set in linear (0.100) - or logarithmic scale (mB) */ - OMX_BS32 sVolume; /**< Volume linear setting in the 0..100 range, OR - Volume logarithmic setting for this port. The values - for volume are in mB (millibels = 1/100 dB) relative - to a gain of 1 (e.g. the output is the same as the - input level). Values are in mB from nMax - (maximum volume) to nMin mB (typically negative). - Since the volume is "voltage" - and not a "power", it takes a setting of - -600 mB to decrease the volume by 1/2. If - a component cannot accurately set the - volume to the requested value, it must - set the volume to the closest value BELOW - the requested value. When getting the - volume setting, the current actual volume - must be returned. */ -} OMX_AUDIO_CONFIG_VOLUMETYPE; - - -/** Audio Volume adjustment for a channel */ -typedef struct OMX_AUDIO_CONFIG_CHANNELVOLUMETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port index indicating which port to - set. Select the input port to set - just that port's volume. Select the - output port to adjust the master - volume. */ - OMX_U32 nChannel; /**< channel to select from 0 to N-1, - using OMX_ALL to apply volume settings - to all channels */ - OMX_BOOL bLinear; /**< Is the volume to be set in linear (0.100) or - logarithmic scale (mB) */ - OMX_BS32 sVolume; /**< Volume linear setting in the 0..100 range, OR - Volume logarithmic setting for this port. - The values for volume are in mB - (millibels = 1/100 dB) relative to a gain - of 1 (e.g. the output is the same as the - input level). Values are in mB from nMax - (maximum volume) to nMin mB (typically negative). - Since the volume is "voltage" - and not a "power", it takes a setting of - -600 mB to decrease the volume by 1/2. If - a component cannot accurately set the - volume to the requested value, it must - set the volume to the closest value BELOW - the requested value. When getting the - volume setting, the current actual volume - must be returned. */ - OMX_BOOL bIsMIDI; /**< TRUE if nChannel refers to a MIDI channel, - FALSE otherwise */ -} OMX_AUDIO_CONFIG_CHANNELVOLUMETYPE; - - -/** Audio balance setting */ -typedef struct OMX_AUDIO_CONFIG_BALANCETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port index indicating which port to - set. Select the input port to set - just that port's balance. Select the - output port to adjust the master - balance. */ - OMX_S32 nBalance; /**< balance setting for this port - (-100 to 100, where -100 indicates - all left, and no right */ -} OMX_AUDIO_CONFIG_BALANCETYPE; - - -/** Audio Port mute */ -typedef struct OMX_AUDIO_CONFIG_MUTETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port index indicating which port to - set. Select the input port to set - just that port's mute. Select the - output port to adjust the master - mute. */ - OMX_BOOL bMute; /**< Mute setting for this port */ -} OMX_AUDIO_CONFIG_MUTETYPE; - - -/** Audio Channel mute */ -typedef struct OMX_AUDIO_CONFIG_CHANNELMUTETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nChannel; /**< channel to select from 0 to N-1, - using OMX_ALL to apply mute settings - to all channels */ - OMX_BOOL bMute; /**< Mute setting for this channel */ - OMX_BOOL bIsMIDI; /**< TRUE if nChannel refers to a MIDI channel, - FALSE otherwise */ -} OMX_AUDIO_CONFIG_CHANNELMUTETYPE; - - - -/** Enable / Disable for loudness control, which boosts bass and to a - * smaller extent high end frequencies to compensate for hearing - * ability at the extreme ends of the audio spectrum - */ -typedef struct OMX_AUDIO_CONFIG_LOUDNESSTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bLoudness; /**< Enable/disable for loudness */ -} OMX_AUDIO_CONFIG_LOUDNESSTYPE; - - -/** Enable / Disable for bass, which controls low frequencies - */ -typedef struct OMX_AUDIO_CONFIG_BASSTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bEnable; /**< Enable/disable for bass control */ - OMX_S32 nBass; /**< bass setting for the port, as a - continuous value from -100 to 100 - (0 means no change in bass level)*/ -} OMX_AUDIO_CONFIG_BASSTYPE; - - -/** Enable / Disable for treble, which controls high frequencies tones - */ -typedef struct OMX_AUDIO_CONFIG_TREBLETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bEnable; /**< Enable/disable for treble control */ - OMX_S32 nTreble; /**< treble setting for the port, as a - continuous value from -100 to 100 - (0 means no change in treble level) */ -} OMX_AUDIO_CONFIG_TREBLETYPE; - - -/** An equalizer is typically used for two reasons: to compensate for an - * sub-optimal frequency response of a system to make it sound more natural - * or to create intentionally some unnatural coloring to the sound to create - * an effect. - * @ingroup effects - */ -typedef struct OMX_AUDIO_CONFIG_EQUALIZERTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bEnable; /**< Enable/disable for equalizer */ - OMX_BU32 sBandIndex; /**< Band number to be set. Upper Limit is - N-1, where N is the number of bands, lower limit is 0 */ - OMX_BU32 sCenterFreq; /**< Center frequecies in Hz. This is a - read only element and is used to determine - the lower, center and upper frequency of - this band. */ - OMX_BS32 sBandLevel; /**< band level in millibels */ -} OMX_AUDIO_CONFIG_EQUALIZERTYPE; - - -/** Stereo widening mode type - * @ingroup effects - */ -typedef enum OMX_AUDIO_STEREOWIDENINGTYPE { - OMX_AUDIO_StereoWideningHeadphones, /**< Stereo widening for loudspeakers */ - OMX_AUDIO_StereoWideningLoudspeakers, /**< Stereo widening for closely spaced loudspeakers */ - OMX_AUDIO_StereoWideningKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_StereoWideningVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_StereoWideningMax = 0x7FFFFFFF -} OMX_AUDIO_STEREOWIDENINGTYPE; - - -/** Control for stereo widening, which is a special 2-channel - * case of the audio virtualizer effect. For example, for 5.1-channel - * output, it translates to virtual surround sound. - * @ingroup effects - */ -typedef struct OMX_AUDIO_CONFIG_STEREOWIDENINGTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bEnable; /**< Enable/disable for stereo widening control */ - OMX_AUDIO_STEREOWIDENINGTYPE eWideningType; /**< Stereo widening algorithm type */ - OMX_U32 nStereoWidening; /**< stereo widening setting for the port, - as a continuous value from 0 to 100 */ -} OMX_AUDIO_CONFIG_STEREOWIDENINGTYPE; - - -/** The chorus effect (or ``choralizer'') is any signal processor which makes - * one sound source (such as a voice) sound like many such sources singing - * (or playing) in unison. Since performance in unison is never exact, chorus - * effects simulate this by making independently modified copies of the input - * signal. Modifications may include (1) delay, (2) frequency shift, and - * (3) amplitude modulation. - * @ingroup effects - */ -typedef struct OMX_AUDIO_CONFIG_CHORUSTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bEnable; /**< Enable/disable for chorus */ - OMX_BU32 sDelay; /**< average delay in milliseconds */ - OMX_BU32 sModulationRate; /**< rate of modulation in millihertz */ - OMX_U32 nModulationDepth; /**< depth of modulation as a percentage of - delay (i.e. 0 to 100) */ - OMX_BU32 nFeedback; /**< Feedback from chorus output to input in percentage */ -} OMX_AUDIO_CONFIG_CHORUSTYPE; - - -/** Reverberation is part of the reflected sound that follows the early - * reflections. In a typical room, this consists of a dense succession of - * echoes whose energy decays exponentially. The reverberation effect structure - * as defined here includes both (early) reflections as well as (late) reverberations. - * @ingroup effects - */ -typedef struct OMX_AUDIO_CONFIG_REVERBERATIONTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bEnable; /**< Enable/disable for reverberation control */ - OMX_BS32 sRoomLevel; /**< Intensity level for the whole room effect - (i.e. both early reflections and late - reverberation) in millibels */ - OMX_BS32 sRoomHighFreqLevel; /**< Attenuation at high frequencies - relative to the intensity at low - frequencies in millibels */ - OMX_BS32 sReflectionsLevel; /**< Intensity level of early reflections - (relative to room value), in millibels */ - OMX_BU32 sReflectionsDelay; /**< Delay time of the first reflection relative - to the direct path, in milliseconds */ - OMX_BS32 sReverbLevel; /**< Intensity level of late reverberation - relative to room level, in millibels */ - OMX_BU32 sReverbDelay; /**< Time delay from the first early reflection - to the beginning of the late reverberation - section, in milliseconds */ - OMX_BU32 sDecayTime; /**< Late reverberation decay time at low - frequencies, in milliseconds */ - OMX_BU32 nDecayHighFreqRatio; /**< Ratio of high frequency decay time relative - to low frequency decay time in percent */ - OMX_U32 nDensity; /**< Modal density in the late reverberation decay, - in percent (i.e. 0 - 100) */ - OMX_U32 nDiffusion; /**< Echo density in the late reverberation decay, - in percent (i.e. 0 - 100) */ - OMX_BU32 sReferenceHighFreq; /**< Reference high frequency in Hertz. This is - the frequency used as the reference for all - the high-frequency settings above */ - -} OMX_AUDIO_CONFIG_REVERBERATIONTYPE; - - -/** Possible settings for the Echo Cancelation structure to use - * @ingroup effects - */ -typedef enum OMX_AUDIO_ECHOCANTYPE { - OMX_AUDIO_EchoCanOff = 0, /**< Echo Cancellation is disabled */ - OMX_AUDIO_EchoCanNormal, /**< Echo Cancellation normal operation - - echo from plastics and face */ - OMX_AUDIO_EchoCanHFree, /**< Echo Cancellation optimized for - Hands Free operation */ - OMX_AUDIO_EchoCanCarKit, /**< Echo Cancellation optimized for - Car Kit (longer echo) */ - OMX_AUDIO_EchoCanKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_AUDIO_EchoCanVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_AUDIO_EchoCanMax = 0x7FFFFFFF -} OMX_AUDIO_ECHOCANTYPE; - - -/** Enable / Disable for echo cancelation, which removes undesired echo's - * from the audio - * @ingroup effects - */ -typedef struct OMX_AUDIO_CONFIG_ECHOCANCELATIONTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_AUDIO_ECHOCANTYPE eEchoCancelation; /**< Echo cancelation settings */ -} OMX_AUDIO_CONFIG_ECHOCANCELATIONTYPE; - - -/** Enable / Disable for noise reduction, which undesired noise from - * the audio - * @ingroup effects - */ -typedef struct OMX_AUDIO_CONFIG_NOISEREDUCTIONTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BOOL bNoiseReduction; /**< Enable/disable for noise reduction */ -} OMX_AUDIO_CONFIG_NOISEREDUCTIONTYPE; - -/** @} */ - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ - diff --git a/subprojects/gst-omx/omx/openmax/OMX_Component.h b/subprojects/gst-omx/omx/openmax/OMX_Component.h deleted file mode 100644 index d5956405e2..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Component.h +++ /dev/null @@ -1,579 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_Component.h - OpenMax IL version 1.1.2 - * The OMX_Component header file contains the definitions used to define - * the public interface of a component. This header file is intended to - * be used by both the application and the component. - */ - -#ifndef OMX_Component_h -#define OMX_Component_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - - -/* Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ - -#include -#include -#include -#include - -/** @ingroup comp */ -typedef enum OMX_PORTDOMAINTYPE { - OMX_PortDomainAudio, - OMX_PortDomainVideo, - OMX_PortDomainImage, - OMX_PortDomainOther, - OMX_PortDomainKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_PortDomainVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_PortDomainMax = 0x7ffffff -} OMX_PORTDOMAINTYPE; - -/** @ingroup comp */ -typedef struct OMX_PARAM_PORTDEFINITIONTYPE { - OMX_U32 nSize; /**< Size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port number the structure applies to */ - OMX_DIRTYPE eDir; /**< Direction (input or output) of this port */ - OMX_U32 nBufferCountActual; /**< The actual number of buffers allocated on this port */ - OMX_U32 nBufferCountMin; /**< The minimum number of buffers this port requires */ - OMX_U32 nBufferSize; /**< Size, in bytes, for buffers to be used for this channel */ - OMX_BOOL bEnabled; /**< Ports default to enabled and are enabled/disabled by - OMX_CommandPortEnable/OMX_CommandPortDisable. - When disabled a port is unpopulated. A disabled port - is not populated with buffers on a transition to IDLE. */ - OMX_BOOL bPopulated; /**< Port is populated with all of its buffers as indicated by - nBufferCountActual. A disabled port is always unpopulated. - An enabled port is populated on a transition to OMX_StateIdle - and unpopulated on a transition to loaded. */ - OMX_PORTDOMAINTYPE eDomain; /**< Domain of the port. Determines the contents of metadata below. */ - union { - OMX_AUDIO_PORTDEFINITIONTYPE audio; - OMX_VIDEO_PORTDEFINITIONTYPE video; - OMX_IMAGE_PORTDEFINITIONTYPE image; - OMX_OTHER_PORTDEFINITIONTYPE other; - } format; - OMX_BOOL bBuffersContiguous; - OMX_U32 nBufferAlignment; -} OMX_PARAM_PORTDEFINITIONTYPE; - -/** @ingroup comp */ -typedef struct OMX_PARAM_U32TYPE { - OMX_U32 nSize; /**< Size of this structure, in Bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_U32 nU32; /**< U32 value */ -} OMX_PARAM_U32TYPE; - -/** @ingroup rpm */ -typedef enum OMX_SUSPENSIONPOLICYTYPE { - OMX_SuspensionDisabled, /**< No suspension; v1.0 behavior */ - OMX_SuspensionEnabled, /**< Suspension allowed */ - OMX_SuspensionPolicyKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_SuspensionPolicyStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_SuspensionPolicyMax = 0x7fffffff -} OMX_SUSPENSIONPOLICYTYPE; - -/** @ingroup rpm */ -typedef struct OMX_PARAM_SUSPENSIONPOLICYTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_SUSPENSIONPOLICYTYPE ePolicy; -} OMX_PARAM_SUSPENSIONPOLICYTYPE; - -/** @ingroup rpm */ -typedef enum OMX_SUSPENSIONTYPE { - OMX_NotSuspended, /**< component is not suspended */ - OMX_Suspended, /**< component is suspended */ - OMX_SuspensionKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_SuspensionVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_SuspendMax = 0x7FFFFFFF -} OMX_SUSPENSIONTYPE; - -/** @ingroup rpm */ -typedef struct OMX_PARAM_SUSPENSIONTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_SUSPENSIONTYPE eType; -} OMX_PARAM_SUSPENSIONTYPE ; - -typedef struct OMX_CONFIG_BOOLEANTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_BOOL bEnabled; -} OMX_CONFIG_BOOLEANTYPE; - -/* Parameter specifying the content uri to use. */ -/** @ingroup cp */ -typedef struct OMX_PARAM_CONTENTURITYPE -{ - OMX_U32 nSize; /**< size of the structure in bytes, including - actual URI name */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U8 contentURI[1]; /**< The URI name */ -} OMX_PARAM_CONTENTURITYPE; - -/* Parameter specifying the pipe to use. */ -/** @ingroup cp */ -typedef struct OMX_PARAM_CONTENTPIPETYPE -{ - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_HANDLETYPE hPipe; /**< The pipe handle*/ -} OMX_PARAM_CONTENTPIPETYPE; - -/** @ingroup rpm */ -typedef struct OMX_RESOURCECONCEALMENTTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_BOOL bResourceConcealmentForbidden; /**< disallow the use of resource concealment - methods (like degrading algorithm quality to - lower resource consumption or functional bypass) - on a component as a resolution to resource conflicts. */ -} OMX_RESOURCECONCEALMENTTYPE; - - -/** @ingroup metadata */ -typedef enum OMX_METADATACHARSETTYPE { - OMX_MetadataCharsetUnknown = 0, - OMX_MetadataCharsetASCII, - OMX_MetadataCharsetBinary, - OMX_MetadataCharsetCodePage1252, - OMX_MetadataCharsetUTF8, - OMX_MetadataCharsetJavaConformantUTF8, - OMX_MetadataCharsetUTF7, - OMX_MetadataCharsetImapUTF7, - OMX_MetadataCharsetUTF16LE, - OMX_MetadataCharsetUTF16BE, - OMX_MetadataCharsetGB12345, - OMX_MetadataCharsetHZGB2312, - OMX_MetadataCharsetGB2312, - OMX_MetadataCharsetGB18030, - OMX_MetadataCharsetGBK, - OMX_MetadataCharsetBig5, - OMX_MetadataCharsetISO88591, - OMX_MetadataCharsetISO88592, - OMX_MetadataCharsetISO88593, - OMX_MetadataCharsetISO88594, - OMX_MetadataCharsetISO88595, - OMX_MetadataCharsetISO88596, - OMX_MetadataCharsetISO88597, - OMX_MetadataCharsetISO88598, - OMX_MetadataCharsetISO88599, - OMX_MetadataCharsetISO885910, - OMX_MetadataCharsetISO885913, - OMX_MetadataCharsetISO885914, - OMX_MetadataCharsetISO885915, - OMX_MetadataCharsetShiftJIS, - OMX_MetadataCharsetISO2022JP, - OMX_MetadataCharsetISO2022JP1, - OMX_MetadataCharsetISOEUCJP, - OMX_MetadataCharsetSMS7Bit, - OMX_MetadataCharsetKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_MetadataCharsetVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_MetadataCharsetTypeMax= 0x7FFFFFFF -} OMX_METADATACHARSETTYPE; - -/** @ingroup metadata */ -typedef enum OMX_METADATASCOPETYPE -{ - OMX_MetadataScopeAllLevels, - OMX_MetadataScopeTopLevel, - OMX_MetadataScopePortLevel, - OMX_MetadataScopeNodeLevel, - OMX_MetadataScopeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_MetadataScopeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_MetadataScopeTypeMax = 0x7fffffff -} OMX_METADATASCOPETYPE; - -/** @ingroup metadata */ -typedef enum OMX_METADATASEARCHMODETYPE -{ - OMX_MetadataSearchValueSizeByIndex, - OMX_MetadataSearchItemByIndex, - OMX_MetadataSearchNextItemByKey, - OMX_MetadataSearchKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_MetadataSearchVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_MetadataSearchTypeMax = 0x7fffffff -} OMX_METADATASEARCHMODETYPE; -/** @ingroup metadata */ -typedef struct OMX_CONFIG_METADATAITEMCOUNTTYPE -{ - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_METADATASCOPETYPE eScopeMode; - OMX_U32 nScopeSpecifier; - OMX_U32 nMetadataItemCount; -} OMX_CONFIG_METADATAITEMCOUNTTYPE; - -/** @ingroup metadata */ -typedef struct OMX_CONFIG_METADATAITEMTYPE -{ - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_METADATASCOPETYPE eScopeMode; - OMX_U32 nScopeSpecifier; - OMX_U32 nMetadataItemIndex; - OMX_METADATASEARCHMODETYPE eSearchMode; - OMX_METADATACHARSETTYPE eKeyCharset; - OMX_U8 nKeySizeUsed; - OMX_U8 nKey[128]; - OMX_METADATACHARSETTYPE eValueCharset; - OMX_STRING sLanguageCountry; - OMX_U32 nValueMaxSize; - OMX_U32 nValueSizeUsed; - OMX_U8 nValue[1]; -} OMX_CONFIG_METADATAITEMTYPE; - -/* @ingroup metadata */ -typedef struct OMX_CONFIG_CONTAINERNODECOUNTTYPE -{ - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_BOOL bAllKeys; - OMX_U32 nParentNodeID; - OMX_U32 nNumNodes; -} OMX_CONFIG_CONTAINERNODECOUNTTYPE; - -/** @ingroup metadata */ -typedef struct OMX_CONFIG_CONTAINERNODEIDTYPE -{ - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_BOOL bAllKeys; - OMX_U32 nParentNodeID; - OMX_U32 nNodeIndex; - OMX_U32 nNodeID; - OMX_STRING cNodeName; - OMX_BOOL bIsLeafType; -} OMX_CONFIG_CONTAINERNODEIDTYPE; - -/** @ingroup metadata */ -typedef struct OMX_PARAM_METADATAFILTERTYPE -{ - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_BOOL bAllKeys; /* if true then this structure refers to all keys and - * the three key fields below are ignored */ - OMX_METADATACHARSETTYPE eKeyCharset; - OMX_U32 nKeySizeUsed; - OMX_U8 nKey [128]; - OMX_U32 nLanguageCountrySizeUsed; - OMX_U8 nLanguageCountry[128]; - OMX_BOOL bEnabled; /* if true then key is part of filter (e.g. - * retained for query later). If false then - * key is not part of filter */ -} OMX_PARAM_METADATAFILTERTYPE; - -/** The OMX_HANDLETYPE structure defines the component handle. The component - * handle is used to access all of the component's public methods and also - * contains pointers to the component's private data area. The component - * handle is initialized by the OMX core (with help from the component) - * during the process of loading the component. After the component is - * successfully loaded, the application can safely access any of the - * component's public functions (although some may return an error because - * the state is inappropriate for the access). - * - * @ingroup comp - */ -typedef struct OMX_COMPONENTTYPE -{ - /** The size of this structure, in bytes. It is the responsibility - of the allocator of this structure to fill in this value. Since - this structure is allocated by the GetHandle function, this - function will fill in this value. */ - OMX_U32 nSize; - - /** nVersion is the version of the OMX specification that the structure - is built against. It is the responsibility of the creator of this - structure to initialize this value and every user of this structure - should verify that it knows how to use the exact version of - this structure found herein. */ - OMX_VERSIONTYPE nVersion; - - /** pComponentPrivate is a pointer to the component private data area. - This member is allocated and initialized by the component when the - component is first loaded. The application should not access this - data area. */ - OMX_PTR pComponentPrivate; - - /** pApplicationPrivate is a pointer that is a parameter to the - OMX_GetHandle method, and contains an application private value - provided by the IL client. This application private data is - returned to the IL Client by OMX in all callbacks */ - OMX_PTR pApplicationPrivate; - - /** refer to OMX_GetComponentVersion in OMX_core.h or the OMX IL - specification for details on the GetComponentVersion method. - */ - OMX_ERRORTYPE (*GetComponentVersion)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_OUT OMX_STRING pComponentName, - OMX_OUT OMX_VERSIONTYPE* pComponentVersion, - OMX_OUT OMX_VERSIONTYPE* pSpecVersion, - OMX_OUT OMX_UUIDTYPE* pComponentUUID); - - /** refer to OMX_SendCommand in OMX_core.h or the OMX IL - specification for details on the SendCommand method. - */ - OMX_ERRORTYPE (*SendCommand)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_COMMANDTYPE Cmd, - OMX_IN OMX_U32 nParam1, - OMX_IN OMX_PTR pCmdData); - - /** refer to OMX_GetParameter in OMX_core.h or the OMX IL - specification for details on the GetParameter method. - */ - OMX_ERRORTYPE (*GetParameter)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_INDEXTYPE nParamIndex, - OMX_INOUT OMX_PTR pComponentParameterStructure); - - - /** refer to OMX_SetParameter in OMX_core.h or the OMX IL - specification for details on the SetParameter method. - */ - OMX_ERRORTYPE (*SetParameter)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_INDEXTYPE nIndex, - OMX_IN OMX_PTR pComponentParameterStructure); - - - /** refer to OMX_GetConfig in OMX_core.h or the OMX IL - specification for details on the GetConfig method. - */ - OMX_ERRORTYPE (*GetConfig)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_INDEXTYPE nIndex, - OMX_INOUT OMX_PTR pComponentConfigStructure); - - - /** refer to OMX_SetConfig in OMX_core.h or the OMX IL - specification for details on the SetConfig method. - */ - OMX_ERRORTYPE (*SetConfig)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_INDEXTYPE nIndex, - OMX_IN OMX_PTR pComponentConfigStructure); - - - /** refer to OMX_GetExtensionIndex in OMX_core.h or the OMX IL - specification for details on the GetExtensionIndex method. - */ - OMX_ERRORTYPE (*GetExtensionIndex)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_STRING cParameterName, - OMX_OUT OMX_INDEXTYPE* pIndexType); - - - /** refer to OMX_GetState in OMX_core.h or the OMX IL - specification for details on the GetState method. - */ - OMX_ERRORTYPE (*GetState)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_OUT OMX_STATETYPE* pState); - - - /** The ComponentTunnelRequest method will interact with another OMX - component to determine if tunneling is possible and to setup the - tunneling. The return codes for this method can be used to - determine if tunneling is not possible, or if tunneling is not - supported. - - Base profile components (i.e. non-interop) do not support this - method and should return OMX_ErrorNotImplemented - - The interop profile component MUST support tunneling to another - interop profile component with a compatible port parameters. - A component may also support proprietary communication. - - If proprietary communication is supported the negotiation of - proprietary communication is done outside of OMX in a vendor - specific way. It is only required that the proper result be - returned and the details of how the setup is done is left - to the component implementation. - - When this method is invoked when nPort in an output port, the - component will: - 1. Populate the pTunnelSetup structure with the output port's - requirements and constraints for the tunnel. - - When this method is invoked when nPort in an input port, the - component will: - 1. Query the necessary parameters from the output port to - determine if the ports are compatible for tunneling - 2. If the ports are compatible, the component should store - the tunnel step provided by the output port - 3. Determine which port (either input or output) is the buffer - supplier, and call OMX_SetParameter on the output port to - indicate this selection. - - The component will return from this call within 5 msec. - - @param [in] hComp - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle method. - @param [in] nPort - nPort is used to select the port on the component to be used - for tunneling. - @param [in] hTunneledComp - Handle of the component to tunnel with. This is the component - handle returned by the call to the OMX_GetHandle method. When - this parameter is 0x0 the component should setup the port for - communication with the application / IL Client. - @param [in] nPortOutput - nPortOutput is used indicate the port the component should - tunnel with. - @param [in] pTunnelSetup - Pointer to the tunnel setup structure. When nPort is an output port - the component should populate the fields of this structure. When - When nPort is an input port the component should review the setup - provided by the component with the output port. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup tun - */ - - OMX_ERRORTYPE (*ComponentTunnelRequest)( - OMX_IN OMX_HANDLETYPE hComp, - OMX_IN OMX_U32 nPort, - OMX_IN OMX_HANDLETYPE hTunneledComp, - OMX_IN OMX_U32 nTunneledPort, - OMX_INOUT OMX_TUNNELSETUPTYPE* pTunnelSetup); - - /** refer to OMX_UseBuffer in OMX_core.h or the OMX IL - specification for details on the UseBuffer method. - @ingroup buf - */ - OMX_ERRORTYPE (*UseBuffer)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_INOUT OMX_BUFFERHEADERTYPE** ppBufferHdr, - OMX_IN OMX_U32 nPortIndex, - OMX_IN OMX_PTR pAppPrivate, - OMX_IN OMX_U32 nSizeBytes, - OMX_IN OMX_U8* pBuffer); - - /** refer to OMX_AllocateBuffer in OMX_core.h or the OMX IL - specification for details on the AllocateBuffer method. - @ingroup buf - */ - OMX_ERRORTYPE (*AllocateBuffer)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_INOUT OMX_BUFFERHEADERTYPE** ppBuffer, - OMX_IN OMX_U32 nPortIndex, - OMX_IN OMX_PTR pAppPrivate, - OMX_IN OMX_U32 nSizeBytes); - - /** refer to OMX_FreeBuffer in OMX_core.h or the OMX IL - specification for details on the FreeBuffer method. - @ingroup buf - */ - OMX_ERRORTYPE (*FreeBuffer)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_U32 nPortIndex, - OMX_IN OMX_BUFFERHEADERTYPE* pBuffer); - - /** refer to OMX_EmptyThisBuffer in OMX_core.h or the OMX IL - specification for details on the EmptyThisBuffer method. - @ingroup buf - */ - OMX_ERRORTYPE (*EmptyThisBuffer)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_BUFFERHEADERTYPE* pBuffer); - - /** refer to OMX_FillThisBuffer in OMX_core.h or the OMX IL - specification for details on the FillThisBuffer method. - @ingroup buf - */ - OMX_ERRORTYPE (*FillThisBuffer)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_BUFFERHEADERTYPE* pBuffer); - - /** The SetCallbacks method is used by the core to specify the callback - structure from the application to the component. This is a blocking - call. The component will return from this call within 5 msec. - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the GetHandle function. - @param [in] pCallbacks - pointer to an OMX_CALLBACKTYPE structure used to provide the - callback information to the component - @param [in] pAppData - pointer to an application defined value. It is anticipated that - the application will pass a pointer to a data structure or a "this - pointer" in this area to allow the callback (in the application) - to determine the context of the call - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - */ - OMX_ERRORTYPE (*SetCallbacks)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_CALLBACKTYPE* pCallbacks, - OMX_IN OMX_PTR pAppData); - - /** ComponentDeInit method is used to deinitialize the component - providing a means to free any resources allocated at component - initialization. NOTE: After this call the component handle is - not valid for further use. - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the GetHandle function. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - */ - OMX_ERRORTYPE (*ComponentDeInit)( - OMX_IN OMX_HANDLETYPE hComponent); - - /** @ingroup buf */ - OMX_ERRORTYPE (*UseEGLImage)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_INOUT OMX_BUFFERHEADERTYPE** ppBufferHdr, - OMX_IN OMX_U32 nPortIndex, - OMX_IN OMX_PTR pAppPrivate, - OMX_IN void* eglImage); - - OMX_ERRORTYPE (*ComponentRoleEnum)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_OUT OMX_U8 *cRole, - OMX_IN OMX_U32 nIndex); - -} OMX_COMPONENTTYPE; - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_ComponentExt.h b/subprojects/gst-omx/omx/openmax/OMX_ComponentExt.h deleted file mode 100644 index e5aa74871c..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_ComponentExt.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (c) 2010 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_ComponentExt.h - OpenMax IL version 1.1.2 - * The OMX_ComponentExt header file contains extensions to the definitions used - * by both the application and the component to access common items. - */ - -#ifndef OMX_ComponentExt_h -#define OMX_ComponentExt_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - -/* Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ -#include - - -/** Set/query the commit mode */ -typedef struct OMX_CONFIG_COMMITMODETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_BOOL bDeferred; -} OMX_CONFIG_COMMITMODETYPE; - -/** Explicit commit */ -typedef struct OMX_CONFIG_COMMITTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; -} OMX_CONFIG_COMMITTYPE; - - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* OMX_ComponentExt_h */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_ContentPipe.h b/subprojects/gst-omx/omx/openmax/OMX_ContentPipe.h deleted file mode 100644 index 5f6310c28a..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_ContentPipe.h +++ /dev/null @@ -1,195 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_ContentPipe.h - OpenMax IL version 1.1.2 - * The OMX_ContentPipe header file contains the definitions used to define - * the public interface for content piples. This header file is intended to - * be used by the component. - */ - -#ifndef OMX_CONTENTPIPE_H -#define OMX_CONTENTPIPE_H - -#ifndef KD_EACCES -/* OpenKODE error codes. CPResult values may be zero (indicating success - or one of the following values) */ -#define KD_EACCES (1) -#define KD_EADDRINUSE (2) -#define KD_EAGAIN (5) -#define KD_EBADF (7) -#define KD_EBUSY (8) -#define KD_ECONNREFUSED (9) -#define KD_ECONNRESET (10) -#define KD_EDEADLK (11) -#define KD_EDESTADDRREQ (12) -#define KD_ERANGE (35) -#define KD_EEXIST (13) -#define KD_EFBIG (14) -#define KD_EHOSTUNREACH (15) -#define KD_EINVAL (17) -#define KD_EIO (18) -#define KD_EISCONN (20) -#define KD_EISDIR (21) -#define KD_EMFILE (22) -#define KD_ENAMETOOLONG (23) -#define KD_ENOENT (24) -#define KD_ENOMEM (25) -#define KD_ENOSPC (26) -#define KD_ENOSYS (27) -#define KD_ENOTCONN (28) -#define KD_EPERM (33) -#define KD_ETIMEDOUT (36) -#define KD_EILSEQ (19) -#endif - -/** Map types from OMX standard types only here so interface is as generic as possible. */ -typedef OMX_U32 CPresult; -typedef char * CPstring; -typedef void * CPhandle; -typedef OMX_U32 CPuint; -typedef OMX_S32 CPint; -typedef char CPbyte; -typedef OMX_BOOL CPbool; - -/** enumeration of origin types used in the CP_PIPETYPE's Seek function - * @ingroup cp - */ -typedef enum CP_ORIGINTYPE { - CP_OriginBegin, - CP_OriginCur, - CP_OriginEnd, - CP_OriginKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - CP_OriginVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - CP_OriginMax = 0X7FFFFFFF -} CP_ORIGINTYPE; - -/** enumeration of contact access types used in the CP_PIPETYPE's Open function - * @ingroup cp - */ -typedef enum CP_ACCESSTYPE { - CP_AccessRead, - CP_AccessWrite, - CP_AccessReadWrite , - CP_AccessKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - CP_AccessVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - CP_AccessMax = 0X7FFFFFFF -} CP_ACCESSTYPE; - -/** enumeration of results returned by the CP_PIPETYPE's CheckAvailableBytes function - * @ingroup cp - */ -typedef enum CP_CHECKBYTESRESULTTYPE -{ - CP_CheckBytesOk, /**< There are at least the request number - of bytes available */ - CP_CheckBytesNotReady, /**< The pipe is still retrieving bytes - and presently lacks sufficient bytes. - Client will be called when they are - sufficient bytes are available. */ - CP_CheckBytesInsufficientBytes , /**< The pipe has retrieved all bytes - but those available are less than those - requested */ - CP_CheckBytesAtEndOfStream, /**< The pipe has reached the end of stream - and no more bytes are available. */ - CP_CheckBytesOutOfBuffers, /**< All read/write buffers are currently in use. */ - CP_CheckBytesKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - CP_CheckBytesVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - CP_CheckBytesMax = 0X7FFFFFFF -} CP_CHECKBYTESRESULTTYPE; - -/** enumeration of content pipe events sent to the client callback. - * @ingroup cp - */ -typedef enum CP_EVENTTYPE{ - CP_BytesAvailable, /** bytes requested in a CheckAvailableBytes call are now available*/ - CP_Overflow, /** enumeration of content pipe events sent to the client callback*/ - CP_PipeDisconnected , /** enumeration of content pipe events sent to the client callback*/ - CP_EventKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - CP_EventVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - CP_EventMax = 0X7FFFFFFF -} CP_EVENTTYPE; - -/** content pipe definition - * @ingroup cp - */ -typedef struct CP_PIPETYPE -{ - /** Open a content stream for reading or writing. */ - CPresult (*Open)( CPhandle* hContent, CPstring szURI, CP_ACCESSTYPE eAccess ); - - /** Close a content stream. */ - CPresult (*Close)( CPhandle hContent ); - - /** Create a content source and open it for writing. */ - CPresult (*Create)( CPhandle *hContent, CPstring szURI ); - - /** Check the that specified number of bytes are available for reading or writing (depending on access type).*/ - CPresult (*CheckAvailableBytes)( CPhandle hContent, CPuint nBytesRequested, CP_CHECKBYTESRESULTTYPE *eResult ); - - /** Seek to certain position in the content relative to the specified origin. */ - CPresult (*SetPosition)( CPhandle hContent, CPint nOffset, CP_ORIGINTYPE eOrigin); - - /** Retrieve the current position relative to the start of the content. */ - CPresult (*GetPosition)( CPhandle hContent, CPuint *pPosition); - - /** Retrieve data of the specified size from the content stream (advance content pointer by size of data). - Note: pipe client provides pointer. This function is appropriate for small high frequency reads. */ - CPresult (*Read)( CPhandle hContent, CPbyte *pData, CPuint nSize); - - /** Retrieve a buffer allocated by the pipe that contains the requested number of bytes. - Buffer contains the next block of bytes, as specified by nSize, of the content. nSize also - returns the size of the block actually read. Content pointer advances the by the returned size. - Note: pipe provides pointer. This function is appropriate for large reads. The client must call - ReleaseReadBuffer when done with buffer. - - In some cases the requested block may not reside in contiguous memory within the - pipe implementation. For instance if the pipe leverages a circular buffer then the requested - block may straddle the boundary of the circular buffer. By default a pipe implementation - performs a copy in this case to provide the block to the pipe client in one contiguous buffer. - If, however, the client sets bForbidCopy, then the pipe returns only those bytes preceding the memory - boundary. Here the client may retrieve the data in segments over successive calls. */ - CPresult (*ReadBuffer)( CPhandle hContent, CPbyte **ppBuffer, CPuint *nSize, CPbool bForbidCopy); - - /** Release a buffer obtained by ReadBuffer back to the pipe. */ - CPresult (*ReleaseReadBuffer)(CPhandle hContent, CPbyte *pBuffer); - - /** Write data of the specified size to the content (advance content pointer by size of data). - Note: pipe client provides pointer. This function is appropriate for small high frequency writes. */ - CPresult (*Write)( CPhandle hContent, CPbyte *data, CPuint nSize); - - /** Retrieve a buffer allocated by the pipe used to write data to the content. - Client will fill buffer with output data. Note: pipe provides pointer. This function is appropriate - for large writes. The client must call WriteBuffer when done it has filled the buffer with data.*/ - CPresult (*GetWriteBuffer)( CPhandle hContent, CPbyte **ppBuffer, CPuint nSize); - - /** Deliver a buffer obtained via GetWriteBuffer to the pipe. Pipe will write the - the contents of the buffer to content and advance content pointer by the size of the buffer */ - CPresult (*WriteBuffer)( CPhandle hContent, CPbyte *pBuffer, CPuint nFilledSize); - - /** Register a per-handle client callback with the content pipe. */ - CPresult (*RegisterCallback)( CPhandle hContent, CPresult (*ClientCallback)(CP_EVENTTYPE eEvent, CPuint iParam)); - -} CP_PIPETYPE; - -#endif - diff --git a/subprojects/gst-omx/omx/openmax/OMX_Core.h b/subprojects/gst-omx/omx/openmax/OMX_Core.h deleted file mode 100644 index a076f2f479..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Core.h +++ /dev/null @@ -1,1431 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_Core.h - OpenMax IL version 1.1.2 - * The OMX_Core header file contains the definitions used by both the - * application and the component to access common items. - */ - -#ifndef OMX_Core_h -#define OMX_Core_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - -/* Each OMX header shall include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ - -#include - - -/** The OMX_COMMANDTYPE enumeration is used to specify the action in the - * OMX_SendCommand macro. - * @ingroup core - */ -typedef enum OMX_COMMANDTYPE -{ - OMX_CommandStateSet, /**< Change the component state */ - OMX_CommandFlush, /**< Flush the data queue(s) of a component */ - OMX_CommandPortDisable, /**< Disable a port on a component. */ - OMX_CommandPortEnable, /**< Enable a port on a component. */ - OMX_CommandMarkBuffer, /**< Mark a component/buffer for observation */ - OMX_CommandKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_CommandVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_CommandMax = 0X7FFFFFFF -} OMX_COMMANDTYPE; - - - -/** The OMX_STATETYPE enumeration is used to indicate or change the component - * state. This enumeration reflects the current state of the component when - * used with the OMX_GetState macro or becomes the parameter in a state change - * command when used with the OMX_SendCommand macro. - * - * The component will be in the Loaded state after the component is initially - * loaded into memory. In the Loaded state, the component is not allowed to - * allocate or hold resources other than to build it's internal parameter - * and configuration tables. The application will send one or more - * SetParameters/GetParameters and SetConfig/GetConfig commands to the - * component and the component will record each of these parameter and - * configuration changes for use later. When the application sends the - * Idle command, the component will acquire the resources needed for the - * specified configuration and will transition to the idle state if the - * allocation is successful. If the component cannot successfully - * transition to the idle state for any reason, the state of the component - * shall be fully rolled back to the Loaded state (e.g. all allocated - * resources shall be released). When the component receives the command - * to go to the Executing state, it shall begin processing buffers by - * sending all input buffers it holds to the application. While - * the component is in the Idle state, the application may also send the - * Pause command. If the component receives the pause command while in the - * Idle state, the component shall send all input buffers it holds to the - * application, but shall not begin processing buffers. This will allow the - * application to prefill buffers. - * - * @ingroup comp - */ - -typedef enum OMX_STATETYPE -{ - OMX_StateInvalid, /**< component has detected that it's internal data - structures are corrupted to the point that - it cannot determine it's state properly */ - OMX_StateLoaded, /**< component has been loaded but has not completed - initialization. The OMX_SetParameter macro - and the OMX_GetParameter macro are the only - valid macros allowed to be sent to the - component in this state. */ - OMX_StateIdle, /**< component initialization has been completed - successfully and the component is ready to - to start. */ - OMX_StateExecuting, /**< component has accepted the start command and - is processing data (if data is available) */ - OMX_StatePause, /**< component has received pause command */ - OMX_StateWaitForResources, /**< component is waiting for resources, either after - preemption or before it gets the resources requested. - See specification for complete details. */ - OMX_StateKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_StateVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_StateMax = 0X7FFFFFFF -} OMX_STATETYPE; - -/** The OMX_ERRORTYPE enumeration defines the standard OMX Errors. These - * errors should cover most of the common failure cases. However, - * vendors are free to add additional error messages of their own as - * long as they follow these rules: - * 1. Vendor error messages shall be in the range of 0x90000000 to - * 0x9000FFFF. - * 2. Vendor error messages shall be defined in a header file provided - * with the component. No error messages are allowed that are - * not defined. - */ -typedef enum OMX_ERRORTYPE -{ - OMX_ErrorNone = 0, - - /** There were insufficient resources to perform the requested operation */ - OMX_ErrorInsufficientResources = (OMX_S32) 0x80001000, - - /** There was an error, but the cause of the error could not be determined */ - OMX_ErrorUndefined = (OMX_S32) 0x80001001, - - /** The component name string was not valid */ - OMX_ErrorInvalidComponentName = (OMX_S32) 0x80001002, - - /** No component with the specified name string was found */ - OMX_ErrorComponentNotFound = (OMX_S32) 0x80001003, - - /** The component specified did not have a "OMX_ComponentInit" or - "OMX_ComponentDeInit entry point */ - OMX_ErrorInvalidComponent = (OMX_S32) 0x80001004, - - /** One or more parameters were not valid */ - OMX_ErrorBadParameter = (OMX_S32) 0x80001005, - - /** The requested function is not implemented */ - OMX_ErrorNotImplemented = (OMX_S32) 0x80001006, - - /** The buffer was emptied before the next buffer was ready */ - OMX_ErrorUnderflow = (OMX_S32) 0x80001007, - - /** The buffer was not available when it was needed */ - OMX_ErrorOverflow = (OMX_S32) 0x80001008, - - /** The hardware failed to respond as expected */ - OMX_ErrorHardware = (OMX_S32) 0x80001009, - - /** The component is in the state OMX_StateInvalid */ - OMX_ErrorInvalidState = (OMX_S32) 0x8000100A, - - /** Stream is found to be corrupt */ - OMX_ErrorStreamCorrupt = (OMX_S32) 0x8000100B, - - /** Ports being connected are not compatible */ - OMX_ErrorPortsNotCompatible = (OMX_S32) 0x8000100C, - - /** Resources allocated to an idle component have been - lost resulting in the component returning to the loaded state */ - OMX_ErrorResourcesLost = (OMX_S32) 0x8000100D, - - /** No more indicies can be enumerated */ - OMX_ErrorNoMore = (OMX_S32) 0x8000100E, - - /** The component detected a version mismatch */ - OMX_ErrorVersionMismatch = (OMX_S32) 0x8000100F, - - /** The component is not ready to return data at this time */ - OMX_ErrorNotReady = (OMX_S32) 0x80001010, - - /** There was a timeout that occurred */ - OMX_ErrorTimeout = (OMX_S32) 0x80001011, - - /** This error occurs when trying to transition into the state you are already in */ - OMX_ErrorSameState = (OMX_S32) 0x80001012, - - /** Resources allocated to an executing or paused component have been - preempted, causing the component to return to the idle state */ - OMX_ErrorResourcesPreempted = (OMX_S32) 0x80001013, - - /** A non-supplier port sends this error to the IL client (via the EventHandler callback) - during the allocation of buffers (on a transition from the LOADED to the IDLE state or - on a port restart) when it deems that it has waited an unusually long time for the supplier - to send it an allocated buffer via a UseBuffer call. */ - OMX_ErrorPortUnresponsiveDuringAllocation = (OMX_S32) 0x80001014, - - /** A non-supplier port sends this error to the IL client (via the EventHandler callback) - during the deallocation of buffers (on a transition from the IDLE to LOADED state or - on a port stop) when it deems that it has waited an unusually long time for the supplier - to request the deallocation of a buffer header via a FreeBuffer call. */ - OMX_ErrorPortUnresponsiveDuringDeallocation = (OMX_S32) 0x80001015, - - /** A supplier port sends this error to the IL client (via the EventHandler callback) - during the stopping of a port (either on a transition from the IDLE to LOADED - state or a port stop) when it deems that it has waited an unusually long time for - the non-supplier to return a buffer via an EmptyThisBuffer or FillThisBuffer call. */ - OMX_ErrorPortUnresponsiveDuringStop = (OMX_S32) 0x80001016, - - /** Attempting a state transtion that is not allowed */ - OMX_ErrorIncorrectStateTransition = (OMX_S32) 0x80001017, - - /* Attempting a command that is not allowed during the present state. */ - OMX_ErrorIncorrectStateOperation = (OMX_S32) 0x80001018, - - /** The values encapsulated in the parameter or config structure are not supported. */ - OMX_ErrorUnsupportedSetting = (OMX_S32) 0x80001019, - - /** The parameter or config indicated by the given index is not supported. */ - OMX_ErrorUnsupportedIndex = (OMX_S32) 0x8000101A, - - /** The port index supplied is incorrect. */ - OMX_ErrorBadPortIndex = (OMX_S32) 0x8000101B, - - /** The port has lost one or more of its buffers and it thus unpopulated. */ - OMX_ErrorPortUnpopulated = (OMX_S32) 0x8000101C, - - /** Component suspended due to temporary loss of resources */ - OMX_ErrorComponentSuspended = (OMX_S32) 0x8000101D, - - /** Component suspended due to an inability to acquire dynamic resources */ - OMX_ErrorDynamicResourcesUnavailable = (OMX_S32) 0x8000101E, - - /** When the macroblock error reporting is enabled the component returns new error - for every frame that has errors */ - OMX_ErrorMbErrorsInFrame = (OMX_S32) 0x8000101F, - - /** A component reports this error when it cannot parse or determine the format of an input stream. */ - OMX_ErrorFormatNotDetected = (OMX_S32) 0x80001020, - - /** The content open operation failed. */ - OMX_ErrorContentPipeOpenFailed = (OMX_S32) 0x80001021, - - /** The content creation operation failed. */ - OMX_ErrorContentPipeCreationFailed = (OMX_S32) 0x80001022, - - /** Separate table information is being used */ - OMX_ErrorSeperateTablesUsed = (OMX_S32) 0x80001023, - - /** Tunneling is unsupported by the component*/ - OMX_ErrorTunnelingUnsupported = (OMX_S32) 0x80001024, - - OMX_ErrorKhronosExtensions = (OMX_S32)0x8F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_ErrorVendorStartUnused = (OMX_S32)0x90000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_ErrorMax = 0x7FFFFFFF -} OMX_ERRORTYPE; - -/** @ingroup core */ -typedef OMX_ERRORTYPE (* OMX_COMPONENTINITTYPE)(OMX_IN OMX_HANDLETYPE hComponent); - -/** @ingroup core */ -typedef struct OMX_COMPONENTREGISTERTYPE -{ - const char * pName; /* Component name, 128 byte limit (including '\0') applies */ - OMX_COMPONENTINITTYPE pInitialize; /* Component instance initialization function */ -} OMX_COMPONENTREGISTERTYPE; - -/** @ingroup core */ -extern OMX_COMPONENTREGISTERTYPE OMX_ComponentRegistered[]; - -/** @ingroup rpm */ -typedef struct OMX_PRIORITYMGMTTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nGroupPriority; /**< Priority of the component group */ - OMX_U32 nGroupID; /**< ID of the component group */ -} OMX_PRIORITYMGMTTYPE; - -/* Component name and Role names are limited to 128 characters including the terminating '\0'. */ -#define OMX_MAX_STRINGNAME_SIZE 128 - -/** @ingroup comp */ -typedef struct OMX_PARAM_COMPONENTROLETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U8 cRole[OMX_MAX_STRINGNAME_SIZE]; /**< name of standard component which defines component role */ -} OMX_PARAM_COMPONENTROLETYPE; - -/** End of Stream Buffer Flag: - * - * A component sets EOS when it has no more data to emit on a particular - * output port. Thus an output port shall set EOS on the last buffer it - * emits. A component's determination of when an output port should - * cease sending data is implemenation specific. - * @ingroup buf - */ - -#define OMX_BUFFERFLAG_EOS 0x00000001 - -/** Start Time Buffer Flag: - * - * The source of a stream (e.g. a demux component) sets the STARTTIME - * flag on the buffer that contains the starting timestamp for the - * stream. The starting timestamp corresponds to the first data that - * should be displayed at startup or after a seek. - * The first timestamp of the stream is not necessarily the start time. - * For instance, in the case of a seek to a particular video frame, - * the target frame may be an interframe. Thus the first buffer of - * the stream will be the intra-frame preceding the target frame and - * the starttime will occur with the target frame (with any other - * required frames required to reconstruct the target intervening). - * - * The STARTTIME flag is directly associated with the buffer's - * timestamp ' thus its association to buffer data and its - * propagation is identical to the timestamp's. - * - * When a Sync Component client receives a buffer with the - * STARTTIME flag it shall perform a SetConfig on its sync port - * using OMX_ConfigTimeClientStartTime and passing the buffer's - * timestamp. - * - * @ingroup buf - */ - -#define OMX_BUFFERFLAG_STARTTIME 0x00000002 - - - -/** Decode Only Buffer Flag: - * - * The source of a stream (e.g. a demux component) sets the DECODEONLY - * flag on any buffer that should shall be decoded but should not be - * displayed. This flag is used, for instance, when a source seeks to - * a target interframe that requires the decode of frames preceding the - * target to facilitate the target's reconstruction. In this case the - * source would emit the frames preceding the target downstream - * but mark them as decode only. - * - * The DECODEONLY is associated with buffer data and propagated in a - * manner identical to the buffer timestamp. - * - * A component that renders data should ignore all buffers with - * the DECODEONLY flag set. - * - * @ingroup buf - */ - -#define OMX_BUFFERFLAG_DECODEONLY 0x00000004 - - -/* Data Corrupt Flag: This flag is set when the IL client believes the data in the associated buffer is corrupt - * @ingroup buf - */ - -#define OMX_BUFFERFLAG_DATACORRUPT 0x00000008 - -/* End of Frame: The buffer contains exactly one end of frame and no data - * occurs after the end of frame. This flag is an optional hint. The absence - * of this flag does not imply the absence of an end of frame within the buffer. - * @ingroup buf -*/ -#define OMX_BUFFERFLAG_ENDOFFRAME 0x00000010 - -/* Sync Frame Flag: This flag is set when the buffer content contains a coded sync frame ' - * a frame that has no dependency on any other frame information - * @ingroup buf - */ -#define OMX_BUFFERFLAG_SYNCFRAME 0x00000020 - -/* Extra data present flag: there is extra data appended to the data stream - * residing in the buffer - * @ingroup buf - */ -#define OMX_BUFFERFLAG_EXTRADATA 0x00000040 - -/** Codec Config Buffer Flag: -* OMX_BUFFERFLAG_CODECCONFIG is an optional flag that is set by an -* output port when all bytes in the buffer form part or all of a set of -* codec specific configuration data. Examples include SPS/PPS nal units -* for OMX_VIDEO_CodingAVC or AudioSpecificConfig data for -* OMX_AUDIO_CodingAAC. Any component that for a given stream sets -* OMX_BUFFERFLAG_CODECCONFIG shall not mix codec configuration bytes -* with frame data in the same buffer, and shall send all buffers -* containing codec configuration bytes before any buffers containing -* frame data that those configurations bytes describe. -* If the stream format for a particular codec has a frame specific -* header at the start of each frame, for example OMX_AUDIO_CodingMP3 or -* OMX_AUDIO_CodingAAC in ADTS mode, then these shall be presented as -* normal without setting OMX_BUFFERFLAG_CODECCONFIG. - * @ingroup buf - */ -#define OMX_BUFFERFLAG_CODECCONFIG 0x00000080 - - - -/** @ingroup buf */ -typedef struct OMX_BUFFERHEADERTYPE -{ - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U8* pBuffer; /**< Pointer to actual block of memory - that is acting as the buffer */ - OMX_U32 nAllocLen; /**< size of the buffer allocated, in bytes */ - OMX_U32 nFilledLen; /**< number of bytes currently in the - buffer */ - OMX_U32 nOffset; /**< start offset of valid data in bytes from - the start of the buffer */ - OMX_PTR pAppPrivate; /**< pointer to any data the application - wants to associate with this buffer */ - OMX_PTR pPlatformPrivate; /**< pointer to any data the platform - wants to associate with this buffer */ - OMX_PTR pInputPortPrivate; /**< pointer to any data the input port - wants to associate with this buffer */ - OMX_PTR pOutputPortPrivate; /**< pointer to any data the output port - wants to associate with this buffer */ - OMX_HANDLETYPE hMarkTargetComponent; /**< The component that will generate a - mark event upon processing this buffer. */ - OMX_PTR pMarkData; /**< Application specific data associated with - the mark sent on a mark event to disambiguate - this mark from others. */ - OMX_U32 nTickCount; /**< Optional entry that the component and - application can update with a tick count - when they access the component. This - value should be in microseconds. Since - this is a value relative to an arbitrary - starting point, this value cannot be used - to determine absolute time. This is an - optional entry and not all components - will update it.*/ - OMX_TICKS nTimeStamp; /**< Timestamp corresponding to the sample - starting at the first logical sample - boundary in the buffer. Timestamps of - successive samples within the buffer may - be inferred by adding the duration of the - of the preceding buffer to the timestamp - of the preceding buffer.*/ - OMX_U32 nFlags; /**< buffer specific flags */ - OMX_U32 nOutputPortIndex; /**< The index of the output port (if any) using - this buffer */ - OMX_U32 nInputPortIndex; /**< The index of the input port (if any) using - this buffer */ -} OMX_BUFFERHEADERTYPE; - -/** The OMX_EXTRADATATYPE enumeration is used to define the - * possible extra data payload types. - * NB: this enum is binary backwards compatible with the previous - * OMX_EXTRADATA_QUANT define. This should be replaced with - * OMX_ExtraDataQuantization. - */ -typedef enum OMX_EXTRADATATYPE -{ - OMX_ExtraDataNone = 0, /**< Indicates that no more extra data sections follow */ - OMX_ExtraDataQuantization, /**< The data payload contains quantization data */ - OMX_ExtraDataKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_ExtraDataVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_ExtraDataMax = 0x7FFFFFFF -} OMX_EXTRADATATYPE; - - -typedef struct OMX_OTHER_EXTRADATATYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_EXTRADATATYPE eType; /* Extra Data type */ - OMX_U32 nDataSize; /* Size of the supporting data to follow */ - OMX_U8 data[1]; /* Supporting data hint */ -} OMX_OTHER_EXTRADATATYPE; - -/** @ingroup comp */ -typedef struct OMX_PORT_PARAM_TYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPorts; /**< The number of ports for this component */ - OMX_U32 nStartPortNumber; /** first port number for this type of port */ -} OMX_PORT_PARAM_TYPE; - -/** @ingroup comp */ -typedef enum OMX_EVENTTYPE -{ - OMX_EventCmdComplete, /**< component has sucessfully completed a command */ - OMX_EventError, /**< component has detected an error condition */ - OMX_EventMark, /**< component has detected a buffer mark */ - OMX_EventPortSettingsChanged, /**< component is reported a port settings change */ - OMX_EventBufferFlag, /**< component has detected an EOS */ - OMX_EventResourcesAcquired, /**< component has been granted resources and is - automatically starting the state change from - OMX_StateWaitForResources to OMX_StateIdle. */ - OMX_EventComponentResumed, /**< Component resumed due to reacquisition of resources */ - OMX_EventDynamicResourcesAvailable, /**< Component has acquired previously unavailable dynamic resources */ - OMX_EventPortFormatDetected, /**< Component has detected a supported format. */ - OMX_EventKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_EventVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_EventMax = 0x7FFFFFFF -} OMX_EVENTTYPE; - -typedef struct OMX_CALLBACKTYPE -{ - /** The EventHandler method is used to notify the application when an - event of interest occurs. Events are defined in the OMX_EVENTTYPE - enumeration. Please see that enumeration for details of what will - be returned for each type of event. Callbacks should not return - an error to the component, so if an error occurs, the application - shall handle it internally. This is a blocking call. - - The application should return from this call within 5 msec to avoid - blocking the component for an excessively long period of time. - - @param hComponent - handle of the component to access. This is the component - handle returned by the call to the GetHandle function. - @param pAppData - pointer to an application defined value that was provided in the - pAppData parameter to the OMX_GetHandle method for the component. - This application defined value is provided so that the application - can have a component specific context when receiving the callback. - @param eEvent - Event that the component wants to notify the application about. - @param nData1 - nData will be the OMX_ERRORTYPE for an error event and will be - an OMX_COMMANDTYPE for a command complete event and OMX_INDEXTYPE for a OMX_PortSettingsChanged event. - @param nData2 - nData2 will hold further information related to the event. Can be OMX_STATETYPE for - a OMX_CommandStateSet command or port index for a OMX_PortSettingsChanged event. - Default value is 0 if not used. ) - @param pEventData - Pointer to additional event-specific data (see spec for meaning). - */ - - OMX_ERRORTYPE (*EventHandler)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_PTR pAppData, - OMX_IN OMX_EVENTTYPE eEvent, - OMX_IN OMX_U32 nData1, - OMX_IN OMX_U32 nData2, - OMX_IN OMX_PTR pEventData); - - /** The EmptyBufferDone method is used to return emptied buffers from an - input port back to the application for reuse. This is a blocking call - so the application should not attempt to refill the buffers during this - call, but should queue them and refill them in another thread. There - is no error return, so the application shall handle any errors generated - internally. - - The application should return from this call within 5 msec. - - @param hComponent - handle of the component to access. This is the component - handle returned by the call to the GetHandle function. - @param pAppData - pointer to an application defined value that was provided in the - pAppData parameter to the OMX_GetHandle method for the component. - This application defined value is provided so that the application - can have a component specific context when receiving the callback. - @param pBuffer - pointer to an OMX_BUFFERHEADERTYPE structure allocated with UseBuffer - or AllocateBuffer indicating the buffer that was emptied. - @ingroup buf - */ - OMX_ERRORTYPE (*EmptyBufferDone)( - OMX_IN OMX_HANDLETYPE hComponent, - OMX_IN OMX_PTR pAppData, - OMX_IN OMX_BUFFERHEADERTYPE* pBuffer); - - /** The FillBufferDone method is used to return filled buffers from an - output port back to the application for emptying and then reuse. - This is a blocking call so the application should not attempt to - empty the buffers during this call, but should queue the buffers - and empty them in another thread. There is no error return, so - the application shall handle any errors generated internally. The - application shall also update the buffer header to indicate the - number of bytes placed into the buffer. - - The application should return from this call within 5 msec. - - @param hComponent - handle of the component to access. This is the component - handle returned by the call to the GetHandle function. - @param pAppData - pointer to an application defined value that was provided in the - pAppData parameter to the OMX_GetHandle method for the component. - This application defined value is provided so that the application - can have a component specific context when receiving the callback. - @param pBuffer - pointer to an OMX_BUFFERHEADERTYPE structure allocated with UseBuffer - or AllocateBuffer indicating the buffer that was filled. - @ingroup buf - */ - OMX_ERRORTYPE (*FillBufferDone)( - OMX_OUT OMX_HANDLETYPE hComponent, - OMX_OUT OMX_PTR pAppData, - OMX_OUT OMX_BUFFERHEADERTYPE* pBuffer); - -} OMX_CALLBACKTYPE; - -/** The OMX_BUFFERSUPPLIERTYPE enumeration is used to dictate port supplier - preference when tunneling between two ports. - @ingroup tun buf -*/ -typedef enum OMX_BUFFERSUPPLIERTYPE -{ - OMX_BufferSupplyUnspecified = 0x0, /**< port supplying the buffers is unspecified, - or don't care */ - OMX_BufferSupplyInput, /**< input port supplies the buffers */ - OMX_BufferSupplyOutput, /**< output port supplies the buffers */ - OMX_BufferSupplyKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_BufferSupplyVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_BufferSupplyMax = 0x7FFFFFFF -} OMX_BUFFERSUPPLIERTYPE; - - -/** buffer supplier parameter - * @ingroup tun - */ -typedef struct OMX_PARAM_BUFFERSUPPLIERTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_BUFFERSUPPLIERTYPE eBufferSupplier; /**< buffer supplier */ -} OMX_PARAM_BUFFERSUPPLIERTYPE; - - -/**< indicates that buffers received by an input port of a tunnel - may not modify the data in the buffers - @ingroup tun - */ -#define OMX_PORTTUNNELFLAG_READONLY 0x00000001 - - -/** The OMX_TUNNELSETUPTYPE structure is used to pass data from an output - port to an input port as part the two ComponentTunnelRequest calls - resulting from a OMX_SetupTunnel call from the IL Client. - @ingroup tun - */ -typedef struct OMX_TUNNELSETUPTYPE -{ - OMX_U32 nTunnelFlags; /**< bit flags for tunneling */ - OMX_BUFFERSUPPLIERTYPE eSupplier; /**< supplier preference */ -} OMX_TUNNELSETUPTYPE; - -/* OMX Component headers is included to enable the core to use - macros for functions into the component for OMX release 1.0. - Developers should not access any structures or data from within - the component header directly */ -/* TO BE REMOVED - #include */ - -/** GetComponentVersion will return information about the component. - This is a blocking call. This macro will go directly from the - application to the component (via a core macro). The - component will return from this call within 5 msec. - @param [in] hComponent - handle of component to execute the command - @param [out] pComponentName - pointer to an empty string of length 128 bytes. The component - will write its name into this string. The name will be - terminated by a single zero byte. The name of a component will - be 127 bytes or less to leave room for the trailing zero byte. - An example of a valid component name is "OMX.ABC.ChannelMixer\0". - @param [out] pComponentVersion - pointer to an OMX Version structure that the component will fill - in. The component will fill in a value that indicates the - component version. NOTE: the component version is NOT the same - as the OMX Specification version (found in all structures). The - component version is defined by the vendor of the component and - its value is entirely up to the component vendor. - @param [out] pSpecVersion - pointer to an OMX Version structure that the component will fill - in. The SpecVersion is the version of the specification that the - component was built against. Please note that this value may or - may not match the structure's version. For example, if the - component was built against the 2.0 specification, but the - application (which creates the structure is built against the - 1.0 specification the versions would be different. - @param [out] pComponentUUID - pointer to the UUID of the component which will be filled in by - the component. The UUID is a unique identifier that is set at - RUN time for the component and is unique to each instantion of - the component. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_GetComponentVersion( \ - hComponent, \ - pComponentName, \ - pComponentVersion, \ - pSpecVersion, \ - pComponentUUID) \ - ((OMX_COMPONENTTYPE*)hComponent)->GetComponentVersion( \ - hComponent, \ - pComponentName, \ - pComponentVersion, \ - pSpecVersion, \ - pComponentUUID) /* Macro End */ - - -/** Send a command to the component. This call is a non-blocking call. - The component should check the parameters and then queue the command - to the component thread to be executed. The component thread shall - send the EventHandler() callback at the conclusion of the command. - This macro will go directly from the application to the component (via - a core macro). The component will return from this call within 5 msec. - - When the command is "OMX_CommandStateSet" the component will queue a - state transition to the new state idenfied in nParam. - - When the command is "OMX_CommandFlush", to flush a port's buffer queues, - the command will force the component to return all buffers NOT CURRENTLY - BEING PROCESSED to the application, in the order in which the buffers - were received. - - When the command is "OMX_CommandPortDisable" or - "OMX_CommandPortEnable", the component's port (given by the value of - nParam) will be stopped or restarted. - - When the command "OMX_CommandMarkBuffer" is used to mark a buffer, the - pCmdData will point to a OMX_MARKTYPE structure containing the component - handle of the component to examine the buffer chain for the mark. nParam1 - contains the index of the port on which the buffer mark is applied. - - Specification text for more details. - - @param [in] hComponent - handle of component to execute the command - @param [in] Cmd - Command for the component to execute - @param [in] nParam - Parameter for the command to be executed. When Cmd has the value - OMX_CommandStateSet, value is a member of OMX_STATETYPE. When Cmd has - the value OMX_CommandFlush, value of nParam indicates which port(s) - to flush. -1 is used to flush all ports a single port index will - only flush that port. When Cmd has the value "OMX_CommandPortDisable" - or "OMX_CommandPortEnable", the component's port is given by - the value of nParam. When Cmd has the value "OMX_CommandMarkBuffer" - the components pot is given by the value of nParam. - @param [in] pCmdData - Parameter pointing to the OMX_MARKTYPE structure when Cmd has the value - "OMX_CommandMarkBuffer". - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_SendCommand( \ - hComponent, \ - Cmd, \ - nParam, \ - pCmdData) \ - ((OMX_COMPONENTTYPE*)hComponent)->SendCommand( \ - hComponent, \ - Cmd, \ - nParam, \ - pCmdData) /* Macro End */ - - -/** The OMX_GetParameter macro will get one of the current parameter - settings from the component. This macro cannot only be invoked when - the component is in the OMX_StateInvalid state. The nParamIndex - parameter is used to indicate which structure is being requested from - the component. The application shall allocate the correct structure - and shall fill in the structure size and version information before - invoking this macro. When the parameter applies to a port, the - caller shall fill in the appropriate nPortIndex value indicating the - port on which the parameter applies. If the component has not had - any settings changed, then the component should return a set of - valid DEFAULT parameters for the component. This is a blocking - call. - - The component should return from this call within 20 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] nParamIndex - Index of the structure to be filled. This value is from the - OMX_INDEXTYPE enumeration. - @param [in,out] pComponentParameterStructure - Pointer to application allocated structure to be filled by the - component. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_GetParameter( \ - hComponent, \ - nParamIndex, \ - pComponentParameterStructure) \ - ((OMX_COMPONENTTYPE*)hComponent)->GetParameter( \ - hComponent, \ - nParamIndex, \ - pComponentParameterStructure) /* Macro End */ - - -/** The OMX_SetParameter macro will send an initialization parameter - structure to a component. Each structure shall be sent one at a time, - in a separate invocation of the macro. This macro can only be - invoked when the component is in the OMX_StateLoaded state, or the - port is disabled (when the parameter applies to a port). The - nParamIndex parameter is used to indicate which structure is being - passed to the component. The application shall allocate the - correct structure and shall fill in the structure size and version - information (as well as the actual data) before invoking this macro. - The application is free to dispose of this structure after the call - as the component is required to copy any data it shall retain. This - is a blocking call. - - The component should return from this call within 20 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] nIndex - Index of the structure to be sent. This value is from the - OMX_INDEXTYPE enumeration. - @param [in] pComponentParameterStructure - pointer to application allocated structure to be used for - initialization by the component. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_SetParameter( \ - hComponent, \ - nParamIndex, \ - pComponentParameterStructure) \ - ((OMX_COMPONENTTYPE*)hComponent)->SetParameter( \ - hComponent, \ - nParamIndex, \ - pComponentParameterStructure) /* Macro End */ - - -/** The OMX_GetConfig macro will get one of the configuration structures - from a component. This macro can be invoked anytime after the - component has been loaded. The nParamIndex call parameter is used to - indicate which structure is being requested from the component. The - application shall allocate the correct structure and shall fill in the - structure size and version information before invoking this macro. - If the component has not had this configuration parameter sent before, - then the component should return a set of valid DEFAULT values for the - component. This is a blocking call. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] nIndex - Index of the structure to be filled. This value is from the - OMX_INDEXTYPE enumeration. - @param [in,out] pComponentConfigStructure - pointer to application allocated structure to be filled by the - component. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp -*/ -#define OMX_GetConfig( \ - hComponent, \ - nConfigIndex, \ - pComponentConfigStructure) \ - ((OMX_COMPONENTTYPE*)hComponent)->GetConfig( \ - hComponent, \ - nConfigIndex, \ - pComponentConfigStructure) /* Macro End */ - - -/** The OMX_SetConfig macro will send one of the configuration - structures to a component. Each structure shall be sent one at a time, - each in a separate invocation of the macro. This macro can be invoked - anytime after the component has been loaded. The application shall - allocate the correct structure and shall fill in the structure size - and version information (as well as the actual data) before invoking - this macro. The application is free to dispose of this structure after - the call as the component is required to copy any data it shall retain. - This is a blocking call. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] nConfigIndex - Index of the structure to be sent. This value is from the - OMX_INDEXTYPE enumeration above. - @param [in] pComponentConfigStructure - pointer to application allocated structure to be used for - initialization by the component. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_SetConfig( \ - hComponent, \ - nConfigIndex, \ - pComponentConfigStructure) \ - ((OMX_COMPONENTTYPE*)hComponent)->SetConfig( \ - hComponent, \ - nConfigIndex, \ - pComponentConfigStructure) /* Macro End */ - - -/** The OMX_GetExtensionIndex macro will invoke a component to translate - a vendor specific configuration or parameter string into an OMX - structure index. There is no requirement for the vendor to support - this command for the indexes already found in the OMX_INDEXTYPE - enumeration (this is done to save space in small components). The - component shall support all vendor supplied extension indexes not found - in the master OMX_INDEXTYPE enumeration. This is a blocking call. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the GetHandle function. - @param [in] cParameterName - OMX_STRING that shall be less than 128 characters long including - the trailing null byte. This is the string that will get - translated by the component into a configuration index. - @param [out] pIndexType - a pointer to a OMX_INDEXTYPE to receive the index value. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_GetExtensionIndex( \ - hComponent, \ - cParameterName, \ - pIndexType) \ - ((OMX_COMPONENTTYPE*)hComponent)->GetExtensionIndex( \ - hComponent, \ - cParameterName, \ - pIndexType) /* Macro End */ - - -/** The OMX_GetState macro will invoke the component to get the current - state of the component and place the state value into the location - pointed to by pState. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [out] pState - pointer to the location to receive the state. The value returned - is one of the OMX_STATETYPE members - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp - */ -#define OMX_GetState( \ - hComponent, \ - pState) \ - ((OMX_COMPONENTTYPE*)hComponent)->GetState( \ - hComponent, \ - pState) /* Macro End */ - - -/** The OMX_UseBuffer macro will request that the component use - a buffer (and allocate its own buffer header) already allocated - by another component, or by the IL Client. This is a blocking - call. - - The component should return from this call within 20 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [out] ppBuffer - pointer to an OMX_BUFFERHEADERTYPE structure used to receive the - pointer to the buffer header - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp buf - */ - -#define OMX_UseBuffer( \ - hComponent, \ - ppBufferHdr, \ - nPortIndex, \ - pAppPrivate, \ - nSizeBytes, \ - pBuffer) \ - ((OMX_COMPONENTTYPE*)hComponent)->UseBuffer( \ - hComponent, \ - ppBufferHdr, \ - nPortIndex, \ - pAppPrivate, \ - nSizeBytes, \ - pBuffer) - - -/** The OMX_AllocateBuffer macro will request that the component allocate - a new buffer and buffer header. The component will allocate the - buffer and the buffer header and return a pointer to the buffer - header. This is a blocking call. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [out] ppBuffer - pointer to an OMX_BUFFERHEADERTYPE structure used to receive - the pointer to the buffer header - @param [in] nPortIndex - nPortIndex is used to select the port on the component the buffer will - be used with. The port can be found by using the nPortIndex - value as an index into the Port Definition array of the component. - @param [in] pAppPrivate - pAppPrivate is used to initialize the pAppPrivate member of the - buffer header structure. - @param [in] nSizeBytes - size of the buffer to allocate. Used when bAllocateNew is true. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp buf - */ -#define OMX_AllocateBuffer( \ - hComponent, \ - ppBuffer, \ - nPortIndex, \ - pAppPrivate, \ - nSizeBytes) \ - ((OMX_COMPONENTTYPE*)hComponent)->AllocateBuffer( \ - hComponent, \ - ppBuffer, \ - nPortIndex, \ - pAppPrivate, \ - nSizeBytes) /* Macro End */ - - -/** The OMX_FreeBuffer macro will release a buffer header from the component - which was allocated using either OMX_AllocateBuffer or OMX_UseBuffer. If - the component allocated the buffer (see the OMX_UseBuffer macro) then - the component shall free the buffer and buffer header. This is a - blocking call. - - The component should return from this call within 20 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] nPortIndex - nPortIndex is used to select the port on the component the buffer will - be used with. - @param [in] pBuffer - pointer to an OMX_BUFFERHEADERTYPE structure allocated with UseBuffer - or AllocateBuffer. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp buf - */ -#define OMX_FreeBuffer( \ - hComponent, \ - nPortIndex, \ - pBuffer) \ - ((OMX_COMPONENTTYPE*)hComponent)->FreeBuffer( \ - hComponent, \ - nPortIndex, \ - pBuffer) /* Macro End */ - - -/** The OMX_EmptyThisBuffer macro will send a buffer full of data to an - input port of a component. The buffer will be emptied by the component - and returned to the application via the EmptyBufferDone call back. - This is a non-blocking call in that the component will record the buffer - and return immediately and then empty the buffer, later, at the proper - time. As expected, this macro may be invoked only while the component - is in the OMX_StateExecuting. If nPortIndex does not specify an input - port, the component shall return an error. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] pBuffer - pointer to an OMX_BUFFERHEADERTYPE structure allocated with UseBuffer - or AllocateBuffer. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp buf - */ -#define OMX_EmptyThisBuffer( \ - hComponent, \ - pBuffer) \ - ((OMX_COMPONENTTYPE*)hComponent)->EmptyThisBuffer( \ - hComponent, \ - pBuffer) /* Macro End */ - - -/** The OMX_FillThisBuffer macro will send an empty buffer to an - output port of a component. The buffer will be filled by the component - and returned to the application via the FillBufferDone call back. - This is a non-blocking call in that the component will record the buffer - and return immediately and then fill the buffer, later, at the proper - time. As expected, this macro may be invoked only while the component - is in the OMX_ExecutingState. If nPortIndex does not specify an output - port, the component shall return an error. - - The component should return from this call within 5 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [in] pBuffer - pointer to an OMX_BUFFERHEADERTYPE structure allocated with UseBuffer - or AllocateBuffer. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp buf - */ -#define OMX_FillThisBuffer( \ - hComponent, \ - pBuffer) \ - ((OMX_COMPONENTTYPE*)hComponent)->FillThisBuffer( \ - hComponent, \ - pBuffer) /* Macro End */ - - - -/** The OMX_UseEGLImage macro will request that the component use - a EGLImage provided by EGL (and allocate its own buffer header) - This is a blocking call. - - The component should return from this call within 20 msec. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the OMX_GetHandle function. - @param [out] ppBuffer - pointer to an OMX_BUFFERHEADERTYPE structure used to receive the - pointer to the buffer header. Note that the memory location used - for this buffer is NOT visible to the IL Client. - @param [in] nPortIndex - nPortIndex is used to select the port on the component the buffer will - be used with. The port can be found by using the nPortIndex - value as an index into the Port Definition array of the component. - @param [in] pAppPrivate - pAppPrivate is used to initialize the pAppPrivate member of the - buffer header structure. - @param [in] eglImage - eglImage contains the handle of the EGLImage to use as a buffer on the - specified port. The component is expected to validate properties of - the EGLImage against the configuration of the port to ensure the component - can use the EGLImage as a buffer. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup comp buf - */ -#define OMX_UseEGLImage( \ - hComponent, \ - ppBufferHdr, \ - nPortIndex, \ - pAppPrivate, \ - eglImage) \ - ((OMX_COMPONENTTYPE*)hComponent)->UseEGLImage( \ - hComponent, \ - ppBufferHdr, \ - nPortIndex, \ - pAppPrivate, \ - eglImage) - -/** The OMX_Init method is used to initialize the OMX core. It shall be the - first call made into OMX and it should only be executed one time without - an interviening OMX_Deinit call. - - The core should return from this call within 20 msec. - - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_APIENTRY OMX_Init(void); - - -/** The OMX_Deinit method is used to deinitialize the OMX core. It shall be - the last call made into OMX. In the event that the core determines that - thare are components loaded when this call is made, the core may return - with an error rather than try to unload the components. - - The core should return from this call within 20 msec. - - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_APIENTRY OMX_Deinit(void); - - -/** The OMX_ComponentNameEnum method will enumerate through all the names of - recognised valid components in the system. This function is provided - as a means to detect all the components in the system run-time. There is - no strict ordering to the enumeration order of component names, although - each name will only be enumerated once. If the OMX core supports run-time - installation of new components, it is only requried to detect newly - installed components when the first call to enumerate component names - is made (i.e. when nIndex is 0x0). - - The core should return from this call in 20 msec. - - @param [out] cComponentName - pointer to a null terminated string with the component name. The - names of the components are strings less than 127 bytes in length - plus the trailing null for a maximum size of 128 bytes. An example - of a valid component name is "OMX.TI.AUDIO.DSP.MIXER\0". Names are - assigned by the vendor, but shall start with "OMX." and then have - the Vendor designation next. - @param [in] nNameLength - number of characters in the cComponentName string. With all - component name strings restricted to less than 128 characters - (including the trailing null) it is recomended that the caller - provide a input string for the cComponentName of 128 characters. - @param [in] nIndex - number containing the enumeration index for the component. - Multiple calls to OMX_ComponentNameEnum with increasing values - of nIndex will enumerate through the component names in the - system until OMX_ErrorNoMore is returned. The value of nIndex - is 0 to (N-1), where N is the number of valid installed components - in the system. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. When the value of nIndex exceeds the number of - components in the system minus 1, OMX_ErrorNoMore will be - returned. Otherwise the appropriate OMX error will be returned. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_APIENTRY OMX_ComponentNameEnum( - OMX_OUT OMX_STRING cComponentName, - OMX_IN OMX_U32 nNameLength, - OMX_IN OMX_U32 nIndex); - - -/** The OMX_GetHandle method will locate the component specified by the - component name given, load that component into memory and then invoke - the component's methods to create an instance of the component. - - The core should return from this call within 20 msec. - - @param [out] pHandle - pointer to an OMX_HANDLETYPE pointer to be filled in by this method. - @param [in] cComponentName - pointer to a null terminated string with the component name. The - names of the components are strings less than 127 bytes in length - plus the trailing null for a maximum size of 128 bytes. An example - of a valid component name is "OMX.TI.AUDIO.DSP.MIXER\0". Names are - assigned by the vendor, but shall start with "OMX." and then have - the Vendor designation next. - @param [in] pAppData - pointer to an application defined value that will be returned - during callbacks so that the application can identify the source - of the callback. - @param [in] pCallBacks - pointer to a OMX_CALLBACKTYPE structure that will be passed to the - component to initialize it with. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_APIENTRY OMX_GetHandle( - OMX_OUT OMX_HANDLETYPE* pHandle, - OMX_IN OMX_STRING cComponentName, - OMX_IN OMX_PTR pAppData, - OMX_IN OMX_CALLBACKTYPE* pCallBacks); - - -/** The OMX_FreeHandle method will free a handle allocated by the OMX_GetHandle - method. If the component reference count goes to zero, the component will - be unloaded from memory. - - The core should return from this call within 20 msec when the component is - in the OMX_StateLoaded state. - - @param [in] hComponent - Handle of the component to be accessed. This is the component - handle returned by the call to the GetHandle function. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_APIENTRY OMX_FreeHandle( - OMX_IN OMX_HANDLETYPE hComponent); - - - -/** The OMX_SetupTunnel method will handle the necessary calls to the components - to setup the specified tunnel the two components. NOTE: This is - an actual method (not a #define macro). This method will make calls into - the component ComponentTunnelRequest method to do the actual tunnel - connection. - - The ComponentTunnelRequest method on both components will be called. - This method shall not be called unless the component is in the - OMX_StateLoaded state except when the ports used for the tunnel are - disabled. In this case, the component may be in the OMX_StateExecuting, - OMX_StatePause, or OMX_StateIdle states. - - The core should return from this call within 20 msec. - - @param [in] hOutput - Handle of the component to be accessed. Also this is the handle - of the component whose port, specified in the nPortOutput parameter - will be used the source for the tunnel. This is the component handle - returned by the call to the OMX_GetHandle function. There is a - requirement that hOutput be the source for the data when - tunelling (i.e. nPortOutput is an output port). If 0x0, the component - specified in hInput will have it's port specified in nPortInput - setup for communication with the application / IL client. - @param [in] nPortOutput - nPortOutput is used to select the source port on component to be - used in the tunnel. - @param [in] hInput - This is the component to setup the tunnel with. This is the handle - of the component whose port, specified in the nPortInput parameter - will be used the destination for the tunnel. This is the component handle - returned by the call to the OMX_GetHandle function. There is a - requirement that hInput be the destination for the data when - tunelling (i.e. nPortInut is an input port). If 0x0, the component - specified in hOutput will have it's port specified in nPortPOutput - setup for communication with the application / IL client. - @param [in] nPortInput - nPortInput is used to select the destination port on component to be - used in the tunnel. - @return OMX_ERRORTYPE - If the command successfully executes, the return code will be - OMX_ErrorNone. Otherwise the appropriate OMX error will be returned. - When OMX_ErrorNotImplemented is returned, one or both components is - a non-interop component and does not support tunneling. - - On failure, the ports of both components are setup for communication - with the application / IL Client. - @ingroup core tun - */ -OMX_API OMX_ERRORTYPE OMX_APIENTRY OMX_SetupTunnel( - OMX_IN OMX_HANDLETYPE hOutput, - OMX_IN OMX_U32 nPortOutput, - OMX_IN OMX_HANDLETYPE hInput, - OMX_IN OMX_U32 nPortInput); - -/** @ingroup cp */ -OMX_API OMX_ERRORTYPE OMX_GetContentPipe( - OMX_OUT OMX_HANDLETYPE *hPipe, - OMX_IN OMX_STRING szURI); - -/** The OMX_GetComponentsOfRole method will return the number of components that support the given - role and (if the compNames field is non-NULL) the names of those components. The call will fail if - an insufficiently sized array of names is supplied. To ensure the array is sufficiently sized the - client should: - * first call this function with the compNames field NULL to determine the number of component names - * second call this function with the compNames field pointing to an array of names allocated - according to the number returned by the first call. - - The core should return from this call within 5 msec. - - @param [in] role - This is generic standard component name consisting only of component class - name and the type within that class (e.g. 'audio_decoder.aac'). - @param [inout] pNumComps - This is used both as input and output. - - If compNames is NULL, the input is ignored and the output specifies how many components support - the given role. - - If compNames is not NULL, on input it bounds the size of the input structure and - on output, it specifies the number of components string names listed within the compNames parameter. - @param [inout] compNames - If NULL this field is ignored. If non-NULL this points to an array of 128-byte strings which accepts - a list of the names of all physical components that implement the specified standard component name. - Each name is NULL terminated. numComps indicates the number of names. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_GetComponentsOfRole ( - OMX_IN OMX_STRING role, - OMX_INOUT OMX_U32 *pNumComps, - OMX_INOUT OMX_U8 **compNames); - -/** The OMX_GetRolesOfComponent method will return the number of roles supported by the given - component and (if the roles field is non-NULL) the names of those roles. The call will fail if - an insufficiently sized array of names is supplied. To ensure the array is sufficiently sized the - client should: - * first call this function with the roles field NULL to determine the number of role names - * second call this function with the roles field pointing to an array of names allocated - according to the number returned by the first call. - - The core should return from this call within 5 msec. - - @param [in] compName - This is the name of the component being queried about. - @param [inout] pNumRoles - This is used both as input and output. - - If roles is NULL, the input is ignored and the output specifies how many roles the component supports. - - If compNames is not NULL, on input it bounds the size of the input structure and - on output, it specifies the number of roles string names listed within the roles parameter. - @param [out] roles - If NULL this field is ignored. If non-NULL this points to an array of 128-byte strings - which accepts a list of the names of all standard components roles implemented on the - specified component name. numComps indicates the number of names. - @ingroup core - */ -OMX_API OMX_ERRORTYPE OMX_GetRolesOfComponent ( - OMX_IN OMX_STRING compName, - OMX_INOUT OMX_U32 *pNumRoles, - OMX_OUT OMX_U8 **roles); - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ - diff --git a/subprojects/gst-omx/omx/openmax/OMX_CoreExt.h b/subprojects/gst-omx/omx/openmax/OMX_CoreExt.h deleted file mode 100644 index b7a5b62334..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_CoreExt.h +++ /dev/null @@ -1,73 +0,0 @@ -/* - * Copyright (c) 2010 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_CoreExt.h - OpenMax IL version 1.1.2 - * The OMX_CoreExt header file contains extensions to the definitions used - * by both the application and the component to access common items. - */ - -#ifndef OMX_CoreExt_h -#define OMX_CoreExt_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - -/* Each OMX header shall include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ -#include - -/** Extensions to the standard IL errors. */ -typedef enum OMX_ERROREXTTYPE -{ - OMX_ErrorInvalidMode = (OMX_S32) (OMX_ErrorKhronosExtensions + 0x00000001), - OMX_ErrorExtMax = 0x7FFFFFFF -} OMX_ERROREXTTYPE; - - -/** Event type extensions. */ -typedef enum OMX_EVENTEXTTYPE -{ - OMX_EventIndexSettingChanged = OMX_EventKhronosExtensions, /**< component signals the IL client of a change - in a param, config, or extension */ - OMX_EventExtMax = 0x7FFFFFFF -} OMX_EVENTEXTTYPE; - - -/** Enable or disable a callback event. */ -typedef struct OMX_CONFIG_CALLBACKREQUESTTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_INDEXTYPE nIndex; /**< the index the callback is requested for */ - OMX_BOOL bEnable; /**< enable (OMX_TRUE) or disable (OMX_FALSE) the callback */ -} OMX_CONFIG_CALLBACKREQUESTTYPE; - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* OMX_CoreExt_h */ -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_IVCommon.h b/subprojects/gst-omx/omx/openmax/OMX_IVCommon.h deleted file mode 100644 index 4c4995ce04..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_IVCommon.h +++ /dev/null @@ -1,920 +0,0 @@ -/** - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** - * @file OMX_IVCommon.h - OpenMax IL version 1.1.2 - * The structures needed by Video and Image components to exchange - * parameters and configuration data with the components. - */ -#ifndef OMX_IVCommon_h -#define OMX_IVCommon_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - -/** - * Each OMX header must include all required header files to allow the header - * to compile without errors. The includes below are required for this header - * file to compile successfully - */ - -#include - -/** @defgroup iv OpenMAX IL Imaging and Video Domain - * Common structures for OpenMAX IL Imaging and Video domains - * @{ - */ - - -/** - * Enumeration defining possible uncompressed image/video formats. - * - * ENUMS: - * Unused : Placeholder value when format is N/A - * Monochrome : black and white - * 8bitRGB332 : Red 7:5, Green 4:2, Blue 1:0 - * 12bitRGB444 : Red 11:8, Green 7:4, Blue 3:0 - * 16bitARGB4444 : Alpha 15:12, Red 11:8, Green 7:4, Blue 3:0 - * 16bitARGB1555 : Alpha 15, Red 14:10, Green 9:5, Blue 4:0 - * 16bitRGB565 : Red 15:11, Green 10:5, Blue 4:0 - * 16bitBGR565 : Blue 15:11, Green 10:5, Red 4:0 - * 18bitRGB666 : Red 17:12, Green 11:6, Blue 5:0 - * 18bitARGB1665 : Alpha 17, Red 16:11, Green 10:5, Blue 4:0 - * 19bitARGB1666 : Alpha 18, Red 17:12, Green 11:6, Blue 5:0 - * 24bitRGB888 : Red 24:16, Green 15:8, Blue 7:0 - * 24bitBGR888 : Blue 24:16, Green 15:8, Red 7:0 - * 24bitARGB1887 : Alpha 23, Red 22:15, Green 14:7, Blue 6:0 - * 25bitARGB1888 : Alpha 24, Red 23:16, Green 15:8, Blue 7:0 - * 32bitBGRA8888 : Blue 31:24, Green 23:16, Red 15:8, Alpha 7:0 - * 32bitARGB8888 : Alpha 31:24, Red 23:16, Green 15:8, Blue 7:0 - * YUV411Planar : U,Y are subsampled by a factor of 4 horizontally - * YUV411PackedPlanar : packed per payload in planar slices - * YUV420Planar : Three arrays Y,U,V. - * YUV420PackedPlanar : packed per payload in planar slices - * YUV420SemiPlanar : Two arrays, one is all Y, the other is U and V - * YUV422Planar : Three arrays Y,U,V. - * YUV422PackedPlanar : packed per payload in planar slices - * YUV422SemiPlanar : Two arrays, one is all Y, the other is U and V - * YCbYCr : Organized as 16bit YUYV (i.e. YCbYCr) - * YCrYCb : Organized as 16bit YVYU (i.e. YCrYCb) - * CbYCrY : Organized as 16bit UYVY (i.e. CbYCrY) - * CrYCbY : Organized as 16bit VYUY (i.e. CrYCbY) - * YUV444Interleaved : Each pixel contains equal parts YUV - * RawBayer8bit : SMIA camera output format - * RawBayer10bit : SMIA camera output format - * RawBayer8bitcompressed : SMIA camera output format - */ -typedef enum OMX_COLOR_FORMATTYPE { - OMX_COLOR_FormatUnused, - OMX_COLOR_FormatMonochrome, - OMX_COLOR_Format8bitRGB332, - OMX_COLOR_Format12bitRGB444, - OMX_COLOR_Format16bitARGB4444, - OMX_COLOR_Format16bitARGB1555, - OMX_COLOR_Format16bitRGB565, - OMX_COLOR_Format16bitBGR565, - OMX_COLOR_Format18bitRGB666, - OMX_COLOR_Format18bitARGB1665, - OMX_COLOR_Format19bitARGB1666, - OMX_COLOR_Format24bitRGB888, - OMX_COLOR_Format24bitBGR888, - OMX_COLOR_Format24bitARGB1887, - OMX_COLOR_Format25bitARGB1888, - OMX_COLOR_Format32bitBGRA8888, - OMX_COLOR_Format32bitARGB8888, - OMX_COLOR_FormatYUV411Planar, - OMX_COLOR_FormatYUV411PackedPlanar, - OMX_COLOR_FormatYUV420Planar, - OMX_COLOR_FormatYUV420PackedPlanar, - OMX_COLOR_FormatYUV420SemiPlanar, - OMX_COLOR_FormatYUV422Planar, - OMX_COLOR_FormatYUV422PackedPlanar, - OMX_COLOR_FormatYUV422SemiPlanar, - OMX_COLOR_FormatYCbYCr, - OMX_COLOR_FormatYCrYCb, - OMX_COLOR_FormatCbYCrY, - OMX_COLOR_FormatCrYCbY, - OMX_COLOR_FormatYUV444Interleaved, - OMX_COLOR_FormatRawBayer8bit, - OMX_COLOR_FormatRawBayer10bit, - OMX_COLOR_FormatRawBayer8bitcompressed, - OMX_COLOR_FormatL2, - OMX_COLOR_FormatL4, - OMX_COLOR_FormatL8, - OMX_COLOR_FormatL16, - OMX_COLOR_FormatL24, - OMX_COLOR_FormatL32, - OMX_COLOR_FormatYUV420PackedSemiPlanar, - OMX_COLOR_FormatYUV422PackedSemiPlanar, - OMX_COLOR_Format18BitBGR666, - OMX_COLOR_Format24BitARGB6666, - OMX_COLOR_Format24BitABGR6666, - OMX_COLOR_FormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_COLOR_FormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_COLOR_FormatMax = 0x7FFFFFFF -} OMX_COLOR_FORMATTYPE; - - -/** - * Defines the matrix for conversion from RGB to YUV or vice versa. - * iColorMatrix should be initialized with the fixed point values - * used in converting between formats. - */ -typedef struct OMX_CONFIG_COLORCONVERSIONTYPE { - OMX_U32 nSize; /**< Size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version info */ - OMX_U32 nPortIndex; /**< Port that this struct applies to */ - OMX_S32 xColorMatrix[3][3]; /**< Stored in signed Q16 format */ - OMX_S32 xColorOffset[4]; /**< Stored in signed Q16 format */ -}OMX_CONFIG_COLORCONVERSIONTYPE; - - -/** - * Structure defining percent to scale each frame dimension. For example: - * To make the width 50% larger, use fWidth = 1.5 and to make the width - * 1/2 the original size, use fWidth = 0.5 - */ -typedef struct OMX_CONFIG_SCALEFACTORTYPE { - OMX_U32 nSize; /**< Size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version info */ - OMX_U32 nPortIndex; /**< Port that this struct applies to */ - OMX_S32 xWidth; /**< Fixed point value stored as Q16 */ - OMX_S32 xHeight; /**< Fixed point value stored as Q16 */ -}OMX_CONFIG_SCALEFACTORTYPE; - - -/** - * Enumeration of possible image filter types - */ -typedef enum OMX_IMAGEFILTERTYPE { - OMX_ImageFilterNone, - OMX_ImageFilterNoise, - OMX_ImageFilterEmboss, - OMX_ImageFilterNegative, - OMX_ImageFilterSketch, - OMX_ImageFilterOilPaint, - OMX_ImageFilterHatch, - OMX_ImageFilterGpen, - OMX_ImageFilterAntialias, - OMX_ImageFilterDeRing, - OMX_ImageFilterSolarize, - OMX_ImageFilterKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_ImageFilterVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_ImageFilterMax = 0x7FFFFFFF -} OMX_IMAGEFILTERTYPE; - - -/** - * Image filter configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eImageFilter : Image filter type enumeration - */ -typedef struct OMX_CONFIG_IMAGEFILTERTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_IMAGEFILTERTYPE eImageFilter; -} OMX_CONFIG_IMAGEFILTERTYPE; - - -/** - * Customized U and V for color enhancement - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * bColorEnhancement : Enable/disable color enhancement - * nCustomizedU : Practical values: 16-240, range: 0-255, value set for - * U component - * nCustomizedV : Practical values: 16-240, range: 0-255, value set for - * V component - */ -typedef struct OMX_CONFIG_COLORENHANCEMENTTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bColorEnhancement; - OMX_U8 nCustomizedU; - OMX_U8 nCustomizedV; -} OMX_CONFIG_COLORENHANCEMENTTYPE; - - -/** - * Define color key and color key mask - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nARGBColor : 32bit Alpha, Red, Green, Blue Color - * nARGBMask : 32bit Mask for Alpha, Red, Green, Blue channels - */ -typedef struct OMX_CONFIG_COLORKEYTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nARGBColor; - OMX_U32 nARGBMask; -} OMX_CONFIG_COLORKEYTYPE; - - -/** - * List of color blend types for pre/post processing - * - * ENUMS: - * None : No color blending present - * AlphaConstant : Function is (alpha_constant * src) + - * (1 - alpha_constant) * dst) - * AlphaPerPixel : Function is (alpha * src) + (1 - alpha) * dst) - * Alternate : Function is alternating pixels from src and dst - * And : Function is (src & dst) - * Or : Function is (src | dst) - * Invert : Function is ~src - */ -typedef enum OMX_COLORBLENDTYPE { - OMX_ColorBlendNone, - OMX_ColorBlendAlphaConstant, - OMX_ColorBlendAlphaPerPixel, - OMX_ColorBlendAlternate, - OMX_ColorBlendAnd, - OMX_ColorBlendOr, - OMX_ColorBlendInvert, - OMX_ColorBlendKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_ColorBlendVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_ColorBlendMax = 0x7FFFFFFF -} OMX_COLORBLENDTYPE; - - -/** - * Color blend configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nRGBAlphaConstant : Constant global alpha values when global alpha is used - * eColorBlend : Color blend type enumeration - */ -typedef struct OMX_CONFIG_COLORBLENDTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nRGBAlphaConstant; - OMX_COLORBLENDTYPE eColorBlend; -} OMX_CONFIG_COLORBLENDTYPE; - - -/** - * Hold frame dimension - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nWidth : Frame width in pixels - * nHeight : Frame height in pixels - */ -typedef struct OMX_FRAMESIZETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nWidth; - OMX_U32 nHeight; -} OMX_FRAMESIZETYPE; - - -/** - * Rotation configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nRotation : +/- integer rotation value - */ -typedef struct OMX_CONFIG_ROTATIONTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nRotation; -} OMX_CONFIG_ROTATIONTYPE; - - -/** - * Possible mirroring directions for pre/post processing - * - * ENUMS: - * None : No mirroring - * Vertical : Vertical mirroring, flip on X axis - * Horizontal : Horizontal mirroring, flip on Y axis - * Both : Both vertical and horizontal mirroring - */ -typedef enum OMX_MIRRORTYPE { - OMX_MirrorNone = 0, - OMX_MirrorVertical, - OMX_MirrorHorizontal, - OMX_MirrorBoth, - OMX_MirrorKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_MirrorVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_MirrorMax = 0x7FFFFFFF -} OMX_MIRRORTYPE; - - -/** - * Mirroring configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eMirror : Mirror type enumeration - */ -typedef struct OMX_CONFIG_MIRRORTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_MIRRORTYPE eMirror; -} OMX_CONFIG_MIRRORTYPE; - - -/** - * Position information only - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nX : X coordinate for the point - * nY : Y coordinate for the point - */ -typedef struct OMX_CONFIG_POINTTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nX; - OMX_S32 nY; -} OMX_CONFIG_POINTTYPE; - - -/** - * Frame size plus position - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nLeft : X Coordinate of the top left corner of the rectangle - * nTop : Y Coordinate of the top left corner of the rectangle - * nWidth : Width of the rectangle - * nHeight : Height of the rectangle - */ -typedef struct OMX_CONFIG_RECTTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nLeft; - OMX_S32 nTop; - OMX_U32 nWidth; - OMX_U32 nHeight; -} OMX_CONFIG_RECTTYPE; - - -/** - * Deblocking state; it is required to be set up before starting the codec - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * bDeblocking : Enable/disable deblocking mode - */ -typedef struct OMX_PARAM_DEBLOCKINGTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bDeblocking; -} OMX_PARAM_DEBLOCKINGTYPE; - - -/** - * Stabilization state - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * bStab : Enable/disable frame stabilization state - */ -typedef struct OMX_CONFIG_FRAMESTABTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bStab; -} OMX_CONFIG_FRAMESTABTYPE; - - -/** - * White Balance control type - * - * STRUCT MEMBERS: - * SunLight : Referenced in JSR-234 - * Flash : Optimal for device's integrated flash - */ -typedef enum OMX_WHITEBALCONTROLTYPE { - OMX_WhiteBalControlOff = 0, - OMX_WhiteBalControlAuto, - OMX_WhiteBalControlSunLight, - OMX_WhiteBalControlCloudy, - OMX_WhiteBalControlShade, - OMX_WhiteBalControlTungsten, - OMX_WhiteBalControlFluorescent, - OMX_WhiteBalControlIncandescent, - OMX_WhiteBalControlFlash, - OMX_WhiteBalControlHorizon, - OMX_WhiteBalControlKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_WhiteBalControlVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_WhiteBalControlMax = 0x7FFFFFFF -} OMX_WHITEBALCONTROLTYPE; - - -/** - * White Balance control configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eWhiteBalControl : White balance enumeration - */ -typedef struct OMX_CONFIG_WHITEBALCONTROLTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_WHITEBALCONTROLTYPE eWhiteBalControl; -} OMX_CONFIG_WHITEBALCONTROLTYPE; - - -/** - * Exposure control type - */ -typedef enum OMX_EXPOSURECONTROLTYPE { - OMX_ExposureControlOff = 0, - OMX_ExposureControlAuto, - OMX_ExposureControlNight, - OMX_ExposureControlBackLight, - OMX_ExposureControlSpotLight, - OMX_ExposureControlSports, - OMX_ExposureControlSnow, - OMX_ExposureControlBeach, - OMX_ExposureControlLargeAperture, - OMX_ExposureControlSmallApperture, - OMX_ExposureControlKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_ExposureControlVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_ExposureControlMax = 0x7FFFFFFF -} OMX_EXPOSURECONTROLTYPE; - - -/** - * White Balance control configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eExposureControl : Exposure control enumeration - */ -typedef struct OMX_CONFIG_EXPOSURECONTROLTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_EXPOSURECONTROLTYPE eExposureControl; -} OMX_CONFIG_EXPOSURECONTROLTYPE; - - -/** - * Defines sensor supported mode. - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nFrameRate : Single shot mode is indicated by a 0 - * bOneShot : Enable for single shot, disable for streaming - * sFrameSize : Framesize - */ -typedef struct OMX_PARAM_SENSORMODETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nFrameRate; - OMX_BOOL bOneShot; - OMX_FRAMESIZETYPE sFrameSize; -} OMX_PARAM_SENSORMODETYPE; - - -/** - * Defines contrast level - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nContrast : Values allowed for contrast -100 to 100, zero means no change - */ -typedef struct OMX_CONFIG_CONTRASTTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nContrast; -} OMX_CONFIG_CONTRASTTYPE; - - -/** - * Defines brightness level - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nBrightness : 0-100% - */ -typedef struct OMX_CONFIG_BRIGHTNESSTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nBrightness; -} OMX_CONFIG_BRIGHTNESSTYPE; - - -/** - * Defines backlight level configuration for a video sink, e.g. LCD panel - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nBacklight : Values allowed for backlight 0-100% - * nTimeout : Number of milliseconds before backlight automatically turns - * off. A value of 0x0 disables backight timeout - */ -typedef struct OMX_CONFIG_BACKLIGHTTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nBacklight; - OMX_U32 nTimeout; -} OMX_CONFIG_BACKLIGHTTYPE; - - -/** - * Defines setting for Gamma - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nGamma : Values allowed for gamma -100 to 100, zero means no change - */ -typedef struct OMX_CONFIG_GAMMATYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nGamma; -} OMX_CONFIG_GAMMATYPE; - - -/** - * Define for setting saturation - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nSaturation : Values allowed for saturation -100 to 100, zero means - * no change - */ -typedef struct OMX_CONFIG_SATURATIONTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nSaturation; -} OMX_CONFIG_SATURATIONTYPE; - - -/** - * Define for setting Lightness - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nLightness : Values allowed for lightness -100 to 100, zero means no - * change - */ -typedef struct OMX_CONFIG_LIGHTNESSTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_S32 nLightness; -} OMX_CONFIG_LIGHTNESSTYPE; - - -/** - * Plane blend configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Index of input port associated with the plane. - * nDepth : Depth of the plane in relation to the screen. Higher - * numbered depths are "behind" lower number depths. - * This number defaults to the Port Index number. - * nAlpha : Transparency blending component for the entire plane. - * See blending modes for more detail. - */ -typedef struct OMX_CONFIG_PLANEBLENDTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nDepth; - OMX_U32 nAlpha; -} OMX_CONFIG_PLANEBLENDTYPE; - - -/** - * Define interlace type - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * bEnable : Enable control variable for this functionality - * (see below) - * nInterleavePortIndex : Index of input or output port associated with - * the interleaved plane. - * pPlanarPortIndexes[4] : Index of input or output planar ports. - */ -typedef struct OMX_PARAM_INTERLEAVETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bEnable; - OMX_U32 nInterleavePortIndex; -} OMX_PARAM_INTERLEAVETYPE; - - -/** - * Defines the picture effect used for an input picture - */ -typedef enum OMX_TRANSITIONEFFECTTYPE { - OMX_EffectNone, - OMX_EffectFadeFromBlack, - OMX_EffectFadeToBlack, - OMX_EffectUnspecifiedThroughConstantColor, - OMX_EffectDissolve, - OMX_EffectWipe, - OMX_EffectUnspecifiedMixOfTwoScenes, - OMX_EffectKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_EffectVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_EffectMax = 0x7FFFFFFF -} OMX_TRANSITIONEFFECTTYPE; - - -/** - * Structure used to configure current transition effect - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eEffect : Effect to enable - */ -typedef struct OMX_CONFIG_TRANSITIONEFFECTTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_TRANSITIONEFFECTTYPE eEffect; -} OMX_CONFIG_TRANSITIONEFFECTTYPE; - - -/** - * Defines possible data unit types for encoded video data. The data unit - * types are used both for encoded video input for playback as well as - * encoded video output from recording. - */ -typedef enum OMX_DATAUNITTYPE { - OMX_DataUnitCodedPicture, - OMX_DataUnitVideoSegment, - OMX_DataUnitSeveralSegments, - OMX_DataUnitArbitraryStreamSection, - OMX_DataUnitKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_DataUnitVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_DataUnitMax = 0x7FFFFFFF -} OMX_DATAUNITTYPE; - - -/** - * Defines possible encapsulation types for coded video data unit. The - * encapsulation information is used both for encoded video input for - * playback as well as encoded video output from recording. - */ -typedef enum OMX_DATAUNITENCAPSULATIONTYPE { - OMX_DataEncapsulationElementaryStream, - OMX_DataEncapsulationGenericPayload, - OMX_DataEncapsulationRtpPayload, - OMX_DataEncapsulationKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_DataEncapsulationVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_DataEncapsulationMax = 0x7FFFFFFF -} OMX_DATAUNITENCAPSULATIONTYPE; - - -/** - * Structure used to configure the type of being decoded/encoded - */ -typedef struct OMX_PARAM_DATAUNITTYPE { - OMX_U32 nSize; /**< Size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_DATAUNITTYPE eUnitType; - OMX_DATAUNITENCAPSULATIONTYPE eEncapsulationType; -} OMX_PARAM_DATAUNITTYPE; - - -/** - * Defines dither types - */ -typedef enum OMX_DITHERTYPE { - OMX_DitherNone, - OMX_DitherOrdered, - OMX_DitherErrorDiffusion, - OMX_DitherOther, - OMX_DitherKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_DitherVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_DitherMax = 0x7FFFFFFF -} OMX_DITHERTYPE; - - -/** - * Structure used to configure current type of dithering - */ -typedef struct OMX_CONFIG_DITHERTYPE { - OMX_U32 nSize; /**< Size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_DITHERTYPE eDither; /**< Type of dithering to use */ -} OMX_CONFIG_DITHERTYPE; - -typedef struct OMX_CONFIG_CAPTUREMODETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; /**< Port that this structure applies to */ - OMX_BOOL bContinuous; /**< If true then ignore frame rate and emit capture - * data as fast as possible (otherwise obey port's frame rate). */ - OMX_BOOL bFrameLimited; /**< If true then terminate capture after the port emits the - * specified number of frames (otherwise the port does not - * terminate the capture until instructed to do so by the client). - * Even if set, the client may manually terminate the capture prior - * to reaching the limit. */ - OMX_U32 nFrameLimit; /**< Limit on number of frames emitted during a capture (only - * valid if bFrameLimited is set). */ -} OMX_CONFIG_CAPTUREMODETYPE; - -typedef enum OMX_METERINGTYPE { - - OMX_MeteringModeAverage, /**< Center-weighted average metering. */ - OMX_MeteringModeSpot, /**< Spot (partial) metering. */ - OMX_MeteringModeMatrix, /**< Matrix or evaluative metering. */ - - OMX_MeteringKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_MeteringVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_EVModeMax = 0x7fffffff -} OMX_METERINGTYPE; - -typedef struct OMX_CONFIG_EXPOSUREVALUETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_METERINGTYPE eMetering; - OMX_S32 xEVCompensation; /**< Fixed point value stored as Q16 */ - OMX_U32 nApertureFNumber; /**< e.g. nApertureFNumber = 2 implies "f/2" - Q16 format */ - OMX_BOOL bAutoAperture; /**< Whether aperture number is defined automatically */ - OMX_U32 nShutterSpeedMsec; /**< Shutterspeed in milliseconds */ - OMX_BOOL bAutoShutterSpeed; /**< Whether shutter speed is defined automatically */ - OMX_U32 nSensitivity; /**< e.g. nSensitivity = 100 implies "ISO 100" */ - OMX_BOOL bAutoSensitivity; /**< Whether sensitivity is defined automatically */ -} OMX_CONFIG_EXPOSUREVALUETYPE; - -/** - * Focus region configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * bCenter : Use center region as focus region of interest - * bLeft : Use left region as focus region of interest - * bRight : Use right region as focus region of interest - * bTop : Use top region as focus region of interest - * bBottom : Use bottom region as focus region of interest - * bTopLeft : Use top left region as focus region of interest - * bTopRight : Use top right region as focus region of interest - * bBottomLeft : Use bottom left region as focus region of interest - * bBottomRight : Use bottom right region as focus region of interest - */ -typedef struct OMX_CONFIG_FOCUSREGIONTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bCenter; - OMX_BOOL bLeft; - OMX_BOOL bRight; - OMX_BOOL bTop; - OMX_BOOL bBottom; - OMX_BOOL bTopLeft; - OMX_BOOL bTopRight; - OMX_BOOL bBottomLeft; - OMX_BOOL bBottomRight; -} OMX_CONFIG_FOCUSREGIONTYPE; - -/** - * Focus Status type - */ -typedef enum OMX_FOCUSSTATUSTYPE { - OMX_FocusStatusOff = 0, - OMX_FocusStatusRequest, - OMX_FocusStatusReached, - OMX_FocusStatusUnableToReach, - OMX_FocusStatusLost, - OMX_FocusStatusKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_FocusStatusVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_FocusStatusMax = 0x7FFFFFFF -} OMX_FOCUSSTATUSTYPE; - -/** - * Focus status configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eFocusStatus : Specifies the focus status - * bCenterStatus : Use center region as focus region of interest - * bLeftStatus : Use left region as focus region of interest - * bRightStatus : Use right region as focus region of interest - * bTopStatus : Use top region as focus region of interest - * bBottomStatus : Use bottom region as focus region of interest - * bTopLeftStatus : Use top left region as focus region of interest - * bTopRightStatus : Use top right region as focus region of interest - * bBottomLeftStatus : Use bottom left region as focus region of interest - * bBottomRightStatus : Use bottom right region as focus region of interest - */ -typedef struct OMX_PARAM_FOCUSSTATUSTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_FOCUSSTATUSTYPE eFocusStatus; - OMX_BOOL bCenterStatus; - OMX_BOOL bLeftStatus; - OMX_BOOL bRightStatus; - OMX_BOOL bTopStatus; - OMX_BOOL bBottomStatus; - OMX_BOOL bTopLeftStatus; - OMX_BOOL bTopRightStatus; - OMX_BOOL bBottomLeftStatus; - OMX_BOOL bBottomRightStatus; -} OMX_PARAM_FOCUSSTATUSTYPE; - -/** @} */ - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_Image.h b/subprojects/gst-omx/omx/openmax/OMX_Image.h deleted file mode 100644 index a6d4666c03..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Image.h +++ /dev/null @@ -1,328 +0,0 @@ -/** - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - */ - -/** - * @file OMX_Image.h - OpenMax IL version 1.1.2 - * The structures needed by Image components to exchange parameters and - * configuration data with the components. - */ -#ifndef OMX_Image_h -#define OMX_Image_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - -/** - * Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ - -#include - -/** @defgroup imaging OpenMAX IL Imaging Domain - * @ingroup iv - * Structures for OpenMAX IL Imaging domain - * @{ - */ - -/** - * Enumeration used to define the possible image compression coding. - */ -typedef enum OMX_IMAGE_CODINGTYPE { - OMX_IMAGE_CodingUnused, /**< Value when format is N/A */ - OMX_IMAGE_CodingAutoDetect, /**< Auto detection of image format */ - OMX_IMAGE_CodingJPEG, /**< JPEG/JFIF image format */ - OMX_IMAGE_CodingJPEG2K, /**< JPEG 2000 image format */ - OMX_IMAGE_CodingEXIF, /**< EXIF image format */ - OMX_IMAGE_CodingTIFF, /**< TIFF image format */ - OMX_IMAGE_CodingGIF, /**< Graphics image format */ - OMX_IMAGE_CodingPNG, /**< PNG image format */ - OMX_IMAGE_CodingLZW, /**< LZW image format */ - OMX_IMAGE_CodingBMP, /**< Windows Bitmap format */ - OMX_IMAGE_CodingKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_IMAGE_CodingVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_IMAGE_CodingMax = 0x7FFFFFFF -} OMX_IMAGE_CODINGTYPE; - - -/** - * Data structure used to define an image path. The number of image paths - * for input and output will vary by type of the image component. - * - * Input (aka Source) : Zero Inputs, one Output, - * Splitter : One Input, 2 or more Outputs, - * Processing Element : One Input, one output, - * Mixer : 2 or more inputs, one output, - * Output (aka Sink) : One Input, zero outputs. - * - * The PortDefinition structure is used to define all of the parameters - * necessary for the compliant component to setup an input or an output - * image path. If additional vendor specific data is required, it should - * be transmitted to the component using the CustomCommand function. - * Compliant components will prepopulate this structure with optimal - * values during the OMX_GetParameter() command. - * - * STRUCT MEMBERS: - * cMIMEType : MIME type of data for the port - * pNativeRender : Platform specific reference for a display if a - * sync, otherwise this field is 0 - * nFrameWidth : Width of frame to be used on port if - * uncompressed format is used. Use 0 for - * unknown, don't care or variable - * nFrameHeight : Height of frame to be used on port if - * uncompressed format is used. Use 0 for - * unknown, don't care or variable - * nStride : Number of bytes per span of an image (i.e. - * indicates the number of bytes to get from - * span N to span N+1, where negative stride - * indicates the image is bottom up - * nSliceHeight : Height used when encoding in slices - * bFlagErrorConcealment : Turns on error concealment if it is supported by - * the OMX component - * eCompressionFormat : Compression format used in this instance of - * the component. When OMX_IMAGE_CodingUnused is - * specified, eColorFormat is valid - * eColorFormat : Decompressed format used by this component - * pNativeWindow : Platform specific reference for a window object if a - * display sink , otherwise this field is 0x0. - */ -typedef struct OMX_IMAGE_PORTDEFINITIONTYPE { - OMX_STRING cMIMEType; - OMX_NATIVE_DEVICETYPE pNativeRender; - OMX_U32 nFrameWidth; - OMX_U32 nFrameHeight; - OMX_S32 nStride; - OMX_U32 nSliceHeight; - OMX_BOOL bFlagErrorConcealment; - OMX_IMAGE_CODINGTYPE eCompressionFormat; - OMX_COLOR_FORMATTYPE eColorFormat; - OMX_NATIVE_WINDOWTYPE pNativeWindow; -} OMX_IMAGE_PORTDEFINITIONTYPE; - - -/** - * Port format parameter. This structure is used to enumerate the various - * data input/output format supported by the port. - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Indicates which port to set - * nIndex : Indicates the enumeration index for the format from - * 0x0 to N-1 - * eCompressionFormat : Compression format used in this instance of the - * component. When OMX_IMAGE_CodingUnused is specified, - * eColorFormat is valid - * eColorFormat : Decompressed format used by this component - */ -typedef struct OMX_IMAGE_PARAM_PORTFORMATTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nIndex; - OMX_IMAGE_CODINGTYPE eCompressionFormat; - OMX_COLOR_FORMATTYPE eColorFormat; -} OMX_IMAGE_PARAM_PORTFORMATTYPE; - - -/** - * Flash control type - * - * ENUMS - * Torch : Flash forced constantly on - */ -typedef enum OMX_IMAGE_FLASHCONTROLTYPE { - OMX_IMAGE_FlashControlOn = 0, - OMX_IMAGE_FlashControlOff, - OMX_IMAGE_FlashControlAuto, - OMX_IMAGE_FlashControlRedEyeReduction, - OMX_IMAGE_FlashControlFillin, - OMX_IMAGE_FlashControlTorch, - OMX_IMAGE_FlashControlKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_IMAGE_FlashControlVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_IMAGE_FlashControlMax = 0x7FFFFFFF -} OMX_IMAGE_FLASHCONTROLTYPE; - - -/** - * Flash control configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eFlashControl : Flash control type - */ -typedef struct OMX_IMAGE_PARAM_FLASHCONTROLTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_IMAGE_FLASHCONTROLTYPE eFlashControl; -} OMX_IMAGE_PARAM_FLASHCONTROLTYPE; - - -/** - * Focus control type - */ -typedef enum OMX_IMAGE_FOCUSCONTROLTYPE { - OMX_IMAGE_FocusControlOn = 0, - OMX_IMAGE_FocusControlOff, - OMX_IMAGE_FocusControlAuto, - OMX_IMAGE_FocusControlAutoLock, - OMX_IMAGE_FocusControlKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_IMAGE_FocusControlVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_IMAGE_FocusControlMax = 0x7FFFFFFF -} OMX_IMAGE_FOCUSCONTROLTYPE; - - -/** - * Focus control configuration - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eFocusControl : Focus control - * nFocusSteps : Focus can take on values from 0 mm to infinity. - * Interest is only in number of steps over this range. - * nFocusStepIndex : Current focus step index - */ -typedef struct OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_IMAGE_FOCUSCONTROLTYPE eFocusControl; - OMX_U32 nFocusSteps; - OMX_U32 nFocusStepIndex; -} OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE; - - -/** - * Q Factor for JPEG compression, which controls the tradeoff between image - * quality and size. Q Factor provides a more simple means of controlling - * JPEG compression quality, without directly programming Quantization - * tables for chroma and luma - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nQFactor : JPEG Q factor value in the range of 1-100. A factor of 1 - * produces the smallest, worst quality images, and a factor - * of 100 produces the largest, best quality images. A - * typical default is 75 for small good quality images - */ -typedef struct OMX_IMAGE_PARAM_QFACTORTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nQFactor; -} OMX_IMAGE_PARAM_QFACTORTYPE; - -/** - * Quantization table type - */ - -typedef enum OMX_IMAGE_QUANTIZATIONTABLETYPE { - OMX_IMAGE_QuantizationTableLuma = 0, - OMX_IMAGE_QuantizationTableChroma, - OMX_IMAGE_QuantizationTableChromaCb, - OMX_IMAGE_QuantizationTableChromaCr, - OMX_IMAGE_QuantizationTableKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_IMAGE_QuantizationTableVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_IMAGE_QuantizationTableMax = 0x7FFFFFFF -} OMX_IMAGE_QUANTIZATIONTABLETYPE; - -/** - * JPEG quantization tables are used to determine DCT compression for - * YUV data, as an alternative to specifying Q factor, providing exact - * control of compression - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eQuantizationTable : Quantization table type - * nQuantizationMatrix[64] : JPEG quantization table of coefficients stored - * in increasing columns then by rows of data (i.e. - * row 1, ... row 8). Quantization values are in - * the range 0-255 and stored in linear order - * (i.e. the component will zig-zag the - * quantization table data if required internally) - */ -typedef struct OMX_IMAGE_PARAM_QUANTIZATIONTABLETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_IMAGE_QUANTIZATIONTABLETYPE eQuantizationTable; - OMX_U8 nQuantizationMatrix[64]; -} OMX_IMAGE_PARAM_QUANTIZATIONTABLETYPE; - - -/** - * Huffman table type, the same Huffman table is applied for chroma and - * luma component - */ -typedef enum OMX_IMAGE_HUFFMANTABLETYPE { - OMX_IMAGE_HuffmanTableAC = 0, - OMX_IMAGE_HuffmanTableDC, - OMX_IMAGE_HuffmanTableACLuma, - OMX_IMAGE_HuffmanTableACChroma, - OMX_IMAGE_HuffmanTableDCLuma, - OMX_IMAGE_HuffmanTableDCChroma, - OMX_IMAGE_HuffmanTableKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_IMAGE_HuffmanTableVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_IMAGE_HuffmanTableMax = 0x7FFFFFFF -} OMX_IMAGE_HUFFMANTABLETYPE; - -/** - * JPEG Huffman table - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eHuffmanTable : Huffman table type - * nNumberOfHuffmanCodeOfLength[16] : 0-16, number of Huffman codes of each - * possible length - * nHuffmanTable[256] : 0-255, the size used for AC and DC - * HuffmanTable are 16 and 162 - */ -typedef struct OMX_IMAGE_PARAM_HUFFMANTTABLETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_IMAGE_HUFFMANTABLETYPE eHuffmanTable; - OMX_U8 nNumberOfHuffmanCodeOfLength[16]; - OMX_U8 nHuffmanTable[256]; -}OMX_IMAGE_PARAM_HUFFMANTTABLETYPE; - -/** @} */ -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_Index.h b/subprojects/gst-omx/omx/openmax/OMX_Index.h deleted file mode 100644 index 44d4ea76d2..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Index.h +++ /dev/null @@ -1,258 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** @file OMX_Index.h - OpenMax IL version 1.1.2 - * The OMX_Index header file contains the definitions for both applications - * and components . - */ - - -#ifndef OMX_Index_h -#define OMX_Index_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - -/* Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ -#include - - -/** The OMX_INDEXTYPE enumeration is used to select a structure when either - * getting or setting parameters and/or configuration data. Each entry in - * this enumeration maps to an OMX specified structure. When the - * OMX_GetParameter, OMX_SetParameter, OMX_GetConfig or OMX_SetConfig methods - * are used, the second parameter will always be an entry from this enumeration - * and the third entry will be the structure shown in the comments for the entry. - * For example, if the application is initializing a cropping function, the - * OMX_SetConfig command would have OMX_IndexConfigCommonInputCrop as the second parameter - * and would send a pointer to an initialized OMX_RECTTYPE structure as the - * third parameter. - * - * The enumeration entries named with the OMX_Config prefix are sent using - * the OMX_SetConfig command and the enumeration entries named with the - * OMX_PARAM_ prefix are sent using the OMX_SetParameter command. - */ -typedef enum OMX_INDEXTYPE { - - OMX_IndexComponentStartUnused = 0x01000000, - OMX_IndexParamPriorityMgmt, /**< reference: OMX_PRIORITYMGMTTYPE */ - OMX_IndexParamAudioInit, /**< reference: OMX_PORT_PARAM_TYPE */ - OMX_IndexParamImageInit, /**< reference: OMX_PORT_PARAM_TYPE */ - OMX_IndexParamVideoInit, /**< reference: OMX_PORT_PARAM_TYPE */ - OMX_IndexParamOtherInit, /**< reference: OMX_PORT_PARAM_TYPE */ - OMX_IndexParamNumAvailableStreams, /**< reference: OMX_PARAM_U32TYPE */ - OMX_IndexParamActiveStream, /**< reference: OMX_PARAM_U32TYPE */ - OMX_IndexParamSuspensionPolicy, /**< reference: OMX_PARAM_SUSPENSIONPOLICYTYPE */ - OMX_IndexParamComponentSuspended, /**< reference: OMX_PARAM_SUSPENSIONTYPE */ - OMX_IndexConfigCapturing, /**< reference: OMX_CONFIG_BOOLEANTYPE */ - OMX_IndexConfigCaptureMode, /**< reference: OMX_CONFIG_CAPTUREMODETYPE */ - OMX_IndexAutoPauseAfterCapture, /**< reference: OMX_CONFIG_BOOLEANTYPE */ - OMX_IndexParamContentURI, /**< reference: OMX_PARAM_CONTENTURITYPE */ - OMX_IndexParamCustomContentPipe, /**< reference: OMX_PARAM_CONTENTPIPETYPE */ - OMX_IndexParamDisableResourceConcealment, /**< reference: OMX_RESOURCECONCEALMENTTYPE */ - OMX_IndexConfigMetadataItemCount, /**< reference: OMX_CONFIG_METADATAITEMCOUNTTYPE */ - OMX_IndexConfigContainerNodeCount, /**< reference: OMX_CONFIG_CONTAINERNODECOUNTTYPE */ - OMX_IndexConfigMetadataItem, /**< reference: OMX_CONFIG_METADATAITEMTYPE */ - OMX_IndexConfigCounterNodeID, /**< reference: OMX_CONFIG_CONTAINERNODEIDTYPE */ - OMX_IndexParamMetadataFilterType, /**< reference: OMX_PARAM_METADATAFILTERTYPE */ - OMX_IndexParamMetadataKeyFilter, /**< reference: OMX_PARAM_METADATAFILTERTYPE */ - OMX_IndexConfigPriorityMgmt, /**< reference: OMX_PRIORITYMGMTTYPE */ - OMX_IndexParamStandardComponentRole, /**< reference: OMX_PARAM_COMPONENTROLETYPE */ - - OMX_IndexPortStartUnused = 0x02000000, - OMX_IndexParamPortDefinition, /**< reference: OMX_PARAM_PORTDEFINITIONTYPE */ - OMX_IndexParamCompBufferSupplier, /**< reference: OMX_PARAM_BUFFERSUPPLIERTYPE */ - OMX_IndexReservedStartUnused = 0x03000000, - - /* Audio parameters and configurations */ - OMX_IndexAudioStartUnused = 0x04000000, - OMX_IndexParamAudioPortFormat, /**< reference: OMX_AUDIO_PARAM_PORTFORMATTYPE */ - OMX_IndexParamAudioPcm, /**< reference: OMX_AUDIO_PARAM_PCMMODETYPE */ - OMX_IndexParamAudioAac, /**< reference: OMX_AUDIO_PARAM_AACPROFILETYPE */ - OMX_IndexParamAudioRa, /**< reference: OMX_AUDIO_PARAM_RATYPE */ - OMX_IndexParamAudioMp3, /**< reference: OMX_AUDIO_PARAM_MP3TYPE */ - OMX_IndexParamAudioAdpcm, /**< reference: OMX_AUDIO_PARAM_ADPCMTYPE */ - OMX_IndexParamAudioG723, /**< reference: OMX_AUDIO_PARAM_G723TYPE */ - OMX_IndexParamAudioG729, /**< reference: OMX_AUDIO_PARAM_G729TYPE */ - OMX_IndexParamAudioAmr, /**< reference: OMX_AUDIO_PARAM_AMRTYPE */ - OMX_IndexParamAudioWma, /**< reference: OMX_AUDIO_PARAM_WMATYPE */ - OMX_IndexParamAudioSbc, /**< reference: OMX_AUDIO_PARAM_SBCTYPE */ - OMX_IndexParamAudioMidi, /**< reference: OMX_AUDIO_PARAM_MIDITYPE */ - OMX_IndexParamAudioGsm_FR, /**< reference: OMX_AUDIO_PARAM_GSMFRTYPE */ - OMX_IndexParamAudioMidiLoadUserSound, /**< reference: OMX_AUDIO_PARAM_MIDILOADUSERSOUNDTYPE */ - OMX_IndexParamAudioG726, /**< reference: OMX_AUDIO_PARAM_G726TYPE */ - OMX_IndexParamAudioGsm_EFR, /**< reference: OMX_AUDIO_PARAM_GSMEFRTYPE */ - OMX_IndexParamAudioGsm_HR, /**< reference: OMX_AUDIO_PARAM_GSMHRTYPE */ - OMX_IndexParamAudioPdc_FR, /**< reference: OMX_AUDIO_PARAM_PDCFRTYPE */ - OMX_IndexParamAudioPdc_EFR, /**< reference: OMX_AUDIO_PARAM_PDCEFRTYPE */ - OMX_IndexParamAudioPdc_HR, /**< reference: OMX_AUDIO_PARAM_PDCHRTYPE */ - OMX_IndexParamAudioTdma_FR, /**< reference: OMX_AUDIO_PARAM_TDMAFRTYPE */ - OMX_IndexParamAudioTdma_EFR, /**< reference: OMX_AUDIO_PARAM_TDMAEFRTYPE */ - OMX_IndexParamAudioQcelp8, /**< reference: OMX_AUDIO_PARAM_QCELP8TYPE */ - OMX_IndexParamAudioQcelp13, /**< reference: OMX_AUDIO_PARAM_QCELP13TYPE */ - OMX_IndexParamAudioEvrc, /**< reference: OMX_AUDIO_PARAM_EVRCTYPE */ - OMX_IndexParamAudioSmv, /**< reference: OMX_AUDIO_PARAM_SMVTYPE */ - OMX_IndexParamAudioVorbis, /**< reference: OMX_AUDIO_PARAM_VORBISTYPE */ - - OMX_IndexConfigAudioMidiImmediateEvent, /**< reference: OMX_AUDIO_CONFIG_MIDIIMMEDIATEEVENTTYPE */ - OMX_IndexConfigAudioMidiControl, /**< reference: OMX_AUDIO_CONFIG_MIDICONTROLTYPE */ - OMX_IndexConfigAudioMidiSoundBankProgram, /**< reference: OMX_AUDIO_CONFIG_MIDISOUNDBANKPROGRAMTYPE */ - OMX_IndexConfigAudioMidiStatus, /**< reference: OMX_AUDIO_CONFIG_MIDISTATUSTYPE */ - OMX_IndexConfigAudioMidiMetaEvent, /**< reference: OMX_AUDIO_CONFIG_MIDIMETAEVENTTYPE */ - OMX_IndexConfigAudioMidiMetaEventData, /**< reference: OMX_AUDIO_CONFIG_MIDIMETAEVENTDATATYPE */ - OMX_IndexConfigAudioVolume, /**< reference: OMX_AUDIO_CONFIG_VOLUMETYPE */ - OMX_IndexConfigAudioBalance, /**< reference: OMX_AUDIO_CONFIG_BALANCETYPE */ - OMX_IndexConfigAudioChannelMute, /**< reference: OMX_AUDIO_CONFIG_CHANNELMUTETYPE */ - OMX_IndexConfigAudioMute, /**< reference: OMX_AUDIO_CONFIG_MUTETYPE */ - OMX_IndexConfigAudioLoudness, /**< reference: OMX_AUDIO_CONFIG_LOUDNESSTYPE */ - OMX_IndexConfigAudioEchoCancelation, /**< reference: OMX_AUDIO_CONFIG_ECHOCANCELATIONTYPE */ - OMX_IndexConfigAudioNoiseReduction, /**< reference: OMX_AUDIO_CONFIG_NOISEREDUCTIONTYPE */ - OMX_IndexConfigAudioBass, /**< reference: OMX_AUDIO_CONFIG_BASSTYPE */ - OMX_IndexConfigAudioTreble, /**< reference: OMX_AUDIO_CONFIG_TREBLETYPE */ - OMX_IndexConfigAudioStereoWidening, /**< reference: OMX_AUDIO_CONFIG_STEREOWIDENINGTYPE */ - OMX_IndexConfigAudioChorus, /**< reference: OMX_AUDIO_CONFIG_CHORUSTYPE */ - OMX_IndexConfigAudioEqualizer, /**< reference: OMX_AUDIO_CONFIG_EQUALIZERTYPE */ - OMX_IndexConfigAudioReverberation, /**< reference: OMX_AUDIO_CONFIG_REVERBERATIONTYPE */ - OMX_IndexConfigAudioChannelVolume, /**< reference: OMX_AUDIO_CONFIG_CHANNELVOLUMETYPE */ - - /* Image specific parameters and configurations */ - OMX_IndexImageStartUnused = 0x05000000, - OMX_IndexParamImagePortFormat, /**< reference: OMX_IMAGE_PARAM_PORTFORMATTYPE */ - OMX_IndexParamFlashControl, /**< reference: OMX_IMAGE_PARAM_FLASHCONTROLTYPE */ - OMX_IndexConfigFocusControl, /**< reference: OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE */ - OMX_IndexParamQFactor, /**< reference: OMX_IMAGE_PARAM_QFACTORTYPE */ - OMX_IndexParamQuantizationTable, /**< reference: OMX_IMAGE_PARAM_QUANTIZATIONTABLETYPE */ - OMX_IndexParamHuffmanTable, /**< reference: OMX_IMAGE_PARAM_HUFFMANTTABLETYPE */ - OMX_IndexConfigFlashControl, /**< reference: OMX_IMAGE_PARAM_FLASHCONTROLTYPE */ - - /* Video specific parameters and configurations */ - OMX_IndexVideoStartUnused = 0x06000000, - OMX_IndexParamVideoPortFormat, /**< reference: OMX_VIDEO_PARAM_PORTFORMATTYPE */ - OMX_IndexParamVideoQuantization, /**< reference: OMX_VIDEO_PARAM_QUANTIZATIONTYPE */ - OMX_IndexParamVideoFastUpdate, /**< reference: OMX_VIDEO_PARAM_VIDEOFASTUPDATETYPE */ - OMX_IndexParamVideoBitrate, /**< reference: OMX_VIDEO_PARAM_BITRATETYPE */ - OMX_IndexParamVideoMotionVector, /**< reference: OMX_VIDEO_PARAM_MOTIONVECTORTYPE */ - OMX_IndexParamVideoIntraRefresh, /**< reference: OMX_VIDEO_PARAM_INTRAREFRESHTYPE */ - OMX_IndexParamVideoErrorCorrection, /**< reference: OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE */ - OMX_IndexParamVideoVBSMC, /**< reference: OMX_VIDEO_PARAM_VBSMCTYPE */ - OMX_IndexParamVideoMpeg2, /**< reference: OMX_VIDEO_PARAM_MPEG2TYPE */ - OMX_IndexParamVideoMpeg4, /**< reference: OMX_VIDEO_PARAM_MPEG4TYPE */ - OMX_IndexParamVideoWmv, /**< reference: OMX_VIDEO_PARAM_WMVTYPE */ - OMX_IndexParamVideoRv, /**< reference: OMX_VIDEO_PARAM_RVTYPE */ - OMX_IndexParamVideoAvc, /**< reference: OMX_VIDEO_PARAM_AVCTYPE */ - OMX_IndexParamVideoH263, /**< reference: OMX_VIDEO_PARAM_H263TYPE */ - OMX_IndexParamVideoProfileLevelQuerySupported, /**< reference: OMX_VIDEO_PARAM_PROFILELEVELTYPE */ - OMX_IndexParamVideoProfileLevelCurrent, /**< reference: OMX_VIDEO_PARAM_PROFILELEVELTYPE */ - OMX_IndexConfigVideoBitrate, /**< reference: OMX_VIDEO_CONFIG_BITRATETYPE */ - OMX_IndexConfigVideoFramerate, /**< reference: OMX_CONFIG_FRAMERATETYPE */ - OMX_IndexConfigVideoIntraVOPRefresh, /**< reference: OMX_CONFIG_INTRAREFRESHVOPTYPE */ - OMX_IndexConfigVideoIntraMBRefresh, /**< reference: OMX_CONFIG_MACROBLOCKERRORMAPTYPE */ - OMX_IndexConfigVideoMBErrorReporting, /**< reference: OMX_CONFIG_MBERRORREPORTINGTYPE */ - OMX_IndexParamVideoMacroblocksPerFrame, /**< reference: OMX_PARAM_MACROBLOCKSTYPE */ - OMX_IndexConfigVideoMacroBlockErrorMap, /**< reference: OMX_CONFIG_MACROBLOCKERRORMAPTYPE */ - OMX_IndexParamVideoSliceFMO, /**< reference: OMX_VIDEO_PARAM_AVCSLICEFMO */ - OMX_IndexConfigVideoAVCIntraPeriod, /**< reference: OMX_VIDEO_CONFIG_AVCINTRAPERIOD */ - OMX_IndexConfigVideoNalSize, /**< reference: OMX_VIDEO_CONFIG_NALSIZE */ - - /* Image & Video common Configurations */ - OMX_IndexCommonStartUnused = 0x07000000, - OMX_IndexParamCommonDeblocking, /**< reference: OMX_PARAM_DEBLOCKINGTYPE */ - OMX_IndexParamCommonSensorMode, /**< reference: OMX_PARAM_SENSORMODETYPE */ - OMX_IndexParamCommonInterleave, /**< reference: OMX_PARAM_INTERLEAVETYPE */ - OMX_IndexConfigCommonColorFormatConversion, /**< reference: OMX_CONFIG_COLORCONVERSIONTYPE */ - OMX_IndexConfigCommonScale, /**< reference: OMX_CONFIG_SCALEFACTORTYPE */ - OMX_IndexConfigCommonImageFilter, /**< reference: OMX_CONFIG_IMAGEFILTERTYPE */ - OMX_IndexConfigCommonColorEnhancement, /**< reference: OMX_CONFIG_COLORENHANCEMENTTYPE */ - OMX_IndexConfigCommonColorKey, /**< reference: OMX_CONFIG_COLORKEYTYPE */ - OMX_IndexConfigCommonColorBlend, /**< reference: OMX_CONFIG_COLORBLENDTYPE */ - OMX_IndexConfigCommonFrameStabilisation,/**< reference: OMX_CONFIG_FRAMESTABTYPE */ - OMX_IndexConfigCommonRotate, /**< reference: OMX_CONFIG_ROTATIONTYPE */ - OMX_IndexConfigCommonMirror, /**< reference: OMX_CONFIG_MIRRORTYPE */ - OMX_IndexConfigCommonOutputPosition, /**< reference: OMX_CONFIG_POINTTYPE */ - OMX_IndexConfigCommonInputCrop, /**< reference: OMX_CONFIG_RECTTYPE */ - OMX_IndexConfigCommonOutputCrop, /**< reference: OMX_CONFIG_RECTTYPE */ - OMX_IndexConfigCommonDigitalZoom, /**< reference: OMX_CONFIG_SCALEFACTORTYPE */ - OMX_IndexConfigCommonOpticalZoom, /**< reference: OMX_CONFIG_SCALEFACTORTYPE*/ - OMX_IndexConfigCommonWhiteBalance, /**< reference: OMX_CONFIG_WHITEBALCONTROLTYPE */ - OMX_IndexConfigCommonExposure, /**< reference: OMX_CONFIG_EXPOSURECONTROLTYPE */ - OMX_IndexConfigCommonContrast, /**< reference: OMX_CONFIG_CONTRASTTYPE */ - OMX_IndexConfigCommonBrightness, /**< reference: OMX_CONFIG_BRIGHTNESSTYPE */ - OMX_IndexConfigCommonBacklight, /**< reference: OMX_CONFIG_BACKLIGHTTYPE */ - OMX_IndexConfigCommonGamma, /**< reference: OMX_CONFIG_GAMMATYPE */ - OMX_IndexConfigCommonSaturation, /**< reference: OMX_CONFIG_SATURATIONTYPE */ - OMX_IndexConfigCommonLightness, /**< reference: OMX_CONFIG_LIGHTNESSTYPE */ - OMX_IndexConfigCommonExclusionRect, /**< reference: OMX_CONFIG_RECTTYPE */ - OMX_IndexConfigCommonDithering, /**< reference: OMX_CONFIG_DITHERTYPE */ - OMX_IndexConfigCommonPlaneBlend, /**< reference: OMX_CONFIG_PLANEBLENDTYPE */ - OMX_IndexConfigCommonExposureValue, /**< reference: OMX_CONFIG_EXPOSUREVALUETYPE */ - OMX_IndexConfigCommonOutputSize, /**< reference: OMX_FRAMESIZETYPE */ - OMX_IndexParamCommonExtraQuantData, /**< reference: OMX_OTHER_EXTRADATATYPE */ - OMX_IndexConfigCommonFocusRegion, /**< reference: OMX_CONFIG_FOCUSREGIONTYPE */ - OMX_IndexConfigCommonFocusStatus, /**< reference: OMX_PARAM_FOCUSSTATUSTYPE */ - OMX_IndexConfigCommonTransitionEffect, /**< reference: OMX_CONFIG_TRANSITIONEFFECTTYPE */ - - /* Reserved Configuration range */ - OMX_IndexOtherStartUnused = 0x08000000, - OMX_IndexParamOtherPortFormat, /**< reference: OMX_OTHER_PARAM_PORTFORMATTYPE */ - OMX_IndexConfigOtherPower, /**< reference: OMX_OTHER_CONFIG_POWERTYPE */ - OMX_IndexConfigOtherStats, /**< reference: OMX_OTHER_CONFIG_STATSTYPE */ - - - /* Reserved Time range */ - OMX_IndexTimeStartUnused = 0x09000000, - OMX_IndexConfigTimeScale, /**< reference: OMX_TIME_CONFIG_SCALETYPE */ - OMX_IndexConfigTimeClockState, /**< reference: OMX_TIME_CONFIG_CLOCKSTATETYPE */ - OMX_IndexConfigTimeActiveRefClock, /**< reference: OMX_TIME_CONFIG_ACTIVEREFCLOCKTYPE */ - OMX_IndexConfigTimeCurrentMediaTime, /**< reference: OMX_TIME_CONFIG_TIMESTAMPTYPE (read only) */ - OMX_IndexConfigTimeCurrentWallTime, /**< reference: OMX_TIME_CONFIG_TIMESTAMPTYPE (read only) */ - OMX_IndexConfigTimeCurrentAudioReference, /**< reference: OMX_TIME_CONFIG_TIMESTAMPTYPE (write only) */ - OMX_IndexConfigTimeCurrentVideoReference, /**< reference: OMX_TIME_CONFIG_TIMESTAMPTYPE (write only) */ - OMX_IndexConfigTimeMediaTimeRequest, /**< reference: OMX_TIME_CONFIG_MEDIATIMEREQUESTTYPE (write only) */ - OMX_IndexConfigTimeClientStartTime, /** - - -/** Khronos standard extension indices. - -This enum lists the current Khronos extension indices to OpenMAX IL. -*/ -typedef enum OMX_INDEXEXTTYPE { - - /* Component parameters and configurations */ - OMX_IndexExtComponentStartUnused = OMX_IndexKhronosExtensions + 0x00100000, - OMX_IndexConfigCallbackRequest, /**< reference: OMX_CONFIG_CALLBACKREQUESTTYPE */ - OMX_IndexConfigCommitMode, /**< reference: OMX_CONFIG_COMMITMODETYPE */ - OMX_IndexConfigCommit, /**< reference: OMX_CONFIG_COMMITTYPE */ - - /* Port parameters and configurations */ - OMX_IndexExtPortStartUnused = OMX_IndexKhronosExtensions + 0x00200000, - - /* Audio parameters and configurations */ - OMX_IndexExtAudioStartUnused = OMX_IndexKhronosExtensions + 0x00400000, - - /* Image parameters and configurations */ - OMX_IndexExtImageStartUnused = OMX_IndexKhronosExtensions + 0x00500000, - - /* Video parameters and configurations */ - OMX_IndexExtVideoStartUnused = OMX_IndexKhronosExtensions + 0x00600000, - OMX_IndexParamNalStreamFormatSupported, /**< reference: OMX_NALSTREAMFORMATTYPE */ - OMX_IndexParamNalStreamFormat, /**< reference: OMX_NALSTREAMFORMATTYPE */ - OMX_IndexParamNalStreamFormatSelect, /**< reference: OMX_NALSTREAMFORMATTYPE */ - - /* Image & Video common configurations */ - OMX_IndexExtCommonStartUnused = OMX_IndexKhronosExtensions + 0x00700000, - - /* Other configurations */ - OMX_IndexExtOtherStartUnused = OMX_IndexKhronosExtensions + 0x00800000, - - /* Time configurations */ - OMX_IndexExtTimeStartUnused = OMX_IndexKhronosExtensions + 0x00900000, - - OMX_IndexExtMax = 0x7FFFFFFF -} OMX_INDEXEXTTYPE; - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* OMX_IndexExt_h */ -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_Other.h b/subprojects/gst-omx/omx/openmax/OMX_Other.h deleted file mode 100644 index caf7f38448..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Other.h +++ /dev/null @@ -1,337 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** @file OMX_Other.h - OpenMax IL version 1.1.2 - * The structures needed by Other components to exchange - * parameters and configuration data with the components. - */ - -#ifndef OMX_Other_h -#define OMX_Other_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - -/* Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ - -#include - - -/** - * Enumeration of possible data types which match to multiple domains or no - * domain at all. For types which are vendor specific, a value above - * OMX_OTHER_VENDORTSTART should be used. - */ -typedef enum OMX_OTHER_FORMATTYPE { - OMX_OTHER_FormatTime = 0, /**< Transmission of various timestamps, elapsed time, - time deltas, etc */ - OMX_OTHER_FormatPower, /**< Perhaps used for enabling/disabling power - management, setting clocks? */ - OMX_OTHER_FormatStats, /**< Could be things such as frame rate, frames - dropped, etc */ - OMX_OTHER_FormatBinary, /**< Arbitrary binary data */ - OMX_OTHER_FormatVendorReserved = 1000, /**< Starting value for vendor specific - formats */ - - OMX_OTHER_FormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_OTHER_FormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_OTHER_FormatMax = 0x7FFFFFFF -} OMX_OTHER_FORMATTYPE; - -/** - * Enumeration of seek modes. - */ -typedef enum OMX_TIME_SEEKMODETYPE { - OMX_TIME_SeekModeFast = 0, /**< Prefer seeking to an approximation - * of the requested seek position over - * the actual seek position if it - * results in a faster seek. */ - OMX_TIME_SeekModeAccurate, /**< Prefer seeking to the actual seek - * position over an approximation - * of the requested seek position even - * if it results in a slower seek. */ - OMX_TIME_SeekModeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_TIME_SeekModeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_TIME_SeekModeMax = 0x7FFFFFFF -} OMX_TIME_SEEKMODETYPE; - -/* Structure representing the seekmode of the component */ -typedef struct OMX_TIME_CONFIG_SEEKMODETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_TIME_SEEKMODETYPE eType; /**< The seek mode */ -} OMX_TIME_CONFIG_SEEKMODETYPE; - -/** Structure representing a time stamp used with the following configs - * on the Clock Component (CC): - * - * OMX_IndexConfigTimeCurrentWallTime: query of the CCs current wall - * time - * OMX_IndexConfigTimeCurrentMediaTime: query of the CCs current media - * time - * OMX_IndexConfigTimeCurrentAudioReference and - * OMX_IndexConfigTimeCurrentVideoReference: audio/video reference - * clock sending SC its reference time - * OMX_IndexConfigTimeClientStartTime: a Clock Component client sends - * this structure to the Clock Component via a SetConfig on its - * client port when it receives a buffer with - * OMX_BUFFERFLAG_STARTTIME set. It must use the timestamp - * specified by that buffer for nStartTimestamp. - * - * Its also used with the following config on components in general: - * - * OMX_IndexConfigTimePosition: IL client querying component position - * (GetConfig) or commanding a component to seek to the given location - * (SetConfig) - */ -typedef struct OMX_TIME_CONFIG_TIMESTAMPTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version - * information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_TICKS nTimestamp; /**< timestamp .*/ -} OMX_TIME_CONFIG_TIMESTAMPTYPE; - -/** Enumeration of possible reference clocks to the media time. */ -typedef enum OMX_TIME_UPDATETYPE { - OMX_TIME_UpdateRequestFulfillment, /**< Update is the fulfillment of a media time request. */ - OMX_TIME_UpdateScaleChanged, /**< Update was generated because the scale chagned. */ - OMX_TIME_UpdateClockStateChanged, /**< Update was generated because the clock state changed. */ - OMX_TIME_UpdateKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_TIME_UpdateVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_TIME_UpdateMax = 0x7FFFFFFF -} OMX_TIME_UPDATETYPE; - -/** Enumeration of possible reference clocks to the media time. */ -typedef enum OMX_TIME_REFCLOCKTYPE { - OMX_TIME_RefClockNone, /**< Use no references. */ - OMX_TIME_RefClockAudio, /**< Use references sent through OMX_IndexConfigTimeCurrentAudioReference */ - OMX_TIME_RefClockVideo, /**< Use references sent through OMX_IndexConfigTimeCurrentVideoReference */ - OMX_TIME_RefClockKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_TIME_RefClockVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_TIME_RefClockMax = 0x7FFFFFFF -} OMX_TIME_REFCLOCKTYPE; - -/** Enumeration of clock states. */ -typedef enum OMX_TIME_CLOCKSTATE { - OMX_TIME_ClockStateRunning, /**< Clock running. */ - OMX_TIME_ClockStateWaitingForStartTime, /**< Clock waiting until the - * prescribed clients emit their - * start time. */ - OMX_TIME_ClockStateStopped, /**< Clock stopped. */ - OMX_TIME_ClockStateKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_TIME_ClockStateVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_TIME_ClockStateMax = 0x7FFFFFFF -} OMX_TIME_CLOCKSTATE; - -/** Structure representing a media time request to the clock component. - * - * A client component sends this structure to the Clock Component via a SetConfig - * on its client port to specify a media timestamp the Clock Component - * should emit. The Clock Component should fulfill the request by sending a - * OMX_TIME_MEDIATIMETYPE when its media clock matches the requested - * timestamp. - * - * The client may require a media time request be fulfilled slightly - * earlier than the media time specified. In this case the client specifies - * an offset which is equal to the difference between wall time corresponding - * to the requested media time and the wall time when it will be - * fulfilled. - * - * A client component may uses these requests and the OMX_TIME_MEDIATIMETYPE to - * time events according to timestamps. If a client must perform an operation O at - * a time T (e.g. deliver a video frame at its corresponding timestamp), it makes a - * media time request at T (perhaps specifying an offset to ensure the request fulfillment - * is a little early). When the clock component passes the resulting OMX_TIME_MEDIATIMETYPE - * structure back to the client component, the client may perform operation O (perhaps having - * to wait a slight amount more time itself as specified by the return values). - */ - -typedef struct OMX_TIME_CONFIG_MEDIATIMEREQUESTTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< port that this structure applies to */ - OMX_PTR pClientPrivate; /**< Client private data to disabiguate this media time - * from others (e.g. the number of the frame to deliver). - * Duplicated in the media time structure that fulfills - * this request. A value of zero is reserved for time scale - * updates. */ - OMX_TICKS nMediaTimestamp; /**< Media timestamp requested.*/ - OMX_TICKS nOffset; /**< Amount of wall clock time by which this - * request should be fulfilled early */ -} OMX_TIME_CONFIG_MEDIATIMEREQUESTTYPE; - -/**< Structure sent from the clock component client either when fulfilling - * a media time request or when the time scale has changed. - * - * In the former case the Clock Component fills this structure and times its emission - * to a client component (via the client port) according to the corresponding media - * time request sent by the client. The Clock Component should time the emission to occur - * when the requested timestamp matches the Clock Component's media time but also the - * prescribed offset early. - * - * Upon scale changes the clock component clears the nClientPrivate data, sends the current - * media time and sets the nScale to the new scale via the client port. It emits a - * OMX_TIME_MEDIATIMETYPE to all clients independent of any requests. This allows clients to - * alter processing to accomodate scaling. For instance a video component might skip inter-frames - * in the case of extreme fastforward. Likewise an audio component might add or remove samples - * from an audio frame to scale audio data. - * - * It is expected that some clock components may not be able to fulfill requests - * at exactly the prescribed time. This is acceptable so long as the request is - * fulfilled at least as early as described and not later. This structure provides - * fields the client may use to wait for the remaining time. - * - * The client may use either the nOffset or nWallTimeAtMedia fields to determine the - * wall time until the nMediaTimestamp actually occurs. In the latter case the - * client can get a more accurate value for offset by getting the current wall - * from the cloc component and subtracting it from nWallTimeAtMedia. - */ - -typedef struct OMX_TIME_MEDIATIMETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nClientPrivate; /**< Client private data to disabiguate this media time - * from others. Copied from the media time request. - * A value of zero is reserved for time scale updates. */ - OMX_TIME_UPDATETYPE eUpdateType; /**< Reason for the update */ - OMX_TICKS nMediaTimestamp; /**< Media time requested. If no media time was - * requested then this is the current media time. */ - OMX_TICKS nOffset; /**< Amount of wall clock time by which this - * request was actually fulfilled early */ - - OMX_TICKS nWallTimeAtMediaTime; /**< Wall time corresponding to nMediaTimeStamp. - * A client may compare this value to current - * media time obtained from the Clock Component to determine - * the wall time until the media timestamp is really - * current. */ - OMX_S32 xScale; /**< Current media time scale in Q16 format. */ - OMX_TIME_CLOCKSTATE eState; /* Seeking Change. Added 7/12.*/ - /**< State of the media time. */ -} OMX_TIME_MEDIATIMETYPE; - -/** Structure representing the current media time scale factor. Applicable only to clock - * component, other components see scale changes via OMX_TIME_MEDIATIMETYPE buffers sent via - * the clock component client ports. Upon recieving this config the clock component changes - * the rate by which the media time increases or decreases effectively implementing trick modes. - */ -typedef struct OMX_TIME_CONFIG_SCALETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_S32 xScale; /**< This is a value in Q16 format which is used for - * scaling the media time */ -} OMX_TIME_CONFIG_SCALETYPE; - -/** Bits used to identify a clock port. Used in OMX_TIME_CONFIG_CLOCKSTATETYPEs nWaitMask field */ -#define OMX_CLOCKPORT0 0x00000001 -#define OMX_CLOCKPORT1 0x00000002 -#define OMX_CLOCKPORT2 0x00000004 -#define OMX_CLOCKPORT3 0x00000008 -#define OMX_CLOCKPORT4 0x00000010 -#define OMX_CLOCKPORT5 0x00000020 -#define OMX_CLOCKPORT6 0x00000040 -#define OMX_CLOCKPORT7 0x00000080 - -/** Structure representing the current mode of the media clock. - * IL Client uses this config to change or query the mode of the - * media clock of the clock component. Applicable only to clock - * component. - * - * On a SetConfig if eState is OMX_TIME_ClockStateRunning media time - * starts immediately at the prescribed start time. If - * OMX_TIME_ClockStateWaitingForStartTime the Clock Component ignores - * the given nStartTime and waits for all clients specified in the - * nWaitMask to send starttimes (via - * OMX_IndexConfigTimeClientStartTime). The Clock Component then starts - * the media clock using the earliest start time supplied. */ -typedef struct OMX_TIME_CONFIG_CLOCKSTATETYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version - * information */ - OMX_TIME_CLOCKSTATE eState; /**< State of the media time. */ - OMX_TICKS nStartTime; /**< Start time of the media time. */ - OMX_TICKS nOffset; /**< Time to offset the media time by - * (e.g. preroll). Media time will be - * reported to be nOffset ticks earlier. - */ - OMX_U32 nWaitMask; /**< Mask of OMX_CLOCKPORT values. */ -} OMX_TIME_CONFIG_CLOCKSTATETYPE; - -/** Structure representing the reference clock currently being used to - * compute media time. IL client uses this config to change or query the - * clock component's active reference clock */ -typedef struct OMX_TIME_CONFIG_ACTIVEREFCLOCKTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_TIME_REFCLOCKTYPE eClock; /**< Reference clock used to compute media time */ -} OMX_TIME_CONFIG_ACTIVEREFCLOCKTYPE; - -/** Descriptor for setting specifics of power type. - * Note: this structure is listed for backwards compatibility. */ -typedef struct OMX_OTHER_CONFIG_POWERTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_BOOL bEnablePM; /**< Flag to enable Power Management */ -} OMX_OTHER_CONFIG_POWERTYPE; - - -/** Descriptor for setting specifics of stats type. - * Note: this structure is listed for backwards compatibility. */ -typedef struct OMX_OTHER_CONFIG_STATSTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - /* what goes here */ -} OMX_OTHER_CONFIG_STATSTYPE; - - -/** - * The PortDefinition structure is used to define all of the parameters - * necessary for the compliant component to setup an input or an output other - * path. - */ -typedef struct OMX_OTHER_PORTDEFINITIONTYPE { - OMX_OTHER_FORMATTYPE eFormat; /**< Type of data expected for this channel */ -} OMX_OTHER_PORTDEFINITIONTYPE; - -/** Port format parameter. This structure is used to enumerate - * the various data input/output format supported by the port. - */ -typedef struct OMX_OTHER_PARAM_PORTFORMATTYPE { - OMX_U32 nSize; /**< size of the structure in bytes */ - OMX_VERSIONTYPE nVersion; /**< OMX specification version information */ - OMX_U32 nPortIndex; /**< Indicates which port to set */ - OMX_U32 nIndex; /**< Indicates the enumeration index for the format from 0x0 to N-1 */ - OMX_OTHER_FORMATTYPE eFormat; /**< Type of data expected for this channel */ -} OMX_OTHER_PARAM_PORTFORMATTYPE; - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_Types.h b/subprojects/gst-omx/omx/openmax/OMX_Types.h deleted file mode 100644 index 8698358786..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Types.h +++ /dev/null @@ -1,359 +0,0 @@ -/* - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_Types.h - OpenMax IL version 1.1.2 - * The OMX_Types header file contains the primitive type definitions used by - * the core, the application and the component. This file may need to be - * modified to be used on systems that do not have "char" set to 8 bits, - * "short" set to 16 bits and "long" set to 32 bits. - */ - -#ifndef OMX_Types_h -#define OMX_Types_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - -/** The OMX_API and OMX_APIENTRY are platform specific definitions used - * to declare OMX function prototypes. They are modified to meet the - * requirements for a particular platform */ -#ifdef __SYMBIAN32__ -# ifdef __OMX_EXPORTS -# define OMX_API __declspec(dllexport) -# else -# ifdef _WIN32 -# define OMX_API __declspec(dllexport) -# else -# define OMX_API __declspec(dllimport) -# endif -# endif -#else -# ifdef _WIN32 -# ifdef __OMX_EXPORTS -# define OMX_API __declspec(dllexport) -# else -# define OMX_API __declspec(dllimport) -# endif -# else -# ifdef __OMX_EXPORTS -# define OMX_API -# else -# define OMX_API extern -# endif -# endif -#endif - -#ifndef OMX_APIENTRY -#define OMX_APIENTRY -#endif - -/** OMX_IN is used to identify inputs to an OMX function. This designation - will also be used in the case of a pointer that points to a parameter - that is used as an output. */ -#ifndef OMX_IN -#define OMX_IN -#endif - -/** OMX_OUT is used to identify outputs from an OMX function. This - designation will also be used in the case of a pointer that points - to a parameter that is used as an input. */ -#ifndef OMX_OUT -#define OMX_OUT -#endif - - -/** OMX_INOUT is used to identify parameters that may be either inputs or - outputs from an OMX function at the same time. This designation will - also be used in the case of a pointer that points to a parameter that - is used both as an input and an output. */ -#ifndef OMX_INOUT -#define OMX_INOUT -#endif - -/** OMX_ALL is used to as a wildcard to select all entities of the same type - * when specifying the index, or referring to a object by an index. (i.e. - * use OMX_ALL to indicate all N channels). When used as a port index - * for a config or parameter this OMX_ALL denotes that the config or - * parameter applies to the entire component not just one port. */ -#define OMX_ALL 0xFFFFFFFF - -/** In the following we define groups that help building doxygen documentation */ - -/** @defgroup core OpenMAX IL core - * Functions and structure related to the OMX IL core - */ - - /** @defgroup comp OpenMAX IL component - * Functions and structure related to the OMX IL component - */ - -/** @defgroup rpm Resource and Policy Management - * Structures for resource and policy management of components - */ - -/** @defgroup buf Buffer Management - * Buffer handling functions and structures - */ - -/** @defgroup tun Tunneling - * @ingroup core comp - * Structures and functions to manage tunnels among component ports - */ - -/** @defgroup cp Content Pipes - * @ingroup core - */ - - /** @defgroup metadata Metadata handling - * - */ - -/** OMX_U8 is an 8 bit unsigned quantity that is byte aligned */ -typedef unsigned char OMX_U8; - -/** OMX_S8 is an 8 bit signed quantity that is byte aligned */ -typedef signed char OMX_S8; - -/** OMX_U16 is a 16 bit unsigned quantity that is 16 bit word aligned */ -typedef unsigned short OMX_U16; - -/** OMX_S16 is a 16 bit signed quantity that is 16 bit word aligned */ -typedef signed short OMX_S16; - -/** OMX_U32 is a 32 bit unsigned quantity that is 32 bit word aligned */ -typedef unsigned long OMX_U32; - -/** OMX_S32 is a 32 bit signed quantity that is 32 bit word aligned */ -typedef signed long OMX_S32; - - -/* Users with compilers that cannot accept the "long long" designation should - define the OMX_SKIP64BIT macro. It should be noted that this may cause - some components to fail to compile if the component was written to require - 64 bit integral types. However, these components would NOT compile anyway - since the compiler does not support the way the component was written. -*/ -#ifndef OMX_SKIP64BIT -#ifdef __SYMBIAN32__ -/** OMX_U64 is a 64 bit unsigned quantity that is 64 bit word aligned */ -typedef unsigned long long OMX_U64; - -/** OMX_S64 is a 64 bit signed quantity that is 64 bit word aligned */ -typedef signed long long OMX_S64; - -#elif defined(WIN32) - -/** OMX_U64 is a 64 bit unsigned quantity that is 64 bit word aligned */ -typedef unsigned __int64 OMX_U64; - -/** OMX_S64 is a 64 bit signed quantity that is 64 bit word aligned */ -typedef signed __int64 OMX_S64; - -#else /* WIN32 */ - -/** OMX_U64 is a 64 bit unsigned quantity that is 64 bit word aligned */ -typedef unsigned long long OMX_U64; - -/** OMX_S64 is a 64 bit signed quantity that is 64 bit word aligned */ -typedef signed long long OMX_S64; - -#endif /* WIN32 */ -#endif - - -/** The OMX_BOOL type is intended to be used to represent a true or a false - value when passing parameters to and from the OMX core and components. The - OMX_BOOL is a 32 bit quantity and is aligned on a 32 bit word boundary. - */ -typedef enum OMX_BOOL { - OMX_FALSE = 0, - OMX_TRUE = !OMX_FALSE, - OMX_BOOL_MAX = 0x7FFFFFFF -} OMX_BOOL; - -/** The OMX_PTR type is intended to be used to pass pointers between the OMX - applications and the OMX Core and components. This is a 32 bit pointer and - is aligned on a 32 bit boundary. - */ -typedef void* OMX_PTR; - -/** The OMX_STRING type is intended to be used to pass "C" type strings between - the application and the core and component. The OMX_STRING type is a 32 - bit pointer to a zero terminated string. The pointer is word aligned and - the string is byte aligned. - */ -typedef char* OMX_STRING; - -/** The OMX_BYTE type is intended to be used to pass arrays of bytes such as - buffers between the application and the component and core. The OMX_BYTE - type is a 32 bit pointer to a zero terminated string. The pointer is word - aligned and the string is byte aligned. - */ -typedef unsigned char* OMX_BYTE; - -/** OMX_UUIDTYPE is a very long unique identifier to uniquely identify - at runtime. This identifier should be generated by a component in a way - that guarantees that every instance of the identifier running on the system - is unique. */ -typedef unsigned char OMX_UUIDTYPE[128]; - -/** The OMX_DIRTYPE enumeration is used to indicate if a port is an input or - an output port. This enumeration is common across all component types. - */ -typedef enum OMX_DIRTYPE -{ - OMX_DirInput, /**< Port is an input port */ - OMX_DirOutput, /**< Port is an output port */ - OMX_DirMax = 0x7FFFFFFF -} OMX_DIRTYPE; - -/** The OMX_ENDIANTYPE enumeration is used to indicate the bit ordering - for numerical data (i.e. big endian, or little endian). - */ -typedef enum OMX_ENDIANTYPE -{ - OMX_EndianBig, /**< big endian */ - OMX_EndianLittle, /**< little endian */ - OMX_EndianMax = 0x7FFFFFFF -} OMX_ENDIANTYPE; - - -/** The OMX_NUMERICALDATATYPE enumeration is used to indicate if data - is signed or unsigned - */ -typedef enum OMX_NUMERICALDATATYPE -{ - OMX_NumericalDataSigned, /**< signed data */ - OMX_NumericalDataUnsigned, /**< unsigned data */ - OMX_NumercialDataMax = 0x7FFFFFFF -} OMX_NUMERICALDATATYPE; - - -/** Unsigned bounded value type */ -typedef struct OMX_BU32 { - OMX_U32 nValue; /**< actual value */ - OMX_U32 nMin; /**< minimum for value (i.e. nValue >= nMin) */ - OMX_U32 nMax; /**< maximum for value (i.e. nValue <= nMax) */ -} OMX_BU32; - - -/** Signed bounded value type */ -typedef struct OMX_BS32 { - OMX_S32 nValue; /**< actual value */ - OMX_S32 nMin; /**< minimum for value (i.e. nValue >= nMin) */ - OMX_S32 nMax; /**< maximum for value (i.e. nValue <= nMax) */ -} OMX_BS32; - - -/** Structure representing some time or duration in microseconds. This structure - * must be interpreted as a signed 64 bit value. The quantity is signed to accommodate - * negative deltas and preroll scenarios. The quantity is represented in microseconds - * to accomodate high resolution timestamps (e.g. DVD presentation timestamps based - * on a 90kHz clock) and to allow more accurate and synchronized delivery (e.g. - * individual audio samples delivered at 192 kHz). The quantity is 64 bit to - * accommodate a large dynamic range (signed 32 bit values would allow only for plus - * or minus 35 minutes). - * - * Implementations with limited precision may convert the signed 64 bit value to - * a signed 32 bit value internally but risk loss of precision. - */ -#ifndef OMX_SKIP64BIT -typedef OMX_S64 OMX_TICKS; -#else -typedef struct OMX_TICKS -{ - OMX_U32 nLowPart; /** low bits of the signed 64 bit tick value */ - OMX_U32 nHighPart; /** high bits of the signed 64 bit tick value */ -} OMX_TICKS; -#endif -#define OMX_TICKS_PER_SECOND 1000000 - -/** Define the public interface for the OMX Handle. The core will not use - this value internally, but the application should only use this value. - */ -typedef void* OMX_HANDLETYPE; - -typedef struct OMX_MARKTYPE -{ - OMX_HANDLETYPE hMarkTargetComponent; /**< The component that will - generate a mark event upon - processing the mark. */ - OMX_PTR pMarkData; /**< Application specific data associated with - the mark sent on a mark event to disambiguate - this mark from others. */ -} OMX_MARKTYPE; - - -/** OMX_NATIVE_DEVICETYPE is used to map a OMX video port to the - * platform & operating specific object used to reference the display - * or can be used by a audio port for native audio rendering */ -typedef void* OMX_NATIVE_DEVICETYPE; - -/** OMX_NATIVE_WINDOWTYPE is used to map a OMX video port to the - * platform & operating specific object used to reference the window */ -typedef void* OMX_NATIVE_WINDOWTYPE; - - -/** Define the OMX IL version that corresponds to this set of header files. - * We also define a combined version that can be used to write or compare - * values of the 32bit nVersion field, assuming a little endian architecture */ -#define OMX_VERSION_MAJOR 1 -#define OMX_VERSION_MINOR 1 -#define OMX_VERSION_REVISION 2 -#define OMX_VERSION_STEP 0 - -#define OMX_VERSION ((OMX_VERSION_STEP<<24) | (OMX_VERSION_REVISION<<16) | (OMX_VERSION_MINOR<<8) | OMX_VERSION_MAJOR) - - -/** The OMX_VERSIONTYPE union is used to specify the version for - a structure or component. For a component, the version is entirely - specified by the component vendor. Components doing the same function - from different vendors may or may not have the same version. For - structures, the version shall be set by the entity that allocates the - structure. For structures specified in the OMX 1.1 specification, the - value of the version shall be set to 1.1.0.0 in all cases. Access to the - OMX_VERSIONTYPE can be by a single 32 bit access (e.g. by nVersion) or - by accessing one of the structure elements to, for example, check only - the Major revision. - */ -typedef union OMX_VERSIONTYPE -{ - struct - { - OMX_U8 nVersionMajor; /**< Major version accessor element */ - OMX_U8 nVersionMinor; /**< Minor version accessor element */ - OMX_U8 nRevision; /**< Revision version accessor element */ - OMX_U8 nStep; /**< Step version accessor element */ - } s; - OMX_U32 nVersion; /**< 32 bit value to make accessing the - version easily done in a single word - size copy/compare operation */ -} OMX_VERSIONTYPE; - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ diff --git a/subprojects/gst-omx/omx/openmax/OMX_Video.h b/subprojects/gst-omx/omx/openmax/OMX_Video.h deleted file mode 100644 index 163e45081f..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_Video.h +++ /dev/null @@ -1,1060 +0,0 @@ -/** - * Copyright (c) 2008 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** - * @file OMX_Video.h - OpenMax IL version 1.1.2 - * The structures is needed by Video components to exchange parameters - * and configuration data with OMX components. - */ -#ifndef OMX_Video_h -#define OMX_Video_h - -/** @defgroup video OpenMAX IL Video Domain - * @ingroup iv - * Structures for OpenMAX IL Video domain - * @{ - */ - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - - -/** - * Each OMX header must include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ - -#include - - -/** - * Enumeration used to define the possible video compression codings. - * NOTE: This essentially refers to file extensions. If the coding is - * being used to specify the ENCODE type, then additional work - * must be done to configure the exact flavor of the compression - * to be used. For decode cases where the user application can - * not differentiate between MPEG-4 and H.264 bit streams, it is - * up to the codec to handle this. - */ -typedef enum OMX_VIDEO_CODINGTYPE { - OMX_VIDEO_CodingUnused, /**< Value when coding is N/A */ - OMX_VIDEO_CodingAutoDetect, /**< Autodetection of coding type */ - OMX_VIDEO_CodingMPEG2, /**< AKA: H.262 */ - OMX_VIDEO_CodingH263, /**< H.263 */ - OMX_VIDEO_CodingMPEG4, /**< MPEG-4 */ - OMX_VIDEO_CodingWMV, /**< all versions of Windows Media Video */ - OMX_VIDEO_CodingRV, /**< all versions of Real Video */ - OMX_VIDEO_CodingAVC, /**< H.264/AVC */ - OMX_VIDEO_CodingMJPEG, /**< Motion JPEG */ - OMX_VIDEO_CodingKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_CodingVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_CodingMax = 0x7FFFFFFF -} OMX_VIDEO_CODINGTYPE; - - -/** - * Data structure used to define a video path. The number of Video paths for - * input and output will vary by type of the Video component. - * - * Input (aka Source) : zero Inputs, one Output, - * Splitter : one Input, 2 or more Outputs, - * Processing Element : one Input, one output, - * Mixer : 2 or more inputs, one output, - * Output (aka Sink) : one Input, zero outputs. - * - * The PortDefinition structure is used to define all of the parameters - * necessary for the compliant component to setup an input or an output video - * path. If additional vendor specific data is required, it should be - * transmitted to the component using the CustomCommand function. Compliant - * components will prepopulate this structure with optimal values during the - * GetDefaultInitParams command. - * - * STRUCT MEMBERS: - * cMIMEType : MIME type of data for the port - * pNativeRender : Platform specific reference for a display if a - * sync, otherwise this field is 0 - * nFrameWidth : Width of frame to be used on channel if - * uncompressed format is used. Use 0 for unknown, - * don't care or variable - * nFrameHeight : Height of frame to be used on channel if - * uncompressed format is used. Use 0 for unknown, - * don't care or variable - * nStride : Number of bytes per span of an image - * (i.e. indicates the number of bytes to get - * from span N to span N+1, where negative stride - * indicates the image is bottom up - * nSliceHeight : Height used when encoding in slices - * nBitrate : Bit rate of frame to be used on channel if - * compressed format is used. Use 0 for unknown, - * don't care or variable - * xFramerate : Frame rate to be used on channel if uncompressed - * format is used. Use 0 for unknown, don't care or - * variable. Units are Q16 frames per second. - * bFlagErrorConcealment : Turns on error concealment if it is supported by - * the OMX component - * eCompressionFormat : Compression format used in this instance of the - * component. When OMX_VIDEO_CodingUnused is - * specified, eColorFormat is used - * eColorFormat : Decompressed format used by this component - * pNativeWindow : Platform specific reference for a window object if a - * display sink , otherwise this field is 0x0. - */ -typedef struct OMX_VIDEO_PORTDEFINITIONTYPE { - OMX_STRING cMIMEType; - OMX_NATIVE_DEVICETYPE pNativeRender; - OMX_U32 nFrameWidth; - OMX_U32 nFrameHeight; - OMX_S32 nStride; - OMX_U32 nSliceHeight; - OMX_U32 nBitrate; - OMX_U32 xFramerate; - OMX_BOOL bFlagErrorConcealment; - OMX_VIDEO_CODINGTYPE eCompressionFormat; - OMX_COLOR_FORMATTYPE eColorFormat; - OMX_NATIVE_WINDOWTYPE pNativeWindow; -} OMX_VIDEO_PORTDEFINITIONTYPE; - -/** - * Port format parameter. This structure is used to enumerate the various - * data input/output format supported by the port. - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Indicates which port to set - * nIndex : Indicates the enumeration index for the format from - * 0x0 to N-1 - * eCompressionFormat : Compression format used in this instance of the - * component. When OMX_VIDEO_CodingUnused is specified, - * eColorFormat is used - * eColorFormat : Decompressed format used by this component - * xFrameRate : Indicates the video frame rate in Q16 format - */ -typedef struct OMX_VIDEO_PARAM_PORTFORMATTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nIndex; - OMX_VIDEO_CODINGTYPE eCompressionFormat; - OMX_COLOR_FORMATTYPE eColorFormat; - OMX_U32 xFramerate; -} OMX_VIDEO_PARAM_PORTFORMATTYPE; - - -/** - * This is a structure for configuring video compression quantization - * parameter values. Codecs may support different QP values for different - * frame types. - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version info - * nPortIndex : Port that this structure applies to - * nQpI : QP value to use for index frames - * nQpP : QP value to use for P frames - * nQpB : QP values to use for bidirectional frames - */ -typedef struct OMX_VIDEO_PARAM_QUANTIZATIONTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nQpI; - OMX_U32 nQpP; - OMX_U32 nQpB; -} OMX_VIDEO_PARAM_QUANTIZATIONTYPE; - - -/** - * Structure for configuration of video fast update parameters. - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version info - * nPortIndex : Port that this structure applies to - * bEnableVFU : Enable/Disable video fast update - * nFirstGOB : Specifies the number of the first macroblock row - * nFirstMB : specifies the first MB relative to the specified first GOB - * nNumMBs : Specifies the number of MBs to be refreshed from nFirstGOB - * and nFirstMB - */ -typedef struct OMX_VIDEO_PARAM_VIDEOFASTUPDATETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bEnableVFU; - OMX_U32 nFirstGOB; - OMX_U32 nFirstMB; - OMX_U32 nNumMBs; -} OMX_VIDEO_PARAM_VIDEOFASTUPDATETYPE; - - -/** - * Enumeration of possible bitrate control types - */ -typedef enum OMX_VIDEO_CONTROLRATETYPE { - OMX_Video_ControlRateDisable, - OMX_Video_ControlRateVariable, - OMX_Video_ControlRateConstant, - OMX_Video_ControlRateVariableSkipFrames, - OMX_Video_ControlRateConstantSkipFrames, - OMX_Video_ControlRateKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_Video_ControlRateVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_Video_ControlRateMax = 0x7FFFFFFF -} OMX_VIDEO_CONTROLRATETYPE; - - -/** - * Structure for configuring bitrate mode of a codec. - * - * STRUCT MEMBERS: - * nSize : Size of the struct in bytes - * nVersion : OMX spec version info - * nPortIndex : Port that this struct applies to - * eControlRate : Control rate type enum - * nTargetBitrate : Target bitrate to encode with - */ -typedef struct OMX_VIDEO_PARAM_BITRATETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_VIDEO_CONTROLRATETYPE eControlRate; - OMX_U32 nTargetBitrate; -} OMX_VIDEO_PARAM_BITRATETYPE; - - -/** - * Enumeration of possible motion vector (MV) types - */ -typedef enum OMX_VIDEO_MOTIONVECTORTYPE { - OMX_Video_MotionVectorPixel, - OMX_Video_MotionVectorHalfPel, - OMX_Video_MotionVectorQuarterPel, - OMX_Video_MotionVectorEighthPel, - OMX_Video_MotionVectorKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_Video_MotionVectorVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_Video_MotionVectorMax = 0x7FFFFFFF -} OMX_VIDEO_MOTIONVECTORTYPE; - - -/** - * Structure for configuring the number of motion vectors used as well - * as their accuracy. - * - * STRUCT MEMBERS: - * nSize : Size of the struct in bytes - * nVersion : OMX spec version info - * nPortIndex : port that this structure applies to - * eAccuracy : Enumerated MV accuracy - * bUnrestrictedMVs : Allow unrestricted MVs - * bFourMV : Allow use of 4 MVs - * sXSearchRange : Search range in horizontal direction for MVs - * sYSearchRange : Search range in vertical direction for MVs - */ -typedef struct OMX_VIDEO_PARAM_MOTIONVECTORTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_VIDEO_MOTIONVECTORTYPE eAccuracy; - OMX_BOOL bUnrestrictedMVs; - OMX_BOOL bFourMV; - OMX_S32 sXSearchRange; - OMX_S32 sYSearchRange; -} OMX_VIDEO_PARAM_MOTIONVECTORTYPE; - - -/** - * Enumeration of possible methods to use for Intra Refresh - */ -typedef enum OMX_VIDEO_INTRAREFRESHTYPE { - OMX_VIDEO_IntraRefreshCyclic, - OMX_VIDEO_IntraRefreshAdaptive, - OMX_VIDEO_IntraRefreshBoth, - OMX_VIDEO_IntraRefreshKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_IntraRefreshVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_IntraRefreshMax = 0x7FFFFFFF -} OMX_VIDEO_INTRAREFRESHTYPE; - - -/** - * Structure for configuring intra refresh mode - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eRefreshMode : Cyclic, Adaptive, or Both - * nAirMBs : Number of intra macroblocks to refresh in a frame when - * AIR is enabled - * nAirRef : Number of times a motion marked macroblock has to be - * intra coded - * nCirMBs : Number of consecutive macroblocks to be coded as "intra" - * when CIR is enabled - */ -typedef struct OMX_VIDEO_PARAM_INTRAREFRESHTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_VIDEO_INTRAREFRESHTYPE eRefreshMode; - OMX_U32 nAirMBs; - OMX_U32 nAirRef; - OMX_U32 nCirMBs; -} OMX_VIDEO_PARAM_INTRAREFRESHTYPE; - - -/** - * Structure for enabling various error correction methods for video - * compression. - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * bEnableHEC : Enable/disable header extension codes (HEC) - * bEnableResync : Enable/disable resynchronization markers - * nResynchMarkerSpacing : Resynch markers interval (in bits) to be - * applied in the stream - * bEnableDataPartitioning : Enable/disable data partitioning - * bEnableRVLC : Enable/disable reversible variable length - * coding - */ -typedef struct OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bEnableHEC; - OMX_BOOL bEnableResync; - OMX_U32 nResynchMarkerSpacing; - OMX_BOOL bEnableDataPartitioning; - OMX_BOOL bEnableRVLC; -} OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE; - - -/** - * Configuration of variable block-size motion compensation (VBSMC) - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * b16x16 : Enable inter block search 16x16 - * b16x8 : Enable inter block search 16x8 - * b8x16 : Enable inter block search 8x16 - * b8x8 : Enable inter block search 8x8 - * b8x4 : Enable inter block search 8x4 - * b4x8 : Enable inter block search 4x8 - * b4x4 : Enable inter block search 4x4 - */ -typedef struct OMX_VIDEO_PARAM_VBSMCTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL b16x16; - OMX_BOOL b16x8; - OMX_BOOL b8x16; - OMX_BOOL b8x8; - OMX_BOOL b8x4; - OMX_BOOL b4x8; - OMX_BOOL b4x4; -} OMX_VIDEO_PARAM_VBSMCTYPE; - - -/** - * H.263 profile types, each profile indicates support for various - * performance bounds and different annexes. - * - * ENUMS: - * Baseline : Baseline Profile: H.263 (V1), no optional modes - * H320 Coding : H.320 Coding Efficiency Backward Compatibility - * Profile: H.263+ (V2), includes annexes I, J, L.4 - * and T - * BackwardCompatible : Backward Compatibility Profile: H.263 (V1), - * includes annex F - * ISWV2 : Interactive Streaming Wireless Profile: H.263+ - * (V2), includes annexes I, J, K and T - * ISWV3 : Interactive Streaming Wireless Profile: H.263++ - * (V3), includes profile 3 and annexes V and W.6.3.8 - * HighCompression : Conversational High Compression Profile: H.263++ - * (V3), includes profiles 1 & 2 and annexes D and U - * Internet : Conversational Internet Profile: H.263++ (V3), - * includes profile 5 and annex K - * Interlace : Conversational Interlace Profile: H.263++ (V3), - * includes profile 5 and annex W.6.3.11 - * HighLatency : High Latency Profile: H.263++ (V3), includes - * profile 6 and annexes O.1 and P.5 - */ -typedef enum OMX_VIDEO_H263PROFILETYPE { - OMX_VIDEO_H263ProfileBaseline = 0x01, - OMX_VIDEO_H263ProfileH320Coding = 0x02, - OMX_VIDEO_H263ProfileBackwardCompatible = 0x04, - OMX_VIDEO_H263ProfileISWV2 = 0x08, - OMX_VIDEO_H263ProfileISWV3 = 0x10, - OMX_VIDEO_H263ProfileHighCompression = 0x20, - OMX_VIDEO_H263ProfileInternet = 0x40, - OMX_VIDEO_H263ProfileInterlace = 0x80, - OMX_VIDEO_H263ProfileHighLatency = 0x100, - OMX_VIDEO_H263ProfileKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_H263ProfileVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_H263ProfileMax = 0x7FFFFFFF -} OMX_VIDEO_H263PROFILETYPE; - - -/** - * H.263 level types, each level indicates support for various frame sizes, - * bit rates, decoder frame rates. - */ -typedef enum OMX_VIDEO_H263LEVELTYPE { - OMX_VIDEO_H263Level10 = 0x01, - OMX_VIDEO_H263Level20 = 0x02, - OMX_VIDEO_H263Level30 = 0x04, - OMX_VIDEO_H263Level40 = 0x08, - OMX_VIDEO_H263Level45 = 0x10, - OMX_VIDEO_H263Level50 = 0x20, - OMX_VIDEO_H263Level60 = 0x40, - OMX_VIDEO_H263Level70 = 0x80, - OMX_VIDEO_H263LevelKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_H263LevelVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_H263LevelMax = 0x7FFFFFFF -} OMX_VIDEO_H263LEVELTYPE; - - -/** - * Specifies the picture type. These values should be OR'd to signal all - * pictures types which are allowed. - * - * ENUMS: - * Generic Picture Types: I, P and B - * H.263 Specific Picture Types: SI and SP - * H.264 Specific Picture Types: EI and EP - * MPEG-4 Specific Picture Types: S - */ -typedef enum OMX_VIDEO_PICTURETYPE { - OMX_VIDEO_PictureTypeI = 0x01, - OMX_VIDEO_PictureTypeP = 0x02, - OMX_VIDEO_PictureTypeB = 0x04, - OMX_VIDEO_PictureTypeSI = 0x08, - OMX_VIDEO_PictureTypeSP = 0x10, - OMX_VIDEO_PictureTypeEI = 0x11, - OMX_VIDEO_PictureTypeEP = 0x12, - OMX_VIDEO_PictureTypeS = 0x14, - OMX_VIDEO_PictureTypeKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_PictureTypeVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_PictureTypeMax = 0x7FFFFFFF -} OMX_VIDEO_PICTURETYPE; - - -/** - * H.263 Params - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nPFrames : Number of P frames between each I frame - * nBFrames : Number of B frames between each I frame - * eProfile : H.263 profile(s) to use - * eLevel : H.263 level(s) to use - * bPLUSPTYPEAllowed : Indicating that it is allowed to use PLUSPTYPE - * (specified in the 1998 version of H.263) to - * indicate custom picture sizes or clock - * frequencies - * nAllowedPictureTypes : Specifies the picture types allowed in the - * bitstream - * bForceRoundingTypeToZero : value of the RTYPE bit (bit 6 of MPPTYPE) is - * not constrained. It is recommended to change - * the value of the RTYPE bit for each reference - * picture in error-free communication - * nPictureHeaderRepetition : Specifies the frequency of picture header - * repetition - * nGOBHeaderInterval : Specifies the interval of non-empty GOB - * headers in units of GOBs - */ -typedef struct OMX_VIDEO_PARAM_H263TYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nPFrames; - OMX_U32 nBFrames; - OMX_VIDEO_H263PROFILETYPE eProfile; - OMX_VIDEO_H263LEVELTYPE eLevel; - OMX_BOOL bPLUSPTYPEAllowed; - OMX_U32 nAllowedPictureTypes; - OMX_BOOL bForceRoundingTypeToZero; - OMX_U32 nPictureHeaderRepetition; - OMX_U32 nGOBHeaderInterval; -} OMX_VIDEO_PARAM_H263TYPE; - - -/** - * MPEG-2 profile types, each profile indicates support for various - * performance bounds and different annexes. - */ -typedef enum OMX_VIDEO_MPEG2PROFILETYPE { - OMX_VIDEO_MPEG2ProfileSimple = 0, /**< Simple Profile */ - OMX_VIDEO_MPEG2ProfileMain, /**< Main Profile */ - OMX_VIDEO_MPEG2Profile422, /**< 4:2:2 Profile */ - OMX_VIDEO_MPEG2ProfileSNR, /**< SNR Profile */ - OMX_VIDEO_MPEG2ProfileSpatial, /**< Spatial Profile */ - OMX_VIDEO_MPEG2ProfileHigh, /**< High Profile */ - OMX_VIDEO_MPEG2ProfileKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_MPEG2ProfileVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_MPEG2ProfileMax = 0x7FFFFFFF -} OMX_VIDEO_MPEG2PROFILETYPE; - - -/** - * MPEG-2 level types, each level indicates support for various frame - * sizes, bit rates, decoder frame rates. No need - */ -typedef enum OMX_VIDEO_MPEG2LEVELTYPE { - OMX_VIDEO_MPEG2LevelLL = 0, /**< Low Level */ - OMX_VIDEO_MPEG2LevelML, /**< Main Level */ - OMX_VIDEO_MPEG2LevelH14, /**< High 1440 */ - OMX_VIDEO_MPEG2LevelHL, /**< High Level */ - OMX_VIDEO_MPEG2LevelKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_MPEG2LevelVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_MPEG2LevelMax = 0x7FFFFFFF -} OMX_VIDEO_MPEG2LEVELTYPE; - - -/** - * MPEG-2 params - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nPFrames : Number of P frames between each I frame - * nBFrames : Number of B frames between each I frame - * eProfile : MPEG-2 profile(s) to use - * eLevel : MPEG-2 levels(s) to use - */ -typedef struct OMX_VIDEO_PARAM_MPEG2TYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nPFrames; - OMX_U32 nBFrames; - OMX_VIDEO_MPEG2PROFILETYPE eProfile; - OMX_VIDEO_MPEG2LEVELTYPE eLevel; -} OMX_VIDEO_PARAM_MPEG2TYPE; - - -/** - * MPEG-4 profile types, each profile indicates support for various - * performance bounds and different annexes. - * - * ENUMS: - * - Simple Profile, Levels 1-3 - * - Simple Scalable Profile, Levels 1-2 - * - Core Profile, Levels 1-2 - * - Main Profile, Levels 2-4 - * - N-bit Profile, Level 2 - * - Scalable Texture Profile, Level 1 - * - Simple Face Animation Profile, Levels 1-2 - * - Simple Face and Body Animation (FBA) Profile, Levels 1-2 - * - Basic Animated Texture Profile, Levels 1-2 - * - Hybrid Profile, Levels 1-2 - * - Advanced Real Time Simple Profiles, Levels 1-4 - * - Core Scalable Profile, Levels 1-3 - * - Advanced Coding Efficiency Profile, Levels 1-4 - * - Advanced Core Profile, Levels 1-2 - * - Advanced Scalable Texture, Levels 2-3 - */ -typedef enum OMX_VIDEO_MPEG4PROFILETYPE { - OMX_VIDEO_MPEG4ProfileSimple = 0x01, - OMX_VIDEO_MPEG4ProfileSimpleScalable = 0x02, - OMX_VIDEO_MPEG4ProfileCore = 0x04, - OMX_VIDEO_MPEG4ProfileMain = 0x08, - OMX_VIDEO_MPEG4ProfileNbit = 0x10, - OMX_VIDEO_MPEG4ProfileScalableTexture = 0x20, - OMX_VIDEO_MPEG4ProfileSimpleFace = 0x40, - OMX_VIDEO_MPEG4ProfileSimpleFBA = 0x80, - OMX_VIDEO_MPEG4ProfileBasicAnimated = 0x100, - OMX_VIDEO_MPEG4ProfileHybrid = 0x200, - OMX_VIDEO_MPEG4ProfileAdvancedRealTime = 0x400, - OMX_VIDEO_MPEG4ProfileCoreScalable = 0x800, - OMX_VIDEO_MPEG4ProfileAdvancedCoding = 0x1000, - OMX_VIDEO_MPEG4ProfileAdvancedCore = 0x2000, - OMX_VIDEO_MPEG4ProfileAdvancedScalable = 0x4000, - OMX_VIDEO_MPEG4ProfileAdvancedSimple = 0x8000, - OMX_VIDEO_MPEG4ProfileKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_MPEG4ProfileVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_MPEG4ProfileMax = 0x7FFFFFFF -} OMX_VIDEO_MPEG4PROFILETYPE; - - -/** - * MPEG-4 level types, each level indicates support for various frame - * sizes, bit rates, decoder frame rates. No need - */ -typedef enum OMX_VIDEO_MPEG4LEVELTYPE { - OMX_VIDEO_MPEG4Level0 = 0x01, /**< Level 0 */ - OMX_VIDEO_MPEG4Level0b = 0x02, /**< Level 0b */ - OMX_VIDEO_MPEG4Level1 = 0x04, /**< Level 1 */ - OMX_VIDEO_MPEG4Level2 = 0x08, /**< Level 2 */ - OMX_VIDEO_MPEG4Level3 = 0x10, /**< Level 3 */ - OMX_VIDEO_MPEG4Level4 = 0x20, /**< Level 4 */ - OMX_VIDEO_MPEG4Level4a = 0x40, /**< Level 4a */ - OMX_VIDEO_MPEG4Level5 = 0x80, /**< Level 5 */ - OMX_VIDEO_MPEG4LevelKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_MPEG4LevelVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_MPEG4LevelMax = 0x7FFFFFFF -} OMX_VIDEO_MPEG4LEVELTYPE; - - -/** - * MPEG-4 configuration. This structure handles configuration options - * which are specific to MPEG4 algorithms - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nSliceHeaderSpacing : Number of macroblocks between slice header (H263+ - * Annex K). Put zero if not used - * bSVH : Enable Short Video Header mode - * bGov : Flag to enable GOV - * nPFrames : Number of P frames between each I frame (also called - * GOV period) - * nBFrames : Number of B frames between each I frame - * nIDCVLCThreshold : Value of intra DC VLC threshold - * bACPred : Flag to use ac prediction - * nMaxPacketSize : Maximum size of packet in bytes. - * nTimeIncRes : Used to pass VOP time increment resolution for MPEG4. - * Interpreted as described in MPEG4 standard. - * eProfile : MPEG-4 profile(s) to use. - * eLevel : MPEG-4 level(s) to use. - * nAllowedPictureTypes : Specifies the picture types allowed in the bitstream - * nHeaderExtension : Specifies the number of consecutive video packet - * headers within a VOP - * bReversibleVLC : Specifies whether reversible variable length coding - * is in use - */ -typedef struct OMX_VIDEO_PARAM_MPEG4TYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nSliceHeaderSpacing; - OMX_BOOL bSVH; - OMX_BOOL bGov; - OMX_U32 nPFrames; - OMX_U32 nBFrames; - OMX_U32 nIDCVLCThreshold; - OMX_BOOL bACPred; - OMX_U32 nMaxPacketSize; - OMX_U32 nTimeIncRes; - OMX_VIDEO_MPEG4PROFILETYPE eProfile; - OMX_VIDEO_MPEG4LEVELTYPE eLevel; - OMX_U32 nAllowedPictureTypes; - OMX_U32 nHeaderExtension; - OMX_BOOL bReversibleVLC; -} OMX_VIDEO_PARAM_MPEG4TYPE; - - -/** - * WMV Versions - */ -typedef enum OMX_VIDEO_WMVFORMATTYPE { - OMX_VIDEO_WMVFormatUnused = 0x01, /**< Format unused or unknown */ - OMX_VIDEO_WMVFormat7 = 0x02, /**< Windows Media Video format 7 */ - OMX_VIDEO_WMVFormat8 = 0x04, /**< Windows Media Video format 8 */ - OMX_VIDEO_WMVFormat9 = 0x08, /**< Windows Media Video format 9 */ - OMX_VIDEO_WMFFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_WMFFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_WMVFormatMax = 0x7FFFFFFF -} OMX_VIDEO_WMVFORMATTYPE; - - -/** - * WMV Params - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eFormat : Version of WMV stream / data - */ -typedef struct OMX_VIDEO_PARAM_WMVTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_VIDEO_WMVFORMATTYPE eFormat; -} OMX_VIDEO_PARAM_WMVTYPE; - - -/** - * Real Video Version - */ -typedef enum OMX_VIDEO_RVFORMATTYPE { - OMX_VIDEO_RVFormatUnused = 0, /**< Format unused or unknown */ - OMX_VIDEO_RVFormat8, /**< Real Video format 8 */ - OMX_VIDEO_RVFormat9, /**< Real Video format 9 */ - OMX_VIDEO_RVFormatG2, /**< Real Video Format G2 */ - OMX_VIDEO_RVFormatKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_RVFormatVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_RVFormatMax = 0x7FFFFFFF -} OMX_VIDEO_RVFORMATTYPE; - - -/** - * Real Video Params - * - * STUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * eFormat : Version of RV stream / data - * nBitsPerPixel : Bits per pixel coded in the frame - * nPaddedWidth : Padded width in pixel of a video frame - * nPaddedHeight : Padded Height in pixels of a video frame - * nFrameRate : Rate of video in frames per second - * nBitstreamFlags : Flags which internal information about the bitstream - * nBitstreamVersion : Bitstream version - * nMaxEncodeFrameSize: Max encoded frame size - * bEnablePostFilter : Turn on/off post filter - * bEnableTemporalInterpolation : Turn on/off temporal interpolation - * bEnableLatencyMode : When enabled, the decoder does not display a decoded - * frame until it has detected that no enhancement layer - * frames or dependent B frames will be coming. This - * detection usually occurs when a subsequent non-B - * frame is encountered - */ -typedef struct OMX_VIDEO_PARAM_RVTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_VIDEO_RVFORMATTYPE eFormat; - OMX_U16 nBitsPerPixel; - OMX_U16 nPaddedWidth; - OMX_U16 nPaddedHeight; - OMX_U32 nFrameRate; - OMX_U32 nBitstreamFlags; - OMX_U32 nBitstreamVersion; - OMX_U32 nMaxEncodeFrameSize; - OMX_BOOL bEnablePostFilter; - OMX_BOOL bEnableTemporalInterpolation; - OMX_BOOL bEnableLatencyMode; -} OMX_VIDEO_PARAM_RVTYPE; - - -/** - * AVC profile types, each profile indicates support for various - * performance bounds and different annexes. - */ -typedef enum OMX_VIDEO_AVCPROFILETYPE { - OMX_VIDEO_AVCProfileBaseline = 0x01, /**< Baseline profile */ - OMX_VIDEO_AVCProfileMain = 0x02, /**< Main profile */ - OMX_VIDEO_AVCProfileExtended = 0x04, /**< Extended profile */ - OMX_VIDEO_AVCProfileHigh = 0x08, /**< High profile */ - OMX_VIDEO_AVCProfileHigh10 = 0x10, /**< High 10 profile */ - OMX_VIDEO_AVCProfileHigh422 = 0x20, /**< High 4:2:2 profile */ - OMX_VIDEO_AVCProfileHigh444 = 0x40, /**< High 4:4:4 profile */ - OMX_VIDEO_AVCProfileKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_AVCProfileVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_AVCProfileMax = 0x7FFFFFFF -} OMX_VIDEO_AVCPROFILETYPE; - - -/** - * AVC level types, each level indicates support for various frame sizes, - * bit rates, decoder frame rates. No need - */ -typedef enum OMX_VIDEO_AVCLEVELTYPE { - OMX_VIDEO_AVCLevel1 = 0x01, /**< Level 1 */ - OMX_VIDEO_AVCLevel1b = 0x02, /**< Level 1b */ - OMX_VIDEO_AVCLevel11 = 0x04, /**< Level 1.1 */ - OMX_VIDEO_AVCLevel12 = 0x08, /**< Level 1.2 */ - OMX_VIDEO_AVCLevel13 = 0x10, /**< Level 1.3 */ - OMX_VIDEO_AVCLevel2 = 0x20, /**< Level 2 */ - OMX_VIDEO_AVCLevel21 = 0x40, /**< Level 2.1 */ - OMX_VIDEO_AVCLevel22 = 0x80, /**< Level 2.2 */ - OMX_VIDEO_AVCLevel3 = 0x100, /**< Level 3 */ - OMX_VIDEO_AVCLevel31 = 0x200, /**< Level 3.1 */ - OMX_VIDEO_AVCLevel32 = 0x400, /**< Level 3.2 */ - OMX_VIDEO_AVCLevel4 = 0x800, /**< Level 4 */ - OMX_VIDEO_AVCLevel41 = 0x1000, /**< Level 4.1 */ - OMX_VIDEO_AVCLevel42 = 0x2000, /**< Level 4.2 */ - OMX_VIDEO_AVCLevel5 = 0x4000, /**< Level 5 */ - OMX_VIDEO_AVCLevel51 = 0x8000, /**< Level 5.1 */ - OMX_VIDEO_AVCLevelKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_AVCLevelVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_AVCLevelMax = 0x7FFFFFFF -} OMX_VIDEO_AVCLEVELTYPE; - - -/** - * AVC loop filter modes - * - * OMX_VIDEO_AVCLoopFilterEnable : Enable - * OMX_VIDEO_AVCLoopFilterDisable : Disable - * OMX_VIDEO_AVCLoopFilterDisableSliceBoundary : Disabled on slice boundaries - */ -typedef enum OMX_VIDEO_AVCLOOPFILTERTYPE { - OMX_VIDEO_AVCLoopFilterEnable = 0, - OMX_VIDEO_AVCLoopFilterDisable, - OMX_VIDEO_AVCLoopFilterDisableSliceBoundary, - OMX_VIDEO_AVCLoopFilterKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_AVCLoopFilterVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_AVCLoopFilterMax = 0x7FFFFFFF -} OMX_VIDEO_AVCLOOPFILTERTYPE; - - -/** - * AVC params - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nSliceHeaderSpacing : Number of macroblocks between slice header, put - * zero if not used - * nPFrames : Number of P frames between each I frame - * nBFrames : Number of B frames between each I frame - * bUseHadamard : Enable/disable Hadamard transform - * nRefFrames : Max number of reference frames to use for inter - * motion search (1-16) - * nRefIdxTrailing : Pic param set ref frame index (index into ref - * frame buffer of trailing frames list), B frame - * support - * nRefIdxForward : Pic param set ref frame index (index into ref - * frame buffer of forward frames list), B frame - * support - * bEnableUEP : Enable/disable unequal error protection. This - * is only valid of data partitioning is enabled. - * bEnableFMO : Enable/disable flexible macroblock ordering - * bEnableASO : Enable/disable arbitrary slice ordering - * bEnableRS : Enable/disable sending of redundant slices - * eProfile : AVC profile(s) to use - * eLevel : AVC level(s) to use - * nAllowedPictureTypes : Specifies the picture types allowed in the - * bitstream - * bFrameMBsOnly : specifies that every coded picture of the - * coded video sequence is a coded frame - * containing only frame macroblocks - * bMBAFF : Enable/disable switching between frame and - * field macroblocks within a picture - * bEntropyCodingCABAC : Entropy decoding method to be applied for the - * syntax elements for which two descriptors appear - * in the syntax tables - * bWeightedPPrediction : Enable/disable weighted prediction shall not - * be applied to P and SP slices - * nWeightedBipredicitonMode : Default weighted prediction is applied to B - * slices - * bconstIpred : Enable/disable intra prediction - * bDirect8x8Inference : Specifies the method used in the derivation - * process for luma motion vectors for B_Skip, - * B_Direct_16x16 and B_Direct_8x8 as specified - * in subclause 8.4.1.2 of the AVC spec - * bDirectSpatialTemporal : Flag indicating spatial or temporal direct - * mode used in B slice coding (related to - * bDirect8x8Inference) . Spatial direct mode is - * more common and should be the default. - * nCabacInitIdx : Index used to init CABAC contexts - * eLoopFilterMode : Enable/disable loop filter - */ -typedef struct OMX_VIDEO_PARAM_AVCTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nSliceHeaderSpacing; - OMX_U32 nPFrames; - OMX_U32 nBFrames; - OMX_BOOL bUseHadamard; - OMX_U32 nRefFrames; - OMX_U32 nRefIdx10ActiveMinus1; - OMX_U32 nRefIdx11ActiveMinus1; - OMX_BOOL bEnableUEP; - OMX_BOOL bEnableFMO; - OMX_BOOL bEnableASO; - OMX_BOOL bEnableRS; - OMX_VIDEO_AVCPROFILETYPE eProfile; - OMX_VIDEO_AVCLEVELTYPE eLevel; - OMX_U32 nAllowedPictureTypes; - OMX_BOOL bFrameMBsOnly; - OMX_BOOL bMBAFF; - OMX_BOOL bEntropyCodingCABAC; - OMX_BOOL bWeightedPPrediction; - OMX_U32 nWeightedBipredicitonMode; - OMX_BOOL bconstIpred ; - OMX_BOOL bDirect8x8Inference; - OMX_BOOL bDirectSpatialTemporal; - OMX_U32 nCabacInitIdc; - OMX_VIDEO_AVCLOOPFILTERTYPE eLoopFilterMode; -} OMX_VIDEO_PARAM_AVCTYPE; - -typedef struct OMX_VIDEO_PARAM_PROFILELEVELTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 eProfile; /**< type is OMX_VIDEO_AVCPROFILETYPE, OMX_VIDEO_H263PROFILETYPE, - or OMX_VIDEO_MPEG4PROFILETYPE depending on context */ - OMX_U32 eLevel; /**< type is OMX_VIDEO_AVCLEVELTYPE, OMX_VIDEO_H263LEVELTYPE, - or OMX_VIDEO_MPEG4PROFILETYPE depending on context */ - OMX_U32 nProfileIndex; /**< Used to query for individual profile support information, - This parameter is valid only for - OMX_IndexParamVideoProfileLevelQuerySupported index, - For all other indices this parameter is to be ignored. */ -} OMX_VIDEO_PARAM_PROFILELEVELTYPE; - -/** - * Structure for dynamically configuring bitrate mode of a codec. - * - * STRUCT MEMBERS: - * nSize : Size of the struct in bytes - * nVersion : OMX spec version info - * nPortIndex : Port that this struct applies to - * nEncodeBitrate : Target average bitrate to be generated in bps - */ -typedef struct OMX_VIDEO_CONFIG_BITRATETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nEncodeBitrate; -} OMX_VIDEO_CONFIG_BITRATETYPE; - -/** - * Defines Encoder Frame Rate setting - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * xEncodeFramerate : Encoding framerate represented in Q16 format - */ -typedef struct OMX_CONFIG_FRAMERATETYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 xEncodeFramerate; /* Q16 format */ -} OMX_CONFIG_FRAMERATETYPE; - -typedef struct OMX_CONFIG_INTRAREFRESHVOPTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL IntraRefreshVOP; -} OMX_CONFIG_INTRAREFRESHVOPTYPE; - -typedef struct OMX_CONFIG_MACROBLOCKERRORMAPTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nErrMapSize; /* Size of the Error Map in bytes */ - OMX_U8 ErrMap[1]; /* Error map hint */ -} OMX_CONFIG_MACROBLOCKERRORMAPTYPE; - -typedef struct OMX_CONFIG_MBERRORREPORTINGTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_BOOL bEnabled; -} OMX_CONFIG_MBERRORREPORTINGTYPE; - -typedef struct OMX_PARAM_MACROBLOCKSTYPE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nMacroblocks; -} OMX_PARAM_MACROBLOCKSTYPE; - -/** - * AVC Slice Mode modes - * - * OMX_VIDEO_SLICEMODE_AVCDefault : Normal frame encoding, one slice per frame - * OMX_VIDEO_SLICEMODE_AVCMBSlice : NAL mode, number of MBs per frame - * OMX_VIDEO_SLICEMODE_AVCByteSlice : NAL mode, number of bytes per frame - */ -typedef enum OMX_VIDEO_AVCSLICEMODETYPE { - OMX_VIDEO_SLICEMODE_AVCDefault = 0, - OMX_VIDEO_SLICEMODE_AVCMBSlice, - OMX_VIDEO_SLICEMODE_AVCByteSlice, - OMX_VIDEO_SLICEMODE_AVCKhronosExtensions = 0x6F000000, /**< Reserved region for introducing Khronos Standard Extensions */ - OMX_VIDEO_SLICEMODE_AVCVendorStartUnused = 0x7F000000, /**< Reserved region for introducing Vendor Extensions */ - OMX_VIDEO_SLICEMODE_AVCLevelMax = 0x7FFFFFFF -} OMX_VIDEO_AVCSLICEMODETYPE; - -/** - * AVC FMO Slice Mode Params - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nNumSliceGroups : Specifies the number of slice groups - * nSliceGroupMapType : Specifies the type of slice groups - * eSliceMode : Specifies the type of slice - */ -typedef struct OMX_VIDEO_PARAM_AVCSLICEFMO { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U8 nNumSliceGroups; - OMX_U8 nSliceGroupMapType; - OMX_VIDEO_AVCSLICEMODETYPE eSliceMode; -} OMX_VIDEO_PARAM_AVCSLICEFMO; - -/** - * AVC IDR Period Configs - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nIDRPeriod : Specifies periodicity of IDR frames - * nPFrames : Specifies internal of coding Intra frames - */ -typedef struct OMX_VIDEO_CONFIG_AVCINTRAPERIOD { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nIDRPeriod; - OMX_U32 nPFrames; -} OMX_VIDEO_CONFIG_AVCINTRAPERIOD; - -/** - * AVC NAL Size Configs - * - * STRUCT MEMBERS: - * nSize : Size of the structure in bytes - * nVersion : OMX specification version information - * nPortIndex : Port that this structure applies to - * nNaluBytes : Specifies the NAL unit size - */ -typedef struct OMX_VIDEO_CONFIG_NALSIZE { - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_U32 nNaluBytes; -} OMX_VIDEO_CONFIG_NALSIZE; - -/** @} */ - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif -/* File EOF */ - diff --git a/subprojects/gst-omx/omx/openmax/OMX_VideoExt.h b/subprojects/gst-omx/omx/openmax/OMX_VideoExt.h deleted file mode 100644 index a9b5d458b9..0000000000 --- a/subprojects/gst-omx/omx/openmax/OMX_VideoExt.h +++ /dev/null @@ -1,69 +0,0 @@ -/* - * Copyright (c) 2010 The Khronos Group Inc. - * - * Permission is hereby granted, free of charge, to any person obtaining - * a copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sublicense, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject - * to the following conditions: - * The above copyright notice and this permission notice shall be included - * in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS - * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF - * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY - * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, - * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE - * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - * - */ - -/** OMX_VideoExt.h - OpenMax IL version 1.1.2 - * The OMX_VideoExt header file contains extensions to the - * definitions used by both the application and the component to - * access video items. - */ - -#ifndef OMX_VideoExt_h -#define OMX_VideoExt_h - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - -/* Each OMX header shall include all required header files to allow the - * header to compile without errors. The includes below are required - * for this header file to compile successfully - */ -#include - -/** NALU Formats */ -typedef enum OMX_NALUFORMATSTYPE { - OMX_NaluFormatStartCodes = 1, - OMX_NaluFormatOneNaluPerBuffer = 2, - OMX_NaluFormatOneByteInterleaveLength = 4, - OMX_NaluFormatTwoByteInterleaveLength = 8, - OMX_NaluFormatFourByteInterleaveLength = 16, - OMX_NaluFormatCodingMax = 0x7FFFFFFF -} OMX_NALUFORMATSTYPE; - - -/** NAL Stream Format */ -typedef struct OMX_NALSTREAMFORMATTYPE{ - OMX_U32 nSize; - OMX_VERSIONTYPE nVersion; - OMX_U32 nPortIndex; - OMX_NALUFORMATSTYPE eNaluFormat; -} OMX_NALSTREAMFORMATTYPE; - - - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* OMX_VideoExt_h */ -/* File EOF */ diff --git a/subprojects/gst-omx/scripts/extract-release-date-from-doap-file.py b/subprojects/gst-omx/scripts/extract-release-date-from-doap-file.py deleted file mode 100755 index f09b60e9d0..0000000000 --- a/subprojects/gst-omx/scripts/extract-release-date-from-doap-file.py +++ /dev/null @@ -1,45 +0,0 @@ -#!/usr/bin/env python3 -# -# extract-release-date-from-doap-file.py VERSION DOAP-FILE -# -# Extract release date for the given release version from a DOAP file -# -# Copyright (C) 2020 Tim-Philipp Müller -# -# This library is free software; you can redistribute it and/or -# modify it under the terms of the GNU Library General Public -# License as published by the Free Software Foundation; either -# version 2 of the License, or (at your option) any later version. -# -# This library 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 -# Library General Public License for more details. -# -# You should have received a copy of the GNU Library General Public -# License along with this library; if not, write to the -# Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, -# Boston, MA 02110-1301, USA. - -import sys -import xml.etree.ElementTree as ET - -if len(sys.argv) != 3: - sys.exit('Usage: {} VERSION DOAP-FILE'.format(sys.argv[0])) - -release_version = sys.argv[1] -doap_fn = sys.argv[2] - -tree = ET.parse(doap_fn) -root = tree.getroot() - -namespaces = {'doap': 'http://usefulinc.com/ns/doap#'} - -for v in root.findall('doap:release/doap:Version', namespaces=namespaces): - if v.findtext('doap:revision', namespaces=namespaces) == release_version: - release_date = v.findtext('doap:created', namespaces=namespaces) - if release_date: - print(release_date) - sys.exit(0) - -sys.exit('Could not find a release with version {} in {}'.format(release_version, doap_fn)) diff --git a/subprojects/gst-omx/scripts/gen-changelog.py b/subprojects/gst-omx/scripts/gen-changelog.py deleted file mode 100755 index 3924e6ea32..0000000000 --- a/subprojects/gst-omx/scripts/gen-changelog.py +++ /dev/null @@ -1,240 +0,0 @@ -#!/usr/bin/env python3 -# -# Makes a GNU-Style ChangeLog from a git repository -import os -import sys -import subprocess -import re - -meson_source_root = os.environ.get('MESON_SOURCE_ROOT') - -meson_dist_root = os.environ.get('MESON_DIST_ROOT') -if meson_dist_root: - output_fn = os.path.join(meson_dist_root, 'ChangeLog') -else: - output_fn = sys.stdout.fileno() - -# commit hash => release version tag string -release_refs = {} - -# These are the pre-monorepo module beginnings -changelog_starts = { - 'gstreamer': '70521179a75db0c7230cc47c6d7f9d63cf73d351', - 'gst-plugins-base': '68746a38d5e48e6f7c220663dcc2f175ff55cb3c', - 'gst-plugins-good': '81f63142d65b62b0971c19ceb79956c49ffc2f06', - 'gst-plugins-ugly': '7d7c3e478e32b7b66c44cc4442d571fbab534740', - 'gst-plugins-bad': 'ea6821e2934fe8d356ea89d5610f0630b3446877', - 'gst-libav': '3c440154c60d1ec0a54186f0fad4aebfd2ecc3ea', - 'gst-rtsp-server': '5029c85a46a8c366c4bf272d503e22bbcd624ece', - 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', - 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', - 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', - 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', - 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', -} - - -def print_help(): - print('', file=sys.stderr) - print('gen-changelog: generate GNU-style changelog from git history', - file=sys.stderr) - print('', file=sys.stderr) - print('Usage: {} [OPTIONS] GSTREAMER-MODULE [START-TAG] [HEAD-TAG]'.format( - sys.argv[0]), file=sys.stderr) - print('', file=sys.stderr) - sys.exit(1) - - -if len(sys.argv) < 2 or len(sys.argv) > 4 or '--help' in sys.argv: - print_help() - -module = sys.argv[1] - -if len(sys.argv) > 2: - start_tag = sys.argv[2] -else: - start_tag = None - -if len(sys.argv) > 3: - head_tag = sys.argv[3] -else: - head_tag = None - -if module not in changelog_starts: - print(f'Unknown module {module}', file=sys.stderr) - print_help() - - -def process_commit(lines, files, subtree_path=None): - # DATE NAME - # BLANK LINE - # Subject - # BLANK LINE - # ... - # FILES - fileincommit = False - lines = [x.strip() for x in lines if x.strip() - and not x.startswith('git-svn-id')] - files = [x.strip() for x in files if x.strip()] - for line in lines: - if line.startswith('* ') and ':' in line: - fileincommit = True - break - - top_line = lines[0] - print(top_line.strip()) - print() - if not fileincommit: - for f in files: - if subtree_path and f.startswith(subtree_path): - # requires Python 3.9 - print('\t* %s:' % f.removeprefix(subtree_path)) - else: - print('\t* %s:' % f) - for line in lines[1:]: - print('\t ', line) - print() - - -def output_commits(module, start_tag, end_tag, subtree_path=None): - # retrieve commit date for start tag so we can filter the log for commits - # after that date. That way we don't include commits from merged-in - # plugin-move branches that go back to the beginning of time. - start_date = get_commit_date_for_ref(start_tag) - - cmd = ['git', 'log', - '--pretty=format:--START-COMMIT--%H%n%ai %an <%ae>%n%n%s%n%b%n--END-COMMIT--', - '--date=short', - '--name-only', - f'--since={start_date}', - f'{start_tag}..{end_tag}', - ] - - if subtree_path: - cmd += ['--', '.'] - - p = subprocess.Popen(args=cmd, shell=False, - stdout=subprocess.PIPE, cwd=meson_source_root) - buf = [] - files = [] - filemode = False - for lin in [x.decode('utf8', errors='replace') for x in p.stdout.readlines()]: - if lin.startswith("--START-COMMIT--"): - commit_hash = lin[16:].strip() - if buf != []: - process_commit(buf, files, subtree_path) - - if commit_hash in release_refs: - version_str = release_refs[commit_hash] - print(f'=== release {version_str} ===\n') - - buf = [] - files = [] - filemode = False - elif lin.startswith("--END-COMMIT--"): - filemode = True - elif filemode is True: - files.append(lin) - else: - buf.append(lin) - if buf != []: - process_commit(buf, files, subtree_path) - - -def get_commit_date_for_ref(ref): - cmd = ['git', 'log', '--pretty=format:%cI', '-1', ref] - r = subprocess.run(cmd, capture_output=True, text=True, - check=True, cwd=meson_source_root) - commit_date = r.stdout.strip() - return commit_date - - -def populate_release_tags_for_premonorepo_module(module_tag_prefix): - if module_tag_prefix != '': - cmd = ['git', 'tag', '--list', f'{module_tag_prefix}*'] - else: - cmd = ['git', 'tag', '--list', '1.*', 'RELEASE-*'] - - p = subprocess.Popen(args=cmd, shell=False, - stdout=subprocess.PIPE, cwd=meson_source_root) - for line in [x.decode('utf8') for x in p.stdout.readlines()]: - git_tag = line.strip() - version_str = git_tag.removeprefix(module_tag_prefix).removeprefix('RELEASE-').split('-')[0].replace('_', '.') - # might have been populated with post-monorepo tags already for gstreamer core - if version_str not in release_refs: - # find last commit before tag in module subdirectory - cmd = ['git', 'log', '--pretty=format:%H', '-1', git_tag] - r = subprocess.run(cmd, capture_output=True, - text=True, check=True, cwd=meson_source_root) - commit_hash = r.stdout.strip() - release_refs[commit_hash] = version_str - - # print(f'{git_tag} => {version_str} => {commit_hash}') - - -def populate_release_tags_for_monorepo_subproject(): - cmd = ['git', 'tag', '--list', '1.*'] - p = subprocess.Popen(args=cmd, shell=False, - stdout=subprocess.PIPE, cwd=meson_source_root) - for line in [x.decode('utf8') for x in p.stdout.readlines()]: - version_str = line.strip() - version_arr = version_str.split('.') - major = int(version_arr[0]) - minor = int(version_arr[1]) - micro = int(version_arr[2]) - # ignore pre-monorepo versions - if major < 1: - continue - if major == 1 and minor < 19: - continue - if major == 1 and minor == 19 and micro < 2: - continue - # find last commit before tag in module subdirectory - cmd = ['git', 'log', '--pretty=format:%H', - '-1', version_str, '--', '.'] - r = subprocess.run(cmd, capture_output=True, text=True, - check=True, cwd=meson_source_root) - commit_hash = r.stdout.strip() - release_refs[commit_hash] = version_str - - -if __name__ == '__main__': - module_tag_prefix = '' if module == 'gstreamer' else f'{module}-' - - populate_release_tags_for_monorepo_subproject() - - with open(output_fn, 'w') as f: - sys.stdout = f - - # Force writing of head tag - if head_tag and head_tag not in release_refs.values(): - print(f'=== release {head_tag} ===\n') - - # Output all commits from start_tag onwards, otherwise output full history. - # (We assume the start_tag is after the monorepo merge if it's specified.) - if start_tag and start_tag != 'start': - output_commits(module, start_tag, 'HEAD', f'subprojects/{module}/') - else: - # First output all post-monorepo commits or commits from start_tag if specified - output_commits(module, 'monorepo-start', - 'HEAD', f'subprojects/{module}/') - - populate_release_tags_for_premonorepo_module(module_tag_prefix) - - # Next output all pre-monorepo commits (modules have their own root) - if not start_tag: - module_start = f'{module_tag_prefix}1.0.0' - elif start_tag == 'start': - module_start = changelog_starts[module] - else: - module_start = f'{module_tag_prefix}{start_tag}' - - output_commits(module, module_start, - f'{module_tag_prefix}1.19.2', None) - - # Write start tag at end for clarity - if not start_tag: - print(f'=== release 1.0.0 ===\n') - elif start_tag != 'start': - print(f'=== release {start_tag} ===\n') diff --git a/subprojects/gst-omx/tests/check/generic/states.c b/subprojects/gst-omx/tests/check/generic/states.c deleted file mode 100644 index 415ac543c2..0000000000 --- a/subprojects/gst-omx/tests/check/generic/states.c +++ /dev/null @@ -1,225 +0,0 @@ -/* GStreamer - * - * unit test for state changes on all elements - * - * Copyright (C) <2005> Thomas Vander Stichele - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library 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 - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#ifdef HAVE_CONFIG_H -# include "config.h" -#endif - -#include - -#include - -static GList *elements = NULL; - -static void -setup (void) -{ - GList *features, *f; - GList *plugins, *p; - gchar **ignorelist = NULL; - const gchar *STATE_IGNORE_ELEMENTS = NULL; - GstRegistry *def; - - GST_DEBUG ("getting elements for package %s", PACKAGE); - STATE_IGNORE_ELEMENTS = g_getenv ("GST_STATE_IGNORE_ELEMENTS"); - if (!g_getenv ("GST_NO_STATE_IGNORE_ELEMENTS") && STATE_IGNORE_ELEMENTS) { - GST_DEBUG ("Will ignore element factories: '%s'", STATE_IGNORE_ELEMENTS); - ignorelist = g_strsplit (STATE_IGNORE_ELEMENTS, " ", 0); - } - - def = gst_registry_get (); - - plugins = gst_registry_get_plugin_list (def); - - for (p = plugins; p; p = p->next) { - GstPlugin *plugin = p->data; - - if (strcmp (gst_plugin_get_source (plugin), PACKAGE) != 0) - continue; - - features = - gst_registry_get_feature_list_by_plugin (def, - gst_plugin_get_name (plugin)); - - for (f = features; f; f = f->next) { - GstPluginFeature *feature = f->data; - const gchar *name = gst_plugin_feature_get_name (feature); - gboolean ignore = FALSE; - - if (!GST_IS_ELEMENT_FACTORY (feature)) - continue; - - if (ignorelist) { - gchar **s; - - for (s = ignorelist; s && *s; ++s) { - if (g_str_has_prefix (name, *s)) { - GST_DEBUG ("ignoring element %s", name); - ignore = TRUE; - } - } - if (ignore) - continue; - } - - GST_DEBUG ("adding element %s", name); - elements = g_list_prepend (elements, (gpointer) g_strdup (name)); - } - gst_plugin_feature_list_free (features); - } - gst_plugin_list_free (plugins); - g_strfreev (ignorelist); -} - -static void -teardown (void) -{ - GList *e; - - for (e = elements; e; e = e->next) { - g_free (e->data); - } - g_list_free (elements); - elements = NULL; -} - - -GST_START_TEST (test_state_changes_up_and_down_seq) -{ - GstElement *element; - GList *e; - - for (e = elements; e; e = e->next) { - const gchar *name = e->data; - - GST_INFO ("testing element %s", name); - element = gst_element_factory_make (name, name); - fail_if (element == NULL, "Could not make element from factory %s", name); - - if (GST_IS_PIPELINE (element)) { - GST_DEBUG ("element %s is a pipeline", name); - } - - gst_element_set_state (element, GST_STATE_READY); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_PLAYING); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_READY); - gst_element_set_state (element, GST_STATE_NULL); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_READY); - gst_element_set_state (element, GST_STATE_PLAYING); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_NULL); - gst_object_unref (GST_OBJECT (element)); - } -} - -GST_END_TEST; - -GST_START_TEST (test_state_changes_up_seq) -{ - GstElement *element; - GList *e; - - for (e = elements; e; e = e->next) { - const gchar *name = e->data; - - GST_INFO ("testing element %s", name); - element = gst_element_factory_make (name, name); - fail_if (element == NULL, "Could not make element from factory %s", name); - - if (GST_IS_PIPELINE (element)) { - GST_DEBUG ("element %s is a pipeline", name); - } - - gst_element_set_state (element, GST_STATE_READY); - - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_READY); - - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_PLAYING); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_READY); - - gst_element_set_state (element, GST_STATE_NULL); - gst_object_unref (GST_OBJECT (element)); - } -} - -GST_END_TEST; - -GST_START_TEST (test_state_changes_down_seq) -{ - GstElement *element; - GList *e; - - for (e = elements; e; e = e->next) { - const gchar *name = e->data; - - GST_INFO ("testing element %s", name); - element = gst_element_factory_make (name, name); - fail_if (element == NULL, "Could not make element from factory %s", name); - - if (GST_IS_PIPELINE (element)) { - GST_DEBUG ("element %s is a pipeline", name); - } - - gst_element_set_state (element, GST_STATE_READY); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_PLAYING); - - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_PLAYING); - - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_READY); - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_PLAYING); - - gst_element_set_state (element, GST_STATE_PAUSED); - gst_element_set_state (element, GST_STATE_READY); - gst_element_set_state (element, GST_STATE_NULL); - gst_object_unref (GST_OBJECT (element)); - } -} - -GST_END_TEST; - - -static Suite * -states_suite (void) -{ - Suite *s = suite_create ("states_omx"); - TCase *tc_chain = tcase_create ("general"); - - suite_add_tcase (s, tc_chain); - tcase_add_checked_fixture (tc_chain, setup, teardown); - tcase_add_test (tc_chain, test_state_changes_up_and_down_seq); - tcase_add_test (tc_chain, test_state_changes_up_seq); - tcase_add_test (tc_chain, test_state_changes_down_seq); - - return s; -} - -GST_CHECK_MAIN (states); diff --git a/subprojects/gst-omx/tests/check/meson.build b/subprojects/gst-omx/tests/check/meson.build deleted file mode 100644 index 26ebfe98ec..0000000000 --- a/subprojects/gst-omx/tests/check/meson.build +++ /dev/null @@ -1,56 +0,0 @@ -# name, condition when to skip the test and extra dependencies -omx_tests = [ - [ 'generic/states' ], -] - -test_defines = [ - '-UG_DISABLE_ASSERT', - '-UG_DISABLE_CAST_CHECKS', - '-DGST_CHECK_TEST_ENVIRONMENT_BEACON="GST_PLUGIN_LOADING_WHITELIST"', -] - -pluginsdirs = [] -if gst_dep.type_name() == 'pkgconfig' - pbase = dependency('gstreamer-plugins-base-' + api_version, required : false) - pluginsdirs = [gst_dep.get_variable('pluginsdir'), - pbase.get_variable('pluginsdir')] -endif - -state_ignore_elements='' - -# FIXME: check, also + PTHREAD_CFLAGS -test_deps = [gst_dep, gstbase_dep, gstcheck_dep] - -# FIXME: add valgrind suppression common/gst.supp gst-plugins-good.supp -foreach t : omx_tests - fname = '@0@.c'.format(t.get(0)) - test_name = t.get(0).underscorify() - extra_deps = [ ] - if t.length() == 3 - extra_deps = t.get(2) - skip_test = t.get(1) - elif t.length() == 2 - skip_test = t.get(1) - else - skip_test = false - endif - if not skip_test - env = environment() - env.set('GST_PLUGIN_SYSTEM_PATH_1_0', '') - env.set('GST_STATE_IGNORE_ELEMENTS', state_ignore_elements) - env.set('CK_DEFAULT_TIMEOUT', '20') - env.set('GST_PLUGIN_LOADING_WHITELIST', 'gstreamer', 'gst-plugins-base', - 'gst-plugins-good', 'gst-omx@' + meson.project_build_root(), separator: ':') - env.set('GST_PLUGIN_PATH_1_0', [meson.global_build_root()] + pluginsdirs) - env.set('GSETTINGS_BACKEND', 'memory') - env.set('GST_OMX_CONFIG_DIR', omx_config_dir) - - env.set('GST_REGISTRY', '@0@/@1@.registry'.format(meson.current_build_dir(), test_name)) - exe = executable(test_name, fname, - include_directories : [configinc], - c_args : ['-DHAVE_CONFIG_H=1' ] + test_defines, - dependencies : [libm] + test_deps + extra_deps, - ) - test(test_name, exe, env: env, timeout: 3 * 60) - endif -endforeach diff --git a/subprojects/gst-omx/tests/meson.build b/subprojects/gst-omx/tests/meson.build deleted file mode 100644 index e41c33e64d..0000000000 --- a/subprojects/gst-omx/tests/meson.build +++ /dev/null @@ -1,8 +0,0 @@ -# FIXME: make check work on windows -if get_option('tests').disabled() or static_build or host_machine.system() == 'windows' - subdir_done() -endif - -if gstcheck_dep.found() - subdir('check') -endif \ No newline at end of file diff --git a/subprojects/gst-omx/tools/listcomponents.c b/subprojects/gst-omx/tools/listcomponents.c deleted file mode 100644 index 3933564b26..0000000000 --- a/subprojects/gst-omx/tools/listcomponents.c +++ /dev/null @@ -1,169 +0,0 @@ -/* - * Copyright (C) 2012 Collabora Ltd. - * Author: Sebastian Dröge - * - * This library 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 - * version 2.1 of the License. - * - * This library 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 this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include -#include - -#ifdef GST_OMX_STRUCT_PACKING -# if GST_OMX_STRUCT_PACKING == 1 -# pragma pack(1) -# elif GST_OMX_STRUCT_PACKING == 2 -# pragma pack(2) -# elif GST_OMX_STRUCT_PACKING == 4 -# pragma pack(4) -# elif GST_OMX_STRUCT_PACKING == 8 -# pragma pack(8) -# else -# error "Unsupported struct packing value" -# endif -#endif - -#include -#include - -#ifdef GST_OMX_STRUCT_PACKING -#pragma pack() -#endif - -gint -main (gint argc, gchar ** argv) -{ - gchar *filename; - GModule *core_module; - OMX_ERRORTYPE err; - OMX_ERRORTYPE (*omx_init) (void); - OMX_ERRORTYPE (*omx_component_name_enum) (OMX_STRING cComponentName, - OMX_U32 nNameLength, OMX_U32 nIndex); - OMX_ERRORTYPE (*omx_get_roles_of_component) (OMX_STRING compName, - OMX_U32 * pNumRoles, OMX_U8 ** roles); - guint32 i; - - if (argc != 2) { - g_printerr ("Usage: %s /path/to/libopenmaxil.so\n", argv[0]); - return -1; - } - - filename = argv[1]; - - if (!g_path_is_absolute (filename)) { - g_printerr ("'%s' is not an absolute filename\n", filename); - return -1; - } - - /* Hack for the Broadcom OpenMAX IL implementation */ - if (g_str_has_suffix (filename, "vc/lib/libopenmaxil.so")) { - gchar *bcm_host_filename; - gchar *bcm_host_path; - GModule *bcm_host_module; - void (*bcm_host_init) (void); - - bcm_host_path = g_path_get_dirname (filename); - bcm_host_filename = - g_build_filename (bcm_host_path, "libbcm_host.so", NULL); - - bcm_host_module = g_module_open (bcm_host_filename, G_MODULE_BIND_LAZY); - - g_free (bcm_host_filename); - g_free (bcm_host_path); - - if (!bcm_host_module) { - g_printerr ("Failed to load 'libbcm_host.so'\n"); - return -1; - } - - if (!g_module_symbol (bcm_host_module, "bcm_host_init", - (gpointer *) & bcm_host_init)) { - g_printerr ("Failed to find 'bcm_host_init' in 'libbcm_host.so'\n"); - return -1; - } - - bcm_host_init (); - } - - core_module = g_module_open (filename, G_MODULE_BIND_LAZY); - if (!core_module) { - g_printerr ("Failed to load '%s'\n", filename); - return -1; - } - - if (!g_module_symbol (core_module, "OMX_Init", (gpointer *) & omx_init)) { - g_printerr ("Failed to find '%s' in '%s'\n", "OMX_Init", filename); - return -1; - } - - if (!g_module_symbol (core_module, "OMX_ComponentNameEnum", - (gpointer *) & omx_component_name_enum)) { - g_printerr ("Failed to find '%s' in '%s'\n", "OMX_ComponentNameEnum", - filename); - return -1; - } - - if (!g_module_symbol (core_module, "OMX_GetRolesOfComponent", - (gpointer *) & omx_get_roles_of_component)) { - g_printerr ("Failed to find '%s' in '%s'\n", "OMX_GetRolesOfComponent", - filename); - return -1; - } - - - if ((err = omx_init ()) != OMX_ErrorNone) { - g_printerr ("Failed to initialize core: %d\n", err); - return -1; - } - - i = 0; - while (err == OMX_ErrorNone) { - gchar component_name[1024]; - - err = omx_component_name_enum (component_name, sizeof (component_name), i); - if (err == OMX_ErrorNone || err == OMX_ErrorNoMore) { - guint32 nroles; - - g_print ("Component %d: %s\n", i, component_name); - - if (omx_get_roles_of_component (component_name, (OMX_U32 *) & nroles, - NULL) == OMX_ErrorNone && nroles > 0) { - gchar **roles = g_new (gchar *, nroles); - gint j; - - roles[0] = g_new0 (gchar, 129 * nroles); - for (j = 1; j < nroles; j++) { - roles[j] = roles[j - 1] + 129; - } - - if (omx_get_roles_of_component (component_name, (OMX_U32 *) & nroles, - (OMX_U8 **) roles) == OMX_ErrorNone) { - for (j = 0; j < nroles; j++) { - g_print (" Role %d: %s\n", j, roles[j]); - } - } - g_free (roles[0]); - g_free (roles); - } - } - i++; - } - - return 0; -} diff --git a/subprojects/gst-omx/tools/meson.build b/subprojects/gst-omx/tools/meson.build deleted file mode 100644 index f73996eadc..0000000000 --- a/subprojects/gst-omx/tools/meson.build +++ /dev/null @@ -1,27 +0,0 @@ -gst_tools = { - 'listcomponents': { - 'files': files('listcomponents.c'), - 'include_directories' : [configinc, omx_inc], - 'deps': [gmodule_dep], - 'extra_c_args': gst_omx_args + extra_c_args, - 'install': false, - }, -} - -if not get_option('tools').disabled() and not static_build - foreach tool, data: gst_tools - exe_name = '@0@-@1@'.format(tool, api_version) - executable(exe_name, - data.get('files'), - install: data.get('install', true), - install_tag: 'bin', - include_directories : data.get('include_directories', [configinc]), - dependencies : data.get('deps', []), - c_args: data.get('extra_c_args', []), - ) - - if data.has_key('man_page') - install_man(data.get('man_page')) - endif - endforeach -endif diff --git a/subprojects/gst-plugins-bad/scripts/gen-changelog.py b/subprojects/gst-plugins-bad/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-plugins-bad/scripts/gen-changelog.py +++ b/subprojects/gst-plugins-bad/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-plugins-base/scripts/gen-changelog.py b/subprojects/gst-plugins-base/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-plugins-base/scripts/gen-changelog.py +++ b/subprojects/gst-plugins-base/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-plugins-good/scripts/gen-changelog.py b/subprojects/gst-plugins-good/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-plugins-good/scripts/gen-changelog.py +++ b/subprojects/gst-plugins-good/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-plugins-ugly/scripts/gen-changelog.py b/subprojects/gst-plugins-ugly/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-plugins-ugly/scripts/gen-changelog.py +++ b/subprojects/gst-plugins-ugly/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-python/scripts/gen-changelog.py b/subprojects/gst-python/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-python/scripts/gen-changelog.py +++ b/subprojects/gst-python/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gst-rtsp-server/scripts/gen-changelog.py b/subprojects/gst-rtsp-server/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gst-rtsp-server/scripts/gen-changelog.py +++ b/subprojects/gst-rtsp-server/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gstreamer-sharp/scripts/gen-changelog.py b/subprojects/gstreamer-sharp/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gstreamer-sharp/scripts/gen-changelog.py +++ b/subprojects/gstreamer-sharp/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gstreamer-vaapi/scripts/gen-changelog.py b/subprojects/gstreamer-vaapi/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gstreamer-vaapi/scripts/gen-changelog.py +++ b/subprojects/gstreamer-vaapi/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gstreamer/scripts/gen-changelog.py b/subprojects/gstreamer/scripts/gen-changelog.py index 3924e6ea32..44739f18cc 100755 --- a/subprojects/gstreamer/scripts/gen-changelog.py +++ b/subprojects/gstreamer/scripts/gen-changelog.py @@ -29,7 +29,6 @@ changelog_starts = { 'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14', 'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc', 'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b', - 'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330', 'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2', 'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b', } diff --git a/subprojects/gstreamer/scripts/git-version.sh b/subprojects/gstreamer/scripts/git-version.sh index d96223a87d..fe1313bb52 100755 --- a/subprojects/gstreamer/scripts/git-version.sh +++ b/subprojects/gstreamer/scripts/git-version.sh @@ -12,7 +12,6 @@ for m in \ gst-python gstreamer-sharp \ gnonlin \ gst-rtsp-server \ - gst-omx \ gst-devtools \ ; do if test -d $m; then