[libpng15] Fixed 64-bit compilation errors (gcc). The errors fixed relate

to conditions where types that are 32 bits in the GCC 32-bit
world (uLong and png_size_t) become 64 bits in the 64-bit
world.  This produces potential truncation errors which the
compiler correctly flags.
diff --git a/ANNOUNCE b/ANNOUNCE
index 15a6b3e..e86ad55 100644
--- a/ANNOUNCE
+++ b/ANNOUNCE
@@ -88,6 +88,11 @@
     png_XYZ_from_xy_checked().
 
 Version 1.5.5beta08 [September 9, 2011]
+  Fixed 64-bit compilation errors (gcc). The errors fixed relate
+    to conditions where types that are 32 bits in the GCC 32-bit
+    world (uLong and png_size_t) become 64 bits in the 64-bit
+    world.  This produces potential truncation errors which the
+    compiler correctly flags.
 
 Send comments/corrections/commendations to png-mng-implement at lists.sf.net:
 (subscription required; visit
diff --git a/CHANGES b/CHANGES
index f063a1c..8511a73 100644
--- a/CHANGES
+++ b/CHANGES
@@ -3572,6 +3572,11 @@
     png_XYZ_from_xy_checked().
 
 Version 1.5.5beta08 [September 9, 2011]
+  Fixed 64-bit compilation errors (gcc). The errors fixed relate
+    to conditions where types that are 32 bits in the GCC 32-bit
+    world (uLong and png_size_t) become 64 bits in the 64-bit
+    world.  This produces potential truncation errors which the
+    compiler correctly flags.
 
 Send comments/corrections/commendations to png-mng-implement at lists.sf.net
 (subscription required; visit
diff --git a/png.c b/png.c
index b16ae9a..3e18b99 100644
--- a/png.c
+++ b/png.c
@@ -107,7 +107,8 @@
 void /* PRIVATE */
 png_reset_crc(png_structp png_ptr)
 {
-   png_ptr->crc = crc32(0, Z_NULL, 0);
+   /* The cast is safe because the crc is a 32 bit value. */
+   png_ptr->crc = (png_uint_32)crc32(0, Z_NULL, 0);
 }
 
 /* Calculate the CRC over a section of data.  We can only pass as
@@ -133,8 +134,35 @@
          need_crc = 0;
    }
 
-   if (need_crc)
-      png_ptr->crc = crc32(png_ptr->crc, ptr, (uInt)length);
+   /* 'uLong' is defined as unsigned long, this means that on some systems it is
+    * a 64 bit value.  crc32, however, returns 32 bits so the following cast is
+    * safe.  'uInt' may be no more than 16 bits, so it is necessary to perform a
+    * loop here.
+    */
+   if (need_crc && length > 0)
+   {
+      uLong crc = png_ptr->crc; /* Should never issue a warning */
+
+      do
+      {
+         uInt safeLength = (uInt)length;
+         if (safeLength == 0)
+            safeLength = (uInt)-1; /* evil, but safe */
+
+         crc = crc32(crc, ptr, safeLength);
+
+         /* The following should never issue compiler warnings, if they do the
+          * target system has characteristics that will probably violate other
+          * assumptions within the libpng code.
+          */
+         ptr += safeLength;
+         length -= safeLength;
+      }
+      while (length > 0);
+
+      /* And the following is always safe because the crc is only 32 bits. */
+      png_ptr->crc = (png_uint_32)crc;
+   }
 }
 
 /* Check a user supplied version number, called from both read and write
diff --git a/png.h b/png.h
index 84411e4..bf557f4 100644
--- a/png.h
+++ b/png.h
@@ -795,7 +795,7 @@
 #define PNG_INFO_iCCP 0x1000   /* ESR, 1.0.6 */
 #define PNG_INFO_sPLT 0x2000   /* ESR, 1.0.6 */
 #define PNG_INFO_sCAL 0x4000   /* ESR, 1.0.6 */
-#define PNG_INFO_IDAT 0x8000L  /* ESR, 1.0.6 */
+#define PNG_INFO_IDAT 0x8000   /* ESR, 1.0.6 */
 
 /* This is used for the transformation routines, as some of them
  * change these values for the row.  It also should enable using
diff --git a/pngpriv.h b/pngpriv.h
index 9ca489d..92e39ab 100644
--- a/pngpriv.h
+++ b/pngpriv.h
@@ -372,16 +372,15 @@
 #define PNG_USER_TRANSFORM    0x100000L
 #define PNG_RGB_TO_GRAY_ERR   0x200000L
 #define PNG_RGB_TO_GRAY_WARN  0x400000L
-#define PNG_RGB_TO_GRAY       0x600000L  /* two bits, RGB_TO_GRAY_ERR|WARN */
-#define PNG_ENCODE_ALPHA      0x800000L  /* Added to libpng-1.5.4 */
-#define PNG_ADD_ALPHA         0x1000000L  /* Added to libpng-1.2.7 */
-#define PNG_EXPAND_tRNS       0x2000000L  /* Added to libpng-1.2.9 */
-#define PNG_SCALE_16_TO_8     0x4000000L  /* Added to libpng-1.5.4 */
-                       /*   0x8000000L  unused */
-                       /*  0x10000000L  unused */
-                       /*  0x20000000L  unused */
-                       /*  0x40000000L  unused */
-
+#define PNG_RGB_TO_GRAY       0x600000L /* two bits, RGB_TO_GRAY_ERR|WARN */
+#define PNG_ENCODE_ALPHA      0x800000L /* Added to libpng-1.5.4 */
+#define PNG_ADD_ALPHA         0x1000000L /* Added to libpng-1.2.7 */
+#define PNG_EXPAND_tRNS       0x2000000L /* Added to libpng-1.2.9 */
+#define PNG_SCALE_16_TO_8     0x4000000L /* Added to libpng-1.5.4 */
+                       /*   0x8000000L unused */
+                       /*  0x10000000L unused */
+                       /*  0x20000000L unused */
+                       /*  0x40000000L unused */
 /* Flags for png_create_struct */
 #define PNG_STRUCT_PNG   0x0001
 #define PNG_STRUCT_INFO  0x0002
@@ -406,22 +405,22 @@
 #define PNG_FLAG_ASSUME_sRGB              0x1000  /* Added to libpng-1.5.4 */
 #define PNG_FLAG_OPTIMIZE_ALPHA           0x2000  /* Added to libpng-1.5.4 */
 #define PNG_FLAG_DETECT_UNINITIALIZED     0x4000  /* Added to libpng-1.5.4 */
-#define PNG_FLAG_KEEP_UNKNOWN_CHUNKS      0x8000L
-#define PNG_FLAG_KEEP_UNSAFE_CHUNKS       0x10000L
-#define PNG_FLAG_LIBRARY_MISMATCH         0x20000L
-#define PNG_FLAG_STRIP_ERROR_NUMBERS      0x40000L
-#define PNG_FLAG_STRIP_ERROR_TEXT         0x80000L
-#define PNG_FLAG_MALLOC_NULL_MEM_OK       0x100000L
-                                  /*      0x200000L  unused */
-                                  /*      0x400000L  unused */
-#define PNG_FLAG_BENIGN_ERRORS_WARN       0x800000L  /* Added to libpng-1.4.0 */
-#define PNG_FLAG_ZTXT_CUSTOM_STRATEGY    0x1000000L  /* 5 lines added */
-#define PNG_FLAG_ZTXT_CUSTOM_LEVEL       0x2000000L  /* to libpng-1.5.4 */
-#define PNG_FLAG_ZTXT_CUSTOM_MEM_LEVEL   0x4000000L
-#define PNG_FLAG_ZTXT_CUSTOM_WINDOW_BITS 0x8000000L
-#define PNG_FLAG_ZTXT_CUSTOM_METHOD      0x10000000L
-                                  /*     0x20000000L  unused */
-                                  /*     0x40000000L  unused */
+#define PNG_FLAG_KEEP_UNKNOWN_CHUNKS      0x8000
+#define PNG_FLAG_KEEP_UNSAFE_CHUNKS       0x10000
+#define PNG_FLAG_LIBRARY_MISMATCH         0x20000
+#define PNG_FLAG_STRIP_ERROR_NUMBERS      0x40000
+#define PNG_FLAG_STRIP_ERROR_TEXT         0x80000
+#define PNG_FLAG_MALLOC_NULL_MEM_OK       0x100000
+                                  /*      0x200000  unused */
+                                  /*      0x400000  unused */
+#define PNG_FLAG_BENIGN_ERRORS_WARN       0x800000  /* Added to libpng-1.4.0 */
+#define PNG_FLAG_ZTXT_CUSTOM_STRATEGY    0x1000000  /* 5 lines added */
+#define PNG_FLAG_ZTXT_CUSTOM_LEVEL       0x2000000  /* to libpng-1.5.4 */
+#define PNG_FLAG_ZTXT_CUSTOM_MEM_LEVEL   0x4000000
+#define PNG_FLAG_ZTXT_CUSTOM_WINDOW_BITS 0x8000000
+#define PNG_FLAG_ZTXT_CUSTOM_METHOD      0x10000000
+                                  /*     0x20000000  unused */
+                                  /*     0x40000000  unused */
 
 #define PNG_FLAG_CRC_ANCILLARY_MASK (PNG_FLAG_CRC_ANCILLARY_USE | \
                                      PNG_FLAG_CRC_ANCILLARY_NOWARN)
