GraphicsMagick: 2 new changesets

GraphicsMagick Commits <[email protected]> Sun, 10 Dec 2023 15:47:21 -0600
Newsgroups gmane.comp.video.graphicsmagick.cvs
Message-ID <mailman.11254.1702244854.7794.graphicsmagick-commit@lists.sourceforge.net>
changeset f9727ab27a5a in /hg/GraphicsMagick
details: http://hg.GraphicsMagick.org/hg/GraphicsMagick?cmd=changeset;node=f9727ab27a5a
summary: coders/wpg.c Fix for oss-fuzz-64935. "unsigned long" produces unwanted results.

changeset 2f766f17cacb in /hg/GraphicsMagick
details: http://hg.GraphicsMagick.org/hg/GraphicsMagick?cmd=changeset;node=2f766f17cacb
summary: coders/wpg.c Fix for oss-fuzz-64935.

diffstat:

 ChangeLog                              |   37 +++
 README.txt                             |    7 +-
 VisualMagick/installer/inc/version.isx |    4 +-
 coders/jbig.c                          |   77 ++++++-
 coders/miff.c                          |    6 +
 coders/wpg.c                           |    4 +-
 configure                              |  341 +++++++++++++++++++-------------
 configure.ac                           |  309 +++++++++++++++++++----------
 fuzzing/oss-fuzz-build.sh              |   78 +++---
 magick/export.c                        |   13 +-
 magick/resource.c                      |   34 +-
 magick/resource.h                      |   10 +
 magick/version.h                       |    4 +-
 www/Changelog.html                     |   43 ++++
 www/INSTALL-unix.html                  |    4 +-
 www/INSTALL-unix.rst                   |    4 +-
 www/README.html                        |    7 +-
 17 files changed, 655 insertions(+), 327 deletions(-)

diffs (truncated from 1883 to 500 lines):

diff -r 867ff859b425 -r 2f766f17cacb ChangeLog
--- a/ChangeLog	Thu Dec 07 19:54:40 2023 +0100
+++ b/ChangeLog	Sun Dec 10 22:46:56 2023 +0100
@@ -1,3 +1,40 @@
+2023-12-07  Fojtik Jaroslav  <[email protected]>
+	* coders/wpg.c Fix for oss-fuzz-64935.
+
+2023-12-10  Bob Friesenhahn  <[email protected]>
+
+	* coders/jbig.c (ReadJBIGImage): Attempt to set maximum image
+	dimensions based on resource limits before calling jbg_dec_in() so
+	it will quit on excessively large images.  This often works, but
+	not all the time.
+
+2023-12-09  Bob Friesenhahn  <[email protected]>
+
+	* fuzzing/oss-fuzz-build.sh: Add -DJPEGXL_ENABLE_SKCMS=false to
+	libjxl build since skcms is not working with static linkage.
+
+	* configure.ac: Try really hard to configure everything, even if
+	pkg-config is not present or misbehaves. If pkg-config is not
+	present, it may be necessary to manually set CPPFLAGs in order to
+	find the FreeType and libxml2 headers.  Also print any error
+	information that pkg-config produces.  jxl_threads is not a hard
+	requirement.  Do not search for TRIO by default.  The user needs
+	to specify --with-trio=yes in order to enable searching for TRIO.
+
+2023-12-08  Bob Friesenhahn  <[email protected]>
+
+	* coders/miff.c (ReadMIFFImage): Handle unexpected EOF in version
+	0 bzip2 compressed MIFF.  Addresses oss-fuzz "Issue 64851:
+	graphicsmagick:coder_MIFF_fuzzer: Timeout in coder_MIFF_fuzzer".
+
+	* coders/jbig.c (ReadJBIGImage): Add error detection. Addresses
+	oss-fuzz "Issue 64781: graphicsmagick:coder_JBIG_fuzzer:
+	Null-dereference READ in jbg_dec_getimage".
+
+	* magick/export.c (ExportGrayQuantumType): Only use 'Special
+	"fast" support for two-color PsudeoClass.' case when image has two
+	colors.  Otherwise output image is not correct!
+
 2023-12-07  Fojtik Jaroslav  <[email protected]>
 
 	* coders/wpg.c Deallocate palette when image load fails.
