deinterlace: Add support for high bitdepth planar YUV formats

Add C implementation for high bitdepth planar YUV formats

Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/1476>
This commit is contained in:
Seungha Yang 2021-12-23 18:23:57 +09:00
parent aabe9136f6
commit 52cb42f4bb
13 changed files with 844 additions and 7 deletions

View file

@ -4892,12 +4892,12 @@
"long-name": "Deinterlacer", "long-name": "Deinterlacer",
"pad-templates": { "pad-templates": {
"sink": { "sink": {
"caps": "video/x-raw:\n format: { AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21 }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n\nvideo/x-raw(ANY):\n format: { ABGR64_LE, BGRA64_LE, AYUV64, ARGB64_LE, ARGB64, RGBA64_LE, ABGR64_BE, BGRA64_BE, ARGB64_BE, RGBA64_BE, GBRA_12LE, GBRA_12BE, Y412_LE, Y412_BE, A444_10LE, GBRA_10LE, A444_10BE, GBRA_10BE, A422_10LE, A422_10BE, A420_10LE, A420_10BE, RGB10A2_LE, BGR10A2_LE, Y410, GBRA, ABGR, VUYA, BGRA, AYUV, ARGB, RGBA, A420, AV12, Y444_16LE, Y444_16BE, v216, P016_LE, P016_BE, Y444_12LE, GBR_12LE, Y444_12BE, GBR_12BE, I422_12LE, I422_12BE, Y212_LE, Y212_BE, I420_12LE, I420_12BE, P012_LE, P012_BE, Y444_10LE, GBR_10LE, Y444_10BE, GBR_10BE, r210, I422_10LE, I422_10BE, NV16_10LE32, Y210, v210, UYVP, I420_10LE, I420_10BE, P010_10LE, NV12_10LE32, NV12_10LE40, P010_10BE, NV12_10BE_8L128, Y444, RGBP, GBR, BGRP, NV24, xBGR, BGRx, xRGB, RGBx, BGR, IYU2, v308, RGB, Y42B, NV61, NV16, VYUY, UYVY, YVYU, YUY2, I420, YV12, NV21, NV12, NV12_8L128, NV12_64Z32, NV12_4L4, NV12_32L32, NV12_16L32S, Y41B, IYU1, YVU9, YUV9, RGB16, BGR16, RGB15, BGR15, RGB8P, GRAY16_LE, GRAY16_BE, GRAY10_LE32, GRAY8 }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n", "caps": "video/x-raw:\n format: { AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21, Y444_16LE, Y444_12LE, Y444_10LE, I422_12LE, I422_10LE, I420_12LE, I420_10LE }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n\nvideo/x-raw(ANY):\n format: { ABGR64_LE, BGRA64_LE, AYUV64, ARGB64_LE, ARGB64, RGBA64_LE, ABGR64_BE, BGRA64_BE, ARGB64_BE, RGBA64_BE, GBRA_12LE, GBRA_12BE, Y412_LE, Y412_BE, A444_10LE, GBRA_10LE, A444_10BE, GBRA_10BE, A422_10LE, A422_10BE, A420_10LE, A420_10BE, RGB10A2_LE, BGR10A2_LE, Y410, GBRA, ABGR, VUYA, BGRA, AYUV, ARGB, RGBA, A420, AV12, Y444_16LE, Y444_16BE, v216, P016_LE, P016_BE, Y444_12LE, GBR_12LE, Y444_12BE, GBR_12BE, I422_12LE, I422_12BE, Y212_LE, Y212_BE, I420_12LE, I420_12BE, P012_LE, P012_BE, Y444_10LE, GBR_10LE, Y444_10BE, GBR_10BE, r210, I422_10LE, I422_10BE, NV16_10LE32, Y210, v210, UYVP, I420_10LE, I420_10BE, P010_10LE, NV12_10LE32, NV12_10LE40, P010_10BE, NV12_10BE_8L128, Y444, RGBP, GBR, BGRP, NV24, xBGR, BGRx, xRGB, RGBx, BGR, IYU2, v308, RGB, Y42B, NV61, NV16, VYUY, UYVY, YVYU, YUY2, I420, YV12, NV21, NV12, NV12_8L128, NV12_64Z32, NV12_4L4, NV12_32L32, NV12_16L32S, Y41B, IYU1, YVU9, YUV9, RGB16, BGR16, RGB15, BGR15, RGB8P, GRAY16_LE, GRAY16_BE, GRAY10_LE32, GRAY8 }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n",
"direction": "sink", "direction": "sink",
"presence": "always" "presence": "always"
}, },
"src": { "src": {
"caps": "video/x-raw:\n format: { AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21 }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n\nvideo/x-raw(ANY):\n format: { ABGR64_LE, BGRA64_LE, AYUV64, ARGB64_LE, ARGB64, RGBA64_LE, ABGR64_BE, BGRA64_BE, ARGB64_BE, RGBA64_BE, GBRA_12LE, GBRA_12BE, Y412_LE, Y412_BE, A444_10LE, GBRA_10LE, A444_10BE, GBRA_10BE, A422_10LE, A422_10BE, A420_10LE, A420_10BE, RGB10A2_LE, BGR10A2_LE, Y410, GBRA, ABGR, VUYA, BGRA, AYUV, ARGB, RGBA, A420, AV12, Y444_16LE, Y444_16BE, v216, P016_LE, P016_BE, Y444_12LE, GBR_12LE, Y444_12BE, GBR_12BE, I422_12LE, I422_12BE, Y212_LE, Y212_BE, I420_12LE, I420_12BE, P012_LE, P012_BE, Y444_10LE, GBR_10LE, Y444_10BE, GBR_10BE, r210, I422_10LE, I422_10BE, NV16_10LE32, Y210, v210, UYVP, I420_10LE, I420_10BE, P010_10LE, NV12_10LE32, NV12_10LE40, P010_10BE, NV12_10BE_8L128, Y444, RGBP, GBR, BGRP, NV24, xBGR, BGRx, xRGB, RGBx, BGR, IYU2, v308, RGB, Y42B, NV61, NV16, VYUY, UYVY, YVYU, YUY2, I420, YV12, NV21, NV12, NV12_8L128, NV12_64Z32, NV12_4L4, NV12_32L32, NV12_16L32S, Y41B, IYU1, YVU9, YUV9, RGB16, BGR16, RGB15, BGR15, RGB8P, GRAY16_LE, GRAY16_BE, GRAY10_LE32, GRAY8 }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n", "caps": "video/x-raw:\n format: { AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21, Y444_16LE, Y444_12LE, Y444_10LE, I422_12LE, I422_10LE, I420_12LE, I420_10LE }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n\nvideo/x-raw(ANY):\n format: { ABGR64_LE, BGRA64_LE, AYUV64, ARGB64_LE, ARGB64, RGBA64_LE, ABGR64_BE, BGRA64_BE, ARGB64_BE, RGBA64_BE, GBRA_12LE, GBRA_12BE, Y412_LE, Y412_BE, A444_10LE, GBRA_10LE, A444_10BE, GBRA_10BE, A422_10LE, A422_10BE, A420_10LE, A420_10BE, RGB10A2_LE, BGR10A2_LE, Y410, GBRA, ABGR, VUYA, BGRA, AYUV, ARGB, RGBA, A420, AV12, Y444_16LE, Y444_16BE, v216, P016_LE, P016_BE, Y444_12LE, GBR_12LE, Y444_12BE, GBR_12BE, I422_12LE, I422_12BE, Y212_LE, Y212_BE, I420_12LE, I420_12BE, P012_LE, P012_BE, Y444_10LE, GBR_10LE, Y444_10BE, GBR_10BE, r210, I422_10LE, I422_10BE, NV16_10LE32, Y210, v210, UYVP, I420_10LE, I420_10BE, P010_10LE, NV12_10LE32, NV12_10LE40, P010_10BE, NV12_10BE_8L128, Y444, RGBP, GBR, BGRP, NV24, xBGR, BGRx, xRGB, RGBx, BGR, IYU2, v308, RGB, Y42B, NV61, NV16, VYUY, UYVY, YVYU, YUY2, I420, YV12, NV21, NV12, NV12_8L128, NV12_64Z32, NV12_4L4, NV12_32L32, NV12_16L32S, Y41B, IYU1, YVU9, YUV9, RGB16, BGR16, RGB15, BGR15, RGB8P, GRAY16_LE, GRAY16_BE, GRAY10_LE32, GRAY8 }\n width: [ 1, 2147483647 ]\n height: [ 1, 2147483647 ]\n framerate: [ 0/1, 2147483647/1 ]\n",
"direction": "src", "direction": "src",
"presence": "always" "presence": "always"
} }

View file

@ -282,9 +282,17 @@ gst_deinterlace_locking_get_type (void)
return deinterlace_locking_type; return deinterlace_locking_type;
} }
#if G_BYTE_ORDER == G_BIG_ENDIAN
#define DEINTERLACE_VIDEO_FORMATS \ #define DEINTERLACE_VIDEO_FORMATS \
"{ AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, " \ "{ AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, " \
"BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21 }" "BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21, " \
"Y444_16BE, Y444_12BE, Y444_10BE, I422_12BE, I422_10BE, I420_12BE, I420_10BE } "
#else
#define DEINTERLACE_VIDEO_FORMATS \
"{ AYUV, ARGB, ABGR, RGBA, BGRA, Y444, xRGB, xBGR, RGBx, BGRx, RGB, " \
"BGR, YUY2, YVYU, UYVY, Y42B, I420, YV12, Y41B, NV12, NV21, " \
"Y444_16LE, Y444_12LE, Y444_10LE, I422_12LE, I422_10LE, I420_12LE, I420_10LE } "
#endif
#define DEINTERLACE_CAPS GST_VIDEO_CAPS_MAKE(DEINTERLACE_VIDEO_FORMATS) #define DEINTERLACE_CAPS GST_VIDEO_CAPS_MAKE(DEINTERLACE_VIDEO_FORMATS)

