]> granicus.if.org Git - libjpeg-turbo/commitdiff
Implement h1v2 fancy upsampling
authorKornel Lesiński <kornel@geekhood.net>
Sun, 10 Jul 2016 18:01:51 +0000 (19:01 +0100)
committerDRC <information@libjpeg-turbo.org>
Wed, 13 Jul 2016 22:28:19 +0000 (17:28 -0500)
This allows fancy upsampling to be used when decompressing 4:2:2 images
that have been losslessly rotated or transposed.

(docs and comments added by DRC)

Based on https://github.com/pornel/libjpeg-turbo/commit/f63aca945debde07e7c6476a1f667b71728c3d44

Closes #89

ChangeLog.md
jdsample.c

index 33b46dc374a82f61655e3ccdcc6728908ac71262..dfd11b44b621235f14b383875329bcbd364872cc 100644 (file)
@@ -43,6 +43,11 @@ Clang/LLVM optimizer uses load combining to transfer multiple adjacent 32-bit
 structure members into a single 64-bit register, and this exposed the ABI
 conformance issue.
 
+4. Fancy upsampling is now supported when decompressing JPEG images that use
+4:4:0 (h1v2) chroma subsampling.  These images are generated when losslessly
+rotating or transposing JPEG images that use 4:2:2 (h2v1) chroma subsampling.
+The h1v2 fancy upsampling algorithm is not currently SIMD-accelerated.
+
 
 1.5.0
 =====
index 91e29dfb2494516d74371c18e11ac8c2b67c5fa5..b1378e1512933af4cff49383f9909f6e1e04c36b 100644 (file)
@@ -303,6 +303,48 @@ h2v1_fancy_upsample (j_decompress_ptr cinfo, jpeg_component_info *compptr,
 }
 
 
+/*
+ * Fancy processing for 1:1 horizontal and 2:1 vertical (4:4:0 subsampling).
+ *
+ * This is a less common case, but it can be encountered when losslessly
+ * rotating/transposing a JPEG file that uses 4:2:2 chroma subsampling.
+ */
+
+METHODDEF(void)
+h1v2_fancy_upsample (j_decompress_ptr cinfo, jpeg_component_info *compptr,
+                     JSAMPARRAY input_data, JSAMPARRAY *output_data_ptr)
+{
+  JSAMPARRAY output_data = *output_data_ptr;
+  JSAMPROW inptr0, inptr1, outptr;
+#if BITS_IN_JSAMPLE == 8
+  int thiscolsum;
+#else
+  JLONG thiscolsum;
+#endif
+  JDIMENSION colctr;
+  int inrow, outrow, v;
+
+  inrow = outrow = 0;
+  while (outrow < cinfo->max_v_samp_factor) {
+    for (v = 0; v < 2; v++) {
+      /* inptr0 points to nearest input row, inptr1 points to next nearest */
+      inptr0 = input_data[inrow];
+      if (v == 0)               /* next nearest is row above */
+        inptr1 = input_data[inrow-1];
+      else                      /* next nearest is row below */
+        inptr1 = input_data[inrow+1];
+      outptr = output_data[outrow++];
+
+      for(colctr = 0; colctr < compptr->downsampled_width; colctr++) {
+        thiscolsum = GETJSAMPLE(*inptr0++) * 3 + GETJSAMPLE(*inptr1++);
+        *outptr++ = (JSAMPLE) ((thiscolsum + 1) >> 2);
+      }
+    }
+    inrow++;
+  }
+}
+
+
 /*
  * Fancy processing for the common case of 2:1 horizontal and 2:1 vertical.
  * Again a triangle filter; see comments for h2v1 case, above.
@@ -431,6 +473,11 @@ jinit_upsampler (j_decompress_ptr cinfo)
         else
           upsample->methods[ci] = h2v1_upsample;
       }
+    } else if (h_in_group == h_out_group &&
+               v_in_group * 2 == v_out_group && do_fancy) {
+      /* Non-fancy upsampling is handled by the generic method */
+      upsample->methods[ci] = h1v2_fancy_upsample;
+      upsample->pub.need_context_rows = TRUE;
     } else if (h_in_group * 2 == h_out_group &&
                v_in_group * 2 == v_out_group) {
       /* Special cases for 2h2v upsampling */