diff -r 867ff859b425 -r 2f766f17cacb README.txt
--- a/README.txt	Thu Dec 07 19:54:40 2023 +0100
+++ b/README.txt	Sun Dec 10 22:46:56 2023 +0100
@@ -258,11 +258,12 @@
      http://sourceforge.net/projects/ctrio/
 
   to substitute for the vsnprintf function when the operating system
-  does not provide one. Older operating systems (e.g. Solaris 2.5)
-  may not provide a vsnprintf function. If vsnprintf (or the TRIO
+  does not provide one. Older operating systems (e.g. Solaris 2.5) may
+  not provide a vsnprintf function. If vsnprintf (or the TRIO
   replacement) is not used, then vsprintf is used instead, which
   decreases the security of GraphicsMagick due to possible buffer
-  overrun exploits.
+  overrun exploits.  It is highly unlikely that TRIO is useful on any
+  modern system.
 
 * GraphicsMagick may optionally use the 'tcmalloc' library provided as
   part of Google gperftools available from
diff -r 867ff859b425 -r 2f766f17cacb VisualMagick/installer/inc/version.isx
--- a/VisualMagick/installer/inc/version.isx	Thu Dec 07 19:54:40 2023 +0100
+++ b/VisualMagick/installer/inc/version.isx	Sun Dec 10 22:46:56 2023 +0100
@@ -10,5 +10,5 @@
 
 #define public MagickPackageName "GraphicsMagick"
 #define public MagickPackageVersion "1.4"
-#define public MagickPackageVersionAddendum ".020231205"
-#define public MagickPackageReleaseDate "snapshot-20231205"
+#define public MagickPackageVersionAddendum ".020231210"
+#define public MagickPackageReleaseDate "snapshot-20231210"
diff -r 867ff859b425 -r 2f766f17cacb coders/jbig.c
--- a/coders/jbig.c	Thu Dec 07 19:54:40 2023 +0100
+++ b/coders/jbig.c	Sun Dec 10 22:46:56 2023 +0100
@@ -1,5 +1,5 @@
 /*
-% Copyright (C) 2003 - 2020 GraphicsMagick Group
+% Copyright (C) 2003 - 2023 GraphicsMagick Group
 % Copyright (C) 2002 ImageMagick Studio
 % Copyright 1991-1999 E. I. du Pont de Nemours and Company
 %
@@ -39,9 +39,11 @@
 #include "magick/blob.h"
 #include "magick/colormap.h"
 #include "magick/constitute.h"
+#include "magick/log.h"
 #include "magick/magick.h"
 #include "magick/monitor.h"
 #include "magick/pixel_cache.h"
+#include "magick/resource.h"
 #include "magick/utility.h"
 
 /*
@@ -133,10 +135,48 @@
     Initialize JBIG toolkit.
   */
   jbg_dec_init(&jbig_info);
-  jbg_dec_maxsize(&jbig_info,(unsigned long) image->columns,
-                  (unsigned long) image->rows);
-  image->columns= jbg_dec_getwidth(&jbig_info);
-  image->rows= jbg_dec_getheight(&jbig_info);
+
+  /*
+    Attempt to set maximum image dimensions based on resource limits.
+
+    This does work in normal cases, but in other cases the first call
+    to jbg_dec_in() takes a very long time, and it returns large image
+    dimensions anyway.
+  */
+  {
+    magick_int64_t
+      width_limit,
+      height_limit,
+      pixels_limit;
+
+    width_limit = GetMagickResourceLimit(WidthResource);
+    height_limit = GetMagickResourceLimit(HeightResource);
+    pixels_limit = GetMagickResourceLimit(PixelsResource);
+
+    if (MagickResourceInfinity != width_limit)
+      if ((image->columns == 0) || (image->columns > (unsigned long) width_limit))
+        image->columns = (unsigned long) width_limit;
+
+    if (MagickResourceInfinity != height_limit)
+      if ((image->rows == 0) || (image->rows > (unsigned long) height_limit))
+        image->rows = (unsigned long) height_limit;
+
+    if ((MagickResourceInfinity != pixels_limit) &&
+        ((magick_int64_t) (image->columns*image->rows)) > pixels_limit)
+      {
+        magick_int64_t max_dimension = sqrt((double) pixels_limit);
+        image->columns = (unsigned long) max_dimension;
+        image->rows = (unsigned long) max_dimension;
+      }
+
+    if (image->logging)
+      (void) LogMagickEvent(CoderEvent,GetMagickModule(),
+                            "JBIG: Setting maximum dimensions %lux%lu",
+                            image->columns, image->rows);
+    jbg_dec_maxsize(&jbig_info,(unsigned long) image->columns,
+                    (unsigned long) image->rows);
+  }
+
   image->depth=1;
   /*
     Read JBIG file.
@@ -145,6 +185,10 @@
   if (buffer == (unsigned char *) NULL)
     ThrowReaderException(ResourceLimitError,MemoryAllocationFailed,image);
   status=JBG_EAGAIN;
+  /* FIXME: Should handle JBG_EOK_INTR for multi-resolution support */
+  if (image->logging)
+    (void) LogMagickEvent(CoderEvent,GetMagickModule(),
+                          "JBIG: Entering jbg_dec_in() decode loop...");
   do
     {
       length=(long) ReadBlob(image,MaxBufferSize,(char *) buffer);
@@ -152,13 +196,23 @@
         break;
       p=buffer;
       count=0;
-      while ((length > 0) && ((status == JBG_EAGAIN) || (status == JBG_EOK)))
+      while ((length > 0) && (status == JBG_EAGAIN))
         {
           status=jbg_dec_in(&jbig_info,p,length,&count);
+          if (image->logging)
+            (void) LogMagickEvent(CoderEvent,GetMagickModule(),
+                                  "JBIG: jbg_dec_in() returns 0x%02x (\"%s\")",
+                                  status, jbg_strerror(status));
           p+=count;
           length-=count;
         }
-    } while ((status == JBG_EAGAIN) || (status == JBG_EOK));
+    } while (status == JBG_EAGAIN);
+  if (JBG_EOK != status)
+    {
+      jbg_dec_free(&jbig_info);
+      MagickFreeMemory(buffer);
+      ThrowReaderException(CorruptImageError,CorruptImage,image);
+    }
   /*
     Create colormap.
   */