View file

@ -89,6 +89,24 @@ gst_deinterlace_method_supported_impl (GstDeinterlaceMethodClass * klass,
return (klass->deinterlace_frame_rgb != NULL); return (klass->deinterlace_frame_rgb != NULL);
case GST_VIDEO_FORMAT_BGR: case GST_VIDEO_FORMAT_BGR:
return (klass->deinterlace_frame_bgr != NULL); return (klass->deinterlace_frame_bgr != NULL);
#if G_BYTE_ORDER == G_BIG_ENDIAN
case GST_VIDEO_FORMAT_Y444_16BE:
case GST_VIDEO_FORMAT_Y444_12BE:
case GST_VIDEO_FORMAT_Y444_10BE:
case GST_VIDEO_FORMAT_I422_12BE:
case GST_VIDEO_FORMAT_I422_10BE:
case GST_VIDEO_FORMAT_I420_12BE:
case GST_VIDEO_FORMAT_I420_10BE:
#else
case GST_VIDEO_FORMAT_Y444_16LE:
case GST_VIDEO_FORMAT_Y444_12LE:
case GST_VIDEO_FORMAT_Y444_10LE:
case GST_VIDEO_FORMAT_I422_12LE:
case GST_VIDEO_FORMAT_I422_10LE:
case GST_VIDEO_FORMAT_I420_12LE:
case GST_VIDEO_FORMAT_I420_10LE:
#endif
return (klass->deinterlace_frame_planar_high != NULL);
default: default:
return FALSE; return FALSE;
} }
@ -171,6 +189,25 @@ gst_deinterlace_method_setup_impl (GstDeinterlaceMethod * self,
case GST_VIDEO_FORMAT_BGR: case GST_VIDEO_FORMAT_BGR:
self->deinterlace_frame = klass->deinterlace_frame_bgr; self->deinterlace_frame = klass->deinterlace_frame_bgr;
break; break;
#if G_BYTE_ORDER == G_BIG_ENDIAN
case GST_VIDEO_FORMAT_Y444_16BE:
case GST_VIDEO_FORMAT_Y444_12BE:
case GST_VIDEO_FORMAT_Y444_10BE:
case GST_VIDEO_FORMAT_I422_12BE:
case GST_VIDEO_FORMAT_I422_10BE:
case GST_VIDEO_FORMAT_I420_12BE:
case GST_VIDEO_FORMAT_I420_10BE:
#else
case GST_VIDEO_FORMAT_Y444_16LE:
case GST_VIDEO_FORMAT_Y444_12LE:
case GST_VIDEO_FORMAT_Y444_10LE:
case GST_VIDEO_FORMAT_I422_12LE:
case GST_VIDEO_FORMAT_I422_10LE:
case GST_VIDEO_FORMAT_I420_12LE:
case GST_VIDEO_FORMAT_I420_10LE:
#endif
self->deinterlace_frame = klass->deinterlace_frame_planar_high;
break;
default: default:
self->deinterlace_frame = NULL; self->deinterlace_frame = NULL;
break; break;
@ -287,6 +324,29 @@ gst_deinterlace_simple_method_supported (GstDeinterlaceMethodClass * mklass,
&& klass->copy_scanline_planar_u != NULL && && klass->copy_scanline_planar_u != NULL &&
klass->interpolate_scanline_planar_v != NULL klass->interpolate_scanline_planar_v != NULL
&& klass->copy_scanline_planar_v != NULL); && klass->copy_scanline_planar_v != NULL);
#if G_BYTE_ORDER == G_BIG_ENDIAN
case GST_VIDEO_FORMAT_Y444_16BE:
case GST_VIDEO_FORMAT_Y444_12BE:
case GST_VIDEO_FORMAT_Y444_10BE:
case GST_VIDEO_FORMAT_I422_12BE:
case GST_VIDEO_FORMAT_I422_10BE:
case GST_VIDEO_FORMAT_I420_12BE:
case GST_VIDEO_FORMAT_I420_10BE:
#else
case GST_VIDEO_FORMAT_Y444_16LE:
case GST_VIDEO_FORMAT_Y444_12LE:
case GST_VIDEO_FORMAT_Y444_10LE:
case GST_VIDEO_FORMAT_I422_12LE:
case GST_VIDEO_FORMAT_I422_10LE:
case GST_VIDEO_FORMAT_I420_12LE:
case GST_VIDEO_FORMAT_I420_10LE:
#endif
return (klass->interpolate_scanline_planar_y_16bits != NULL
&& klass->copy_scanline_planar_y_16bits != NULL &&
klass->interpolate_scanline_planar_u_16bits != NULL
&& klass->copy_scanline_planar_u_16bits != NULL &&
klass->interpolate_scanline_planar_v_16bits != NULL
&& klass->copy_scanline_planar_v_16bits != NULL);
default: default:
return FALSE; return FALSE;
} }
@ -743,6 +803,33 @@ gst_deinterlace_simple_method_setup (GstDeinterlaceMethod * method,
klass->interpolate_scanline_planar_v; klass->interpolate_scanline_planar_v;
self->copy_scanline_planar[2] = klass->copy_scanline_planar_v; self->copy_scanline_planar[2] = klass->copy_scanline_planar_v;
break; break;
#if G_BYTE_ORDER == G_BIG_ENDIAN
case GST_VIDEO_FORMAT_Y444_16BE:
case GST_VIDEO_FORMAT_Y444_12BE:
case GST_VIDEO_FORMAT_Y444_10BE:
case GST_VIDEO_FORMAT_I422_12BE:
case GST_VIDEO_FORMAT_I422_10BE:
case GST_VIDEO_FORMAT_I420_12BE:
case GST_VIDEO_FORMAT_I420_10BE:
#else
case GST_VIDEO_FORMAT_Y444_16LE:
case GST_VIDEO_FORMAT_Y444_12LE:
case GST_VIDEO_FORMAT_Y444_10LE:
case GST_VIDEO_FORMAT_I422_12LE:
case GST_VIDEO_FORMAT_I422_10LE:
case GST_VIDEO_FORMAT_I420_12LE:
case GST_VIDEO_FORMAT_I420_10LE:
#endif
self->interpolate_scanline_planar[0] =
klass->interpolate_scanline_planar_y_16bits;
self->copy_scanline_planar[0] = klass->copy_scanline_planar_y_16bits;
self->interpolate_scanline_planar[1] =
klass->interpolate_scanline_planar_u_16bits;
self->copy_scanline_planar[1] = klass->copy_scanline_planar_u_16bits;
self->interpolate_scanline_planar[2] =
klass->interpolate_scanline_planar_v_16bits;
self->copy_scanline_planar[2] = klass->copy_scanline_planar_v_16bits;
break;
default: default:
break; break;
} }
@ -788,6 +875,9 @@ gst_deinterlace_simple_method_class_init (GstDeinterlaceSimpleMethodClass
gst_deinterlace_simple_method_deinterlace_frame_nv12; gst_deinterlace_simple_method_deinterlace_frame_nv12;
dm_class->deinterlace_frame_nv21 = dm_class->deinterlace_frame_nv21 =
gst_deinterlace_simple_method_deinterlace_frame_nv12; gst_deinterlace_simple_method_deinterlace_frame_nv12;
/* same as 8bits planar */
dm_class->deinterlace_frame_planar_high =
gst_deinterlace_simple_method_deinterlace_frame_planar;
dm_class->fields_required = 2; dm_class->fields_required = 2;
dm_class->setup = gst_deinterlace_simple_method_setup; dm_class->setup = gst_deinterlace_simple_method_setup;
dm_class->supported = gst_deinterlace_simple_method_supported; dm_class->supported = gst_deinterlace_simple_method_supported;
@ -849,6 +939,16 @@ gst_deinterlace_simple_method_class_init (GstDeinterlaceSimpleMethodClass
gst_deinterlace_simple_method_interpolate_scanline_planar_v; gst_deinterlace_simple_method_interpolate_scanline_planar_v;
klass->copy_scanline_planar_v = klass->copy_scanline_planar_v =
gst_deinterlace_simple_method_copy_scanline_planar_v; gst_deinterlace_simple_method_copy_scanline_planar_v;
/* planar high bitdepth formats use the same methods as 8bits planar,
* (i.e,memcpy) but interpolate_scanline_planar_{y,u,v}_16bits methods will
* be configured by each subclass */
klass->copy_scanline_planar_y_16bits =
gst_deinterlace_simple_method_copy_scanline_planar_y;
klass->copy_scanline_planar_u_16bits =
gst_deinterlace_simple_method_copy_scanline_planar_u;
klass->copy_scanline_planar_v_16bits =
gst_deinterlace_simple_method_copy_scanline_planar_v;
} }
static void static void