diff --git a/pngrutil.c b/pngrutil.c
index 99bfdca..039c77f 100644
--- a/pngrutil.c
+++ b/pngrutil.c
@@ -87,10 +87,10 @@
 png_get_int_32)(png_const_bytep buf)
 {
    png_uint_32 uval = png_get_uint_32(buf);
-   if ((uval & 0x80000000L) == 0) /* non-negative */
+   if ((uval & 0x80000000) == 0) /* non-negative */
       return uval;
 
-   uval = (uval ^ 0xffffffffL) + 1;  /* 2's complement: -x = ~x+1 */
+   uval = (uval ^ 0xffffffff) + 1;  /* 2's complement: -x = ~x+1 */
    return -(png_int_32)uval;
 }
 
diff --git a/pngset.c b/pngset.c
index ac90d46..79968d3 100644
--- a/pngset.c
+++ b/pngset.c
@@ -620,7 +620,7 @@
 {
    png_charp new_iccp_name;
    png_bytep new_iccp_profile;
-   png_uint_32 length;
+   png_size_t length;
 
    png_debug1(1, "in %s storage function", "iCCP");
 
@@ -966,10 +966,10 @@
    {
       png_sPLT_tp to = np + info_ptr->splt_palettes_num + i;
       png_const_sPLT_tp from = entries + i;
-      png_uint_32 length;
+      png_size_t length;
 
       length = png_strlen(from->name) + 1;
-      to->name = (png_charp)png_malloc_warn(png_ptr, (png_size_t)length);
+      to->name = (png_charp)png_malloc_warn(png_ptr, length);
 
       if (to->name == NULL)
       {
@@ -980,7 +980,7 @@
 
       png_memcpy(to->name, from->name, length);
       to->entries = (png_sPLT_entryp)png_malloc_warn(png_ptr,
-          (png_size_t)(from->nentries * png_sizeof(png_sPLT_entry)));
+          from->nentries * png_sizeof(png_sPLT_entry));
 
       if (to->entries == NULL)
       {
diff --git a/pngvalid.c b/pngvalid.c
index 0b441a3..8c2eb0d 100644
--- a/pngvalid.c
+++ b/pngvalid.c
@@ -2217,7 +2217,10 @@
     * the buffer, at the start.
     */
    uInt datalen = png_get_uint_32(buffer);
-   png_save_uint_32(buffer+datalen+8, crc32(0L, buffer+4, datalen+4));
+   uLong crc = crc32(0L, buffer+4, datalen+4);
+   /* The cast to png_uint_32 is safe because a crc32 is always a 32 bit value.
+    */
+   png_save_uint_32(buffer+datalen+8, (png_uint_32)crc);
 }
 
 static void
diff --git a/pngwutil.c b/pngwutil.c
index 3ae5ed4..4e422ce 100644
--- a/pngwutil.c
+++ b/pngwutil.c
@@ -1860,7 +1860,7 @@
 {
    PNG_pCAL;
    png_size_t purpose_len, units_len, total_len;
-   png_uint_32p params_len;
+   png_size_tp params_len;
    png_byte buf[10];
    png_charp new_purpose;
    int i;
@@ -1876,8 +1876,8 @@
    png_debug1(3, "pCAL units length = %d", (int)units_len);
    total_len = purpose_len + units_len + 10;
 
-   params_len = (png_uint_32p)png_malloc(png_ptr,
-       (png_alloc_size_t)(nparams * png_sizeof(png_uint_32)));
+   params_len = (png_size_tp)png_malloc(png_ptr,
+       (png_alloc_size_t)(nparams * png_sizeof(png_size_t)));
 
    /* Find the length of each parameter, making sure we don't count the
     * null terminator for the last parameter.
@@ -1887,13 +1887,12 @@
       params_len[i] = png_strlen(params[i]) + (i == nparams - 1 ? 0 : 1);
       png_debug2(3, "pCAL parameter %d length = %lu", i,
           (unsigned long)params_len[i]);
-      total_len += (png_size_t)params_len[i];
+      total_len += params_len[i];
    }
 
    png_debug1(3, "pCAL total length = %d", (int)total_len);
    png_write_chunk_start(png_ptr, png_pCAL, (png_uint_32)total_len);
-   png_write_chunk_data(png_ptr, (png_const_bytep)new_purpose,
-       (png_size_t)purpose_len);
+   png_write_chunk_data(png_ptr, (png_const_bytep)new_purpose, purpose_len);
    png_save_int_32(buf, X0);
    png_save_int_32(buf + 4, X1);
    buf[8] = (png_byte)type;
@@ -1905,8 +1904,7 @@
 
    for (i = 0; i < nparams; i++)
    {
-      png_write_chunk_data(png_ptr, (png_const_bytep)params[i],
-          (png_size_t)params_len[i]);
+      png_write_chunk_data(png_ptr, (png_const_bytep)params[i], params_len[i]);
    }
 
    png_free(png_ptr, params_len);