@@ -170,7 +224,7 @@
       if (!AllocateImageColormap(image,2))
         {
           MagickFreeMemory(buffer);
-          ThrowReaderException(ResourceLimitError,MemoryAllocationFailed,image);
+
         }
       image->colormap[0].red=0;
       image->colormap[0].green=0;
@@ -184,6 +238,11 @@
   image->is_grayscale=MagickTrue;
   image->is_monochrome=MagickTrue;
   image->colorspace=GRAYColorspace;
+  if (image->logging)
+    (void) LogMagickEvent(CoderEvent,GetMagickModule(),
+                          "JBIG: %lux%lu, resolution %gx%g",
+                          image->columns, image->rows,
+                          image->x_resolution,image->y_resolution);
   if (image_info->ping)
     {
       jbg_dec_free(&jbig_info);
@@ -269,7 +328,7 @@
     description[]="Joint Bi-level Image experts Group interchange format";
 
   static const char
-    version[]="JBIG-Kit " JBG_VERSION;
+    version[]="JBIG-Kit " JBG_VERSION " (" JBG_LICENCE " license)";
 
   MagickInfo
     *entry;
diff -r 867ff859b425 -r 2f766f17cacb coders/miff.c
--- a/coders/miff.c	Thu Dec 07 19:54:40 2023 +0100
+++ b/coders/miff.c	Sun Dec 10 22:46:56 2023 +0100
@@ -1859,6 +1859,12 @@
                         {
                           length=(int) (1.01*pixels_size+600);
                           bzip_info.avail_in=(unsigned int) ReadBlob(image,length,bzip_info.next_in);
+                          if (bzip_info.avail_in == 0)
+                            {
+                              (void) BZ2_bzDecompressEnd(&bzip_info);
+                              ThrowMIFFReaderException(CorruptImageError,UnexpectedEndOfFile,
+                                                   image);
+                            }
                         }
                       else
                         {
diff -r 867ff859b425 -r 2f766f17cacb coders/wpg.c
--- a/coders/wpg.c	Thu Dec 07 19:54:40 2023 +0100
+++ b/coders/wpg.c	Sun Dec 10 22:46:56 2023 +0100
@@ -1694,8 +1694,8 @@
               }
 
               if ( (WPG_Palette.StartIndex > WPG_Palette.NumOfEntries) ||
-                   ((((unsigned long)WPG_Palette.NumOfEntries-(unsigned long)WPG_Palette.StartIndex) >
-                     ((Rec2.RecordLength-2-2) / 3))) )
+                   ((((magick_int32_t)WPG_Palette.NumOfEntries-(magick_int32_t)WPG_Palette.StartIndex) >
+                   (((magick_int32_t)Rec2.RecordLength-2-2) / 4))) )
               {
                 MagickFreeResourceLimitedMemory(pPalette);
                 ThrowReaderException(CorruptImageError,InvalidColormapIndex,image);
diff -r 867ff859b425 -r 2f766f17cacb configure
--- a/configure	Thu Dec 07 19:54:40 2023 +0100
+++ b/configure	Sun Dec 10 22:46:56 2023 +0100
@@ -1863,7 +1863,7 @@
   --without-lzma          disable LZMA support
   --without-png           disable PNG support
   --without-tiff          disable TIFF support
-  --without-trio          disable TRIO support
+  --with-trio             enable TRIO support
   --without-ttf           disable TrueType support
   --with-tcmalloc         enable Google perftools tcmalloc (minimal) memory
                           allocation library support
@@ -19776,16 +19776,16 @@
     DISTCHECK_CONFIG_FLAGS="${DISTCHECK_CONFIG_FLAGS} --with-tiff=$with_tiff "
 fi
 
-# Disable TRIO.
+# Enable TRIO.
 
 # Check whether --with-trio was given.
 if test "${with_trio+set}" = set; then :
   withval=$with_trio; with_trio=$withval
 else
-  with_trio='yes'
-fi
-
-if test "$with_trio" != 'yes' ; then
+  with_trio='no'
+fi
+
+if test "$with_trio" != 'no' ; then
     DISTCHECK_CONFIG_FLAGS="${DISTCHECK_CONFIG_FLAGS} --with-trio=$with_trio "
 fi
 
@@ -23989,6 +23989,12 @@
       printf "ZLIB_CFLAGS=${ZLIB_CFLAGS}\n"
     fi
     pkg_config_to_flags 'zlib' "${ZLIB_LIBS}" "${ZLIB_CFLAGS}"
+  else
+    if test -n "${ZLIB_PKG_ERRORS}"
+    then
+      printf "${ZLIB_PKG_ERRORS}\n"
+    fi
+    failed=0
   fi
   ac_fn_c_check_header_mongrel "$LINENO" "zconf.h" "ac_cv_header_zconf_h" "$ac_includes_default"
 if test "x$ac_cv_header_zconf_h" = xyes; then :
@@ -24274,6 +24280,7 @@
       LIBS=$OLD_LIBS
     else
       LIB_ZLIB='-lz'
+      pkg_config_to_flags 'zlib' "${LIB_ZLIB}" ''
 
 $as_echo "#define HasZLIB 1" >>confdefs.h
 
@@ -24545,6 +24552,12 @@
       printf "LZMA_CFLAGS=${LZMA_CFLAGS}\n"
     fi
     pkg_config_to_flags 'liblzma' "${LZMA_LIBS}" "${LZMA_CFLAGS}"
+  else
+    if test -n "${LZMA_PKG_ERRORS}"
+    then
+      printf "${LZMA_PKG_ERRORS}\n"
+    fi
+    failed=0
   fi
   ac_fn_c_check_header_mongrel "$LINENO" "lzma.h" "ac_cv_header_lzma_h" "$ac_includes_default"
 if test "x$ac_cv_header_lzma_h" = xyes; then :
@@ -24618,6 +24631,7 @@
             ;;
         esac
       done
+      pkg_config_to_flags 'liblzma' "${LIB_LZMA}" ''
 
 $as_echo "#define HasLZMA 1" >>confdefs.h
 
@@ -24727,13 +24741,20 @@
 $as_echo "yes" >&6; }
 	passed=`expr $passed + 1`
 fi