View file

@ -101,6 +101,8 @@ struct _GstDeinterlaceMethodClass {
GstDeinterlaceMethodDeinterlaceFunction deinterlace_frame_rgb; GstDeinterlaceMethodDeinterlaceFunction deinterlace_frame_rgb;
GstDeinterlaceMethodDeinterlaceFunction deinterlace_frame_bgr; GstDeinterlaceMethodDeinterlaceFunction deinterlace_frame_bgr;
GstDeinterlaceMethodDeinterlaceFunction deinterlace_frame_planar_high;
const gchar *name; const gchar *name;
const gchar *nick; const gchar *nick;
}; };
@ -213,6 +215,14 @@ struct _GstDeinterlaceSimpleMethodClass {
GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_u; GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_u;
GstDeinterlaceSimpleMethodFunction copy_scanline_planar_v; GstDeinterlaceSimpleMethodFunction copy_scanline_planar_v;
GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_v; GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_v;
/* Planar high bitdepth formats */
GstDeinterlaceSimpleMethodFunction copy_scanline_planar_y_16bits;
GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_y_16bits;
GstDeinterlaceSimpleMethodFunction copy_scanline_planar_u_16bits;
GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_u_16bits;
GstDeinterlaceSimpleMethodFunction copy_scanline_planar_v_16bits;
GstDeinterlaceSimpleMethodFunction interpolate_scanline_planar_v_16bits;
}; };
GType gst_deinterlace_simple_method_get_type (void); GType gst_deinterlace_simple_method_get_type (void);

View file

