GraphicsMagick: 2 new changesets

GraphicsMagick Commits <[email protected]>
Newsgroups gmane.comp.video.graphicsmagick.cvs
Message-ID <mailman.11297.1682785995.1602.graphicsmagick-commit@lists.sourceforge.net>
changeset 716ae84b9960 in /hg/GraphicsMagick
details: http://hg.GraphicsMagick.org/hg/GraphicsMagick?cmd=changeset;node=716ae84b9960
summary: coders/topol.c: First attempt to make a writer.

changeset 5b54e4cb9eea in /hg/GraphicsMagick
details: http://hg.GraphicsMagick.org/hg/GraphicsMagick?cmd=changeset;node=5b54e4cb9eea
summary: Merge heads

diffstat:

 ChangeLog          |   10 +++
 coders/mat.c       |   10 ++-
 coders/topol.c     |  171 +++++++++++++++++++++++++++++++++++++++++++++++++---
 magick/blob.c      |   23 +++++++
 magick/blob.h      |    1 +
 www/Changelog.html |    8 ++
 6 files changed, 211 insertions(+), 12 deletions(-)

diffs (384 lines):

diff -r ca23f27fe474 -r 5b54e4cb9eea ChangeLog
--- a/ChangeLog	Sat Apr 29 10:13:35 2023 -0500
+++ b/ChangeLog	Sat Apr 29 18:32:33 2023 +0200
@@ -1,5 +1,15 @@
+2023-04-29  Fojtik Jaroslav  <[email protected]>
+
+	* coders/topol.c: First attempt to make a writer.
+	* magick/blob.h magick/blob.c: New function WriteBlobLSBDouble.
+
 2023-04-29  Bob Friesenhahn  <[email protected]>
 
+	* coders/mat.c (InsertComplexDoubleRow): If computed f is nan,
+	then use 0.0.  Addresses SourceForge issue #708 "Undefined
+	behavior while converting negative infinity to integer".
+	(InsertComplexFloatRow):  If computed f is nan, then use 0.0.
+
 	* magick/attribute.c (GenerateEXIFAttribute): Assure that float
 	and double values are suitably alligned.  Addresses SourceForge
 	issue #709 "Undefined behavior while loading a value of type float
diff -r ca23f27fe474 -r 5b54e4cb9eea coders/mat.c
--- a/coders/mat.c	Sat Apr 29 10:13:35 2023 -0500
+++ b/coders/mat.c	Sat Apr 29 18:32:33 2023 +0200
@@ -1,5 +1,5 @@
 /*
-% Copyright (C) 2003-2022 GraphicsMagick Group
+% Copyright (C) 2003-2023 GraphicsMagick Group
 % Copyright (C) 2002 ImageMagick Studio
 %
 % This program is covered by multiple licenses, which are described in
@@ -171,6 +171,8 @@
     if (*p > 0)
     {
       f = (*p / MaxVal) * (Quantum)(MaxRGB - q->red);  /* first multiplier should be in a range <0;1> */
+      if (MAGICK_ISNAN(f))
+        f=0.0;
       /*if(f<0) f=0; */
       if (f + q->red >= MaxRGB)
         q->red = MaxRGB;