-  if test $failed -eq 0 ; then
+  if test $failed -eq 0
+  then
     if test -n "$VERBOSE"
     then
       printf "ZSTD_LIBS=${ZSTD_LIBS}\n"
       printf "ZSTD_CFLAGS=${ZSTD_CFLAGS}\n"
     fi
     pkg_config_to_flags 'libzstd' "${ZSTD_LIBS}" "${ZSTD_CFLAGS}"
+  else
+    if test -n "${ZSTD_PKG_ERRORS}"
+    then
+      printf "${ZSTD_PKG_ERRORS}\n"
+    fi
+    failed=0
   fi
   ac_fn_c_check_header_mongrel "$LINENO" "zstd.h" "ac_cv_header_zstd_h" "$ac_includes_default"
 if test "x$ac_cv_header_zstd_h" = xyes; then :
@@ -24799,6 +24820,7 @@
       LIBS=$OLD_LIBS
     else
       LIB_ZSTD='-lzstd'
+      pkg_config_to_flags 'libzstd' "${LIB_ZSTD}" ''
       #LIBS="$LIB_ZSTD $LIBS"
 
 $as_echo "#define HasZSTD 1" >>confdefs.h
@@ -24822,7 +24844,6 @@
 
 
 
-
 #
 # Check for XML
 #