@ -99,8 +99,14 @@ void deinterlace_line_vfir (guint8 * ORC_RESTRICT d1,
const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2,
const guint8 * ORC_RESTRICT s3, const guint8 * ORC_RESTRICT s4, const guint8 * ORC_RESTRICT s3, const guint8 * ORC_RESTRICT s4,
const guint8 * ORC_RESTRICT s5, int n); const guint8 * ORC_RESTRICT s5, int n);
void deinterlace_line_vfir_16bits (guint16 * ORC_RESTRICT d1,
const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2,
const guint16 * ORC_RESTRICT s3, const guint16 * ORC_RESTRICT s4,
const guint16 * ORC_RESTRICT s5, int n);
void deinterlace_line_linear (guint8 * ORC_RESTRICT d1, void deinterlace_line_linear (guint8 * ORC_RESTRICT d1,
const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, int n); const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, int n);
void deinterlace_line_linear_16bits (guint16 * ORC_RESTRICT d1,
const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2, int n);
void deinterlace_line_linear_blend (guint8 * ORC_RESTRICT d1, void deinterlace_line_linear_blend (guint8 * ORC_RESTRICT d1,
const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2,
const guint8 * ORC_RESTRICT s3, int n); const guint8 * ORC_RESTRICT s3, int n);
@ -440,6 +446,296 @@ deinterlace_line_vfir (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1,
#endif #endif
/* deinterlace_line_vfir_16bits */
#ifdef DISABLE_ORC
void
deinterlace_line_vfir_16bits (guint16 * ORC_RESTRICT d1,
const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2,
const guint16 * ORC_RESTRICT s3, const guint16 * ORC_RESTRICT s4,
const guint16 * ORC_RESTRICT s5, int n)
{
int i;
orc_union16 *ORC_RESTRICT ptr0;
const orc_union16 *ORC_RESTRICT ptr4;
const orc_union16 *ORC_RESTRICT ptr5;
const orc_union16 *ORC_RESTRICT ptr6;
const orc_union16 *ORC_RESTRICT ptr7;
const orc_union16 *ORC_RESTRICT ptr8;
orc_union16 var35;
orc_union16 var36;
orc_union16 var37;
orc_union16 var38;
orc_union16 var39;
#if defined(__APPLE__) && __GNUC__ == 4 && __GNUC_MINOR__ == 2 && defined (__i386__)
volatile orc_union32 var40;
#else
orc_union32 var40;
#endif
orc_union16 var41;
orc_union32 var42;
orc_union32 var43;
orc_union32 var44;
orc_union32 var45;
orc_union32 var46;
orc_union32 var47;
orc_union32 var48;
orc_union32 var49;
orc_union32 var50;
orc_union32 var51;
orc_union32 var52;
orc_union32 var53;
orc_union32 var54;
ptr0 = (orc_union16 *) d1;
ptr4 = (orc_union16 *) s1;
ptr5 = (orc_union16 *) s2;
ptr6 = (orc_union16 *) s3;
ptr7 = (orc_union16 *) s4;
ptr8 = (orc_union16 *) s5;
/* 16: loadpl */
var40.i = 0x00000004; /* 4 or 1.97626e-323f */
for (i = 0; i < n; i++) {
/* 0: loadw */
var35 = ptr4[i];
/* 1: convuwl */
var42.i = (orc_uint16) var35.i;
/* 2: loadw */
var36 = ptr8[i];
/* 3: convuwl */
var43.i = (orc_uint16) var36.i;
/* 4: addl */
var44.i = ((orc_uint32) var42.i) + ((orc_uint32) var43.i);
/* 5: loadw */
var37 = ptr5[i];
/* 6: convuwl */
var45.i = (orc_uint16) var37.i;
/* 7: loadw */
var38 = ptr7[i];
/* 8: convuwl */
var46.i = (orc_uint16) var38.i;
/* 9: addl */
var47.i = ((orc_uint32) var45.i) + ((orc_uint32) var46.i);
/* 10: shll */
var48.i = ((orc_uint32) var47.i) << 2;
/* 11: loadw */
var39 = ptr6[i];
/* 12: convuwl */
var49.i = (orc_uint16) var39.i;
/* 13: shll */
var50.i = ((orc_uint32) var49.i) << 1;
/* 14: subl */
var51.i = ((orc_uint32) var48.i) - ((orc_uint32) var44.i);
/* 15: addl */
var52.i = ((orc_uint32) var51.i) + ((orc_uint32) var50.i);
/* 17: addl */
var53.i = ((orc_uint32) var52.i) + ((orc_uint32) var40.i);
/* 18: shrsl */
var54.i = var53.i >> 3;
/* 19: convsuslw */
var41.i = ORC_CLAMP_UW (var54.i);
/* 20: storew */
ptr0[i] = var41;
}
}
#else
static void
_backup_deinterlace_line_vfir_16bits (OrcExecutor * ORC_RESTRICT ex)
{
int i;
int n = ex->n;
orc_union16 *ORC_RESTRICT ptr0;
const orc_union16 *ORC_RESTRICT ptr4;
const orc_union16 *ORC_RESTRICT ptr5;
const orc_union16 *ORC_RESTRICT ptr6;
const orc_union16 *ORC_RESTRICT ptr7;
const orc_union16 *ORC_RESTRICT ptr8;
orc_union16 var35;
orc_union16 var36;
orc_union16 var37;
orc_union16 var38;
orc_union16 var39;
#if defined(__APPLE__) && __GNUC__ == 4 && __GNUC_MINOR__ == 2 && defined (__i386__)
volatile orc_union32 var40;
#else
orc_union32 var40;
#endif
orc_union16 var41;
orc_union32 var42;
orc_union32 var43;
orc_union32 var44;
orc_union32 var45;
orc_union32 var46;
orc_union32 var47;
orc_union32 var48;
orc_union32 var49;
orc_union32 var50;
orc_union32 var51;
orc_union32 var52;
orc_union32 var53;
orc_union32 var54;
ptr0 = (orc_union16 *) ex->arrays[0];
ptr4 = (orc_union16 *) ex->arrays[4];
ptr5 = (orc_union16 *) ex->arrays[5];
ptr6 = (orc_union16 *) ex->arrays[6];
ptr7 = (orc_union16 *) ex->arrays[7];
ptr8 = (orc_union16 *) ex->arrays[8];
/* 16: loadpl */
var40.i = 0x00000004; /* 4 or 1.97626e-323f */
for (i = 0; i < n; i++) {
/* 0: loadw */
var35 = ptr4[i];
/* 1: convuwl */
var42.i = (orc_uint16) var35.i;
/* 2: loadw */
var36 = ptr8[i];
/* 3: convuwl */
var43.i = (orc_uint16) var36.i;
/* 4: addl */
var44.i = ((orc_uint32) var42.i) + ((orc_uint32) var43.i);
/* 5: loadw */
var37 = ptr5[i];
/* 6: convuwl */
var45.i = (orc_uint16) var37.i;
/* 7: loadw */
var38 = ptr7[i];
/* 8: convuwl */
var46.i = (orc_uint16) var38.i;
/* 9: addl */
var47.i = ((orc_uint32) var45.i) + ((orc_uint32) var46.i);
/* 10: shll */
var48.i = ((orc_uint32) var47.i) << 2;
/* 11: loadw */
var39 = ptr6[i];
/* 12: convuwl */
var49.i = (orc_uint16) var39.i;
/* 13: shll */
var50.i = ((orc_uint32) var49.i) << 1;
/* 14: subl */
var51.i = ((orc_uint32) var48.i) - ((orc_uint32) var44.i);
/* 15: addl */
var52.i = ((orc_uint32) var51.i) + ((orc_uint32) var50.i);
/* 17: addl */
var53.i = ((orc_uint32) var52.i) + ((orc_uint32) var40.i);
/* 18: shrsl */
var54.i = var53.i >> 3;
/* 19: convsuslw */
var41.i = ORC_CLAMP_UW (var54.i);
/* 20: storew */
ptr0[i] = var41;
}
}
void
deinterlace_line_vfir_16bits (guint16 * ORC_RESTRICT d1,
const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2,
const guint16 * ORC_RESTRICT s3, const guint16 * ORC_RESTRICT s4,
const guint16 * ORC_RESTRICT s5, int n)
{
OrcExecutor _ex, *ex = &_ex;
static volatile int p_inited = 0;
static OrcCode *c = 0;
void (*func) (OrcExecutor *);
if (!p_inited) {
orc_once_mutex_lock ();
if (!p_inited) {
OrcProgram *p;
#if 1
static const orc_uint8 bc[] = {
1, 9, 28, 100, 101, 105, 110, 116, 101, 114, 108, 97, 99, 101, 95, 108,
105, 110, 101, 95, 118, 102, 105, 114, 95, 49, 54, 98, 105, 116, 115,
11,
2, 2, 12, 2, 2, 12, 2, 2, 12, 2, 2, 12, 2, 2, 12, 2,
2, 14, 4, 2, 0, 0, 0, 14, 4, 1, 0, 0, 0, 14, 4, 4,
0, 0, 0, 14, 4, 3, 0, 0, 0, 20, 4, 20, 4, 20, 4, 154,
32, 4, 154, 33, 8, 103, 32, 32, 33, 154, 33, 5, 154, 34, 7, 103,
33, 33, 34, 124, 33, 33, 16, 154, 34, 6, 124, 34, 34, 17, 129, 33,
33, 32, 103, 33, 33, 34, 103, 33, 33, 18, 125, 33, 33, 19, 166, 0,
33, 2, 0,
};
p = orc_program_new_from_static_bytecode (bc);
orc_program_set_backup_function (p, _backup_deinterlace_line_vfir_16bits);
#else
p = orc_program_new ();
orc_program_set_name (p, "deinterlace_line_vfir_16bits");
orc_program_set_backup_function (p, _backup_deinterlace_line_vfir_16bits);
orc_program_add_destination (p, 2, "d1");
orc_program_add_source (p, 2, "s1");
orc_program_add_source (p, 2, "s2");
orc_program_add_source (p, 2, "s3");
orc_program_add_source (p, 2, "s4");
orc_program_add_source (p, 2, "s5");
orc_program_add_constant (p, 4, 0x00000002, "c1");
orc_program_add_constant (p, 4, 0x00000001, "c2");
orc_program_add_constant (p, 4, 0x00000004, "c3");
orc_program_add_constant (p, 4, 0x00000003, "c4");
orc_program_add_temporary (p, 4, "t1");
orc_program_add_temporary (p, 4, "t2");
orc_program_add_temporary (p, 4, "t3");
orc_program_append_2 (p, "convuwl", 0, ORC_VAR_T1, ORC_VAR_S1, ORC_VAR_D1,
ORC_VAR_D1);
orc_program_append_2 (p, "convuwl", 0, ORC_VAR_T2, ORC_VAR_S5, ORC_VAR_D1,
ORC_VAR_D1);
orc_program_append_2 (p, "addl", 0, ORC_VAR_T1, ORC_VAR_T1, ORC_VAR_T2,
ORC_VAR_D1);
orc_program_append_2 (p, "convuwl", 0, ORC_VAR_T2, ORC_VAR_S2, ORC_VAR_D1,
ORC_VAR_D1);
orc_program_append_2 (p, "convuwl", 0, ORC_VAR_T3, ORC_VAR_S4, ORC_VAR_D1,
ORC_VAR_D1);
orc_program_append_2 (p, "addl", 0, ORC_VAR_T2, ORC_VAR_T2, ORC_VAR_T3,
ORC_VAR_D1);
orc_program_append_2 (p, "shll", 0, ORC_VAR_T2, ORC_VAR_T2, ORC_VAR_C1,
ORC_VAR_D1);
orc_program_append_2 (p, "convuwl", 0, ORC_VAR_T3, ORC_VAR_S3, ORC_VAR_D1,
ORC_VAR_D1);
orc_program_append_2 (p, "shll", 0, ORC_VAR_T3, ORC_VAR_T3, ORC_VAR_C2,
ORC_VAR_D1);
orc_program_append_2 (p, "subl", 0, ORC_VAR_T2, ORC_VAR_T2, ORC_VAR_T1,
ORC_VAR_D1);
orc_program_append_2 (p, "addl", 0, ORC_VAR_T2, ORC_VAR_T2, ORC_VAR_T3,
ORC_VAR_D1);
orc_program_append_2 (p, "addl", 0, ORC_VAR_T2, ORC_VAR_T2, ORC_VAR_C3,
ORC_VAR_D1);
orc_program_append_2 (p, "shrsl", 0, ORC_VAR_T2, ORC_VAR_T2, ORC_VAR_C4,
ORC_VAR_D1);
orc_program_append_2 (p, "convsuslw", 0, ORC_VAR_D1, ORC_VAR_T2,
ORC_VAR_D1, ORC_VAR_D1);
#endif
orc_program_compile (p);
c = orc_program_take_code (p);
orc_program_free (p);
}
p_inited = TRUE;
orc_once_mutex_unlock ();
}
ex->arrays[ORC_VAR_A2] = c;
ex->program = 0;
ex->n = n;
ex->arrays[ORC_VAR_D1] = d1;
ex->arrays[ORC_VAR_S1] = (void *) s1;
ex->arrays[ORC_VAR_S2] = (void *) s2;
ex->arrays[ORC_VAR_S3] = (void *) s3;
ex->arrays[ORC_VAR_S4] = (void *) s4;
ex->arrays[ORC_VAR_S5] = (void *) s5;
func = c->exec;
func (ex);
}
#endif
/* deinterlace_line_linear */ /* deinterlace_line_linear */
#ifdef DISABLE_ORC #ifdef DISABLE_ORC
void void
@ -558,6 +854,128 @@ deinterlace_line_linear (guint8 * ORC_RESTRICT d1,
#endif #endif
/* deinterlace_line_linear_16bits */
#ifdef DISABLE_ORC
void
deinterlace_line_linear_16bits (guint16 * ORC_RESTRICT d1,
const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2, int n)
{
int i;
orc_union16 *ORC_RESTRICT ptr0;
const orc_union16 *ORC_RESTRICT ptr4;
const orc_union16 *ORC_RESTRICT ptr5;
orc_union16 var32;
orc_union16 var33;
orc_union16 var34;
ptr0 = (orc_union16 *) d1;
ptr4 = (orc_union16 *) s1;
ptr5 = (orc_union16 *) s2;
for (i = 0; i < n; i++) {
/* 0: loadw */
var32 = ptr4[i];
/* 1: loadw */
var33 = ptr5[i];
/* 2: avguw */
var34.i = ((orc_uint16) var32.i + (orc_uint16) var33.i + 1) >> 1;
/* 3: storew */
ptr0[i] = var34;
}
}
#else
static void
_backup_deinterlace_line_linear_16bits (OrcExecutor * ORC_RESTRICT ex)
{
int i;
int n = ex->n;
orc_union16 *ORC_RESTRICT ptr0;
const orc_union16 *ORC_RESTRICT ptr4;
const orc_union16 *ORC_RESTRICT ptr5;
orc_union16 var32;
orc_union16 var33;
orc_union16 var34;
ptr0 = (orc_union16 *) ex->arrays[0];
ptr4 = (orc_union16 *) ex->arrays[4];
ptr5 = (orc_union16 *) ex->arrays[5];
for (i = 0; i < n; i++) {
/* 0: loadw */
var32 = ptr4[i];
/* 1: loadw */
var33 = ptr5[i];
/* 2: avguw */
var34.i = ((orc_uint16) var32.i + (orc_uint16) var33.i + 1) >> 1;
/* 3: storew */
ptr0[i] = var34;
}
}
void
deinterlace_line_linear_16bits (guint16 * ORC_RESTRICT d1,
const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2, int n)
{
OrcExecutor _ex, *ex = &_ex;
static volatile int p_inited = 0;
static OrcCode *c = 0;
void (*func) (OrcExecutor *);
if (!p_inited) {
orc_once_mutex_lock ();
if (!p_inited) {
OrcProgram *p;
#if 1
static const orc_uint8 bc[] = {
1, 9, 30, 100, 101, 105, 110, 116, 101, 114, 108, 97, 99, 101, 95, 108,
105, 110, 101, 95, 108, 105, 110, 101, 97, 114, 95, 49, 54, 98, 105,
116,
115, 11, 2, 2, 12, 2, 2, 12, 2, 2, 76, 0, 4, 5, 2, 0,
};
p = orc_program_new_from_static_bytecode (bc);
orc_program_set_backup_function (p,
_backup_deinterlace_line_linear_16bits);
#else
p = orc_program_new ();
orc_program_set_name (p, "deinterlace_line_linear_16bits");
orc_program_set_backup_function (p,
_backup_deinterlace_line_linear_16bits);
orc_program_add_destination (p, 2, "d1");
orc_program_add_source (p, 2, "s1");
orc_program_add_source (p, 2, "s2");
orc_program_append_2 (p, "avguw", 0, ORC_VAR_D1, ORC_VAR_S1, ORC_VAR_S2,
ORC_VAR_D1);
#endif
orc_program_compile (p);
c = orc_program_take_code (p);
orc_program_free (p);
}
p_inited = TRUE;
orc_once_mutex_unlock ();
}
ex->arrays[ORC_VAR_A2] = c;
ex->program = 0;
ex->n = n;
ex->arrays[ORC_VAR_D1] = d1;
ex->arrays[ORC_VAR_S1] = (void *) s1;
ex->arrays[ORC_VAR_S2] = (void *) s2;
func = c->exec;
func (ex);
}
#endif
/* deinterlace_line_linear_blend */ /* deinterlace_line_linear_blend */
#ifdef DISABLE_ORC #ifdef DISABLE_ORC
void void

View file

@ -1,8 +1,7 @@
/* autogenerated from tvtime.orc */ /* autogenerated from tvtime.orc */
#ifndef _TVTIME_H_ #pragma once
#define _TVTIME_H_
#include <glib.h> #include <glib.h>
@ -81,7 +80,9 @@ typedef union { orc_int64 i; double f; orc_int32 x2[2]; float x2f[2]; orc_int16
#endif #endif
void deinterlace_line_vfir (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, const guint8 * ORC_RESTRICT s3, const guint8 * ORC_RESTRICT s4, const guint8 * ORC_RESTRICT s5, int n); void deinterlace_line_vfir (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, const guint8 * ORC_RESTRICT s3, const guint8 * ORC_RESTRICT s4, const guint8 * ORC_RESTRICT s5, int n);
void deinterlace_line_vfir_16bits (guint16 * ORC_RESTRICT d1, const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2, const guint16 * ORC_RESTRICT s3, const guint16 * ORC_RESTRICT s4, const guint16 * ORC_RESTRICT s5, int n);
void deinterlace_line_linear (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, int n); void deinterlace_line_linear (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, int n);
void deinterlace_line_linear_16bits (guint16 * ORC_RESTRICT d1, const guint16 * ORC_RESTRICT s1, const guint16 * ORC_RESTRICT s2, int n);
void deinterlace_line_linear_blend (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, const guint8 * ORC_RESTRICT s3, int n); void deinterlace_line_linear_blend (guint8 * ORC_RESTRICT d1, const guint8 * ORC_RESTRICT s1, const guint8 * ORC_RESTRICT s2, const guint8 * ORC_RESTRICT s3, int n);
void deinterlace_line_greedy (orc_uint8 * ORC_RESTRICT d1, const orc_uint8 * ORC_RESTRICT s1, const orc_uint8 * ORC_RESTRICT s2, const orc_uint8 * ORC_RESTRICT s3, const orc_uint8 * ORC_RESTRICT s4, int p1, int n); void deinterlace_line_greedy (orc_uint8 * ORC_RESTRICT d1, const orc_uint8 * ORC_RESTRICT s1, const orc_uint8 * ORC_RESTRICT s2, const orc_uint8 * ORC_RESTRICT s3, const orc_uint8 * ORC_RESTRICT s4, int p1, int n);
@ -89,5 +90,3 @@ void deinterlace_line_greedy (orc_uint8 * ORC_RESTRICT d1, const orc_uint8 * ORC
} }
#endif #endif
#endif

View file

@ -26,6 +26,33 @@ shrsw t2, t2, 3
convsuswb d1, t2 convsuswb d1, t2
.function deinterlace_line_vfir_16bits
.dest 2 d1 guint16
.source 2 s1 guint16
.source 2 s2 guint16
.source 2 s3 guint16
.source 2 s4 guint16
.source 2 s5 guint16
.temp 4 t1
.temp 4 t2
.temp 4 t3
convuwl t1, s1
convuwl t2, s5
addl t1, t1, t2
convuwl t2, s2
convuwl t3, s4
addl t2, t2, t3
shll t2, t2, 2
convuwl t3, s3
shll t3, t3, 1
subl t2, t2, t1
addl t2, t2, t3
addl t2, t2, 4
shrsl t2, t2, 3
convsuslw d1, t2
.function deinterlace_line_linear .function deinterlace_line_linear
.dest 1 d1 guint8 .dest 1 d1 guint8
.source 1 s1 guint8 .source 1 s1 guint8
@ -34,6 +61,14 @@ convsuswb d1, t2
avgub d1, s1, s2 avgub d1, s1, s2
.function deinterlace_line_linear_16bits
.dest 2 d1 guint16
.source 2 s1 guint16
.source 2 s2 guint16
avguw d1, s1, s2
.function deinterlace_line_linear_blend .function deinterlace_line_linear_blend
.dest 1 d1 guint8 .dest 1 d1 guint8
.source 1 s1 guint8 .source 1 s1 guint8

View file

@ -54,6 +54,13 @@ deinterlace_scanline_linear_c (GstDeinterlaceSimpleMethod * self,
deinterlace_line_linear (out, s1, s2, size); deinterlace_line_linear (out, s1, s2, size);
} }
static void
deinterlace_scanline_linear_c_16bits (GstDeinterlaceSimpleMethod * self,
guint16 * out, const guint16 * s1, const guint16 * s2, gint size)
{
deinterlace_line_linear_16bits (out, s1, s2, size / 2);
}
static void static void
deinterlace_scanline_linear_packed_c (GstDeinterlaceSimpleMethod * self, deinterlace_scanline_linear_packed_c (GstDeinterlaceSimpleMethod * self,
guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size) guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size)
@ -82,6 +89,15 @@ deinterlace_scanline_linear_planar_v_c (GstDeinterlaceSimpleMethod * self,
deinterlace_scanline_linear_c (self, out, scanlines->t0, scanlines->b0, size); deinterlace_scanline_linear_c (self, out, scanlines->t0, scanlines->b0, size);
} }
static void
deinterlace_scanline_linear_planar_plane_16bits_c (GstDeinterlaceSimpleMethod *
self, guint8 * out, const GstDeinterlaceScanlineData * scanlines,
guint size)
{
deinterlace_scanline_linear_c_16bits (self, (guint16 *) out,
(const guint16 *) scanlines->t0, (const guint16 *) scanlines->b0, size);
}
G_DEFINE_TYPE (GstDeinterlaceMethodLinear, gst_deinterlace_method_linear, G_DEFINE_TYPE (GstDeinterlaceMethodLinear, gst_deinterlace_method_linear,
GST_TYPE_DEINTERLACE_SIMPLE_METHOD); GST_TYPE_DEINTERLACE_SIMPLE_METHOD);
@ -117,6 +133,12 @@ gst_deinterlace_method_linear_class_init (GstDeinterlaceMethodLinearClass *
dism_class->interpolate_scanline_planar_v = dism_class->interpolate_scanline_planar_v =
deinterlace_scanline_linear_planar_v_c; deinterlace_scanline_linear_planar_v_c;
dism_class->interpolate_scanline_planar_y_16bits =
deinterlace_scanline_linear_planar_plane_16bits_c;
dism_class->interpolate_scanline_planar_u_16bits =
deinterlace_scanline_linear_planar_plane_16bits_c;
dism_class->interpolate_scanline_planar_v_16bits =
deinterlace_scanline_linear_planar_plane_16bits_c;
} }
static void static void

View file

@ -75,6 +75,19 @@ deinterlace_c (guint8 * dst, const guint8 * lum_m4, const guint8 * lum_m3,
} }
} }
static inline void
deinterlace_c_16bits (guint16 * dst, const guint16 * lum_m4,
const guint16 * lum_m3, const guint16 * lum_m2, const guint16 * lum_m1,
const guint16 * lum, gint size)
{
if (lum_m2 == NULL) {
deinterlace_line_linear_16bits (dst, lum_m1, lum_m3, size);
} else {
deinterlace_line_vfir_16bits (dst, lum_m4, lum_m3, lum_m2, lum_m1,
lum, size);
}
}
static void static void
deinterlace_line_packed_c (GstDeinterlaceSimpleMethod * self, guint8 * dst, deinterlace_line_packed_c (GstDeinterlaceSimpleMethod * self, guint8 * dst,
const GstDeinterlaceScanlineData * scanlines, guint size) const GstDeinterlaceScanlineData * scanlines, guint size)
@ -127,6 +140,20 @@ deinterlace_line_planar_v_c (GstDeinterlaceSimpleMethod * self, guint8 * dst,
deinterlace_c (dst, lum_m4, lum_m3, lum_m2, lum_m1, lum, size); deinterlace_c (dst, lum_m4, lum_m3, lum_m2, lum_m1, lum, size);
} }
static void
deinterlace_line_planar_plane_16bits_c (GstDeinterlaceSimpleMethod * self,
guint8 * dst, const GstDeinterlaceScanlineData * scanlines, guint size)
{
const guint16 *lum_m4 = (const guint16 *) scanlines->tt1;
const guint16 *lum_m3 = (const guint16 *) scanlines->t0;
const guint16 *lum_m2 = (const guint16 *) scanlines->m1;
const guint16 *lum_m1 = (const guint16 *) scanlines->b0;
const guint16 *lum = (const guint16 *) scanlines->bb1;
deinterlace_c_16bits ((guint16 *) dst, lum_m4, lum_m3, lum_m2, lum_m1, lum,
size);
}
#undef BUILD_X86_ASM #undef BUILD_X86_ASM
#ifdef BUILD_X86_ASM #ifdef BUILD_X86_ASM
@ -306,6 +333,13 @@ gst_deinterlace_method_vfir_class_init (GstDeinterlaceMethodVFIRClass * klass)
dism_class->interpolate_scanline_planar_u = deinterlace_line_planar_u_c; dism_class->interpolate_scanline_planar_u = deinterlace_line_planar_u_c;
dism_class->interpolate_scanline_planar_v = deinterlace_line_planar_v_c; dism_class->interpolate_scanline_planar_v = deinterlace_line_planar_v_c;
#endif #endif
dism_class->interpolate_scanline_planar_y_16bits =
deinterlace_line_planar_plane_16bits_c;
dism_class->interpolate_scanline_planar_u_16bits =
deinterlace_line_planar_plane_16bits_c;
dism_class->interpolate_scanline_planar_v_16bits =
deinterlace_line_planar_plane_16bits_c;
} }
static void static void

View file

@ -150,6 +150,14 @@ gst_deinterlace_method_weave_class_init (GstDeinterlaceMethodWeaveClass * klass)
dism_class->interpolate_scanline_planar_v = dism_class->interpolate_scanline_planar_v =
deinterlace_scanline_weave_planar_v; deinterlace_scanline_weave_planar_v;
/* we do just memcpy, nothing different */
dism_class->interpolate_scanline_planar_y_16bits =
deinterlace_scanline_weave_planar_y;
dism_class->interpolate_scanline_planar_u_16bits =
deinterlace_scanline_weave_planar_u;
dism_class->interpolate_scanline_planar_v_16bits =
deinterlace_scanline_weave_planar_v;
dism_class->copy_scanline_ayuv = copy_scanline_packed; dism_class->copy_scanline_ayuv = copy_scanline_packed;
dism_class->copy_scanline_yuy2 = copy_scanline_packed; dism_class->copy_scanline_yuy2 = copy_scanline_packed;
dism_class->copy_scanline_yvyu = copy_scanline_packed; dism_class->copy_scanline_yvyu = copy_scanline_packed;

View file

@ -151,6 +151,14 @@ gst_deinterlace_method_weave_bff_class_init (GstDeinterlaceMethodWeaveBFFClass *
dism_class->interpolate_scanline_planar_v = dism_class->interpolate_scanline_planar_v =
deinterlace_scanline_weave_planar_v; deinterlace_scanline_weave_planar_v;
/* we do just memcpy, nothing different */
dism_class->interpolate_scanline_planar_y_16bits =
deinterlace_scanline_weave_planar_y;
dism_class->interpolate_scanline_planar_u_16bits =
deinterlace_scanline_weave_planar_u;
dism_class->interpolate_scanline_planar_v_16bits =
deinterlace_scanline_weave_planar_v;
dism_class->copy_scanline_ayuv = copy_scanline_packed; dism_class->copy_scanline_ayuv = copy_scanline_packed;
dism_class->copy_scanline_yuy2 = copy_scanline_packed; dism_class->copy_scanline_yuy2 = copy_scanline_packed;
dism_class->copy_scanline_yvyu = copy_scanline_packed; dism_class->copy_scanline_yvyu = copy_scanline_packed;

View file

@ -152,6 +152,14 @@ gst_deinterlace_method_weave_tff_class_init (GstDeinterlaceMethodWeaveTFFClass *
dism_class->interpolate_scanline_planar_v = dism_class->interpolate_scanline_planar_v =
deinterlace_scanline_weave_planar_v; deinterlace_scanline_weave_planar_v;
/* we do just memcpy, nothing different */
dism_class->interpolate_scanline_planar_y_16bits =
deinterlace_scanline_weave_planar_y;
dism_class->interpolate_scanline_planar_u_16bits =
deinterlace_scanline_weave_planar_u;
dism_class->interpolate_scanline_planar_v_16bits =
deinterlace_scanline_weave_planar_v;
dism_class->copy_scanline_ayuv = copy_scanline_packed; dism_class->copy_scanline_ayuv = copy_scanline_packed;
dism_class->copy_scanline_yuy2 = copy_scanline_packed; dism_class->copy_scanline_yuy2 = copy_scanline_packed;
dism_class->copy_scanline_yvyu = copy_scanline_packed; dism_class->copy_scanline_yvyu = copy_scanline_packed;

View file

@ -76,6 +76,10 @@ static void
filter_scanline_yadif_planar (GstDeinterlaceSimpleMethod * self, filter_scanline_yadif_planar (GstDeinterlaceSimpleMethod * self,
guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size); guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size);
static void
filter_scanline_yadif_planar_16bits (GstDeinterlaceSimpleMethod * self,
guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size);
static void static void
filter_scanline_yadif_semiplanar (GstDeinterlaceSimpleMethod * self, filter_scanline_yadif_semiplanar (GstDeinterlaceSimpleMethod * self,
guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size); guint8 * out, const GstDeinterlaceScanlineData * scanlines, guint size);
@ -114,6 +118,24 @@ filter_line_c_planar_mode2 (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp, const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w); const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w);
static void
filter_line_c_planar_mode0_16bits (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
const void *ORC_RESTRICT ttwo, const void *ORC_RESTRICT btwo,
const void *ORC_RESTRICT tptwo, const void *ORC_RESTRICT bptwo,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w);
static void
filter_line_c_planar_mode2_16bits (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
const void *ORC_RESTRICT ttwo, const void *ORC_RESTRICT btwo,
const void *ORC_RESTRICT tptwo, const void *ORC_RESTRICT bptwo,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w);
static void (*filter_mode2) (void *ORC_RESTRICT dst, static void (*filter_mode2) (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero, const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp, const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
@ -130,6 +152,21 @@ static void (*filter_mode0) (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp, const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w); const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w);
static void (*filter_mode2_16bits) (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
const void *ORC_RESTRICT ttwo, const void *ORC_RESTRICT btwo,
const void *ORC_RESTRICT tptwo, const void *ORC_RESTRICT bptwo,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w);
static void (*filter_mode0_16bits) (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
const void *ORC_RESTRICT ttwo, const void *ORC_RESTRICT btwo,
const void *ORC_RESTRICT tptwo, const void *ORC_RESTRICT bptwo,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w);
static void static void
copy_scanline (GstDeinterlaceSimpleMethod * self, guint8 * out, copy_scanline (GstDeinterlaceSimpleMethod * self, guint8 * out,
@ -166,6 +203,9 @@ static void
dism_class->copy_scanline_bgr = copy_scanline; dism_class->copy_scanline_bgr = copy_scanline;
dism_class->copy_scanline_nv12 = copy_scanline; dism_class->copy_scanline_nv12 = copy_scanline;
dism_class->copy_scanline_nv21 = copy_scanline; dism_class->copy_scanline_nv21 = copy_scanline;
dism_class->copy_scanline_planar_y_16bits = copy_scanline;
dism_class->copy_scanline_planar_u_16bits = copy_scanline;
dism_class->copy_scanline_planar_v_16bits = copy_scanline;
dism_class->interpolate_scanline_planar_y = filter_scanline_yadif_planar; dism_class->interpolate_scanline_planar_y = filter_scanline_yadif_planar;
dism_class->interpolate_scanline_planar_u = filter_scanline_yadif_planar; dism_class->interpolate_scanline_planar_u = filter_scanline_yadif_planar;
@ -182,6 +222,12 @@ static void
dism_class->interpolate_scanline_bgr = filter_scanline_yadif_packed_3; dism_class->interpolate_scanline_bgr = filter_scanline_yadif_packed_3;
dism_class->interpolate_scanline_nv12 = filter_scanline_yadif_semiplanar; dism_class->interpolate_scanline_nv12 = filter_scanline_yadif_semiplanar;
dism_class->interpolate_scanline_nv21 = filter_scanline_yadif_semiplanar; dism_class->interpolate_scanline_nv21 = filter_scanline_yadif_semiplanar;
dism_class->interpolate_scanline_planar_y_16bits =
filter_scanline_yadif_planar_16bits;
dism_class->interpolate_scanline_planar_u_16bits =
filter_scanline_yadif_planar_16bits;
dism_class->interpolate_scanline_planar_v_16bits =
filter_scanline_yadif_planar_16bits;
} }
#define FFABS(a) ABS(a) #define FFABS(a) ABS(a)
@ -299,6 +345,42 @@ filter_line_c_planar (void *ORC_RESTRICT dst, const void *ORC_RESTRICT tzero,
FILTER (start, end, 1); FILTER (start, end, 1);
} }
ALWAYS_INLINE static void
filter_line_c_planar_16bits (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero,
const void *ORC_RESTRICT bzero, const void *ORC_RESTRICT mone,
const void *ORC_RESTRICT mp, const void *ORC_RESTRICT ttwo,
const void *ORC_RESTRICT btwo, const void *ORC_RESTRICT tptwo,
const void *ORC_RESTRICT bptwo, const void *ORC_RESTRICT ttone,
const void *ORC_RESTRICT ttp, const void *ORC_RESTRICT bbone,
const void *ORC_RESTRICT bbp, int w, int mode)
{
int x;
const int start = 0;
const int colors = 1;
const int y_alternates_every = 0;
const int end = w;
guint16 *sdst = (guint16 *) dst + 3;
guint16 *stzero = (guint16 *) tzero + 3;
guint16 *sbzero = (guint16 *) bzero + 3;
guint16 *smone = (guint16 *) mone + 3;
guint16 *smp = (guint16 *) mp + 3;
guint16 *sttwo = (guint16 *) ttwo + 3;
guint16 *sbtwo = (guint16 *) btwo + 3;
guint16 *stptwo = (guint16 *) tptwo + 3;
guint16 *sbptwo = (guint16 *) bptwo + 3;
guint16 *sttone = (guint16 *) ttone + 3;
guint16 *sttp = (guint16 *) ttp + 3;
guint16 *sbbone = (guint16 *) bbone + 3;
guint16 *sbbp = (guint16 *) bbp + 3;
/* The function is called for processing the middle
* pixels of each line, excluding 3 at each end.
* This allows the FILTER macro to be
* called so that it processes all the pixels normally. A constant value of
* true for is_not_edge lets the compiler ignore the if statement. */
FILTER (start, end, 1);
}
ALWAYS_INLINE G_GNUC_UNUSED static void ALWAYS_INLINE G_GNUC_UNUSED static void
filter_line_c_planar_mode0 (void *ORC_RESTRICT dst, filter_line_c_planar_mode0 (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero, const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
@ -325,6 +407,32 @@ filter_line_c_planar_mode2 (void *ORC_RESTRICT dst,
ttone, ttp, bbone, bbp, w, 2); ttone, ttp, bbone, bbp, w, 2);
} }
ALWAYS_INLINE G_GNUC_UNUSED static void
filter_line_c_planar_mode0_16bits (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
const void *ORC_RESTRICT ttwo, const void *ORC_RESTRICT btwo,
const void *ORC_RESTRICT tptwo, const void *ORC_RESTRICT bptwo,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w)
{
filter_line_c_planar_16bits (dst, tzero, bzero, mone, mp, ttwo, btwo, tptwo,
bptwo, ttone, ttp, bbone, bbp, w, 0);
}
ALWAYS_INLINE G_GNUC_UNUSED static void
filter_line_c_planar_mode2_16bits (void *ORC_RESTRICT dst,
const void *ORC_RESTRICT tzero, const void *ORC_RESTRICT bzero,
const void *ORC_RESTRICT mone, const void *ORC_RESTRICT mp,
const void *ORC_RESTRICT ttwo, const void *ORC_RESTRICT btwo,
const void *ORC_RESTRICT tptwo, const void *ORC_RESTRICT bptwo,
const void *ORC_RESTRICT ttone, const void *ORC_RESTRICT ttp,
const void *ORC_RESTRICT bbone, const void *ORC_RESTRICT bbp, int w)
{
filter_line_c_planar_16bits (dst, tzero, bzero, mone, mp, ttwo, btwo, tptwo,
bptwo, ttone, ttp, bbone, bbp, w, 2);
}
ALWAYS_INLINE static void ALWAYS_INLINE static void
filter_edges (guint8 * sdst, const guint8 * stzero, const guint8 * sbzero, filter_edges (guint8 * sdst, const guint8 * stzero, const guint8 * sbzero,
const guint8 * smone, const guint8 * smp, const guint8 * sttwo, const guint8 * smone, const guint8 * smp, const guint8 * sttwo,
@ -344,6 +452,39 @@ filter_edges (guint8 * sdst, const guint8 * stzero, const guint8 * sbzero,
FILTER (w - border, w, 0); FILTER (w - border, w, 0);
} }
ALWAYS_INLINE static void
filter_edges_16bits (guint8 * sdst_, const guint8 * stzero_,
const guint8 * sbzero_,
const guint8 * smone_, const guint8 * smp_, const guint8 * sttwo_,
const guint8 * sbtwo_, const guint8 * stptwo_, const guint8 * sbptwo_,
const guint8 * sttone_, const guint8 * sttp_, const guint8 * sbbone_,
const guint8 * sbbp_, int w, int colors, int y_alternates_every,
int mode, const int bpp)
{
int x;
const int edge = colors * (MAX_ALIGN / bpp);
const int border = 3 * colors;
guint16 *sdst = (guint16 *) sdst_;
guint16 *stzero = (guint16 *) stzero_;
guint16 *sbzero = (guint16 *) sbzero_;
guint16 *smone = (guint16 *) smone_;
guint16 *smp = (guint16 *) smp_;
guint16 *sttwo = (guint16 *) sttwo_;
guint16 *sbtwo = (guint16 *) sbtwo_;
guint16 *stptwo = (guint16 *) stptwo_;
guint16 *sbptwo = (guint16 *) sbptwo_;
guint16 *sttone = (guint16 *) sttone_;
guint16 *sttp = (guint16 *) sttp_;
guint16 *sbbone = (guint16 *) sbbone_;
guint16 *sbbp = (guint16 *) sbbp_;
/* Only edge pixels need to be processed here. A constant value of false
* for is_not_edge should let the compiler ignore the whole branch. */
FILTER (0, border, 0);
FILTER (w - edge, w - border, 1);
FILTER (w - border, w, 0);
}
static void static void
filter_scanline_yadif_semiplanar (GstDeinterlaceSimpleMethod * self, filter_scanline_yadif_semiplanar (GstDeinterlaceSimpleMethod * self,
guint8 * out, const GstDeinterlaceScanlineData * s_orig, guint size) guint8 * out, const GstDeinterlaceScanlineData * s_orig, guint size)
@ -451,9 +592,49 @@ filter_scanline_yadif_planar (GstDeinterlaceSimpleMethod * self,
(void *) s.bbp, w - edge); (void *) s.bbp, w - edge);
} }
ALWAYS_INLINE static void
filter_scanline_yadif_planar_16bits (GstDeinterlaceSimpleMethod * self,
guint8 * out, const GstDeinterlaceScanlineData * s_orig, guint size)
{
guint8 *dst = out;
const int bpp = 2;
int w = size / bpp;
int edge = MAX_ALIGN / bpp;
GstDeinterlaceScanlineData s = *s_orig;
int mode = (s.tt1 == NULL || s.bb1 == NULL || s.ttp == NULL
|| s.bbp == NULL) ? 2 : 0;
/* When starting up, some data might not yet be available, so use the current frame */
if (s.m1 == NULL)
s.m1 = s.mp;
if (s.tt1 == NULL)
s.tt1 = s.ttp;
if (s.bb1 == NULL)
s.bb1 = s.bbp;
if (s.t2 == NULL)
s.t2 = s.tp2;
if (s.b2 == NULL)
s.b2 = s.bp2;
filter_edges_16bits (dst, s.t0, s.b0, s.m1, s.mp, s.t2, s.b2, s.tp2, s.bp2,
s.tt1, s.ttp, s.bb1, s.bbp, w, 1, 0, mode, bpp);
if (mode == 0)
filter_mode0_16bits (dst, (void *) s.t0, (void *) s.b0, (void *) s.m1,
(void *) s.mp, (void *) s.t2, (void *) s.b2, (void *) s.tp2,
(void *) s.bp2, (void *) s.tt1, (void *) s.ttp, (void *) s.bb1,
(void *) s.bbp, w - edge);
else
filter_mode2_16bits (dst, (void *) s.t0, (void *) s.b0, (void *) s.m1,
(void *) s.mp, (void *) s.t2, (void *) s.b2, (void *) s.tp2,
(void *) s.bp2, (void *) s.tt1, (void *) s.ttp, (void *) s.bb1,
(void *) s.bbp, w - edge);
}
static void static void
gst_deinterlace_method_yadif_init (GstDeinterlaceMethodYadif * self) gst_deinterlace_method_yadif_init (GstDeinterlaceMethodYadif * self)
{ {
/* TODO: add asm support for high bitdepth */
#if (defined __x86_64__ || defined _M_X64) && defined HAVE_NASM #if (defined __x86_64__ || defined _M_X64) && defined HAVE_NASM
if ( if (
# if defined HAVE_ORC # if defined HAVE_ORC
@ -467,16 +648,22 @@ gst_deinterlace_method_yadif_init (GstDeinterlaceMethodYadif * self)
GST_DEBUG ("SSSE3 optimization enabled"); GST_DEBUG ("SSSE3 optimization enabled");
filter_mode0 = gst_yadif_filter_line_mode0_ssse3; filter_mode0 = gst_yadif_filter_line_mode0_ssse3;
filter_mode2 = gst_yadif_filter_line_mode2_ssse3; filter_mode2 = gst_yadif_filter_line_mode2_ssse3;
filter_mode0_16bits = filter_line_c_planar_mode0_16bits;
filter_mode2_16bits = filter_line_c_planar_mode2_16bits;
} else { } else {
GST_DEBUG ("SSE2 optimization enabled"); GST_DEBUG ("SSE2 optimization enabled");
filter_mode0 = gst_yadif_filter_line_mode0_sse2; filter_mode0 = gst_yadif_filter_line_mode0_sse2;
filter_mode2 = gst_yadif_filter_line_mode2_sse2; filter_mode2 = gst_yadif_filter_line_mode2_sse2;
filter_mode0_16bits = filter_line_c_planar_mode0_16bits;
filter_mode2_16bits = filter_line_c_planar_mode2_16bits;
} }
#else #else
{ {
GST_DEBUG ("SSE optimization disabled"); GST_DEBUG ("SSE optimization disabled");
filter_mode0 = filter_line_c_planar_mode0; filter_mode0 = filter_line_c_planar_mode0;
filter_mode2 = filter_line_c_planar_mode2; filter_mode2 = filter_line_c_planar_mode2;
filter_mode0_16bits = filter_line_c_planar_mode0_16bits;
filter_mode2_16bits = filter_line_c_planar_mode2_16bits;
} }
#endif #endif
} }