emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] trunk r113284: Scale ImageMagick images more carefully.


From: Paul Eggert
Subject: [Emacs-diffs] trunk r113284: Scale ImageMagick images more carefully.
Date: Thu, 04 Jul 2013 15:25:58 +0000
User-agent: Bazaar (2.6b2)

------------------------------------------------------------
revno: 113284
revision-id: address@hidden
parent: address@hidden
committer: Paul Eggert <address@hidden>
branch nick: trunk
timestamp: Thu 2013-07-04 08:25:54 -0700
message:
  Scale ImageMagick images more carefully.
  
  * image.c (scale_image_size) [HAVE_IMAGEMAGICK]: New function.
  (compute_image_size): Use it.  Define only if HAVE_IMAGEMAGICK.
  Be more careful about avoiding undefined behavior after
  integer overflow and division by zero.
modified:
  src/ChangeLog                  changelog-20091113204419-o5vbwnq5f7feedwu-1438
  src/image.c                    image.c-20091113204419-o5vbwnq5f7feedwu-2969
=== modified file 'src/ChangeLog'
--- a/src/ChangeLog     2013-07-04 10:25:54 +0000
+++ b/src/ChangeLog     2013-07-04 15:25:54 +0000
@@ -1,3 +1,11 @@
+2013-07-04  Paul Eggert  <address@hidden>
+
+       Scale ImageMagick images more carefully.
+       * image.c (scale_image_size) [HAVE_IMAGEMAGICK]: New function.
+       (compute_image_size): Use it.  Define only if HAVE_IMAGEMAGICK.
+       Be more careful about avoiding undefined behavior after
+       integer overflow and division by zero.
+
 2013-07-04  YAMAMOTO Mitsuharu  <address@hidden>
 
        * w32fns.c (Qgeometry, Qworkarea, Qmm_size, Qframes): New variables.

=== modified file 'src/image.c'
--- a/src/image.c       2013-07-04 02:08:56 +0000
+++ b/src/image.c       2013-07-04 15:25:54 +0000
@@ -7625,6 +7625,31 @@
 #endif /* HAVE_GIF */
 
 
+#ifdef HAVE_IMAGEMAGICK
+
+/***********************************************************************
+                                ImageMagick
+***********************************************************************/
+
+/* Scale an image size by returning SIZE / DIVISOR * MULTIPLIER,
+   safely rounded and clipped to int range.  */
+
+static int
+scale_image_size (int size, size_t divisor, size_t multiplier)
+{
+  if (divisor != 0)
+    {
+      double s = size;
+      double scaled = s * multiplier / divisor + 0.5;
+      if (scaled < INT_MAX)
+       return scaled;
+    }
+  return INT_MAX;
+}
+
+/* Compute the desired size of an image with native size WIDTH x HEIGHT.
+   Use SPEC to deduce the size.  Store the desired size into
+   *D_WIDTH x *D_HEIGHT.  Store -1 x -1 if the native size is OK.  */
 static void
 compute_image_size (size_t width, size_t height,
                    Lisp_Object spec,
@@ -7638,39 +7663,36 @@
      unspecified should be calculated from the specified to preserve
      aspect ratio.  */
   value = image_spec_value (spec, QCwidth, NULL);
-  desired_width = (INTEGERP (value)  ? XFASTINT (value) : -1);
+  desired_width = NATNUMP (value) ? min (XFASTINT (value), INT_MAX) : -1;
   value = image_spec_value (spec, QCheight, NULL);
-  desired_height = (INTEGERP (value) ? XFASTINT (value) : -1);
+  desired_height = NATNUMP (value) ? min (XFASTINT (value), INT_MAX) : -1;
 
   if (desired_width == -1)
     {
       value = image_spec_value (spec, QCmax_width, NULL);
-      if (INTEGERP (value) &&
-         width > XFASTINT (value))
+      if (NATNUMP (value))
        {
-         /* The image is wider than :max-width. */
-         desired_width = XFASTINT (value);
-         if (desired_height == -1)
+         int max_width = min (XFASTINT (value), INT_MAX);
+         if (max_width < width)
            {
-             value = image_spec_value (spec, QCmax_height, NULL);
-             if (INTEGERP (value))
+             /* The image is wider than :max-width. */
+             desired_width = max_width;
+             if (desired_height == -1)
                {
-                 /* We have no specified height, but we have a
-                    :max-height value, so check that we satisfy both
-                    conditions. */
-                 desired_height = (double) desired_width / width * height;
-                 if (desired_height > XFASTINT (value))
+                 desired_height = scale_image_size (desired_width,
+                                                    width, height);
+                 value = image_spec_value (spec, QCmax_height, NULL);
+                 if (NATNUMP (value))
                    {
-                     desired_height = XFASTINT (value);
-                     desired_width = (double) desired_height / height * width;
+                     int max_height = min (XFASTINT (value), INT_MAX);
+                     if (max_height < desired_height)
+                       {
+                         desired_height = max_height;
+                         desired_width = scale_image_size (desired_height,
+                                                           height, width);
+                       }
                    }
                }
-             else
-               {
-                 /* We have no specified height and no specified
-                    max-height, so just compute the height. */
-                 desired_height = (double) desired_width / width * height;
-               }
            }
        }
     }
@@ -7678,28 +7700,26 @@
   if (desired_height == -1)
     {
       value = image_spec_value (spec, QCmax_height, NULL);
-      if (INTEGERP (value) &&
-         height > XFASTINT (value))
-         desired_height = XFASTINT (value);
+      if (NATNUMP (value))
+       {
+         int max_height = min (XFASTINT (value), INT_MAX);
+         if (max_height < height)
+           desired_height = max_height;
+       }
     }
 
   if (desired_width != -1 && desired_height == -1)
     /* w known, calculate h.  */
-    desired_height = (double) desired_width / width * height;
+    desired_height = scale_image_size (desired_width, width, height);
 
   if (desired_width == -1 && desired_height != -1)
     /* h known, calculate w.  */
-    desired_width = (double) desired_height / height * width;
+    desired_width = scale_image_size (desired_height, height, width);
 
   *d_width = desired_width;
   *d_height = desired_height;
 }
 
-/***********************************************************************
-                                ImageMagick
-***********************************************************************/
-#if defined (HAVE_IMAGEMAGICK)
-
 static Lisp_Object Qimagemagick;
 
 static bool imagemagick_image_p (Lisp_Object);


reply via email to

[Prev in Thread] Current Thread [Next in Thread]