@@ -24841,9 +24862,6 @@
     OLD_LIBS=$LIBS
     failed=0
     passed=0
-    xml2_config=''
-    xml2_cflags=''
-    xml2_libs=''
 
 pkg_failed=no
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libxml-2.0" >&5
@@ -24915,16 +24933,29 @@
 $as_echo "yes" >&6; }
 	passed=`expr $passed + 1`
 fi
-    if test $failed -eq 0 ; then
+    if test $failed -eq 0
+    then
       if test -n "$VERBOSE"
       then
         printf "XML_LIBS=${XML_LIBS}\n"
         printf "XML_CFLAGS=${XML_CFLAGS}\n"
       fi
       pkg_config_to_flags 'libxml-2.0' "${XML_LIBS}" "${XML_CFLAGS}"
+    else
+      if test -n "${XML_PKG_ERRORS}"
+      then
+        printf "${XML_PKG_ERRORS}\n"
+      fi
+      failed=0
     fi
     failed=0
     passed=0
+
+    # libxml2 normally requires pkg-config in order to produce the
+    # necessary additional include path.  For example
+    # "-I/usr/include/libxml2", but if pkg-config was not available,
+    # the user could supply that manually using CPPFLAGS.
+    #
     # Incantation tested with libxml2 2.7.8 configured with
     #   --with-minimum --with-http --with-ftp --with-push --with-zlib --with-sax1
     # Note that SAX1 interfaces don't seem to be directly used but parsers fail to work
