Browse code

diracdec: add support for 12 bit videos

The DSP lacked a function needed to convert signed to unsigned. This was
ignored when originally adding support and templating for bit depths
greater than 8. The 10 bit function was used for 12 bit pictures and
resulted in an improper conversion.

Signed-off-by: Rostislav Pehlivanov <atomnuker@gmail.com>

Rostislav Pehlivanov authored on 2016/01/21 23:44:42
Showing 2 changed files
... ...
@@ -1839,9 +1839,12 @@ static int dirac_decode_frame_internal(DiracContext *s)
1839 1839
 
1840 1840
         if (!s->num_refs) { /* intra */
1841 1841
             for (y = 0; y < p->height; y += 16) {
1842
+                int idx = (s->bit_depth - 8) >> 1;
1842 1843
                 ff_spatial_idwt_slice2(&d, y+16); /* decode */
1843
-                s->diracdsp.put_signed_rect_clamped[s->pshift](frame + y*p->stride, p->stride,
1844
-                                                               p->idwt_buf + y*p->idwt_stride, p->idwt_stride, p->width, 16);
1844
+                s->diracdsp.put_signed_rect_clamped[idx](frame + y*p->stride,
1845
+                                                         p->stride,
1846
+                                                         p->idwt_buf + y*p->idwt_stride,
1847
+                                                         p->idwt_stride, p->width, 16);
1845 1848
             }
1846 1849
         } else { /* inter */
1847 1850
             int rowheight = p->ybsep*p->stride;
... ...
@@ -168,6 +168,23 @@ static void put_signed_rect_clamped_10bit_c(uint8_t *_dst, int dst_stride, const
168 168
     }
169 169
 }
170 170
 
171
+static void put_signed_rect_clamped_12bit_c(uint8_t *_dst, int dst_stride, const uint8_t *_src, int src_stride, int width, int height)
172
+{
173
+    int x, y;
174
+    uint16_t *dst = (uint16_t *)_dst;
175
+    int32_t *src = (int32_t *)_src;
176
+    for (y = 0; y < height; y++) {
177
+        for (x = 0; x < width; x+=4) {
178
+            dst[x  ] = av_clip(src[x  ] + 2048, 0, (1 << 12) - 1);
179
+            dst[x+1] = av_clip(src[x+1] + 2048, 0, (1 << 12) - 1);
180
+            dst[x+2] = av_clip(src[x+2] + 2048, 0, (1 << 12) - 1);
181
+            dst[x+3] = av_clip(src[x+3] + 2048, 0, (1 << 12) - 1);
182
+        }
183
+        dst += dst_stride >> 1;
184
+        src += src_stride >> 2;
185
+    }
186
+}
187
+
171 188
 static void add_rect_clamped_c(uint8_t *dst, const uint16_t *src, int stride,
172 189
                                const int16_t *idwt, int idwt_stride,
173 190
                                int width, int height)
... ...
@@ -197,6 +214,7 @@ av_cold void ff_diracdsp_init(DiracDSPContext *c)
197 197
     c->add_rect_clamped = add_rect_clamped_c;
198 198
     c->put_signed_rect_clamped[0] = put_signed_rect_clamped_8bit_c;
199 199
     c->put_signed_rect_clamped[1] = put_signed_rect_clamped_10bit_c;
200
+    c->put_signed_rect_clamped[2] = put_signed_rect_clamped_12bit_c;
200 201
 
201 202
     c->add_dirac_obmc[0] = add_obmc8_c;
202 203
     c->add_dirac_obmc[1] = add_obmc16_c;