@@ -185,6 +187,8 @@
     if (*p < 0)
     {
       f = (*p / MinVal) * (Quantum)(MaxRGB - q->blue); /* first multiplier should be in a range <0;1>; *p<0 and MinVal<0. */
+      if (MAGICK_ISNAN(f))
+        f=0.0;
       /*if(f<0) f=0; */
       if (f + q->blue >= MaxRGB)
         q->blue = MaxRGB;
@@ -230,6 +234,8 @@
     if (*p > 0)
     {
       f = (*p / MaxVal) * (Quantum)(MaxRGB - q->red);
+      if (MAGICK_ISNAN(f))
+        f=0.0;
       /*if(f<0) f=0;    //Only for Assert, should be commented out */
       if (f + q->red < MaxRGB)
         q->red += (int)f;
@@ -244,6 +250,8 @@
     if (*p < 0)
     {
       f = (*p / MinVal) * (Quantum)(MaxRGB - q->blue); /* f is positive only <0; inf> */
+      if (MAGICK_ISNAN(f))
+        f=0.0;
       /*if(f<0) f=0;    //Only for Assert, should be commented out */
       if (f + q->blue < MaxRGB)
         q->blue += (int) f;
diff -r ca23f27fe474 -r 5b54e4cb9eea coders/topol.c
--- a/coders/topol.c	Sat Apr 29 10:13:35 2023 -0500
+++ b/coders/topol.c	Sat Apr 29 18:32:33 2023 +0200
@@ -20,13 +20,13 @@
 %                                                                             %
 %                              Software Design                                %
 %                              Jaroslav Fojtik                                %
-%                                2003 - 2018                                  %
+%                                2003 - 2023                                  %
 %                                                                             %
 %                                                                             %
 %                                                                             %
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 %
-%
+% Note: TopoL GIS is here: http://www.topol.eu/articles/about
 */
 
 /*
@@ -294,17 +294,17 @@
 %                                                                             %
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 %
-%  Method ReadTOPOLImage reads an TOPOL X image file and returns it.  It
+%  Method ReadTopoLImage reads an TOPOL X image file and returns it.  It
 %  allocates the memory necessary for the new Image structure and returns a
 %  pointer to the new image.
 %
-%  The format of the ReadTOPOLImage method is:
+%  The format of the ReadTopoLImage method is:
 %
-%      Image *ReadTOPOLImage(const ImageInfo *image_info,ExceptionInfo *exception)
+%      Image *ReadTopoLImage(const ImageInfo *image_info,ExceptionInfo *exception)
 %
 %  A description of each parameter follows:
 %
-%    o image:  Method ReadTOPOLImage returns a pointer to the image after
+%    o image:  Method ReadTopoLImage returns a pointer to the image after
 %      reading. A null image is returned if there is a memory shortage or if
 %      the image cannot be read.
 %
@@ -325,7 +325,7 @@
   ThrowReaderException(code_,reason_,image_); \
 }
 
-static Image *ReadTOPOLImage(const ImageInfo * image_info, ExceptionInfo * exception)
+static Image *ReadTopoLImage(const ImageInfo * image_info, ExceptionInfo * exception)
 {
   Image
     *image,
@@ -418,7 +418,7 @@
     }
   if (Header.Komprese != 0 || (Header.Version >= 2 && Header.TileCompression != 0))
     ThrowTOPOLReaderException(CorruptImageError, UnrecognizedImageCompression, image);
-  if (((Header.Rows == 0 || Header.Cols == 0)) ||
+  if(Header.Rows == 0 || Header.Cols == 0 ||
       ((Header.Version >= 2) &&
        (Header.TileWidth == 0 ||
         Header.TileHeight == 0 ||
@@ -466,7 +466,7 @@
 
   i = GetBlobSize(image);
   if(i>0)
-    if(((magick_uint64_t)8*Header.Cols*(magick_uint64_t)Header.Rows) / image->depth > (magick_uint64_t)GetBlobSize(image))
+    if(((magick_uint64_t)depth*Header.Cols*(magick_uint64_t)Header.Rows) / 8 > (magick_uint64_t)GetBlobSize(image))
       goto TOPOL_KO;    /* Check for forged image that overflows file size. */
 
   /* If ping is true, then only set image size and colors without reading any image data. */
@@ -743,6 +743,154 @@
   if (logging) (void)LogMagickEvent(CoderEvent,GetMagickModule(),"return");
   return (image);
 }
+
+
+/*
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%                                                                             %
+%                                                                             %
+%                                                                             %
+%   W r i t e T o p o L I m a g e                                             %
+%                                                                             %
+%                                                                             %
+%                                                                             %
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+%  Function WriteTopoLImage writes an WPG image to a file.
+%
+%  The format of the WriteTopoLImage method is:
+%
+%      unsigned int WriteTopoLImage(const ImageInfo *image_info,Image *image)
+%
+%  A description of each parameter follows.
+%
+%    o status: Function WriteTopoLImage return True if the image is written.
+%      False is returned is there is a memory shortage or if the image file
+%      fails to write.
+%
+%    o image_info: Specifies a pointer to a ImageInfo structure.
+%
+%    o image:  A pointer to an Image structure.
+*/
+static MagickPassFail WriteTopoLImage(const ImageInfo *image_info, Image *image)
+{
+  long y;
+  unsigned int status;
+  int logging;
+  unsigned char *pixels;
+  RasHeader Header;
+  size_t DataSize;
+  QuantumType qt;
+  int bpp;
+
+	/* Open output image file. */
+  assert(image_info != (const ImageInfo *) NULL);
+  assert(image_info->signature == MagickSignature);
+  assert(image != (Image *)NULL);
+  assert(image->signature == MagickSignature);
+  logging = LogMagickEvent(CoderEvent,GetMagickModule(),"enter TopoL");
+
+  DataSize = 0;
+  memset(&Header,0,sizeof(Header));
+  memset(&Header.Name,' ',sizeof(Header.Name));
+  //Header.Version = 0;
+  Header.Cols = image->columns;
+  Header.Rows = image->rows;
+  if(image->colors>=1 && image->colors<=255)
+  {
+    if(image->colors <= 2)
+    {
+      Header.FileType = 0;
+      DataSize = (Header.Cols+7) / 8;
+      qt = GrayQuantum;
+      bpp =1;
+    } else if(image->colors <= 16)
+    {
+      Header.FileType = 4;
+      DataSize = (Header.Cols+1) / 2;
+      qt = IndexQuantum;
+      bpp = 4;
+    }
+    else
+    {
+      Header.FileType = 2;
+      DataSize = Header.Cols;
+      qt = IndexQuantum;
+      bpp = 8;
+    }
+  }
+  else		// RGB
+  {
+    Header.FileType = 5;
+    DataSize = 3*Header.Cols;
+    qt = RGBQuantum;
+    bpp = 8;
+  }
+
+  if(DataSize==0)
+    ThrowWriterException(FileOpenError,UnableToOpenFile,image);
+  pixels = MagickAllocateResourceLimitedMemory(unsigned char *,(size_t) (DataSize));
+
+  status = OpenBlob(image_info,image,WriteBinaryBlobMode,&image->exception);
+  if(status == MagickFail)
+    ThrowWriterException(FileOpenError,UnableToOpenFile,image);
+
+	/* Write TopoL hader. */
+  WriteBlob(image, 20, Header.Name);
+  WriteBlobLSBShort(image, Header.Rows);
+  WriteBlobLSBShort(image, Header.Cols);
+  WriteBlobLSBShort(image, Header.FileType);
+  WriteBlobLSBLong(image, Header.Zoom);
+  WriteBlobLSBShort(image, Header.Version);
+  WriteBlobLSBShort(image, Header.Komprese);
+  WriteBlobLSBShort(image, Header.Stav);
+
+  WriteBlobLSBDouble(image, Header.xRasMin);
+  WriteBlobLSBDouble(image, Header.yRasMin);
+  WriteBlobLSBDouble(image, Header.xRasMax);
+  WriteBlobLSBDouble(image, Header.yRasMax);
+  WriteBlobLSBDouble(image, Header.Scale);
+	//from release 2
+  WriteBlobLSBShort(image, Header.TileWidth);
+  WriteBlobLSBShort(image, Header.TileHeight);
+  WriteBlobLSBLong(image, Header.TileOffsets);
+  WriteBlobLSBLong(image, Header.TileByteCounts);
+  WriteBlobByte(image, Header.TileCompression);
+
+  WriteBlob(image, 423, Header.Dummy);
+
+	/* Palette */
+
+
+	/* Store image data. */
+  for(y=0; y<(long)image->rows; y++)
+  {
+    if(AcquireImagePixels(image,0,y,image->columns,1,&image->exception)  == (const PixelPacket *)NULL)
+    {
+      status=MagickFail;
+      break;
+    }
+    if(ExportImagePixelArea(image,qt,bpp,pixels,0,0) != MagickPass)
+    {
+      status = MagickFail;
+      break;
+    }
+    if(WriteBlob(image,DataSize,pixels) != DataSize)
+    {
+      status = MagickFail;
+      break;
+    }
+  }
+
+  CloseBlob(image);
+
+  if(logging)
+    (void)LogMagickEvent(CoderEvent,GetMagickModule(),"return TopoL");
+
+  return(status);
+}
+
+
 
 /*
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -772,9 +920,10 @@
   MagickInfo * entry;
 
   entry = SetMagickInfo("TOPOL");
-  entry->decoder = (DecoderHandler) ReadTOPOLImage;
+  entry->decoder = (DecoderHandler) ReadTopoLImage;
+  entry->encoder = (EncoderHandler) WriteTopoLImage;
   entry->seekable_stream = True;
-  entry->description = "TOPOL X Image";
+  entry->description = "TopoL X Image";
   entry->module = "TOPOL";
   (void) RegisterMagickInfo(entry);
 }
diff -r ca23f27fe474 -r 5b54e4cb9eea magick/blob.c
--- a/magick/blob.c	Sat Apr 29 10:13:35 2023 -0500
+++ b/magick/blob.c	Sat Apr 29 18:32:33 2023 +0200
@@ -5458,6 +5458,7 @@
 */
 MagickExport size_t WriteBlobLSBLong(Image *image,const magick_uint32_t value)
 {
+#if defined(WORDS_BIGENDIAN)
   unsigned char
     buffer[4];
 
@@ -5468,6 +5469,12 @@
   buffer[2]=(unsigned char) (value >> 16);
   buffer[3]=(unsigned char) (value >> 24);
   return(WriteBlob(image,4,buffer));
+#else
+  assert(image != (Image *) NULL);
+  assert(image->signature == MagickSignature);
+  assert(sizeof(value) == 4);
+  return(WriteBlob(image,4,&value));
+#endif
 }
 
 /*
@@ -5602,6 +5609,21 @@
   buffer[1]=(unsigned char) (uvalue.uint16 >> 8);
   return(WriteBlob(image,2,buffer));
 }
+
+
+MagickExport size_t WriteBlobLSBDouble(Image *image, double d)
+{
+  assert(image != (Image *) NULL);
+  assert(image->signature == MagickSignature);
+  assert(sizeof(d) == 8);
+
+#if defined(WORDS_BIGENDIAN)
+  MagickSwabDouble(&d);
+#endif
+  return(WriteBlob(image,8,&d));
+}
+
+
 
 /*
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -5654,6 +5676,7 @@
 
   return octets_read;
 }
+
 
 /*
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff -r ca23f27fe474 -r 5b54e4cb9eea magick/blob.h
--- a/magick/blob.h	Sat Apr 29 10:13:35 2023 -0500
+++ b/magick/blob.h	Sat Apr 29 18:32:33 2023 +0200
@@ -398,6 +398,7 @@
                                                     const magick_int32_t value);
 
 
+  extern MagickExport size_t WriteBlobLSBDouble(Image *image, double d);
 
   /*
     Write a 32-bit unsigned "long" value to the file or BLOB in big-endian
diff -r ca23f27fe474 -r 5b54e4cb9eea www/Changelog.html
--- a/www/Changelog.html	Sat Apr 29 10:13:35 2023 -0500
+++ b/www/Changelog.html	Sat Apr 29 18:32:33 2023 +0200
@@ -40,6 +40,14 @@
 <p>2023-04-29  Bob Friesenhahn  &lt;<a class="reference external" href="mailto:bfriesen&#37;&#52;&#48;simple&#46;dallas&#46;tx&#46;us">bfriesen<span>&#64;</span>simple<span>&#46;</span>dallas<span>&#46;</span>tx<span>&#46;</span>us</a>&gt;</p>
 <blockquote>
 <ul class="simple">
+<li><p>coders/mat.c (InsertComplexDoubleRow): If computed f is nan,
+then use 0.0.  Addresses SourceForge issue #708 &quot;Undefined
+behavior while converting negative infinity to integer&quot;.
+(InsertComplexFloatRow):  If computed f is nan, then use 0.0.</p></li>
+<li><p>magick/attribute.c (GenerateEXIFAttribute): Assure that float
+and double values are suitably alligned.  Addresses SourceForge
+issue #709 &quot;Undefined behavior while loading a value of type float
+from an unaligned address&quot;.</p></li>
 <li><p>coders/tiff.c (ReadTIFFImage): Validate that TIFFGetField() did
 return count and text rather than just relying on its return
 status.  Addresses SourceForge issue #710 &quot;Undefined behavior
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.