@@ -25068,24 +25099,25 @@
 $as_echo_n "checking if XML package is complete ... " >&6; }
     if test $passed -gt 0
     then
-    if test $failed -gt 0
-    then
-        { $as_echo "$as_me:${as_lineno-$LINENO}: result: no -- some components failed test" >&5
+        if test $failed -gt 0
+        then
+            { $as_echo "$as_me:${as_lineno-$LINENO}: result: no -- some components failed test" >&5
 $as_echo "no -- some components failed test" >&6; }
-        have_xml='no (failed tests)'
-        CPPFLAGS=$OLD_CPPFLAGS
-        LDFLAGS=$OLD_LDFLAGS
-        LIBS=$OLD_LIBS
-    else
-        LIB_XML="-lxml2"
+            have_xml='no (failed tests)'
+            CPPFLAGS=$OLD_CPPFLAGS
+            LDFLAGS=$OLD_LDFLAGS
+            LIBS=$OLD_LIBS
+        else
+            LIB_XML="-lxml2"
+            pkg_config_to_flags 'libxml-2.0' "${LIB_XML}" ''
 
 $as_echo "#define HasXML 1" >>confdefs.h
 
-        { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
-$as_echo "yes" >&6; }
-        have_xml='yes'
-        for ac_func in xmlNanoHTTPOpen \
-                        xmlNanoFTPNewCtxt
+            { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+            have_xml='yes'
+            for ac_func in xmlNanoHTTPOpen \
+                            xmlNanoFTPNewCtxt
 do :
   as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
 ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
@@ -25097,7 +25129,7 @@
 fi
 done
 
-    fi
+        fi
     else
         { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
 $as_echo "no" >&6; }
@@ -26457,6 +26489,12 @@
         printf "LCMS2_CFLAGS=${LCMS2_CFLAGS}\n"
       fi
       pkg_config_to_flags 'lcms2' "${LCMS2_LIBS}" "${LCMS2_CFLAGS}"
+    else
+      if test -n "${LCMS2_PKG_ERRORS}"
+      then
+        printf "${LCMS2_PKG_ERRORS}\n"
+      fi
+      failed=0
     fi
 
     # Check for <lcms2.h>
@@ -26556,6 +26594,7 @@
         LIBS=$OLD_LIBS
       else
         LIB_LCMS='-llcms2'
+        pkg_config_to_flags 'lcms2' "${LIB_LCMS}" ''
         #LIBS="$LIB_LCMS $LIBS"
         #AC_DEFINE(HasLCMS2,1,Define if you have LCMS v2 library)
         { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
@@ -26675,6 +26714,12 @@
       printf "PNG_CFLAGS=${PNG_CFLAGS}\n"
     fi
     pkg_config_to_flags 'libpng' "${PNG_LIBS}" "${PNG_CFLAGS}"
+  else
+    if test -n "${PNG_PKG_ERRORS}"
+    then
+      printf "${PNG_PKG_ERRORS}\n"
+    fi
+    failed=0
   fi
 
   if test "$with_png" != 'yes'; then
@@ -27020,21 +27065,22 @@
 $as_echo_n "checking if ${pnglib} package is complete... " >&6; }
               if test $passed -gt 0 ; then
                 if test $failed -gt 0 ; then
-                { $as_echo "$as_me:${as_lineno-$LINENO}: result: no -- some components failed test" >&5
+                  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no -- some components failed test" >&5
 $as_echo "no -- some components failed test" >&6; }
-                have_png='no (failed tests)'
-                CPPFLAGS=$OLD_CPPFLAGS
-                LDFLAGS=$OLD_LDFLAGS
-                LIBS=$OLD_LIBS
+                  have_png='no (failed tests)'
+                  CPPFLAGS=$OLD_CPPFLAGS
+                  LDFLAGS=$OLD_LDFLAGS
+                  LIBS=$OLD_LIBS
                 else