mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-25 03:01:03 +00:00
gst-omx: Retire the whole package
The OpenMAX standard is long dead and even the Raspberry Pi OS no longer supports it. Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4976>
This commit is contained in:
parent
62d3e8fc32
commit
48c43e5b7f
136 changed files with 0 additions and 37670 deletions
2
.gitignore
vendored
2
.gitignore
vendored
|
@ -22,7 +22,6 @@ prefix/
|
||||||
/gst-integration-testsuites
|
/gst-integration-testsuites
|
||||||
/gst-editing-services
|
/gst-editing-services
|
||||||
/gstreamer-vaapi
|
/gstreamer-vaapi
|
||||||
/gst-omx
|
|
||||||
/gstreamer-sharp
|
/gstreamer-sharp
|
||||||
/pygobject
|
/pygobject
|
||||||
/gst-python
|
/gst-python
|
||||||
|
@ -47,7 +46,6 @@ subprojects/*/
|
||||||
!subprojects/gst-examples
|
!subprojects/gst-examples
|
||||||
!subprojects/gst-integration-testsuites
|
!subprojects/gst-integration-testsuites
|
||||||
!subprojects/gst-libav
|
!subprojects/gst-libav
|
||||||
!subprojects/gst-omx
|
|
||||||
!subprojects/gst-plugins-bad
|
!subprojects/gst-plugins-bad
|
||||||
!subprojects/gst-plugins-base
|
!subprojects/gst-plugins-base
|
||||||
!subprojects/gst-plugins-good
|
!subprojects/gst-plugins-good
|
||||||
|
|
|
@ -61,8 +61,6 @@ variables:
|
||||||
SIMPLE_BUILD: >-
|
SIMPLE_BUILD: >-
|
||||||
${DEFAULT_MESON_ARGS}
|
${DEFAULT_MESON_ARGS}
|
||||||
-Dsharp=enabled
|
-Dsharp=enabled
|
||||||
-Domx=enabled
|
|
||||||
-Dgst-omx:target=generic
|
|
||||||
-Ddoc=disabled
|
-Ddoc=disabled
|
||||||
|
|
||||||
workflow:
|
workflow:
|
||||||
|
@ -287,7 +285,6 @@ commitlint:
|
||||||
- subprojects/gst-editing-services/**/*
|
- subprojects/gst-editing-services/**/*
|
||||||
- subprojects/gst-integration-testsuites/**/*
|
- subprojects/gst-integration-testsuites/**/*
|
||||||
- subprojects/gst-libav/**/*
|
- subprojects/gst-libav/**/*
|
||||||
- subprojects/gst-omx/**/*
|
|
||||||
- subprojects/gst-plugins-bad/**/*
|
- subprojects/gst-plugins-bad/**/*
|
||||||
- subprojects/gst-plugins-base/**/*
|
- subprojects/gst-plugins-base/**/*
|
||||||
- subprojects/gst-plugins-good/**/*
|
- subprojects/gst-plugins-good/**/*
|
||||||
|
@ -598,7 +595,6 @@ integration testsuites fedora:
|
||||||
variables:
|
variables:
|
||||||
MESON_ARGS: >-
|
MESON_ARGS: >-
|
||||||
${SIMPLE_BUILD}
|
${SIMPLE_BUILD}
|
||||||
-Domx=disabled
|
|
||||||
-Dsharp=disabled
|
-Dsharp=disabled
|
||||||
-Dvaapi=disabled
|
-Dvaapi=disabled
|
||||||
-Dexamples=disabled
|
-Dexamples=disabled
|
||||||
|
@ -845,7 +841,6 @@ build documentation:
|
||||||
- subprojects/gst-devtools/**/*
|
- subprojects/gst-devtools/**/*
|
||||||
- subprojects/gst-editing-services/**/*
|
- subprojects/gst-editing-services/**/*
|
||||||
- subprojects/gst-libav/**/*
|
- subprojects/gst-libav/**/*
|
||||||
- subprojects/gst-omx/**/*
|
|
||||||
- subprojects/gst-plugins-bad/**/*
|
- subprojects/gst-plugins-bad/**/*
|
||||||
- subprojects/gst-plugins-base/**/*
|
- subprojects/gst-plugins-base/**/*
|
||||||
- subprojects/gst-plugins-good/**/*
|
- subprojects/gst-plugins-good/**/*
|
||||||
|
|
|
@ -105,7 +105,6 @@ dnf install -y \
|
||||||
valgrind \
|
valgrind \
|
||||||
vulkan \
|
vulkan \
|
||||||
vulkan-devel \
|
vulkan-devel \
|
||||||
mesa-omx-drivers \
|
|
||||||
mesa-libGL \
|
mesa-libGL \
|
||||||
mesa-libGL-devel \
|
mesa-libGL-devel \
|
||||||
mesa-libGLU \
|
mesa-libGLU \
|
||||||
|
|
|
@ -84,7 +84,6 @@ meson \
|
||||||
-Dbad=disabled \
|
-Dbad=disabled \
|
||||||
-Dlibav=disabled \
|
-Dlibav=disabled \
|
||||||
-Dges=disabled \
|
-Dges=disabled \
|
||||||
-Domx=disabled \
|
|
||||||
-Dvaapi=disabled \
|
-Dvaapi=disabled \
|
||||||
-Dsharp=disabled \
|
-Dsharp=disabled \
|
||||||
-Drs=disabled \
|
-Drs=disabled \
|
||||||
|
|
|
@ -28,9 +28,6 @@ werror = true
|
||||||
[gst-docs:built-in options]
|
[gst-docs:built-in options]
|
||||||
werror = true
|
werror = true
|
||||||
|
|
||||||
[gst-omx:built-in options]
|
|
||||||
werror = true
|
|
||||||
|
|
||||||
[gst-devtools:built-in options]
|
[gst-devtools:built-in options]
|
||||||
werror = true
|
werror = true
|
||||||
|
|
||||||
|
|
|
@ -453,10 +453,6 @@ def get_subprocess_env(options, gst_version):
|
||||||
encoding_targets.add(
|
encoding_targets.add(
|
||||||
os.path.abspath(os.path.join(os.path.dirname(path), '..')))
|
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):
|
for p in sorted(presets):
|
||||||
prepend_env_var(env, 'GST_PRESET_PATH', p, options.sysroot)
|
prepend_env_var(env, 'GST_PRESET_PATH', p, options.sysroot)
|
||||||
|
|
||||||
|
|
|
@ -105,7 +105,6 @@ subprojects = [
|
||||||
['gst-integration-testsuites', { 'option': get_option('devtools') }],
|
['gst-integration-testsuites', { 'option': get_option('devtools') }],
|
||||||
['gst-editing-services', { 'option': get_option('ges'), 'build-hotdoc': true}],
|
['gst-editing-services', { 'option': get_option('ges'), 'build-hotdoc': true}],
|
||||||
['gstreamer-vaapi', { 'option': get_option('vaapi'), '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') }],
|
['gstreamer-sharp', { 'option': get_option('sharp') }],
|
||||||
['pygobject', { 'option': get_option('python'), 'match_gst_version': false, 'sysdep': 'pygobject-3.0', 'sysdep_version': '>= 3.8' }],
|
['pygobject', { 'option': get_option('python'), 'match_gst_version': false, 'sysdep': 'pygobject-3.0', 'sysdep_version': '>= 3.8' }],
|
||||||
['gst-python', { 'option': get_option('python')}],
|
['gst-python', { 'option': get_option('python')}],
|
||||||
|
|
|
@ -8,7 +8,6 @@ option('devtools', type : 'feature', value : 'enabled')
|
||||||
option('ges', type : 'feature', value : 'enabled')
|
option('ges', type : 'feature', value : 'enabled')
|
||||||
option('rtsp_server', type : 'feature', value : 'enabled')
|
option('rtsp_server', type : 'feature', value : 'enabled')
|
||||||
option('rs', type : 'feature', value : 'disabled')
|
option('rs', type : 'feature', value : 'disabled')
|
||||||
option('omx', type : 'feature', value : 'disabled')
|
|
||||||
option('vaapi', type : 'feature', value : 'disabled')
|
option('vaapi', type : 'feature', value : 'disabled')
|
||||||
option('gst-examples', type : 'feature', value : 'auto', description : 'Build gst-examples subproject')
|
option('gst-examples', type : 'feature', value : 'auto', description : 'Build gst-examples subproject')
|
||||||
# Bindings
|
# Bindings
|
||||||
|
|
|
@ -29,7 +29,6 @@ changelog_starts = {
|
||||||
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
||||||
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
||||||
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
||||||
'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330',
|
|
||||||
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
||||||
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,7 +13,6 @@ release_modules = [
|
||||||
'gst-devtools',
|
'gst-devtools',
|
||||||
'gst-python',
|
'gst-python',
|
||||||
'gstreamer-vaapi',
|
'gstreamer-vaapi',
|
||||||
'gst-omx',
|
|
||||||
'gst-docs',
|
'gst-docs',
|
||||||
'gstreamer-sharp',
|
'gstreamer-sharp',
|
||||||
]
|
]
|
||||||
|
|
|
@ -101,7 +101,6 @@ GST_PROJECTS = [
|
||||||
'gstreamer-vaapi',
|
'gstreamer-vaapi',
|
||||||
'gstreamer-sharp',
|
'gstreamer-sharp',
|
||||||
'gst-python',
|
'gst-python',
|
||||||
'gst-omx',
|
|
||||||
'gst-editing-services',
|
'gst-editing-services',
|
||||||
'gst-devtools',
|
'gst-devtools',
|
||||||
'gst-docs',
|
'gst-docs',
|
||||||
|
@ -120,7 +119,6 @@ GST_PROJECTS_ID = {
|
||||||
'gst-plugins-good': 1353,
|
'gst-plugins-good': 1353,
|
||||||
'gst-plugins-base': 1352,
|
'gst-plugins-base': 1352,
|
||||||
'gst-plugins-bad': 1351,
|
'gst-plugins-bad': 1351,
|
||||||
'gst-omx': 1350,
|
|
||||||
'gst-libav': 1349,
|
'gst-libav': 1349,
|
||||||
'gst-integration-testsuites': 1348,
|
'gst-integration-testsuites': 1348,
|
||||||
'gst-examples': 1347,
|
'gst-examples': 1347,
|
||||||
|
|
|
@ -29,7 +29,6 @@ changelog_starts = {
|
||||||
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
||||||
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
||||||
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
||||||
'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330',
|
|
||||||
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
||||||
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
||||||
}
|
}
|
||||||
|
|
|
@ -43,14 +43,6 @@ Technologies](http://en.wikipedia.org/wiki/Imagination_Technologies) or
|
||||||
[S3 Graphics](http://en.wikipedia.org/wiki/S3_Graphics). Accessible to
|
[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.
|
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)
|
- [OVD](http://developer.amd.com/sdks/AMDAPPSDK/assets/OpenVideo_Decode_API.PDF)
|
||||||
(*Open Video Decode*): Another API from [AMD
|
(*Open Video Decode*): Another API from [AMD
|
||||||
Graphics](http://en.wikipedia.org/wiki/AMD_Graphics), designed to be a
|
Graphics](http://en.wikipedia.org/wiki/AMD_Graphics), designed to be a
|
||||||
|
|
|
@ -29,7 +29,6 @@ changelog_starts = {
|
||||||
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
||||||
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
||||||
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
||||||
'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330',
|
|
||||||
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
||||||
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,7 +29,6 @@ changelog_starts = {
|
||||||
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
||||||
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
||||||
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
||||||
'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330',
|
|
||||||
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
||||||
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,7 +29,6 @@ changelog_starts = {
|
||||||
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
'gst-editing-services': 'ee8bf88ebf131cf7c7161356540efc20bf411e14',
|
||||||
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
'gst-python': 'b3e564eff577e2f577d795051bbcca85d47c89dc',
|
||||||
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
'gstreamer-vaapi': 'c89e9afc5d43837c498a55f8f13ddf235442b83b',
|
||||||
'gst-omx': 'd2463b017f222e678978582544a9c9a80edfd330',
|
|
||||||
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
'gst-devtools': 'da962d096af9460502843e41b7d25fdece7ff1c2',
|
||||||
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
'gstreamer-sharp': 'b94528f8e7979df49fedf137dfa228d8fe475e1b',
|
||||||
}
|
}
|
||||||
|
|
3
subprojects/gst-omx/.gitignore
vendored
3
subprojects/gst-omx/.gitignore
vendored
|
@ -1,3 +0,0 @@
|
||||||
*~
|
|
||||||
*.bak
|
|
||||||
*.swp
|
|
|
@ -1,2 +0,0 @@
|
||||||
Sebastian Dröge <sebastian.droege@collabora.co.uk>
|
|
||||||
|
|
|
@ -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.
|
|
||||||
|
|
||||||
<one line to give the library's name and a brief idea of what it does.>
|
|
||||||
Copyright (C) <year> <name of author>
|
|
||||||
|
|
||||||
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.
|
|
||||||
|
|
||||||
<signature of Ty Coon>, 1 April 1990
|
|
||||||
Ty Coon, President of Vice
|
|
||||||
|
|
||||||
That's all there is to it!
|
|
File diff suppressed because it is too large
Load diff
|
@ -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
|
|
|
@ -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
|
|
|
@ -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
|
|
|
@ -1 +0,0 @@
|
||||||
install_data (['gstomx.conf'], install_dir : omx_conf_dir)
|
|
|
@ -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
|
|
|
@ -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}
|
|
||||||
|
|
|
@ -1 +0,0 @@
|
||||||
install_data (['gstomx.conf'], install_dir : omx_conf_dir)
|
|
|
@ -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
|
|
|
@ -1,5 +0,0 @@
|
||||||
tizonia_cdata = cdata
|
|
||||||
configure_file(input : 'gstomx.conf.in',
|
|
||||||
output : 'gstomx.conf',
|
|
||||||
configuration : tizonia_cdata,
|
|
||||||
install_dir : omx_conf_dir)
|
|
|
@ -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
|
|
|
@ -1 +0,0 @@
|
||||||
install_data (['gstomx.conf'], install_dir : omx_conf_dir)
|
|
|
@ -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"
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,3 +0,0 @@
|
||||||
---
|
|
||||||
short-description: GStreamer plugins from OpenMax
|
|
||||||
...
|
|
|
@ -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)
|
|
||||||
|
|
|
@ -1 +0,0 @@
|
||||||
gst-index
|
|
|
@ -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,
|
|
||||||
};
|
|
||||||
|
|
|
@ -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
|
|
File diff suppressed because it is too large
Load diff
|
@ -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
|
|
|
@ -1,412 +0,0 @@
|
||||||
<Project
|
|
||||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
|
||||||
xmlns:rdfs="http://www.w3.org/2000/01/rdf-schema#"
|
|
||||||
xmlns="http://usefulinc.com/ns/doap#"
|
|
||||||
xmlns:foaf="http://xmlns.com/foaf/0.1/"
|
|
||||||
xmlns:admin="http://webns.net/mvcb/">
|
|
||||||
|
|
||||||
<name>GStreamer OpenMAX IL wrapper plugin</name>
|
|
||||||
<shortname>gst-omx</shortname>
|
|
||||||
<homepage rdf:resource="http://gstreamer.freedesktop.org/modules/gst-omx.html" />
|
|
||||||
<created>2005-06-17</created>
|
|
||||||
<shortdesc xml:lang="en">
|
|
||||||
a basic collection of elements
|
|
||||||
</shortdesc>
|
|
||||||
<description xml:lang="en">
|
|
||||||
This plugin wraps available OpenMAX IL components and makes
|
|
||||||
them available as standard GStreamer elements.
|
|
||||||
</description>
|
|
||||||
<category></category>
|
|
||||||
<bug-database rdf:resource="https://gitlab.freedesktop.org/gstreamer/gst-omx/issues/" />
|
|
||||||
<screenshots></screenshots>
|
|
||||||
<mailing-list rdf:resource="http://lists.freedesktop.org/mailman/listinfo/gstreamer-devel" />
|
|
||||||
<programming-language>C</programming-language>
|
|
||||||
<license rdf:resource="http://usefulinc.com/doap/licenses/lgpl"/>
|
|
||||||
<download-page rdf:resource="http://gstreamer.freedesktop.org/download/" />
|
|
||||||
|
|
||||||
<repository>
|
|
||||||
<GitRepository>
|
|
||||||
<location rdf:resource="git://gitlab.freedesktop.org/gstreamer/gst-omx"/>
|
|
||||||
<browse rdf:resource="http://gitlab.freedesktop.org/gstreamer/gst-omx"/>
|
|
||||||
</GitRepository>
|
|
||||||
</repository>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.22.0</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2023-01-23</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.22.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.21.90</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2023-01-13</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.21.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.21.3</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2022-12-05</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.21.3.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.21.2</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2022-11-07</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.21.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.21.1</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2022-10-04</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.21.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.20.0</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2022-02-03</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.20.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.19.90</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2022-01-28</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.19.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.19.3</revision>
|
|
||||||
<branch>main</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2021-11-03</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.19.3.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.19.2</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2021-09-23</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.19.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.19.1</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2021-06-01</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.19.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.18.0</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2020-09-08</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.18.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.17.90</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2020-08-20</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.17.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.17.2</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2020-07-03</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.17.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.17.1</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2020-06-19</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.17.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.16.0</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2019-04-19</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.16.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.15.90</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2019-04-11</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.15.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.15.2</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2019-02-26</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.15.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.15.1</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2019-01-17</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.15.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.14.0</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2018-03-19</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.14.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.13.91</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2018-03-13</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.13.91.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.13.90</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2018-03-03</created>
|
|
||||||
<file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.13.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.13.1</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2018-02-15</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.13.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.12.4</revision>
|
|
||||||
<branch>1.12</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-12-07</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.12.4.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.12.3</revision>
|
|
||||||
<branch>1.12</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-09-18</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.12.3.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.12.2</revision>
|
|
||||||
<branch>1.12</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-07-14</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.12.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.12.1</revision>
|
|
||||||
<branch>1.12</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-06-20</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.12.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.12.0</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-05-04</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.12.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.11.91</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-04-27</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.11.91.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.11.90</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-04-07</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.11.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.11.2</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-02-24</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.11.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.11.1</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2017-01-12</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.11.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.10.0</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2016-11-01</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.10.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.9.90</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2016-09-30</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.9.90.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.9.2</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2016-09-01</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.9.2.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.9.1</revision>
|
|
||||||
<branch>master</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2016-06-06</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.9.1.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.2.0</revision>
|
|
||||||
<branch>1.2</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2014-07-23</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.2.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<release>
|
|
||||||
<Version>
|
|
||||||
<revision>1.0.0</revision>
|
|
||||||
<branch>1.0</branch>
|
|
||||||
<name></name>
|
|
||||||
<created>2013-03-22</created>
|
|
||||||
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gst-omx/gst-omx-1.0.0.tar.xz" />
|
|
||||||
</Version>
|
|
||||||
</release>
|
|
||||||
|
|
||||||
<maintainer>
|
|
||||||
<foaf:Person>
|
|
||||||
<foaf:name>Sebastian Dröge</foaf:name>
|
|
||||||
<foaf:mbox_sha1sum>7c1069ea873ef7751e4eca5f1a42744b0e9a3a0a</foaf:mbox_sha1sum>
|
|
||||||
</foaf:Person>
|
|
||||||
</maintainer>
|
|
||||||
|
|
||||||
</Project>
|
|
|
@ -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 <OMX_VideoExt.h>'''
|
|
||||||
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())
|
|
|
@ -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)
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,493 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, Collabora Ltd.
|
|
||||||
* Copyright (C) 2013, Collabora Ltd.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>
|
|
||||||
*
|
|
||||||
* 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 <gmodule.h>
|
|
||||||
#include <gst/gst.h>
|
|
||||||
#include <gst/video/video.h>
|
|
||||||
#include <string.h>
|
|
||||||
|
|
||||||
#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 <OMX_Core.h>
|
|
||||||
#include <OMX_Component.h>
|
|
||||||
|
|
||||||
#ifdef USE_OMX_TARGET_RPI
|
|
||||||
#include <OMX_Broadcom.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_VIDEO_EXT
|
|
||||||
#include <OMX_VideoExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_INDEX_EXT
|
|
||||||
#include <OMX_IndexExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_COMPONENT_EXT
|
|
||||||
#include <OMX_ComponentExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_CORE_EXT
|
|
||||||
#include <OMX_CoreExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_AUDIO_EXT
|
|
||||||
#include <OMX_AudioExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_IV_COMMON_EXT
|
|
||||||
#include <OMX_IVCommonExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_IMAGE_EXT
|
|
||||||
#include <OMX_ImageExt.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef HAVE_OTHER_EXT
|
|
||||||
#include <OMX_OtherExt.h>
|
|
||||||
#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__ */
|
|
|
@ -1,296 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian@centricular.com>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,511 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,65 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,554 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2019, Collabora Ltd.
|
|
||||||
* Author: George Kiagiadakis <george.kiagiadakis@collabora.com>
|
|
||||||
*
|
|
||||||
* 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/allocators/gstdmabuf.h>
|
|
||||||
|
|
||||||
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);
|
|
||||||
}
|
|
|
@ -1,114 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2019, Collabora Ltd.
|
|
||||||
* Author: George Kiagiadakis <george.kiagiadakis@collabora.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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
|
|
|
@ -1,220 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
* Copyright (C) 2014, LG Electronics, Inc. <jun.ji@lge.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian@centricular.com>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,61 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,64 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Fluendo, S.A.
|
|
||||||
* Copyright (C) 2014, Metrological Media Innovations B.V.
|
|
||||||
* Author: Josep Torra <josep@fluendo.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <josep@fluendo.com>");
|
|
||||||
|
|
||||||
gst_omx_set_default_role (&audiosink_class->cdata, "audio_render.local");
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
gst_omx_analog_audio_sink_init (GstOMXAnalogAudioSink * self)
|
|
||||||
{
|
|
||||||
}
|
|
|
@ -1,61 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Fluendo, S.A.
|
|
||||||
* Copyright (C) 2014, Metrological Media Innovations B.V.
|
|
||||||
* Author: Josep Torra <josep@fluendo.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,100 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#include <gst/audio/audio.h>
|
|
||||||
#include <gst/audio/gstaudiodecoder.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,87 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#include <gst/audio/audio.h>
|
|
||||||
#include <gst/audio/gstaudioencoder.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,103 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Fluendo, S.A.
|
|
||||||
* Copyright (C) 2014, Metrological Media Innovations B.V.
|
|
||||||
* Author: Josep Torra <josep@fluendo.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#include <gst/audio/audio.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,674 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, Collabora Ltd.
|
|
||||||
* Copyright (C) 2013-2019, Collabora Ltd.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>
|
|
||||||
* George Kiagiadakis <george.kiagiadakis@collabora.com>
|
|
||||||
*
|
|
||||||
* 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/allocators/gstdmabuf.h>
|
|
||||||
|
|
||||||
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);
|
|
||||||
}
|
|
|
@ -1,101 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright 2014 Advanced Micro Devices, Inc.
|
|
||||||
* Author: Christian König <christian.koenig@amd.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#include <gst/video/gstvideometa.h>
|
|
||||||
#include <gst/video/gstvideopool.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
|
@ -1,99 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,302 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,216 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,894 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#include "gstomxh264enc.h"
|
|
||||||
#include "gstomxh264utils.h"
|
|
||||||
|
|
||||||
#ifdef USE_OMX_TARGET_RPI
|
|
||||||
#include <OMX_Broadcom.h>
|
|
||||||
#include <OMX_Index.h>
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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);
|
|
||||||
}
|
|
|
@ -1,73 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,131 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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;
|
|
||||||
}
|
|
|
@ -1,36 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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__ */
|
|
|
@ -1,224 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Copyright (C) 2017 Xilinx, Inc.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,61 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Copyright (C) 2017 Xilinx, Inc.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,748 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Copyright (C) 2017 Xilinx, Inc.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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);
|
|
||||||
}
|
|
|
@ -1,72 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Copyright (C) 2017 Xilinx, Inc.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,138 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Copyright (C) 2017 Xilinx, Inc.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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;
|
|
||||||
}
|
|
|
@ -1,37 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Copyright (C) 2017 Xilinx, Inc.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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__ */
|
|
|
@ -1,66 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Fluendo, S.A.
|
|
||||||
* Copyright (C) 2014, Metrological Media Innovations B.V.
|
|
||||||
* Author: Josep Torra <josep@fluendo.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <josep@fluendo.com>");
|
|
||||||
|
|
||||||
gst_omx_set_default_role (&audiosink_class->cdata, "audio_render.hdmi");
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
gst_omx_hdmi_audio_sink_init (GstOMXHdmiAudioSink * self)
|
|
||||||
{
|
|
||||||
}
|
|
|
@ -1,61 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Fluendo, S.A.
|
|
||||||
* Copyright (C) 2014, Metrological Media Innovations B.V.
|
|
||||||
* Author: Josep Torra <josep@fluendo.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,98 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2013, Collabora Ltd.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,246 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian@centricular.com>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2014, Sebastian Dröge <sebastian@centricular.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,278 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2017
|
|
||||||
* Author: Julien Isorce <julien.isorce@gmail.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <julien.isorce@gmail.com>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,65 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2017
|
|
||||||
* Author: Julien Isorce <julien.isorce@gmail.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,101 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,59 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
|
@ -1,102 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,336 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,157 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2013, Collabora Ltd.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
|
|
||||||
#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 <sebastian.droege@collabora.co.uk>");
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,61 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2013, Collabora Ltd.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#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__ */
|
|
||||||
|
|
|
@ -1,356 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, Collabora Ltd.
|
|
||||||
* Copyright (C) 2013, Collabora Ltd.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk> *
|
|
||||||
* Copyright 2014 Advanced Micro Devices, Inc.
|
|
||||||
* Author: Christian König <christian.koenig@amd.com>
|
|
||||||
*
|
|
||||||
* 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 <math.h>
|
|
||||||
|
|
||||||
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;
|
|
||||||
}
|
|
|
@ -1,74 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright 2014 Advanced Micro Devices, Inc.
|
|
||||||
* Author: Christian König <christian.koenig@amd.com>
|
|
||||||
*
|
|
||||||
* 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 <gst/gst.h>
|
|
||||||
#include <gst/video/video.h>
|
|
||||||
#include <gst/video/gstvideodecoder.h>
|
|
||||||
#include <gst/video/gstvideoencoder.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,119 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#include <gst/video/video.h>
|
|
||||||
#include <gst/video/gstvideodecoder.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,133 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2011, Hewlett-Packard Development Company, L.P.
|
|
||||||
* Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>, 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 <gst/gst.h>
|
|
||||||
#include <gst/video/video.h>
|
|
||||||
#include <gst/video/gstvideoencoder.h>
|
|
||||||
|
|
||||||
#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__ */
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue