summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWim Taymans <wim.taymans@collabora.co.uk>2013-04-01 16:16:27 +0200
committerWim Taymans <wim.taymans@collabora.co.uk>2013-05-16 17:13:43 +0200
commit873f7e7d4590268e064789cbd8028a36c75e6910 (patch)
tree9fed99244c2102d74b502711584b6c8eac14dfe2
parent0ecc45bc10a80987f54ee4b1c0b58935c2354a10 (diff)
video: don't perform subsampling while packing
Don't perform subsampling when packing but let this be done by a separate subsampling step.
-rw-r--r--gst-libs/gst/video/video-format.c82
-rw-r--r--gst-libs/gst/video/video-format.h9
-rw-r--r--gst-libs/gst/video/video-orc.orc56
3 files changed, 65 insertions, 82 deletions
diff --git a/gst-libs/gst/video/video-format.c b/gst-libs/gst/video/video-format.c
index 8fb69f727..427874fae 100644
--- a/gst-libs/gst/video/video-format.c
+++ b/gst-libs/gst/video/video-format.c
@@ -318,13 +318,13 @@ pack_v210 (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
y4 = s[4 * (i + 4) + 1] >> 6;
y5 = s[4 * (i + 5) + 1] >> 6;
- u0 = (s[4 * (i + 0) + 2] + s[4 * (i + 1) + 2] + 1) >> 7;
- u1 = (s[4 * (i + 2) + 2] + s[4 * (i + 3) + 2] + 1) >> 7;
- u2 = (s[4 * (i + 4) + 2] + s[4 * (i + 5) + 2] + 1) >> 7;
+ u0 = s[4 * (i + 0) + 2] >> 6;
+ u1 = s[4 * (i + 2) + 2] >> 6;
+ u2 = s[4 * (i + 4) + 2] >> 6;
- v0 = (s[4 * (i + 0) + 3] + s[4 * (i + 1) + 3] + 1) >> 7;
- v1 = (s[4 * (i + 2) + 3] + s[4 * (i + 3) + 3] + 1) >> 7;
- v2 = (s[4 * (i + 4) + 3] + s[4 * (i + 5) + 3] + 1) >> 7;
+ v0 = s[4 * (i + 0) + 3] >> 6;
+ v1 = s[4 * (i + 2) + 3] >> 6;
+ v2 = s[4 * (i + 4) + 3] >> 6;
a0 = u0 | (y0 << 10) | (v0 << 20);
a1 = y1 | (u1 << 10) | (y2 << 20);
@@ -402,10 +402,8 @@ pack_Y41B (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
destY[i + 2] = s[i * 4 + 9];
destY[i + 3] = s[i * 4 + 13];
- destU[i >> 2] =
- (s[i * 4 + 2] + s[i * 4 + 6] + s[i * 4 + 10] + s[i * 4 + 14] + 2) >> 2;
- destV[i >> 2] =
- (s[i * 4 + 3] + s[i * 4 + 7] + s[i * 4 + 11] + s[i * 4 + 15] + 2) >> 2;
+ destU[i >> 2] = s[i * 4 + 2];
+ destV[i >> 2] = s[i * 4 + 3];
}
if (i == width - 3) {
@@ -413,14 +411,14 @@ pack_Y41B (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
destY[i + 1] = s[i * 4 + 5];
destY[i + 2] = s[i * 4 + 9];
- destU[i >> 2] = (s[i * 4 + 2] + s[i * 4 + 6] + s[i * 4 + 10] + 1) / 3;
- destV[i >> 2] = (s[i * 4 + 3] + s[i * 4 + 7] + s[i * 4 + 11] + 1) / 3;
+ destU[i >> 2] = s[i * 4 + 2];
+ destV[i >> 2] = s[i * 4 + 3];
} else if (i == width - 2) {
destY[i] = s[i * 4 + 1];
destY[i + 1] = s[i * 4 + 5];
- destU[i >> 2] = (s[i * 4 + 2] + s[i * 4 + 6] + 1) >> 1;
- destV[i >> 2] = (s[i * 4 + 3] + s[i * 4 + 7] + 1) >> 1;
+ destU[i >> 2] = s[i * 4 + 2];
+ destV[i >> 2] = s[i * 4 + 3];
} else if (i == width - 1) {
destY[i + 1] = s[i * 4 + 5];
@@ -997,8 +995,8 @@ pack_UYVP (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
y0 = s[4 * (i + 0) + 1];
y1 = s[4 * (i + 1) + 1];
- u0 = (s[4 * (i + 0) + 2] + s[4 * (i + 1) + 2] + 1) >> 1;
- v0 = (s[4 * (i + 0) + 3] + s[4 * (i + 1) + 3] + 1) >> 1;
+ u0 = s[4 * (i + 0) + 2];
+ v0 = s[4 * (i + 0) + 3];
d[(i / 2) * 5 + 0] = u0 >> 8;
d[(i / 2) * 5 + 1] = (u0 & 0xc0) | y0 >> 10;
@@ -1151,10 +1149,8 @@ pack_410 (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
destY[i + 2] = s[i * 4 + 9];
destY[i + 3] = s[i * 4 + 13];
if (y % 4 == 0) {
- destU[i >> 2] =
- (s[i * 4 + 2] + s[i * 4 + 6] + s[i * 4 + 10] + s[i * 4 + 14]) >> 2;
- destV[i >> 2] =
- (s[i * 4 + 3] + s[i * 4 + 7] + s[i * 4 + 11] + s[i * 4 + 15]) >> 2;
+ destU[i >> 2] = s[i * 4 + 2];
+ destV[i >> 2] = s[i * 4 + 3];
}
}
@@ -1163,15 +1159,15 @@ pack_410 (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
destY[i + 1] = s[i * 4 + 5];
destY[i + 2] = s[i * 4 + 9];
if (y % 4 == 0) {
- destU[i >> 2] = (s[i * 4 + 2] + s[i * 4 + 6] + s[i * 4 + 10]) / 3;
- destV[i >> 2] = (s[i * 4 + 3] + s[i * 4 + 7] + s[i * 4 + 11]) / 3;
+ destU[i >> 2] = s[i * 4 + 2];
+ destV[i >> 2] = s[i * 4 + 3];
}
} else if (i == width - 2) {
destY[i] = s[i * 4 + 1];
destY[i + 1] = s[i * 4 + 5];
if (y % 4 == 0) {
- destU[i >> 2] = (s[i * 4 + 2] + s[i * 4 + 6]) >> 1;
- destV[i >> 2] = (s[i * 4 + 3] + s[i * 4 + 7]) >> 1;
+ destU[i >> 2] = s[i * 4 + 2];
+ destV[i >> 2] = s[i * 4 + 3];
}
} else if (i == width - 1) {
destY[i] = s[i * 4 + 1];
@@ -1244,23 +1240,21 @@ pack_IYU1 (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
d[(i >> 2) * 6 + 2] = s[i * 4 + 5];
d[(i >> 2) * 6 + 4] = s[i * 4 + 9];
d[(i >> 2) * 6 + 5] = s[i * 4 + 13];
- d[(i >> 2) * 6 + 0] =
- (s[i * 4 + 2] + s[i * 4 + 6] + s[i * 4 + 10] + s[i * 4 + 14]) >> 2;
- d[(i >> 2) * 6 + 3] =
- (s[i * 4 + 3] + s[i * 4 + 7] + s[i * 4 + 11] + s[i * 4 + 15]) >> 2;
+ d[(i >> 2) * 6 + 0] = s[i * 4 + 2];
+ d[(i >> 2) * 6 + 3] = s[i * 4 + 3];
}
if (i == width - 3) {
d[(i >> 2) * 6 + 1] = s[i * 4 + 1];
d[(i >> 2) * 6 + 2] = s[i * 4 + 5];
d[(i >> 2) * 6 + 4] = s[i * 4 + 9];
- d[(i >> 2) * 6 + 0] = (s[i * 4 + 2] + s[i * 4 + 6] + s[i * 4 + 10]) / 3;
- d[(i >> 2) * 6 + 3] = (s[i * 4 + 3] + s[i * 4 + 7] + s[i * 4 + 11]) / 3;
+ d[(i >> 2) * 6 + 0] = s[i * 4 + 2];
+ d[(i >> 2) * 6 + 3] = s[i * 4 + 3];
} else if (i == width - 2) {
d[(i >> 2) * 6 + 1] = s[i * 4 + 1];
d[(i >> 2) * 6 + 2] = s[i * 4 + 5];
- d[(i >> 2) * 6 + 0] = (s[i * 4 + 2] + s[i * 4 + 6]) >> 1;
- d[(i >> 2) * 6 + 3] = (s[i * 4 + 3] + s[i * 4 + 7]) >> 1;
+ d[(i >> 2) * 6 + 0] = s[i * 4 + 2];
+ d[(i >> 2) * 6 + 3] = s[i * 4 + 3];
} else if (i == width - 1) {
d[(i >> 2) * 6 + 1] = s[i * 4 + 1];
d[(i >> 2) * 6 + 0] = s[i * 4 + 2];
@@ -1586,10 +1580,10 @@ pack_I420_10LE (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
const guint16 *s = src;
for (i = 0; i < width - 1; i += 2) {
- Y0 = (s[i * 4 + 1]) >> 6;
- Y1 = (s[i * 4 + 5]) >> 6;
- U = ((s[i * 4 + 2] + s[i * 4 + 6] + 1) >> 1) >> 6;
- V = ((s[i * 4 + 3] + s[i * 4 + 7] + 1) >> 1) >> 6;
+ Y0 = s[i * 4 + 1] >> 6;
+ Y1 = s[i * 4 + 5] >> 6;
+ U = s[i * 4 + 2] >> 6;
+ V = s[i * 4 + 3] >> 6;
GST_WRITE_UINT16_LE (destY + i + 0, Y0);
GST_WRITE_UINT16_LE (destY + i + 1, Y1);
@@ -1655,8 +1649,8 @@ pack_I420_10BE (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
for (i = 0; i < width - 1; i += 2) {
Y0 = s[i * 4 + 1] >> 6;
Y1 = s[i * 4 + 5] >> 6;
- U = ((s[i * 4 + 2] + s[i * 4 + 6] + 1) >> 1) >> 6;
- V = ((s[i * 4 + 3] + s[i * 4 + 7] + 1) >> 1) >> 6;
+ U = s[i * 4 + 2] >> 6;
+ V = s[i * 4 + 3] >> 6;
GST_WRITE_UINT16_BE (destY + i + 0, Y0);
GST_WRITE_UINT16_BE (destY + i + 1, Y1);
@@ -1718,10 +1712,10 @@ pack_I422_10LE (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
const guint16 *s = src;
for (i = 0; i < width - 1; i += 2) {
- Y0 = (s[i * 4 + 1]) >> 6;
- Y1 = (s[i * 4 + 5]) >> 6;
- U = ((s[i * 4 + 2] + s[i * 4 + 6] + 1) >> 1) >> 6;
- V = ((s[i * 4 + 3] + s[i * 4 + 7] + 1) >> 1) >> 6;
+ Y0 = s[i * 4 + 1] >> 6;
+ Y1 = s[i * 4 + 5] >> 6;
+ U = s[i * 4 + 2] >> 6;
+ V = s[i * 4 + 3] >> 6;
GST_WRITE_UINT16_LE (destY + i + 0, Y0);
GST_WRITE_UINT16_LE (destY + i + 1, Y1);
@@ -1785,8 +1779,8 @@ pack_I422_10BE (const GstVideoFormatInfo * info, GstVideoPackFlags flags,
for (i = 0; i < width - 1; i += 2) {
Y0 = s[i * 4 + 1] >> 6;
Y1 = s[i * 4 + 5] >> 6;
- U = ((s[i * 4 + 2] + s[i * 4 + 6] + 1) >> 1) >> 6;
- V = ((s[i * 4 + 3] + s[i * 4 + 7] + 1) >> 1) >> 6;
+ U = s[i * 4 + 2] >> 6;
+ V = s[i * 4 + 3] >> 6;
GST_WRITE_UINT16_BE (destY + i + 0, Y0);
GST_WRITE_UINT16_BE (destY + i + 1, Y1);
diff --git a/gst-libs/gst/video/video-format.h b/gst-libs/gst/video/video-format.h
index 9cb4f2b7e..90d320b75 100644
--- a/gst-libs/gst/video/video-format.h
+++ b/gst-libs/gst/video/video-format.h
@@ -230,6 +230,10 @@ typedef enum
* format @info. The pixels will be unpacked into @dest which each component
* interleaved. @dest should at least be big enough to hold @width *
* n_components * size(unpack_format) bytes.
+ *
+ * For subsampled formats, the components will be duplicated in the destination
+ * array. Reconstruction of the missing components can be performed in a
+ * separate step after unpacking.
*/
typedef void (*GstVideoFormatUnpack) (const GstVideoFormatInfo *info,
GstVideoPackFlags flags, gpointer dest,
@@ -244,7 +248,7 @@ typedef void (*GstVideoFormatUnpack) (const GstVideoFormatInfo *info,
* @sstride: the source array stride
* @data: pointers to the destination data planes
* @stride: strides of the destination planes
- * @chroma_site: the chroma siting of the target when subsampled
+ * @chroma_site: the chroma siting of the target when subsampled (not used)
* @y: the y position in the image to pack to
* @width: the amount of pixels to pack.
*
@@ -255,6 +259,9 @@ typedef void (*GstVideoFormatUnpack) (const GstVideoFormatInfo *info,
* This function operates on pack_lines lines, meaning that @src should
* contain at least pack_lines lines with a stride of @sstride and @y
* should be a multiple of pack_lines.
+ *
+ * Subsampled formats will use the horizontally cosited component in the
+ * destination. Subsampling should be performed before packing.
*/
typedef void (*GstVideoFormatPack) (const GstVideoFormatInfo *info,
GstVideoPackFlags flags,
diff --git a/gst-libs/gst/video/video-orc.orc b/gst-libs/gst/video/video-orc.orc
index 445be2441..1dab8a9b2 100644
--- a/gst-libs/gst/video/video-orc.orc
+++ b/gst-libs/gst/video/video-orc.orc
@@ -93,10 +93,8 @@ mergewl d, ay, uv
x2 splitlw uv, ay, ayuv
x2 select1wb y, ay
x2 splitwb vv, uu, uv
-splitwb t1, t2, uu
-avgub u, t1, t2
-splitwb t1, t2, vv
-avgub v, t1, t2
+select0wb u, uu
+select0wb v, vv
.function video_orc_unpack_YUY2
.dest 8 ayuv guint8
@@ -117,32 +115,28 @@ x2 mergewl ayuv, ayay, uvuv
.dest 4 yuy2 guint8
.source 8 ayuv guint8
.temp 2 yy
-.temp 2 uv1
-.temp 2 uv2
+.temp 2 uv
.temp 4 ayay
.temp 4 uvuv
x2 splitlw uvuv, ayay, ayuv
-splitlw uv1, uv2, uvuv
-x2 avgub uv1, uv1, uv2
+select0lw uv, uvuv
x2 select1wb yy, ayay
-x2 mergebw yuy2, yy, uv1
+x2 mergebw yuy2, yy, uv
.function video_orc_pack_UYVY
.dest 4 yuy2 guint8
.source 8 ayuv guint8
.temp 2 yy
-.temp 2 uv1
-.temp 2 uv2
+.temp 2 uv
.temp 4 ayay
.temp 4 uvuv
x2 splitlw uvuv, ayay, ayuv
-splitlw uv1, uv2, uvuv
-x2 avgub uv1, uv1, uv2
+select0lw uv, uvuv
x2 select1wb yy, ayay
-x2 mergebw yuy2, uv1, yy
+x2 mergebw yuy2, uv, yy
.function video_orc_unpack_UYVY
@@ -180,17 +174,15 @@ x2 mergewl ayuv, ayay, uvuv
.dest 4 yuy2 guint8
.source 8 ayuv guint8
.temp 2 yy
-.temp 2 uv1
-.temp 2 uv2
+.temp 2 uv
.temp 4 ayay
.temp 4 uvuv
x2 splitlw uvuv, ayay, ayuv
-splitlw uv1, uv2, uvuv
-x2 avgub uv1, uv1, uv2
+select0lw uv, uvuv
x2 select1wb yy, ayay
-swapw uv1, uv1
-x2 mergebw yuy2, yy, uv1
+swapw uv, uv
+x2 mergebw yuy2, yy, uv
.function video_orc_unpack_YUV9
@@ -236,13 +228,11 @@ x2 mergewl ayuv, ayay, uvuv
.source 8 ayuv guint8
.temp 4 ayay
.temp 4 uvuv
-.temp 2 uv1
-.temp 2 uv2
+.temp 2 uv
x2 splitlw uvuv, ayay, ayuv
-splitlw uv1, uv2, uvuv
-x2 avgub uv1, uv1, uv2
-splitwb v, u, uv1
+select0lw uv, uvuv
+splitwb v, u, uv
x2 select1wb y, ayay
@@ -405,8 +395,7 @@ x2 mergewl d, ay, uvuv
x2 splitlw uvuv, ay, ayuv
x2 select1wb y, ay
-splitlw uv1, uv2, uvuv
-x2 avgub uv, uv1, uv2
+select0lw uv, uvuv
.function video_orc_unpack_NV21
.dest 8 d guint8
@@ -429,14 +418,11 @@ x2 mergewl d, ay, uvuv
.source 8 ayuv guint8
.temp 4 ay
.temp 4 uvuv
-.temp 2 uv1
-.temp 2 uv2
.temp 2 uv
x2 splitlw uvuv, ay, ayuv
x2 select1wb y, ay
-splitlw uv1, uv2, uvuv
-x2 avgub uv, uv1, uv2
+select0lw uv, uvuv
swapw vu, uv
@@ -491,17 +477,13 @@ mergewl d, ay, uv
.temp 4 uv
.temp 2 uu
.temp 2 vv
-.temp 1 t1
-.temp 1 t2
x2 splitlw uv, ay, ayuv
x2 select1wb y, ay
x2 select0wb a, ay
x2 splitwb vv, uu, uv
-splitwb t1, t2, uu
-avgub u, t1, t2
-splitwb t1, t2, vv
-avgub v, t1, t2
+select0wb u, uu
+select0wb v, vv
.function video_orc_resample_bilinear_u32
.dest 4 d1 guint8