SOURCES: libjpeg-crop.patch (NEW) - croppatch in diff form

qboosh qboosh at pld-linux.org
Sun Jan 27 21:30:30 CET 2008


Author: qboosh                       Date: Sun Jan 27 20:30:30 2008 GMT
Module: SOURCES                       Tag: HEAD
---- Log message:
- croppatch in diff form

---- Files affected:
SOURCES:
   libjpeg-crop.patch (NONE -> 1.1)  (NEW)

---- Diffs:

================================================================
Index: SOURCES/libjpeg-crop.patch
diff -u /dev/null SOURCES/libjpeg-crop.patch:1.1
--- /dev/null	Sun Jan 27 21:30:30 2008
+++ SOURCES/libjpeg-crop.patch	Sun Jan 27 21:30:24 2008
@@ -0,0 +1,1884 @@
+diff -Nur jpeg-6b.orig/jerror.h jpeg-6b/jerror.h
+--- jpeg-6b.orig/jerror.h	1997-10-18 20:59:10.000000000 +0200
++++ jpeg-6b/jerror.h	2000-03-05 23:34:27.000000000 +0100
+@@ -45,6 +45,7 @@
+ JMESSAGE(JERR_BAD_ALLOC_CHUNK, "MAX_ALLOC_CHUNK is wrong, please fix")
+ JMESSAGE(JERR_BAD_BUFFER_MODE, "Bogus buffer control mode")
+ JMESSAGE(JERR_BAD_COMPONENT_ID, "Invalid component ID %d in SOS")
++JMESSAGE(JERR_BAD_CROP_SPEC, "Invalid crop request")
+ JMESSAGE(JERR_BAD_DCT_COEF, "DCT coefficient out of range")
+ JMESSAGE(JERR_BAD_DCTSIZE, "IDCT output block size %d not supported")
+ JMESSAGE(JERR_BAD_HUFF_TABLE, "Bogus Huffman table definition")
+diff -Nur jpeg-6b.orig/jpegtran.c jpeg-6b/jpegtran.c
+--- jpeg-6b.orig/jpegtran.c	1997-07-24 04:37:26.000000000 +0200
++++ jpeg-6b/jpegtran.c	2003-09-21 21:30:21.000000000 +0200
+@@ -1,7 +1,7 @@
+ /*
+  * jpegtran.c
+  *
+- * Copyright (C) 1995-1997, Thomas G. Lane.
++ * Copyright (C) 1995-2001, Thomas G. Lane.
+  * This file is part of the Independent JPEG Group's software.
+  * For conditions of distribution and use, see the accompanying README file.
+  *
+@@ -64,8 +64,10 @@
+ #endif
+ #if TRANSFORMS_SUPPORTED
+   fprintf(stderr, "Switches for modifying the image:\n");
++  fprintf(stderr, "  -crop WxH+X+Y  Crop to a rectangular subarea\n");
+   fprintf(stderr, "  -grayscale     Reduce to grayscale (omit color data)\n");
+   fprintf(stderr, "  -flip [horizontal|vertical]  Mirror image (left-right or top-bottom)\n");
++  fprintf(stderr, "  -perfect       Fail if there is non-transformable edge blocks\n");
+   fprintf(stderr, "  -rotate [90|180|270]         Rotate image (degrees clockwise)\n");
+   fprintf(stderr, "  -transpose     Transpose image\n");
+   fprintf(stderr, "  -transverse    Transverse transpose image\n");
+@@ -133,7 +135,9 @@
+   copyoption = JCOPYOPT_DEFAULT;
+   transformoption.transform = JXFORM_NONE;
+   transformoption.trim = FALSE;
++  transformoption.perfect = FALSE;
+   transformoption.force_grayscale = FALSE;
++  transformoption.crop = FALSE;
+   cinfo->err->trace_level = 0;
+ 
+   /* Scan command line options, adjust parameters */
+@@ -160,7 +164,7 @@
+       exit(EXIT_FAILURE);
+ #endif
+ 
+-    } else if (keymatch(arg, "copy", 1)) {
++    } else if (keymatch(arg, "copy", 2)) {
+       /* Select which extra markers to copy. */
+       if (++argn >= argc)	/* advance to next argument */
+ 	usage();
+@@ -173,6 +177,20 @@
+       } else
+ 	usage();
+ 
++    } else if (keymatch(arg, "crop", 2)) {
++      /* Perform lossless cropping. */
++#if TRANSFORMS_SUPPORTED
++      if (++argn >= argc)	/* advance to next argument */
++	usage();
++      if (! jtransform_parse_crop_spec(&transformoption, argv[argn])) {
++	fprintf(stderr, "%s: bogus -crop argument '%s'\n",
++		progname, argv[argn]);
++	exit(EXIT_FAILURE);
++      }
++#else
++      select_transform(JXFORM_NONE);	/* force an error */
++#endif
++
+     } else if (keymatch(arg, "debug", 1) || keymatch(arg, "verbose", 1)) {
+       /* Enable debug printouts. */
+       /* On first -d, print version identification */
+@@ -233,7 +251,12 @@
+ 	usage();
+       outfilename = argv[argn];	/* save it away for later use */
+ 
+-    } else if (keymatch(arg, "progressive", 1)) {
++    } else if (keymatch(arg, "perfect", 2)) {
++      /* Fail if there is any partial edge MCUs that the transform can't
++       * handle. */
++      transformoption.perfect = TRUE;
++
++    } else if (keymatch(arg, "progressive", 2)) {
+       /* Select simple progressive mode. */
+ #ifdef C_PROGRESSIVE_SUPPORTED
+       simple_progressive = TRUE;
+@@ -342,8 +365,10 @@
+   jvirt_barray_ptr * src_coef_arrays;
+   jvirt_barray_ptr * dst_coef_arrays;
+   int file_index;
+-  FILE * input_file;
+-  FILE * output_file;
++  /* We assume all-in-memory processing and can therefore use only a
++   * single file pointer for sequential input and output operation. 
++   */
++  FILE * fp;
+ 
+   /* On Mac, fetch a command line. */
+ #ifdef USE_CCOMMAND
+@@ -406,24 +431,13 @@
+ 
+   /* Open the input file. */
+   if (file_index < argc) {
+-    if ((input_file = fopen(argv[file_index], READ_BINARY)) == NULL) {
+-      fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index]);
++    if ((fp = fopen(argv[file_index], READ_BINARY)) == NULL) {
++      fprintf(stderr, "%s: can't open %s for reading\n", progname, argv[file_index]);
+       exit(EXIT_FAILURE);
+     }
+   } else {
+     /* default input file is stdin */
+-    input_file = read_stdin();
+-  }
+-
+-  /* Open the output file. */
+-  if (outfilename != NULL) {
+-    if ((output_file = fopen(outfilename, WRITE_BINARY)) == NULL) {
+-      fprintf(stderr, "%s: can't open %s\n", progname, outfilename);
+-      exit(EXIT_FAILURE);
+-    }
+-  } else {
+-    /* default output file is stdout */
+-    output_file = write_stdout();
++    fp = read_stdin();
+   }
+ 
+ #ifdef PROGRESS_REPORT
+@@ -431,7 +445,7 @@
+ #endif
+ 
+   /* Specify data source for decompression */
+-  jpeg_stdio_src(&srcinfo, input_file);
++  jpeg_stdio_src(&srcinfo, fp);
+ 
+   /* Enable saving of extra markers that we want to copy */
+   jcopy_markers_setup(&srcinfo, copyoption);
+@@ -443,6 +457,15 @@
+    * jpeg_read_coefficients so that memory allocation will be done right.
+    */
+ #if TRANSFORMS_SUPPORTED
++  /* Fails right away if -perfect is given and transformation is not perfect.
++   */
++  if (transformoption.perfect &&
++      !jtransform_perfect_transform(srcinfo.image_width, srcinfo.image_height,
++      srcinfo.max_h_samp_factor * DCTSIZE, srcinfo.max_v_samp_factor * DCTSIZE,
++      transformoption.transform)) {
++    fprintf(stderr, "%s: transformation is not perfect\n", progname);
++    exit(EXIT_FAILURE);
++  }
+   jtransform_request_workspace(&srcinfo, &transformoption);
+ #endif
+ 
+@@ -463,11 +486,32 @@
+   dst_coef_arrays = src_coef_arrays;
+ #endif
+ 
++  /* Close input file, if we opened it.
++   * Note: we assume that jpeg_read_coefficients consumed all input
++   * until JPEG_REACHED_EOI, and that jpeg_finish_decompress will
++   * only consume more while (! cinfo->inputctl->eoi_reached).
++   * We cannot call jpeg_finish_decompress here since we still need the
++   * virtual arrays allocated from the source object for processing.
++   */
++  if (fp != stdin)
++    fclose(fp);
++
++  /* Open the output file. */
++  if (outfilename != NULL) {
++    if ((fp = fopen(outfilename, WRITE_BINARY)) == NULL) {
++      fprintf(stderr, "%s: can't open %s for writing\n", progname, outfilename);
++      exit(EXIT_FAILURE);
++    }
++  } else {
++    /* default output file is stdout */
++    fp = write_stdout();
++  }
++
+   /* Adjust default compression parameters by re-parsing the options */
+   file_index = parse_switches(&dstinfo, argc, argv, 0, TRUE);
+ 
+   /* Specify data destination for compression */
+-  jpeg_stdio_dest(&dstinfo, output_file);
++  jpeg_stdio_dest(&dstinfo, fp);
+ 
+   /* Start compressor (note no image data is actually written here) */
+   jpeg_write_coefficients(&dstinfo, dst_coef_arrays);
+@@ -488,11 +532,9 @@
+   (void) jpeg_finish_decompress(&srcinfo);
+   jpeg_destroy_decompress(&srcinfo);
+ 
+-  /* Close files, if we opened them */
+-  if (input_file != stdin)
+-    fclose(input_file);
+-  if (output_file != stdout)
+-    fclose(output_file);
++  /* Close output file, if we opened it */
++  if (fp != stdout)
++    fclose(fp);
+ 
+ #ifdef PROGRESS_REPORT
+   end_progress_monitor((j_common_ptr) &dstinfo);
+diff -Nur jpeg-6b.orig/transupp.c jpeg-6b/transupp.c
+--- jpeg-6b.orig/transupp.c	1997-08-10 02:15:26.000000000 +0200
++++ jpeg-6b/transupp.c	2003-09-21 22:50:33.000000000 +0200
+@@ -1,7 +1,7 @@
+ /*
+  * transupp.c
+  *
+- * Copyright (C) 1997, Thomas G. Lane.
++ * Copyright (C) 1997-2001, Thomas G. Lane.
+  * This file is part of the Independent JPEG Group's software.
+  * For conditions of distribution and use, see the accompanying README file.
+  *
+@@ -20,6 +20,7 @@
+ #include "jinclude.h"
+ #include "jpeglib.h"
+ #include "transupp.h"		/* My own external interface */
++#include <ctype.h>		/* to declare isdigit() */
+ 
+ 
+ #if TRANSFORMS_SUPPORTED
+@@ -28,7 +29,8 @@
+  * Lossless image transformation routines.  These routines work on DCT
+  * coefficient arrays and thus do not require any lossy decompression
+  * or recompression of the image.
+- * Thanks to Guido Vollbeding for the initial design and code of this feature.
++ * Thanks to Guido Vollbeding for the initial design and code of this feature,
++ * and to Ben Jackson for introducing the cropping feature.
+  *
+  * Horizontal flipping is done in-place, using a single top-to-bottom
+  * pass through the virtual source array.  It will thus be much the
+@@ -42,6 +44,13 @@
+  * arrays for most of the transforms.  That could result in much thrashing
+  * if the image is larger than main memory.
+  *
++ * If cropping or trimming is involved, the destination arrays may be smaller
++ * than the source arrays.  Note it is not possible to do horizontal flip
++ * in-place when a nonzero Y crop offset is specified, since we'd have to move
++ * data from one block row to another but the virtual array manager doesn't
++ * guarantee we can touch more than one row at a time.  So in that case,
++ * we have to use a separate destination array.
++ *
+  * Some notes about the operating environment of the individual transform
+  * routines:
+  * 1. Both the source and destination virtual arrays are allocated from the
+@@ -54,20 +63,65 @@
+  *    and we may as well take that as the effective iMCU size.
+  * 4. When "trim" is in effect, the destination's dimensions will be the
+  *    trimmed values but the source's will be untrimmed.
+- * 5. All the routines assume that the source and destination buffers are
++ * 5. When "crop" is in effect, the destination's dimensions will be the
++ *    cropped values but the source's will be uncropped.  Each transform
++ *    routine is responsible for picking up source data starting at the
++ *    correct X and Y offset for the crop region.  (The X and Y offsets
++ *    passed to the transform routines are measured in iMCU blocks of the
++ *    destination.)
++ * 6. All the routines assume that the source and destination buffers are
+  *    padded out to a full iMCU boundary.  This is true, although for the
+  *    source buffer it is an undocumented property of jdcoefct.c.
+- * Notes 2,3,4 boil down to this: generally we should use the destination's
+- * dimensions and ignore the source's.
+  */
+ 
+ 
+ LOCAL(void)
+-do_flip_h (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
+-	   jvirt_barray_ptr *src_coef_arrays)
+-/* Horizontal flip; done in-place, so no separate dest array is required */
++do_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
++	 JDIMENSION x_crop_offset, JDIMENSION y_crop_offset,
++	 jvirt_barray_ptr *src_coef_arrays,
++	 jvirt_barray_ptr *dst_coef_arrays)
++/* Crop.  This is only used when no rotate/flip is requested with the crop. */
++{
++  JDIMENSION dst_blk_y, x_crop_blocks, y_crop_blocks;
++  int ci, offset_y;
++  JBLOCKARRAY src_buffer, dst_buffer;
++  jpeg_component_info *compptr;
++
++  /* We simply have to copy the right amount of data (the destination's
++   * image size) starting at the given X and Y offsets in the source.
++   */
++  for (ci = 0; ci < dstinfo->num_components; ci++) {
++    compptr = dstinfo->comp_info + ci;
++    x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
++    y_crop_blocks = y_crop_offset * compptr->v_samp_factor;
++    for (dst_blk_y = 0; dst_blk_y < compptr->height_in_blocks;
++	 dst_blk_y += compptr->v_samp_factor) {
++      dst_buffer = (*srcinfo->mem->access_virt_barray)
++	((j_common_ptr) srcinfo, dst_coef_arrays[ci], dst_blk_y,
++	 (JDIMENSION) compptr->v_samp_factor, TRUE);
++      src_buffer = (*srcinfo->mem->access_virt_barray)
++	((j_common_ptr) srcinfo, src_coef_arrays[ci],
++	 dst_blk_y + y_crop_blocks,
++	 (JDIMENSION) compptr->v_samp_factor, FALSE);
++      for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
++	jcopy_block_row(src_buffer[offset_y] + x_crop_blocks,
++			dst_buffer[offset_y],
++			compptr->width_in_blocks);
++      }
++    }
++  }
++}
++
++
++LOCAL(void)
++do_flip_h_no_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
++		   JDIMENSION x_crop_offset,
++		   jvirt_barray_ptr *src_coef_arrays)
++/* Horizontal flip; done in-place, so no separate dest array is required.
++ * NB: this only works when y_crop_offset is zero.
++ */
+ {
+-  JDIMENSION MCU_cols, comp_width, blk_x, blk_y;
++  JDIMENSION MCU_cols, comp_width, blk_x, blk_y, x_crop_blocks;
+   int ci, k, offset_y;
+   JBLOCKARRAY buffer;
+   JCOEFPTR ptr1, ptr2;
+@@ -79,17 +133,19 @@
+    * mirroring by changing the signs of odd-numbered columns.
+    * Partial iMCUs at the right edge are left untouched.
+    */
+-  MCU_cols = dstinfo->image_width / (dstinfo->max_h_samp_factor * DCTSIZE);
++  MCU_cols = srcinfo->image_width / (dstinfo->max_h_samp_factor * DCTSIZE);
+ 
+   for (ci = 0; ci < dstinfo->num_components; ci++) {
+     compptr = dstinfo->comp_info + ci;
+     comp_width = MCU_cols * compptr->h_samp_factor;
++    x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
+     for (blk_y = 0; blk_y < compptr->height_in_blocks;
+ 	 blk_y += compptr->v_samp_factor) {
+       buffer = (*srcinfo->mem->access_virt_barray)
+ 	((j_common_ptr) srcinfo, src_coef_arrays[ci], blk_y,
+ 	 (JDIMENSION) compptr->v_samp_factor, TRUE);
+       for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
++	/* Do the mirroring */
+ 	for (blk_x = 0; blk_x * 2 < comp_width; blk_x++) {
+ 	  ptr1 = buffer[offset_y][blk_x];
+ 	  ptr2 = buffer[offset_y][comp_width - blk_x - 1];
+@@ -105,6 +161,79 @@
+ 	    *ptr2++ = -temp1;
+ 	  }
+ 	}
++	if (x_crop_blocks > 0) {
++	  /* Now left-justify the portion of the data to be kept.
++	   * We can't use a single jcopy_block_row() call because that routine
++	   * depends on memcpy(), whose behavior is unspecified for overlapping
++	   * source and destination areas.  Sigh.
++	   */
++	  for (blk_x = 0; blk_x < compptr->width_in_blocks; blk_x++) {
++	    jcopy_block_row(buffer[offset_y] + blk_x + x_crop_blocks,
++			    buffer[offset_y] + blk_x,
++			    (JDIMENSION) 1);
++	  }
++	}
++      }
++    }
++  }
++}
++
++
++LOCAL(void)
++do_flip_h (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
++	   JDIMENSION x_crop_offset, JDIMENSION y_crop_offset,
++	   jvirt_barray_ptr *src_coef_arrays,
++	   jvirt_barray_ptr *dst_coef_arrays)
++/* Horizontal flip in general cropping case */
++{
++  JDIMENSION MCU_cols, comp_width, dst_blk_x, dst_blk_y;
++  JDIMENSION x_crop_blocks, y_crop_blocks;
++  int ci, k, offset_y;
++  JBLOCKARRAY src_buffer, dst_buffer;
++  JBLOCKROW src_row_ptr, dst_row_ptr;
++  JCOEFPTR src_ptr, dst_ptr;
++  jpeg_component_info *compptr;
++
++  /* Here we must output into a separate array because we can't touch
++   * different rows of a single virtual array simultaneously.  Otherwise,
++   * this is essentially the same as the routine above.
++   */
++  MCU_cols = srcinfo->image_width / (dstinfo->max_h_samp_factor * DCTSIZE);
++
++  for (ci = 0; ci < dstinfo->num_components; ci++) {
++    compptr = dstinfo->comp_info + ci;
++    comp_width = MCU_cols * compptr->h_samp_factor;
++    x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
++    y_crop_blocks = y_crop_offset * compptr->v_samp_factor;
++    for (dst_blk_y = 0; dst_blk_y < compptr->height_in_blocks;
++	 dst_blk_y += compptr->v_samp_factor) {
++      dst_buffer = (*srcinfo->mem->access_virt_barray)
++	((j_common_ptr) srcinfo, dst_coef_arrays[ci], dst_blk_y,
++	 (JDIMENSION) compptr->v_samp_factor, TRUE);
++      src_buffer = (*srcinfo->mem->access_virt_barray)
++	((j_common_ptr) srcinfo, src_coef_arrays[ci],
++	 dst_blk_y + y_crop_blocks,
++	 (JDIMENSION) compptr->v_samp_factor, FALSE);
++      for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
++	dst_row_ptr = dst_buffer[offset_y];
++	src_row_ptr = src_buffer[offset_y];
++	for (dst_blk_x = 0; dst_blk_x < compptr->width_in_blocks; dst_blk_x++) {
++	  if (x_crop_blocks + dst_blk_x < comp_width) {
++	    /* Do the mirrorable blocks */
++	    dst_ptr = dst_row_ptr[dst_blk_x];
++	    src_ptr = src_row_ptr[comp_width - x_crop_blocks - dst_blk_x - 1];
++	    /* this unrolled loop doesn't need to know which row it's on... */
++	    for (k = 0; k < DCTSIZE2; k += 2) {
++	      *dst_ptr++ = *src_ptr++;	 /* copy even column */
++	      *dst_ptr++ = - *src_ptr++; /* copy odd column with sign change */
++	    }
++	  } else {
++	    /* Copy last partial block(s) verbatim */
++	    jcopy_block_row(src_row_ptr + dst_blk_x + x_crop_blocks,
++			    dst_row_ptr + dst_blk_x,
++			    (JDIMENSION) 1);
++	  }
++	}
+       }
+     }
+   }
+@@ -113,11 +242,13 @@
+ 
+ LOCAL(void)
+ do_flip_v (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
++	   JDIMENSION x_crop_offset, JDIMENSION y_crop_offset,
+ 	   jvirt_barray_ptr *src_coef_arrays,
+ 	   jvirt_barray_ptr *dst_coef_arrays)
+ /* Vertical flip */
+ {
+   JDIMENSION MCU_rows, comp_height, dst_blk_x, dst_blk_y;
++  JDIMENSION x_crop_blocks, y_crop_blocks;
+   int ci, i, j, offset_y;
+   JBLOCKARRAY src_buffer, dst_buffer;
+   JBLOCKROW src_row_ptr, dst_row_ptr;
+@@ -131,33 +262,38 @@
+    * of odd-numbered rows.
+    * Partial iMCUs at the bottom edge are copied verbatim.
+    */
+-  MCU_rows = dstinfo->image_height / (dstinfo->max_v_samp_factor * DCTSIZE);
++  MCU_rows = srcinfo->image_height / (dstinfo->max_v_samp_factor * DCTSIZE);
+ 
+   for (ci = 0; ci < dstinfo->num_components; ci++) {
+     compptr = dstinfo->comp_info + ci;
+     comp_height = MCU_rows * compptr->v_samp_factor;
++    x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
++    y_crop_blocks = y_crop_offset * compptr->v_samp_factor;
+     for (dst_blk_y = 0; dst_blk_y < compptr->height_in_blocks;
+ 	 dst_blk_y += compptr->v_samp_factor) {
+       dst_buffer = (*srcinfo->mem->access_virt_barray)
+ 	((j_common_ptr) srcinfo, dst_coef_arrays[ci], dst_blk_y,
+ 	 (JDIMENSION) compptr->v_samp_factor, TRUE);
+-      if (dst_blk_y < comp_height) {
++      if (y_crop_blocks + dst_blk_y < comp_height) {
+ 	/* Row is within the mirrorable area. */
+ 	src_buffer = (*srcinfo->mem->access_virt_barray)
+ 	  ((j_common_ptr) srcinfo, src_coef_arrays[ci],
+-	   comp_height - dst_blk_y - (JDIMENSION) compptr->v_samp_factor,
++	   comp_height - y_crop_blocks - dst_blk_y -
++	   (JDIMENSION) compptr->v_samp_factor,
+ 	   (JDIMENSION) compptr->v_samp_factor, FALSE);
+       } else {
+ 	/* Bottom-edge blocks will be copied verbatim. */
+ 	src_buffer = (*srcinfo->mem->access_virt_barray)
+-	  ((j_common_ptr) srcinfo, src_coef_arrays[ci], dst_blk_y,
++	  ((j_common_ptr) srcinfo, src_coef_arrays[ci],
++	   dst_blk_y + y_crop_blocks,
+ 	   (JDIMENSION) compptr->v_samp_factor, FALSE);
+       }
+       for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
+-	if (dst_blk_y < comp_height) {
++	if (y_crop_blocks + dst_blk_y < comp_height) {
+ 	  /* Row is within the mirrorable area. */
+ 	  dst_row_ptr = dst_buffer[offset_y];
+ 	  src_row_ptr = src_buffer[compptr->v_samp_factor - offset_y - 1];
++	  src_row_ptr += x_crop_blocks;
+ 	  for (dst_blk_x = 0; dst_blk_x < compptr->width_in_blocks;
+ 	       dst_blk_x++) {
+ 	    dst_ptr = dst_row_ptr[dst_blk_x];
+@@ -173,7 +309,8 @@
+ 	  }
+ 	} else {
+ 	  /* Just copy row verbatim. */
+-	  jcopy_block_row(src_buffer[offset_y], dst_buffer[offset_y],
++	  jcopy_block_row(src_buffer[offset_y] + x_crop_blocks,
++			  dst_buffer[offset_y],
+ 			  compptr->width_in_blocks);
+ 	}
+       }
+@@ -184,11 +321,12 @@
+ 
+ LOCAL(void)
+ do_transpose (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
++	      JDIMENSION x_crop_offset, JDIMENSION y_crop_offset,
+ 	      jvirt_barray_ptr *src_coef_arrays,
+ 	      jvirt_barray_ptr *dst_coef_arrays)
+ /* Transpose source into destination */
+ {
+-  JDIMENSION dst_blk_x, dst_blk_y;
++  JDIMENSION dst_blk_x, dst_blk_y, x_crop_blocks, y_crop_blocks;
+   int ci, i, j, offset_x, offset_y;
+   JBLOCKARRAY src_buffer, dst_buffer;
+   JCOEFPTR src_ptr, dst_ptr;
+@@ -201,6 +339,8 @@
+    */
+   for (ci = 0; ci < dstinfo->num_components; ci++) {
+     compptr = dstinfo->comp_info + ci;
++    x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
++    y_crop_blocks = y_crop_offset * compptr->v_samp_factor;
+     for (dst_blk_y = 0; dst_blk_y < compptr->height_in_blocks;
+ 	 dst_blk_y += compptr->v_samp_factor) {
+       dst_buffer = (*srcinfo->mem->access_virt_barray)
+@@ -210,11 +350,12 @@
+ 	for (dst_blk_x = 0; dst_blk_x < compptr->width_in_blocks;
+ 	     dst_blk_x += compptr->h_samp_factor) {
+ 	  src_buffer = (*srcinfo->mem->access_virt_barray)
+-	    ((j_common_ptr) srcinfo, src_coef_arrays[ci], dst_blk_x,
++	    ((j_common_ptr) srcinfo, src_coef_arrays[ci],
++	     dst_blk_x + x_crop_blocks,
+ 	     (JDIMENSION) compptr->h_samp_factor, FALSE);
+ 	  for (offset_x = 0; offset_x < compptr->h_samp_factor; offset_x++) {
+-	    src_ptr = src_buffer[offset_x][dst_blk_y + offset_y];
+ 	    dst_ptr = dst_buffer[offset_y][dst_blk_x + offset_x];
++	    src_ptr = src_buffer[offset_x][dst_blk_y + offset_y + y_crop_blocks];
+ 	    for (i = 0; i < DCTSIZE; i++)
+ 	      for (j = 0; j < DCTSIZE; j++)
+ 		dst_ptr[j*DCTSIZE+i] = src_ptr[i*DCTSIZE+j];
+@@ -228,6 +369,7 @@
+ 
+ LOCAL(void)
+ do_rot_90 (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
++	   JDIMENSION x_crop_offset, JDIMENSION y_crop_offset,
+ 	   jvirt_barray_ptr *src_coef_arrays,
+ 	   jvirt_barray_ptr *dst_coef_arrays)
+ /* 90 degree rotation is equivalent to
+@@ -237,6 +379,7 @@
+  */
+ {
+   JDIMENSION MCU_cols, comp_width, dst_blk_x, dst_blk_y;
++  JDIMENSION x_crop_blocks, y_crop_blocks;
+   int ci, i, j, offset_x, offset_y;
+   JBLOCKARRAY src_buffer, dst_buffer;
+   JCOEFPTR src_ptr, dst_ptr;
+@@ -246,11 +389,13 @@
+    * at the (output) right edge properly.  They just get transposed and
+    * not mirrored.
+    */
+-  MCU_cols = dstinfo->image_width / (dstinfo->max_h_samp_factor * DCTSIZE);
++  MCU_cols = srcinfo->image_height / (dstinfo->max_h_samp_factor * DCTSIZE);
+ 
+   for (ci = 0; ci < dstinfo->num_components; ci++) {
+     compptr = dstinfo->comp_info + ci;
+     comp_width = MCU_cols * compptr->h_samp_factor;
++    x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
++    y_crop_blocks = y_crop_offset * compptr->v_samp_factor;
+     for (dst_blk_y = 0; dst_blk_y < compptr->height_in_blocks;
+ 	 dst_blk_y += compptr->v_samp_factor) {
+       dst_buffer = (*srcinfo->mem->access_virt_barray)
+@@ -259,15 +404,26 @@
+       for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
+ 	for (dst_blk_x = 0; dst_blk_x < compptr->width_in_blocks;
+ 	     dst_blk_x += compptr->h_samp_factor) {
+-	  src_buffer = (*srcinfo->mem->access_virt_barray)
+-	    ((j_common_ptr) srcinfo, src_coef_arrays[ci], dst_blk_x,
+-	     (JDIMENSION) compptr->h_samp_factor, FALSE);
++	  if (x_crop_blocks + dst_blk_x < comp_width) {
++	    /* Block is within the mirrorable area. */
++	    src_buffer = (*srcinfo->mem->access_virt_barray)
++	      ((j_common_ptr) srcinfo, src_coef_arrays[ci],
++	       comp_width - x_crop_blocks - dst_blk_x -
++	       (JDIMENSION) compptr->h_samp_factor,
++	       (JDIMENSION) compptr->h_samp_factor, FALSE);
++	  } else {
++	    /* Edge blocks are transposed but not mirrored. */
++	    src_buffer = (*srcinfo->mem->access_virt_barray)
++	      ((j_common_ptr) srcinfo, src_coef_arrays[ci],
++	       dst_blk_x + x_crop_blocks,
++	       (JDIMENSION) compptr->h_samp_factor, FALSE);
++	  }
+ 	  for (offset_x = 0; offset_x < compptr->h_samp_factor; offset_x++) {
+-	    src_ptr = src_buffer[offset_x][dst_blk_y + offset_y];
+-	    if (dst_blk_x < comp_width) {
++	    dst_ptr = dst_buffer[offset_y][dst_blk_x + offset_x];
++	    if (x_crop_blocks + dst_blk_x < comp_width) {
+ 	      /* Block is within the mirrorable area. */
+-	      dst_ptr = dst_buffer[offset_y]
+-		[comp_width - dst_blk_x - offset_x - 1];
++	      src_ptr = src_buffer[compptr->h_samp_factor - offset_x - 1]
++		[dst_blk_y + offset_y + y_crop_blocks];
+ 	      for (i = 0; i < DCTSIZE; i++) {
+ 		for (j = 0; j < DCTSIZE; j++)
<<Diff was trimmed, longer than 597 lines>>


More information about the pld-cvs-commit mailing list