y4m: share common code among encoder and decoder
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/8719>
This commit is contained in:
parent
6bcf0e3276
commit
4cf598bcf3
@ -37,6 +37,7 @@
|
||||
#include <string.h>
|
||||
|
||||
#include "gsty4mdec.h"
|
||||
#include "gsty4mformat.h"
|
||||
|
||||
#define MAX_SIZE 32768
|
||||
|
||||
@ -387,6 +388,7 @@ gst_y4m_dec_parse_header (GstY4mDec * y4mdec, char *header)
|
||||
gulong par_n = 0, par_d = 0;
|
||||
gulong width = 0, height = 0;
|
||||
GstVideoFormat format = GST_VIDEO_FORMAT_I420;
|
||||
GstVideoInterlaceMode interlace_mode;
|
||||
|
||||
if (memcmp (header, "YUV4MPEG2 ", 10) != 0) {
|
||||
GST_ERROR_OBJECT (y4mdec, "y4m start code not found");
|
||||
@ -458,59 +460,15 @@ gst_y4m_dec_parse_header (GstY4mDec * y4mdec, char *header)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
gst_video_info_init (&y4mdec->info);
|
||||
gst_video_info_set_format (&y4mdec->out_info, format, width, height);
|
||||
y4mdec->info = y4mdec->out_info;
|
||||
|
||||
switch (y4mdec->info.finfo->format) {
|
||||
case GST_VIDEO_FORMAT_I420:
|
||||
y4mdec->info.offset[0] = 0;
|
||||
y4mdec->info.stride[0] = width;
|
||||
y4mdec->info.offset[1] = y4mdec->info.stride[0] * height;
|
||||
y4mdec->info.stride[1] = GST_ROUND_UP_2 (width) / 2;
|
||||
y4mdec->info.offset[2] =
|
||||
y4mdec->info.offset[1] +
|
||||
y4mdec->info.stride[1] * (GST_ROUND_UP_2 (height) / 2);
|
||||
y4mdec->info.stride[2] = GST_ROUND_UP_2 (width) / 2;
|
||||
y4mdec->info.size =
|
||||
y4mdec->info.offset[2] +
|
||||
y4mdec->info.stride[2] * (GST_ROUND_UP_2 (height) / 2);
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y42B:
|
||||
y4mdec->info.offset[0] = 0;
|
||||
y4mdec->info.stride[0] = width;
|
||||
y4mdec->info.offset[1] = y4mdec->info.stride[0] * height;
|
||||
y4mdec->info.stride[1] = GST_ROUND_UP_2 (width) / 2;
|
||||
y4mdec->info.offset[2] =
|
||||
y4mdec->info.offset[1] + y4mdec->info.stride[1] * height;
|
||||
y4mdec->info.stride[2] = GST_ROUND_UP_2 (width) / 2;
|
||||
y4mdec->info.size =
|
||||
y4mdec->info.offset[2] + y4mdec->info.stride[2] * height;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y444:
|
||||
y4mdec->info.offset[0] = 0;
|
||||
y4mdec->info.stride[0] = width;
|
||||
y4mdec->info.offset[1] = y4mdec->info.stride[0] * height;
|
||||
y4mdec->info.stride[1] = width;
|
||||
y4mdec->info.offset[2] =
|
||||
y4mdec->info.offset[1] + y4mdec->info.stride[1] * height;
|
||||
y4mdec->info.stride[2] = width;
|
||||
y4mdec->info.size =
|
||||
y4mdec->info.offset[2] + y4mdec->info.stride[2] * height;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
switch (interlaced_char) {
|
||||
case 0:
|
||||
case '?':
|
||||
case 'p':
|
||||
y4mdec->info.interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
||||
interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
||||
break;
|
||||
case 't':
|
||||
case 'b':
|
||||
y4mdec->info.interlace_mode = GST_VIDEO_INTERLACE_MODE_INTERLEAVED;
|
||||
interlace_mode = GST_VIDEO_INTERLACE_MODE_INTERLEAVED;
|
||||
break;
|
||||
default:
|
||||
GST_ERROR_OBJECT (y4mdec, "Unknown interlaced char '%c'",
|
||||
@ -528,10 +486,17 @@ gst_y4m_dec_parse_header (GstY4mDec * y4mdec, char *header)
|
||||
if (par_d == 0)
|
||||
par_d = 1;
|
||||
|
||||
y4mdec->info.fps_n = fps_n;
|
||||
y4mdec->info.fps_d = fps_d;
|
||||
y4mdec->info.par_n = par_n;
|
||||
y4mdec->info.par_d = par_d;
|
||||
gst_video_info_set_interlaced_format (&y4mdec->out_info, format,
|
||||
interlace_mode, width, height);
|
||||
|
||||
GST_VIDEO_INFO_FPS_N (&y4mdec->out_info) = fps_n;
|
||||
GST_VIDEO_INFO_FPS_D (&y4mdec->out_info) = fps_d;
|
||||
GST_VIDEO_INFO_PAR_N (&y4mdec->out_info) = par_n;
|
||||
GST_VIDEO_INFO_PAR_D (&y4mdec->out_info) = par_d;
|
||||
|
||||
if (!gst_y4m_video_unpadded_info (&y4mdec->info, &y4mdec->out_info))
|
||||
return FALSE;
|
||||
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
@ -43,6 +43,7 @@
|
||||
#include <string.h>
|
||||
|
||||
#include "gsty4menc.h"
|
||||
#include "gsty4mformat.h"
|
||||
|
||||
/* Filter signals and args */
|
||||
enum
|
||||
@ -139,69 +140,30 @@ gst_y4m_encode_set_format (GstVideoEncoder * encoder,
|
||||
GstY4mEncode *y4menc;
|
||||
GstVideoInfo *info, out_info;
|
||||
GstVideoCodecState *output_state;
|
||||
gint width, height;
|
||||
GstVideoFormat format;
|
||||
gsize cr_h;
|
||||
|
||||
y4menc = GST_Y4M_ENCODE (encoder);
|
||||
info = &state->info;
|
||||
|
||||
format = GST_VIDEO_INFO_FORMAT (info);
|
||||
width = GST_VIDEO_INFO_WIDTH (info);
|
||||
height = GST_VIDEO_INFO_HEIGHT (info);
|
||||
|
||||
gst_video_info_set_format (&out_info, format, width, height);
|
||||
|
||||
switch (format) {
|
||||
switch (GST_VIDEO_INFO_FORMAT (info)) {
|
||||
case GST_VIDEO_FORMAT_I420:
|
||||
y4menc->colorspace = "420";
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = GST_ROUND_UP_2 (width) / 2;
|
||||
out_info.stride[2] = out_info.stride[1];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
cr_h = GST_ROUND_UP_2 (height) / 2;
|
||||
if (GST_VIDEO_INFO_IS_INTERLACED (info))
|
||||
cr_h = GST_ROUND_UP_2 (height);
|
||||
out_info.offset[2] = out_info.offset[1] + out_info.stride[1] * cr_h;
|
||||
out_info.size = out_info.offset[2] + out_info.stride[2] * cr_h;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y42B:
|
||||
y4menc->colorspace = "422";
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = GST_ROUND_UP_2 (width) / 2;
|
||||
out_info.stride[2] = out_info.stride[1];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
out_info.offset[2] = out_info.offset[1] + out_info.stride[1] * height;
|
||||
/* simplification of ROUNDUP4(w)*h + 2*(ROUNDUP8(w)/2)*h */
|
||||
out_info.size = out_info.offset[2] + out_info.stride[2] * height;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y41B:
|
||||
y4menc->colorspace = "411";
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = GST_ROUND_UP_2 (width) / 4;
|
||||
out_info.stride[2] = out_info.stride[1];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
out_info.offset[2] = out_info.offset[1] + out_info.stride[1] * height;
|
||||
/* simplification of ROUNDUP4(w)*h + 2*((ROUNDUP16(w)/4)*h */
|
||||
out_info.size = (width + (GST_ROUND_UP_2 (width) / 2)) * height;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y444:
|
||||
y4menc->colorspace = "444";
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = out_info.stride[0];
|
||||
out_info.stride[2] = out_info.stride[0];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
out_info.offset[2] = out_info.offset[1] * 2;
|
||||
out_info.size = out_info.stride[0] * height * 3;
|
||||
break;
|
||||
default:
|
||||
goto invalid_format;
|
||||
}
|
||||
|
||||
if (!gst_y4m_video_unpadded_info (&out_info, info))
|
||||
goto invalid_format;
|
||||
|
||||
y4menc->info = *info;
|
||||
y4menc->out_info = out_info;
|
||||
y4menc->padded = !gst_video_info_is_equal (info, &out_info);
|
||||
|
93
subprojects/gst-plugins-good/gst/y4m/gsty4mformat.c
Normal file
93
subprojects/gst-plugins-good/gst/y4m/gsty4mformat.c
Normal file
@ -0,0 +1,93 @@
|
||||
/* GStreamer
|
||||
* Copyright (C) 2025 Igalia, S.L.
|
||||
* Author: Victor Jaquez <vjaquez@igalia.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
* Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include "gsty4mformat.h"
|
||||
|
||||
gboolean
|
||||
gst_y4m_video_unpadded_info (GstVideoInfo * y4m_info,
|
||||
const GstVideoInfo * vinfo)
|
||||
{
|
||||
g_return_val_if_fail (y4m_info && vinfo, FALSE);
|
||||
|
||||
gsize cr_h;
|
||||
guint width, height;
|
||||
GstVideoFormat format;
|
||||
GstVideoInfo out_info;
|
||||
|
||||
format = GST_VIDEO_INFO_FORMAT (vinfo);
|
||||
width = GST_VIDEO_INFO_WIDTH (vinfo);
|
||||
height = GST_VIDEO_INFO_HEIGHT (vinfo);
|
||||
|
||||
out_info = *vinfo;
|
||||
|
||||
switch (format) {
|
||||
case GST_VIDEO_FORMAT_I420:
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = GST_ROUND_UP_2 (width) / 2;
|
||||
out_info.stride[2] = out_info.stride[1];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
cr_h = GST_ROUND_UP_2 (height) / 2;
|
||||
if (GST_VIDEO_INFO_IS_INTERLACED (vinfo))
|
||||
cr_h = GST_ROUND_UP_2 (height);
|
||||
out_info.offset[2] = out_info.offset[1] + out_info.stride[1] * cr_h;
|
||||
out_info.size = out_info.offset[2] + out_info.stride[2] * cr_h;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y42B:
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = GST_ROUND_UP_2 (width) / 2;
|
||||
out_info.stride[2] = out_info.stride[1];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
out_info.offset[2] = out_info.offset[1] + out_info.stride[1] * height;
|
||||
/* simplification of ROUNDUP4(w)*h + 2*(ROUNDUP8(w)/2)*h */
|
||||
out_info.size = out_info.offset[2] + out_info.stride[2] * height;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y41B:
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = GST_ROUND_UP_2 (width) / 4;
|
||||
out_info.stride[2] = out_info.stride[1];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
out_info.offset[2] = out_info.offset[1] + out_info.stride[1] * height;
|
||||
/* simplification of ROUNDUP4(w)*h + 2*((ROUNDUP16(w)/4)*h */
|
||||
out_info.size = (width + (GST_ROUND_UP_2 (width) / 2)) * height;
|
||||
break;
|
||||
case GST_VIDEO_FORMAT_Y444:
|
||||
out_info.stride[0] = width;
|
||||
out_info.stride[1] = out_info.stride[0];
|
||||
out_info.stride[2] = out_info.stride[0];
|
||||
out_info.offset[0] = 0;
|
||||
out_info.offset[1] = out_info.stride[0] * height;
|
||||
out_info.offset[2] = out_info.offset[1] * 2;
|
||||
out_info.size = out_info.stride[0] * height * 3;
|
||||
break;
|
||||
default:
|
||||
GST_FIXME ("%s is not supported", gst_video_format_to_string (format));
|
||||
}
|
||||
|
||||
*y4m_info = out_info;
|
||||
|
||||
return TRUE;
|
||||
}
|
27
subprojects/gst-plugins-good/gst/y4m/gsty4mformat.h
Normal file
27
subprojects/gst-plugins-good/gst/y4m/gsty4mformat.h
Normal file
@ -0,0 +1,27 @@
|
||||
/* GStreamer
|
||||
* Copyright (C) 2025 Igalia, S.L.
|
||||
* Author: Victor Jaquez <vjaquez@igalia.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
* Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <gst/gst.h>
|
||||
#include <gst/video/video.h>
|
||||
|
||||
gboolean gst_y4m_video_unpadded_info (GstVideoInfo * y4m_info,
|
||||
const GstVideoInfo * vinfo);
|
@ -1,5 +1,6 @@
|
||||
y4m_sources = [
|
||||
'plugin.c',
|
||||
'gsty4mformat.c',
|
||||
'gsty4menc.c',
|
||||
'gsty4mdec.c'
|
||||
]
|
||||
|
Loading…
x
Reference in New Issue
Block a user