summaryrefslogtreecommitdiff
path: root/graphics/gd
diff options
context:
space:
mode:
authorNorikatsu Shigemura <nork@FreeBSD.org>2003-08-18 16:15:10 +0000
committerNorikatsu Shigemura <nork@FreeBSD.org>2003-08-18 16:15:10 +0000
commitefb928619b234d49b326a13f59a6e2ee354bf902 (patch)
treec62bd82140831e81442480b9cefc699e0c08f08d /graphics/gd
parentUpdate to 5.0.8. As reported by Paul Szabo in (diff)
o Main modification
graphics/gd(based on 1.8.4) -> graphics/gd1 graphics/gd2(based on 2.0.15) -> graphics/gd graphics/p5-GD(based on 1.41) -> graphics/p5-GD1 graphics/p5-GD2(based on 2.07) -> graphics/p5-GD japanese/gd -> japanese/gd1 japanese/gd2 -> japanese/gd o Include some feature WITH_XPM(w/, w/o WITHOUT_X11) o Chase this modification o Fix build error [1] PR: ports/54540 Submitted by: Ports Fury Approved by: maintainer (blanket) Reported by: bento via kris [1]
Notes
Notes: svn path=/head/; revision=87214
Diffstat (limited to 'graphics/gd')
-rw-r--r--graphics/gd/Makefile57
-rw-r--r--graphics/gd/distinfo3
-rw-r--r--graphics/gd/files/Makefile.bsd53
-rw-r--r--graphics/gd/files/Makefile.lib36
-rw-r--r--graphics/gd/files/gd2togif.c40
-rw-r--r--graphics/gd/files/gd_biggif_out.c823
-rw-r--r--graphics/gd/files/gd_gif_in.c16
-rw-r--r--graphics/gd/files/gd_gif_out.c44
-rw-r--r--graphics/gd/files/gd_lzw_out.c795
-rw-r--r--graphics/gd/files/gdcmpgif.c85
-rw-r--r--graphics/gd/files/giftogd2.c48
-rw-r--r--graphics/gd/files/patch-gd.h41
-rw-r--r--graphics/gd/files/patch-gdcache.h10
-rw-r--r--graphics/gd/files/patch-gdft.c92
-rw-r--r--graphics/gd/files/patch-gdkanji.c87
-rw-r--r--graphics/gd/files/patch-gdtest.c81
-rw-r--r--graphics/gd/files/patch-gdttf.c17
-rw-r--r--graphics/gd/files/patch-gif11
-rw-r--r--graphics/gd/files/patch-index.html71
-rw-r--r--graphics/gd/pkg-descr33
-rw-r--r--graphics/gd/pkg-plist37
21 files changed, 2269 insertions, 211 deletions
diff --git a/graphics/gd/Makefile b/graphics/gd/Makefile
index afc96e0f11ee..eb459fc819fc 100644
--- a/graphics/gd/Makefile
+++ b/graphics/gd/Makefile
@@ -1,14 +1,13 @@
# New ports collection makefile for: gd
-# Date created: 27 Mar 1998
-# Whom: jeff@cetlink.net
+# Date created: 27 Mar 1998
+# Whom: jeff@cetlink.net
#
# $FreeBSD$
#
PORTNAME= gd
-PORTVERSION= 1.8.4
-PORTREVISION= 7
-PORTEPOCH= 1
+PORTVERSION= 2.0.15
+PORTREVISION= 1
CATEGORIES+= graphics
MASTER_SITES= http://www.boutell.com/gd/http/ \
ftp://ftp.boutell.com/pub/boutell/gd/ \
@@ -22,22 +21,52 @@ LIB_DEPENDS= jpeg.9:${PORTSDIR}/graphics/jpeg \
png.5:${PORTSDIR}/graphics/png \
freetype.9:${PORTSDIR}/print/freetype2
-MAKEFILE= ${FILESDIR}/Makefile.lib
+MAKE_ENV= WRKSRC="${WRKSRC}" CPPFLAGS="${CPPFLAGS}" LDFLAGS="${LDFLAGS}"
+MAKEFILE= ${FILESDIR}/Makefile.bsd
INSTALLS_SHLIB= yes
-.if defined(WITH_X11)
+.include <bsd.port.pre.mk>
+
+.if defined(WITH_XPM)
+.if defined(WITHOUT_X11)
+LIB_DEPENDS+= Xpm:${PORTSDIR}/graphics/xpm
+CPPFLAGS+= -I${X11BASE}/include/X11 -I${X11BASE}/include -DHAVE_LIBXPM -DXPM_NOX
+LDFLAGS+= -L${X11BASE}/lib -lXpm
+.else
USE_XPM= yes
+CPPFLAGS+= -I${X11BASE}/include/X11 -I${X11BASE}/include -DHAVE_LIBXPM
+LDFLAGS+= -L${X11BASE}/lib -lXpm -lX11
+.endif
+.endif
+
+.if defined(WITH_LZW) || defined(HAVE_UNISYS_LICENSE) || \
+ (defined(USA_RESIDENT) && ${USA_RESIDENT} == "YES")
+CPPFLAGS+= -DLZW_LICENSED
+.endif
+
+.if defined(GD_FONTS)
+USE_PERL5_BUILD= yes
+SCRIPTS_ENV+= GD_FONTS="${GD_FONTS}"
.endif
pre-everything::
-.if !defined(WITH_X11)
- @${ECHO_MSG}
- @${ECHO_MSG} "If you want to compile with Xpm support,"
- @${ECHO_MSG} "hit Ctrl-C right now and use \"make WITH_X11=yes\""
- @${ECHO_MSG}
+ @${ECHO_MSG} ""
+ @${ECHO_MSG} "gd has the following tunables:"
+ @${ECHO_MSG} ""
+ @${ECHO_MSG} " WITH_XPM=yes Turns on Xpm support"
+ @${ECHO_MSG} " WITH_XPM=yes WITHOUT_X11=yes Turns on X-less Xpm support"
+.if !defined(USA_RESIDENT) || ${USA_RESIDENT} != "YES"
+ @${ECHO_MSG} " WITH_LZW=yes Turns on GIF compression support"
.endif
+ @${ECHO_MSG} ""
post-extract:
- @${CP} ${FILESDIR}/gd_gif_in.c ${WRKSRC}
+ @${CP} ${FILESDIR}/g* ${WRKSRC}
+
+post-install:
+.if !defined(NOPORTDOCS)
+ @${MKDIR} ${DOCSDIR}
+ ${INSTALL_DATA} ${WRKSRC}/index.html ${DOCSDIR}
+.endif
-.include <bsd.port.mk>
+.include <bsd.port.post.mk>
diff --git a/graphics/gd/distinfo b/graphics/gd/distinfo
index ed8787c2bd67..4297649caf8a 100644
--- a/graphics/gd/distinfo
+++ b/graphics/gd/distinfo
@@ -1,2 +1 @@
-MD5 (gd-1.8.4.tar.gz) = 2aef76e79f206f9798233f025f5dd28d
-MD5 (gd_gif_in.c.bz2) = 54132aea09471bb997672436dd9a1a96
+MD5 (gd-2.0.15.tar.gz) = 6ededf633b4fd054662ec123c7825fbb
diff --git a/graphics/gd/files/Makefile.bsd b/graphics/gd/files/Makefile.bsd
new file mode 100644
index 000000000000..a6530d92a53e
--- /dev/null
+++ b/graphics/gd/files/Makefile.bsd
@@ -0,0 +1,53 @@
+PROGS!= ${MAKE} -V BIN_PROGRAMS -f ${WRKSRC}/makefile.sample
+PROGS+= gd2togif gdcmpgif giftogd2
+PROGS+= annotate # new utility, not included in makefile.sample
+TESTS= gdtest gddemo gd2time gdtestft testac fontsizetest fontwheeltest
+SRCS= gd.c gd_gd.c gd_gd2.c gd_io.c gd_io_dp.c gd_io_file.c \
+ gd_io_ss.c gd_jpeg.c gd_png.c gd_ss.c gd_topal.c \
+ gd_wbmp.c gdcache.c gdfontg.c gdfontl.c gdfontmb.c \
+ gdfonts.c gdfontt.c gdft.c gdhelpers.c gdhelpers.h \
+ gdkanji.c gdtables.c gdxpm.c jisx0208.h \
+ wbmp.c wbmp.h
+SRCS+= gd_gif_in.c gd_gif_out.c gd_biggif_out.c gd_lzw_out.c
+MAKEDIR=/usr/share/mk
+LIB=gd
+SHLIB_MAJOR=4
+SHLIB_MINOR=0
+INCS= gd.h gd_io.h gdcache.h gdfontg.h gdfontl.h gdfontmb.h \
+ gdfonts.h gdfontt.h
+SHLIB_NAME!= ${MAKE} -V SHLIB_NAME LIB=${LIB} \
+ SHLIB_MAJOR=${SHLIB_MAJOR} SHLIB_MINOR=${SHLIB_MINOR} -f ${MAKEDIR}/bsd.lib.mk
+
+CFLAGS+= -I${.CURDIR} -I${LOCALBASE}/include/freetype2/freetype \
+ -I${LOCALBASE}/include/freetype2 -I${LOCALBASE}/include \
+ -DHAVE_LIBPNG -DHAVE_LIBJPEG -DHAVE_LIBFREETYPE -DHAVE_LIBZ \
+ ${CPPFLAGS}
+LDADD= -L${LOCALBASE}/lib -lpng -lz -ljpeg -lfreetype -lm \
+ ${LDFLAGS}
+
+# The package comes with tests, but without any sort of test-harness,
+# to run them all automaticly. So building tests is disabled here. -mi
+all: lib${LIB}.a ${SHLIB_NAME} ${PROGS} # ${TESTS}
+
+lib${LIB}.a ${SHLIB_NAME}: ${SRCS}
+ ${MAKE} LIB=${LIB} SRCS="${SRCS}" \
+ SHLIB_MAJOR=${SHLIB_MAJOR} SHLIB_MINOR=${SHLIB_MINOR} \
+ CFLAGS="${CFLAGS}" -ECFLAGS LDADD="${LDADD}" \
+ -f ${MAKEDIR}/bsd.lib.mk ${.TARGET}
+
+${PROGS} ${TESTS}: ${SHLIB_NAME} lib${LIB}.a
+ ${MAKE} PROG=${.TARGET} NOMAN=1 LDADD="-L${.CURDIR} -lgd" \
+ CFLAGS="${CFLAGS}" -ECFLAGS -f ${MAKEDIR}/bsd.prog.mk
+
+install:
+ mkdir -p ${PREFIX}/include
+ ${MAKE} LIB=${LIB} LIBDIR=${PREFIX}/lib NOPROFILE=true \
+ SHLIB_MAJOR=${SHLIB_MAJOR} SHLIB_MINOR=${SHLIB_MINOR} \
+ -f ${MAKEDIR}/bsd.lib.mk install
+ cd ${.CURDIR} && ${BSD_INSTALL_DATA} ${INCS} ${PREFIX}/include
+ cd ${.CURDIR} && ${BSD_INSTALL_PROGRAM} ${PROGS} ${PREFIX}/bin/
+ ${BSD_INSTALL_SCRIPT} ${.CURDIR}/bdftogd ${PREFIX}/bin/
+
+.if exists(${.CURDIR}/Makefile.fonts)
+.include "Makefile.fonts"
+.endif
diff --git a/graphics/gd/files/Makefile.lib b/graphics/gd/files/Makefile.lib
deleted file mode 100644
index 8306444eb839..000000000000
--- a/graphics/gd/files/Makefile.lib
+++ /dev/null
@@ -1,36 +0,0 @@
-# $FreeBSD$
-
-PREFIX?= /usr/local
-SHLIB_VER?= 2
-
-LIB= gd1
-LIBDIR= ${PREFIX}/lib
-SHLIB_MAJOR= ${SHLIB_VER}
-SHLIB_MINOR= 0
-NOPROFILE= yes
-NOOBJ= yes
-
-INCS= gd.h gd_io.h gdcache.h gdfontg.h gdfontl.h gdfontmb.h \
- gdfonts.h gdfontt.h
-INCSDIR= ${PREFIX}/include/gd
-INCDIR= ${INSCDIR} # for pre-bsd.incs.mk API
-
-SRCS= gd.c gd_gd.c gd_gd2.c gd_io.c gd_io_dp.c gd_io_file.c gd_ss.c \
- gd_io_ss.c gd_png.c gd_jpeg.c gdxpm.c gdfontt.c gdfonts.c \
- gdfontmb.c gdfontl.c gdfontg.c gdtables.c gdft.c gdttf.c \
- gdcache.c gdkanji.c wbmp.c gd_wbmp.c gdhelpers.c gd_gif_in.c
-
-CFLAGS+= -I${.CURDIR} -I${LOCALBASE}/include/freetype2/freetype \
- -I${LOCALBASE}/include/freetype2 -I${LOCALBASE}/include \
- -DHAVE_LIBPNG -DHAVE_LIBJPEG -DHAVE_LIBFREETYPE -DHAVE_LIBZ
-LDADD= -L${LOCALBASE}/lib -lfreetype -ljpeg -lpng -lz
-
-.ifdef WITH_X11
-CFLAGS+= -I${X11BASE}/include/X11 -I${X11BASE}/include -DHAVE_LIBXPM
-LDADD+= -L${X11BASE}/lib -lXpm -lX11
-.endif
-
-beforeinstall:
- mkdir -p ${INCSDIR}
-
-.include <bsd.lib.mk>
diff --git a/graphics/gd/files/gd2togif.c b/graphics/gd/files/gd2togif.c
new file mode 100644
index 000000000000..d5fbb8921c3a
--- /dev/null
+++ b/graphics/gd/files/gd2togif.c
@@ -0,0 +1,40 @@
+#include <stdio.h>
+#include "gd.h"
+
+/* A short program which converts a .gif file into a .gd file, for
+ your convenience in creating images on the fly from a
+ basis image that must be loaded quickly. The .gd format
+ is not intended to be a general-purpose format. */
+
+int main(int argc, char **argv)
+{
+ gdImagePtr im;
+ FILE *in, *out;
+ if (argc != 3) {
+ fprintf(stderr, "Usage: gd2togif filename.gd2 filename.gif\n");
+ exit(1);
+ }
+ in = fopen(argv[1], "rb");
+ if (!in) {
+ fprintf(stderr, "Input file does not exist!\n");
+ exit(1);
+ }
+ im = gdImageCreateFromGd2(in);
+ fclose(in);
+ if (!im) {
+ fprintf(stderr, "Input is not in GIF format!\n");
+ exit(1);
+ }
+ out = fopen(argv[2], "wb");
+ if (!out) {
+ fprintf(stderr, "Output file cannot be written to!\n");
+ gdImageDestroy(im);
+ exit(1);
+ }
+ gdImageGif(im, out);
+ fclose(out);
+ gdImageDestroy(im);
+
+ return 0;
+}
+
diff --git a/graphics/gd/files/gd_biggif_out.c b/graphics/gd/files/gd_biggif_out.c
new file mode 100644
index 000000000000..29ec90f87d56
--- /dev/null
+++ b/graphics/gd/files/gd_biggif_out.c
@@ -0,0 +1,823 @@
+#include <stdio.h>
+#include <math.h>
+#include <string.h>
+#include <stdlib.h>
+#include "gd.h"
+
+/*
+** Wrapper functions for this module.
+*/
+
+void gdImageBigGif(gdImagePtr im, FILE *outFile)
+{
+ gdIOCtx *out = gdNewFileCtx(outFile);
+ gdImageBigGifCtx(im, out);
+ out->gd_free(out);
+}
+
+void* gdImageBigGifPtr(gdImagePtr im, int *size)
+{
+ void *rv;
+ gdIOCtx *out = gdNewDynamicCtx(2048, NULL);
+ gdImageBigGifCtx(im, out);
+ rv = gdDPExtractData(out,size);
+ out->gd_free(out);
+ return rv;
+}
+
+/* Code drawn from ppmtogif.c, from the pbmplus package
+**
+** Based on GIFENCOD by David Rowley <mgardi@watdscu.waterloo.edu>. A
+** Lempel-Zim compression based on "compress".
+**
+** Modified by Marcel Wijkstra <wijkstra@fwi.uva.nl>
+**
+** Copyright (C) 1989 by Jef Poskanzer.
+**
+** Permission to use, copy, modify, and distribute this software and its
+** documentation for any purpose and without fee is hereby granted, provided
+** that the above copyright notice appear in all copies and that both that
+** copyright notice and this permission notice appear in supporting
+** documentation. This software is provided "as is" without express or
+** implied warranty.
+**
+** The Graphics Interchange Format(c) is the Copyright property of
+** CompuServe Incorporated. GIF(sm) is a Service Mark property of
+** CompuServe Incorporated.
+*
+* Heavily modified by Mouse, 1998-02-12.
+* Remove LZW compression.
+* Added miGIF run length compression.
+*
+*/
+
+/*
+ * a code_int must be able to hold 2**GIFBITS values of type int, and also -1
+ */
+typedef int code_int;
+
+static int colorstobpp(int colors);
+static void BumpPixel (void);
+static int GIFNextPixel (gdImagePtr im);
+static void GIFEncode (gdIOCtx *fp, int GWidth, int GHeight, int GInterlace, int Background, int Transparent, int BitsPerPixel, int *Red, int *Green, int *Blue, gdImagePtr im);
+/*static void Putword (int w, gdIOCtx *fp); */
+static void GIFcompress (int, gdIOCtx *, gdImagePtr, int);
+static void output (code_int code);
+
+/* UNUSED
+* static void char_init (void);
+* static void char_out (int c);
+*/
+
+/* Allows for reuse */
+static void init_statics(void);
+
+void gdImageBigGifCtx(gdImagePtr im, gdIOCtx *out)
+{
+ int interlace, transparent, BitsPerPixel;
+
+ interlace = im->interlace;
+ transparent = im->transparent;
+
+ BitsPerPixel = colorstobpp(im->colorsTotal);
+ /* Clear any old values in statics strewn through the GIF code */
+ init_statics();
+ /* All set, let's do it. */
+ GIFEncode(
+ out, im->sx, im->sy, interlace, 0, transparent, BitsPerPixel,
+ im->red, im->green, im->blue, im);
+}
+
+static int
+colorstobpp(int colors)
+{
+ int bpp = 0;
+
+ if ( colors <= 2 )
+ bpp = 1;
+ else if ( colors <= 4 )
+ bpp = 2;
+ else if ( colors <= 8 )
+ bpp = 3;
+ else if ( colors <= 16 )
+ bpp = 4;
+ else if ( colors <= 32 )
+ bpp = 5;
+ else if ( colors <= 64 )
+ bpp = 6;
+ else if ( colors <= 128 )
+ bpp = 7;
+ else if ( colors <= 256 )
+ bpp = 8;
+ return bpp;
+ }
+
+/*****************************************************************************
+ *
+ * GIFENCODE.C - GIF Image compression interface
+ *
+ * GIFEncode( FName, GHeight, GWidth, GInterlace, Background, Transparent,
+ * BitsPerPixel, Red, Green, Blue, gdImagePtr )
+ *
+ *****************************************************************************/
+
+#define TRUE 1
+#define FALSE 0
+
+static int Width, Height;
+static int curx, cury;
+static long CountDown;
+static int Pass = 0;
+static int Interlace;
+
+/*
+ * Bump the 'curx' and 'cury' to point to the next pixel
+ */
+static void
+BumpPixel(void)
+{
+ /*
+ * Bump the current X position
+ */
+ ++curx;
+
+ /*
+ * If we are at the end of a scan line, set curx back to the beginning
+ * If we are interlaced, bump the cury to the appropriate spot,
+ * otherwise, just increment it.
+ */
+ if( curx == Width ) {
+ curx = 0;
+
+ if( !Interlace )
+ ++cury;
+ else {
+ switch( Pass ) {
+
+ case 0:
+ cury += 8;
+ if( cury >= Height ) {
+ ++Pass;
+ cury = 4;
+ }
+ break;
+
+ case 1:
+ cury += 8;
+ if( cury >= Height ) {
+ ++Pass;
+ cury = 2;
+ }
+ break;
+
+ case 2:
+ cury += 4;
+ if( cury >= Height ) {
+ ++Pass;
+ cury = 1;
+ }
+ break;
+
+ case 3:
+ cury += 2;
+ break;
+ }
+ }
+ }
+}
+
+/*
+ * Return the next pixel from the image
+ */
+static int
+GIFNextPixel(gdImagePtr im)
+{
+ int r;
+
+ if( CountDown == 0 )
+ return EOF;
+
+ --CountDown;
+
+ r = gdImageGetPixel(im, curx, cury);
+
+ BumpPixel();
+
+ return r;
+}
+
+/* public */
+
+static void
+GIFEncode(gdIOCtx *fp, int GWidth, int GHeight, int GInterlace, int Background, int Transparent, int BitsPerPixel, int *Red, int *Green, int *Blue, gdImagePtr im)
+{
+ int B;
+ int RWidth, RHeight;
+ int LeftOfs, TopOfs;
+ int Resolution;
+ int ColorMapSize;
+ int InitCodeSize;
+ int i;
+
+ Interlace = GInterlace;
+
+ ColorMapSize = 1 << BitsPerPixel;
+
+ RWidth = Width = GWidth;
+ RHeight = Height = GHeight;
+ LeftOfs = TopOfs = 0;
+
+ Resolution = BitsPerPixel;
+
+ /*
+ * Calculate number of bits we are expecting
+ */
+ CountDown = (long)Width * (long)Height;
+
+ /*
+ * Indicate which pass we are on (if interlace)
+ */
+ Pass = 0;
+
+ /*
+ * The initial code size
+ */
+ if( BitsPerPixel <= 1 )
+ InitCodeSize = 2;
+ else
+ InitCodeSize = BitsPerPixel;
+
+ /*
+ * Set up the current x and y position
+ */
+ curx = cury = 0;
+
+ /*
+ * Write the Magic header
+ */
+ gdPutBuf( Transparent < 0 ? "GIF87a" : "GIF89a", 6, fp );
+
+ /*
+ * Write out the screen width and height
+ */
+ Putword( RWidth, fp );
+ Putword( RHeight, fp );
+
+ /*
+ * Indicate that there is a global colour map
+ */
+ B = 0x80; /* Yes, there is a color map */
+
+ /*
+ * OR in the resolution
+ */
+ B |= (Resolution - 1) << 4;
+
+ /*
+ * OR in the Bits per Pixel
+ */
+ B |= (BitsPerPixel - 1);
+
+ /*
+ * Write it out
+ */
+ gdPutC( B, fp );
+
+ /*
+ * Write out the Background colour
+ */
+ gdPutC( Background, fp );
+
+ /*
+ * Byte of 0's (future expansion)
+ */
+ gdPutC( 0, fp );
+
+ /*
+ * Write out the Global Colour Map
+ */
+ for( i=0; i<ColorMapSize; ++i ) {
+ gdPutC( Red[i], fp );
+ gdPutC( Green[i], fp );
+ gdPutC( Blue[i], fp );
+ }
+
+ /*
+ * Write out extension for transparent colour index, if necessary.
+ */
+ if ( Transparent >= 0 ) {
+ gdPutC( '!', fp );
+ gdPutC( 0xf9, fp );
+ gdPutC( 4, fp );
+ gdPutC( 1, fp );
+ gdPutC( 0, fp );
+ gdPutC( 0, fp );
+ gdPutC( (unsigned char) Transparent, fp );
+ gdPutC( 0, fp );
+ }
+
+ /*
+ * Write an Image separator
+ */
+ gdPutC( ',', fp );
+
+ /*
+ * Write the Image header
+ */
+
+ Putword( LeftOfs, fp );
+ Putword( TopOfs, fp );
+ Putword( Width, fp );
+ Putword( Height, fp );
+
+ /*
+ * Write out whether or not the image is interlaced
+ */
+ if( Interlace )
+ gdPutC( 0x40, fp );
+ else
+ gdPutC( 0x00, fp );
+
+ /*
+ * Write out the initial code size
+ */
+ gdPutC( InitCodeSize, fp );
+
+ /*
+ * Go and actually compress the data
+ */
+ GIFcompress( InitCodeSize+1, fp, im, Background );
+
+ /*
+ * Write out a Zero-length packet (to end the series)
+ */
+ gdPutC( 0, fp );
+
+ /*
+ * Write the GIF file terminator
+ */
+ gdPutC( ';', fp );
+}
+
+/* Write out a word to the GIF file */
+/*static void */
+/*Putword(int w, gdIOCtx *fp) */
+/*{ */
+/* fputc( w & 0xff, fp ); */
+/* fputc( (w / 256) & 0xff, fp ); */
+/*} */
+
+#define GIFBITS 12
+
+/*-----------------------------------------------------------------------
+ *
+ * miGIF Compression - mouse and ivo's GIF-compatible compression
+ *
+ * -run length encoding compression routines-
+ *
+ * Copyright (C) 1998 Hutchison Avenue Software Corporation
+ * http://www.hasc.com
+ * info@hasc.com
+ *
+ * Permission to use, copy, modify, and distribute this software and its
+ * documentation for any purpose and without fee is hereby granted, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation. This software is provided "AS IS." The Hutchison Avenue
+ * Software Corporation disclaims all warranties, either express or implied,
+ * including but not limited to implied warranties of merchantability and
+ * fitness for a particular purpose, with respect to this code and accompanying
+ * documentation.
+ *
+ * The miGIF compression routines do not, strictly speaking, generate files
+ * conforming to the GIF spec, since the image data is not LZW-compressed
+ * (this is the point: in order to avoid transgression of the Unisys patent
+ * on the LZW algorithm.) However, miGIF generates data streams that any
+ * reasonably sane LZW decompresser will decompress to what we want.
+ *
+ * miGIF compression uses run length encoding. It compresses horizontal runs
+ * of pixels of the same color. This type of compression gives good results
+ * on images with many runs, for example images with lines, text and solid
+ * shapes on a solid-colored background. It gives little or no compression
+ * on images with few runs, for example digital or scanned photos.
+ *
+ * der Mouse
+ * mouse@rodents.montreal.qc.ca
+ * 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B
+ *
+ * ivo@hasc.com
+ *
+ * The Graphics Interchange Format(c) is the Copyright property of
+ * CompuServe Incorporated. GIF(sm) is a Service Mark property of
+ * CompuServe Incorporated.
+ *
+ */
+
+static int rl_pixel;
+static int rl_basecode;
+static int rl_count;
+static int rl_table_pixel;
+static int rl_table_max;
+static int just_cleared;
+static int out_bits;
+static int out_bits_init;
+static int out_count;
+static int out_bump;
+static int out_bump_init;
+static int out_clear;
+static int out_clear_init;
+static int max_ocodes;
+static int code_clear;
+static int code_eof;
+static unsigned int obuf;
+static int obits;
+static gdIOCtx *ofile;
+static unsigned char oblock[256];
+static int oblen;
+
+/* Used only when debugging GIF compression code */
+/* #define DEBUGGING_ENVARS */
+
+#ifdef DEBUGGING_ENVARS
+
+static int verbose_set = 0;
+static int verbose;
+#define VERBOSE (verbose_set?verbose:set_verbose())
+
+static int set_verbose(void)
+{
+ verbose = !!getenv("GIF_VERBOSE");
+ verbose_set = 1;
+ return(verbose);
+}
+
+#else
+
+#define VERBOSE 0
+
+#endif
+
+
+static const char *binformat(unsigned int v, int nbits)
+{
+ static char bufs[8][64];
+ static int bhand = 0;
+ unsigned int bit;
+ int bno;
+ char *bp;
+
+ bhand --;
+ if (bhand < 0) bhand = (sizeof(bufs)/sizeof(bufs[0]))-1;
+ bp = &bufs[bhand][0];
+ for (bno=nbits-1,bit=1U<<bno;bno>=0;bno--,bit>>=1)
+ { *bp++ = (v & bit) ? '1' : '0';
+ if (((bno&3) == 0) && (bno != 0)) *bp++ = '.';
+ }
+ *bp = '\0';
+ return(&bufs[bhand][0]);
+}
+
+static void write_block(void)
+{
+ int i;
+
+ if (VERBOSE)
+ { printf("write_block %d:",oblen);
+ for (i=0;i<oblen;i++) printf(" %02x",oblock[i]);
+ printf("\n");
+ }
+ gdPutC(oblen,ofile);
+ gdPutBuf(&oblock[0],oblen,ofile);
+ oblen = 0;
+}
+
+static void block_out(unsigned char c)
+{
+ if (VERBOSE) printf("block_out %s\n",binformat(c,8));
+ oblock[oblen++] = c;
+ if (oblen >= 255) write_block();
+}
+
+static void block_flush(void)
+{
+ if (VERBOSE) printf("block_flush\n");
+ if (oblen > 0) write_block();
+}
+
+static void output(int val)
+{
+ if (VERBOSE) printf("output %s [%s %d %d]\n",binformat(val,out_bits),binformat(obuf,obits),obits,out_bits);
+ obuf |= val << obits;
+ obits += out_bits;
+ while (obits >= 8)
+ { block_out(obuf&0xff);
+ obuf >>= 8;
+ obits -= 8;
+ }
+ if (VERBOSE) printf("output leaving [%s %d]\n",binformat(obuf,obits),obits);
+}
+
+static void output_flush(void)
+{
+ if (VERBOSE) printf("output_flush\n");
+ if (obits > 0) block_out(obuf);
+ block_flush();
+}
+
+static void did_clear(void)
+{
+ if (VERBOSE) printf("did_clear\n");
+ out_bits = out_bits_init;
+ out_bump = out_bump_init;
+ out_clear = out_clear_init;
+ out_count = 0;
+ rl_table_max = 0;
+ just_cleared = 1;
+}
+
+static void output_plain(int c)
+{
+ if (VERBOSE) printf("output_plain %s\n",binformat(c,out_bits));
+ just_cleared = 0;
+ output(c);
+ out_count ++;
+ if (out_count >= out_bump)
+ { out_bits ++;
+ out_bump += 1 << (out_bits - 1);
+ }
+ if (out_count >= out_clear)
+ { output(code_clear);
+ did_clear();
+ }
+}
+
+static unsigned int isqrt(unsigned int x)
+{
+ unsigned int r;
+ unsigned int v;
+
+ if (x < 2) return(x);
+ for (v=x,r=1;v;v>>=2,r<<=1) ;
+ while (1)
+ { v = ((x / r) + r) / 2;
+ if ((v == r) || (v == r+1)) return(r);
+ r = v;
+ }
+}
+
+static unsigned int compute_triangle_count(unsigned int count, unsigned int nrepcodes)
+{
+ unsigned int perrep;
+ unsigned int cost;
+
+ cost = 0;
+ perrep = (nrepcodes * (nrepcodes+1)) / 2;
+ while (count >= perrep)
+ { cost += nrepcodes;
+ count -= perrep;
+ }
+ if (count > 0)
+ { unsigned int n;
+ n = isqrt(count);
+ while ((n*(n+1)) >= 2*count) n --;
+ while ((n*(n+1)) < 2*count) n ++;
+ cost += n;
+ }
+ return(cost);
+}
+
+static void max_out_clear(void)
+{
+ out_clear = max_ocodes;
+}
+
+static void reset_out_clear(void)
+{
+ out_clear = out_clear_init;
+ if (out_count >= out_clear)
+ { output(code_clear);
+ did_clear();
+ }
+}
+
+static void rl_flush_fromclear(int count)
+{
+ int n;
+
+ if (VERBOSE) printf("rl_flush_fromclear %d\n",count);
+ max_out_clear();
+ rl_table_pixel = rl_pixel;
+ n = 1;
+ while (count > 0)
+ { if (n == 1)
+ { rl_table_max = 1;
+ output_plain(rl_pixel);
+ count --;
+ }
+ else if (count >= n)
+ { rl_table_max = n;
+ output_plain(rl_basecode+n-2);
+ count -= n;
+ }
+ else if (count == 1)
+ { rl_table_max ++;
+ output_plain(rl_pixel);
+ count = 0;
+ }
+ else
+ { rl_table_max ++;
+ output_plain(rl_basecode+count-2);
+ count = 0;
+ }
+ if (out_count == 0) n = 1; else n ++;
+ }
+ reset_out_clear();
+ if (VERBOSE) printf("rl_flush_fromclear leaving table_max=%d\n",rl_table_max);
+}
+
+static void rl_flush_clearorrep(int count)
+{
+ int withclr;
+
+ if (VERBOSE) printf("rl_flush_clearorrep %d\n",count);
+ withclr = 1 + compute_triangle_count(count,max_ocodes);
+ if (withclr < count)
+ { output(code_clear);
+ did_clear();
+ rl_flush_fromclear(count);
+ }
+ else
+ { for (;count>0;count--) output_plain(rl_pixel);
+ }
+}
+
+static void rl_flush_withtable(int count)
+{
+ int repmax;
+ int repleft;
+ int leftover;
+
+ if (VERBOSE) printf("rl_flush_withtable %d\n",count);
+ repmax = count / rl_table_max;
+ leftover = count % rl_table_max;
+ repleft = (leftover ? 1 : 0);
+ if (out_count+repmax+repleft > max_ocodes)
+ { repmax = max_ocodes - out_count;
+ leftover = count - (repmax * rl_table_max);
+ repleft = 1 + compute_triangle_count(leftover,max_ocodes);
+ }
+ if (VERBOSE) printf("rl_flush_withtable repmax=%d leftover=%d repleft=%d\n",repmax,leftover,repleft);
+ if (1+compute_triangle_count(count,max_ocodes) < repmax+repleft)
+ { output(code_clear);
+ did_clear();
+ rl_flush_fromclear(count);
+ return;
+ }
+ max_out_clear();
+ for (;repmax>0;repmax--) output_plain(rl_basecode+rl_table_max-2);
+ if (leftover)
+ { if (just_cleared)
+ { rl_flush_fromclear(leftover);
+ }
+ else if (leftover == 1)
+ { output_plain(rl_pixel);
+ }
+ else
+ { output_plain(rl_basecode+leftover-2);
+ }
+ }
+ reset_out_clear();
+}
+
+static void rl_flush(void)
+{
+ /* UNUSED int table_reps; */
+ /* UNUSED int table_extra; */
+
+ if (VERBOSE) printf("rl_flush [ %d %d\n",rl_count,rl_pixel);
+ if (rl_count == 1)
+ { output_plain(rl_pixel);
+ rl_count = 0;
+ if (VERBOSE) printf("rl_flush ]\n");
+ return;
+ }
+ if (just_cleared)
+ { rl_flush_fromclear(rl_count);
+ }
+ else if ((rl_table_max < 2) || (rl_table_pixel != rl_pixel))
+ { rl_flush_clearorrep(rl_count);
+ }
+ else
+ { rl_flush_withtable(rl_count);
+ }
+ if (VERBOSE) printf("rl_flush ]\n");
+ rl_count = 0;
+}
+
+static void GIFcompress(int init_bits, gdIOCtx *outfile, gdImagePtr im, int background)
+{
+ int c;
+
+ ofile = outfile;
+ obuf = 0;
+ obits = 0;
+ oblen = 0;
+ code_clear = 1 << (init_bits - 1);
+ code_eof = code_clear + 1;
+ rl_basecode = code_eof + 1;
+ out_bump_init = (1 << (init_bits - 1)) - 1;
+ /* for images with a lot of runs, making out_clear_init larger will
+ give better compression. */
+ out_clear_init = (init_bits <= 3) ? 9 : (out_bump_init-1);
+#ifdef DEBUGGING_ENVARS
+ { const char *ocienv;
+ ocienv = getenv("GIF_OUT_CLEAR_INIT");
+ if (ocienv)
+ { out_clear_init = atoi(ocienv);
+ if (VERBOSE) printf("[overriding out_clear_init to %d]\n",out_clear_init);
+ }
+ }
+#endif
+ out_bits_init = init_bits;
+ max_ocodes = (1 << GIFBITS) - ((1 << (out_bits_init - 1)) + 3);
+ did_clear();
+ output(code_clear);
+ rl_count = 0;
+ while (1)
+ { c = GIFNextPixel(im);
+ if ((rl_count > 0) && (c != rl_pixel)) rl_flush();
+ if (c == EOF) break;
+ if (rl_pixel == c)
+ { rl_count ++;
+ }
+ else
+ { rl_pixel = c;
+ rl_count = 1;
+ }
+ }
+ output(code_eof);
+ output_flush();
+}
+
+/*-----------------------------------------------------------------------
+ *
+ * End of miGIF section - See copyright notice at start of section.
+ *
+ *-----------------------------------------------------------------------
+*/
+
+/******************************************************************************
+ *
+ * GIF Specific routines
+ *
+ ******************************************************************************/
+
+/*
+ * Number of characters so far in this 'packet'
+ */
+static int a_count;
+
+/*
+ * Set up the 'byte output' routine
+ */
+
+/* UNUSED
+* static void
+* char_init(void)
+* {
+* a_count = 0;
+* }
+*/
+
+/*
+ * Define the storage for the packet accumulator
+ */
+
+/* UNUSED static char accum[ 256 ]; */
+
+static void init_statics(void) {
+ /* Some of these are properly initialized later. What I'm doing
+ here is making sure code that depends on C's initialization
+ of statics doesn't break when the code gets called more
+ than once. */
+ Width = 0;
+ Height = 0;
+ curx = 0;
+ cury = 0;
+ CountDown = 0;
+ Pass = 0;
+ Interlace = 0;
+ a_count = 0;
+}
+
+
+/* +-------------------------------------------------------------------+ */
+/* | Copyright 1990, 1991, 1993, David Koblas. (koblas@netcom.com) | */
+/* | Permission to use, copy, modify, and distribute this software | */
+/* | and its documentation for any purpose and without fee is hereby | */
+/* | granted, provided that the above copyright notice appear in all | */
+/* | copies and that both that copyright notice and this permission | */
+/* | notice appear in supporting documentation. This software is | */
+/* | provided "as is" without express or implied warranty. | */
+/* +-------------------------------------------------------------------+ */
+
diff --git a/graphics/gd/files/gd_gif_in.c b/graphics/gd/files/gd_gif_in.c
index 6e779c820963..fc1b587cc8b4 100644
--- a/graphics/gd/files/gd_gif_in.c
+++ b/graphics/gd/files/gd_gif_in.c
@@ -76,6 +76,18 @@ static void ReadImage (gdImagePtr im, gdIOCtx *fd, int len, int height, unsigned
int ZeroDataBlock;
+gdImagePtr gdImageCreateFromGifSource(gdSourcePtr inSource)
+{
+ gdIOCtx *in = gdNewSSCtx(inSource, NULL);
+ gdImagePtr im;
+
+ im = gdImageCreateFromGifCtx(in);
+
+ in->gd_free(in);
+
+ return im;
+}
+
gdImagePtr
gdImageCreateFromGif(FILE *fdFile)
{
@@ -84,7 +96,7 @@ gdImageCreateFromGif(FILE *fdFile)
im = gdImageCreateFromGifCtx(fd);
- fd->free(fd);
+ fd->gd_free(fd);
return im;
}
@@ -92,7 +104,7 @@ gdImageCreateFromGif(FILE *fdFile)
gdImagePtr
gdImageCreateFromGifCtx(gdIOCtxPtr fd)
{
- int imageNumber;
+/* 1.4 int imageNumber; */
int BitPixel;
int ColorResolution;
int Background;
diff --git a/graphics/gd/files/gd_gif_out.c b/graphics/gd/files/gd_gif_out.c
new file mode 100644
index 000000000000..bc8a4f06d54b
--- /dev/null
+++ b/graphics/gd/files/gd_gif_out.c
@@ -0,0 +1,44 @@
+#include <stdio.h>
+#include <math.h>
+#include <string.h>
+#include <stdlib.h>
+#include "gd.h"
+
+/*
+** Wrapper functions for GIF output.
+*/
+
+void gdImageGifToSink(gdImagePtr im, gdSinkPtr outSink)
+{
+ gdIOCtx *out = gdNewSSCtx(NULL,outSink);
+ gdImageGifCtx(im, out);
+ out->gd_free(out);
+}
+
+void gdImageGifCtx(gdImagePtr im, gdIOCtx *out)
+{
+#ifdef LZW_LICENCED
+ gdImageLzwCtx(im, out);
+#else
+ gdImageBigGifCtx(im, out);
+#endif
+}
+
+void gdImageGif(gdImagePtr im, FILE *outFile)
+{
+#ifdef LZW_LICENCED
+ gdImageLzw(im, outFile);
+#else
+ gdImageBigGif(im, outFile);
+#endif
+}
+
+void* gdImageGifPtr(gdImagePtr im, int *size)
+{
+#ifdef LZW_LICENCED
+ return gdImageLzwPtr(im, size);
+#else
+ return gdImageBigGifPtr(im, size);
+#endif
+}
+
diff --git a/graphics/gd/files/gd_lzw_out.c b/graphics/gd/files/gd_lzw_out.c
new file mode 100644
index 000000000000..ee130c5e5a38
--- /dev/null
+++ b/graphics/gd/files/gd_lzw_out.c
@@ -0,0 +1,795 @@
+#include <stdio.h>
+#include <math.h>
+#include <string.h>
+#include <stdlib.h>
+#include "gd.h"
+
+/* Code drawn from ppmtogif.c, from the pbmplus package
+**
+** Based on GIFENCOD by David Rowley <mgardi@watdscu.waterloo.edu>. A
+** Lempel-Zim compression based on "compress".
+**
+** Modified by Marcel Wijkstra <wijkstra@fwi.uva.nl>
+**
+** Copyright (C) 1989 by Jef Poskanzer.
+**
+** Permission to use, copy, modify, and distribute this software and its
+** documentation for any purpose and without fee is hereby granted, provided
+** that the above copyright notice appear in all copies and that both that
+** copyright notice and this permission notice appear in supporting
+** documentation. This software is provided "as is" without express or
+** implied warranty.
+**
+** The Graphics Interchange Format(c) is the Copyright property of
+** CompuServe Incorporated. GIF(sm) is a Service Mark property of
+** CompuServe Incorporated.
+*/
+
+/*
+ * a code_int must be able to hold 2**GIFBITS values of type int, and also -1
+ */
+typedef int code_int;
+
+#ifdef SIGNED_COMPARE_SLOW
+typedef unsigned long int count_int;
+typedef unsigned short int count_short;
+#else /*SIGNED_COMPARE_SLOW*/
+typedef long int count_int;
+#endif /*SIGNED_COMPARE_SLOW*/
+
+static int colorstobpp(int colors);
+static void BumpPixel (void);
+static int GIFNextPixel (gdImagePtr im);
+static void GIFEncode (gdIOCtx *fp, int GWidth, int GHeight, int GInterlace, int Background, int Transparent, int BitsPerPixel, int *Red, int *Green, int *Blue, gdImagePtr im);
+/*static void Putword (int w, gdIOCtx *fp); */
+static void compress (int init_bits, gdIOCtx *outfile, gdImagePtr im);
+static void output (code_int code);
+static void cl_block (void);
+static void cl_hash (register count_int hsize);
+static void char_init (void);
+static void char_out (int c);
+static void flush_char (void);
+/* Allows for reuse */
+static void init_statics(void);
+
+void gdImageLzwCtx(gdImagePtr im, gdIOCtx *out)
+{
+ int interlace, transparent, BitsPerPixel;
+
+ interlace = im->interlace;
+ transparent = im->transparent;
+
+ BitsPerPixel = colorstobpp(im->colorsTotal);
+ /* Clear any old values in statics strewn through the GIF code */
+ init_statics();
+ /* All set, let's do it. */
+ GIFEncode(
+ out, im->sx, im->sy, interlace, 0, transparent, BitsPerPixel,
+ im->red, im->green, im->blue, im);
+}
+
+void gdImageLzw(gdImagePtr im, FILE *outFile)
+{
+ gdIOCtx *out = gdNewFileCtx(outFile);
+ gdImageLzwCtx(im, out);
+ out->gd_free(out);
+}
+
+void* gdImageLzwPtr(gdImagePtr im, int *size)
+{
+ void *rv;
+ gdIOCtx *out = gdNewDynamicCtx(2048, NULL);
+ gdImageLzwCtx(im, out);
+ rv = gdDPExtractData(out,size);
+ out->gd_free(out);
+ return rv;
+}
+
+
+
+static int
+colorstobpp(int colors)
+{
+ int bpp = 0;
+
+ if ( colors <= 2 )
+ bpp = 1;
+ else if ( colors <= 4 )
+ bpp = 2;
+ else if ( colors <= 8 )
+ bpp = 3;
+ else if ( colors <= 16 )
+ bpp = 4;
+ else if ( colors <= 32 )
+ bpp = 5;
+ else if ( colors <= 64 )
+ bpp = 6;
+ else if ( colors <= 128 )
+ bpp = 7;
+ else if ( colors <= 256 )
+ bpp = 8;
+ return bpp;
+ }
+
+/*****************************************************************************
+ *
+ * GIFENCODE.C - GIF Image compression interface
+ *
+ * GIFEncode( FName, GHeight, GWidth, GInterlace, Background, Transparent,
+ * BitsPerPixel, Red, Green, Blue, gdImagePtr )
+ *
+ *****************************************************************************/
+
+#define TRUE 1
+#define FALSE 0
+
+static int Width, Height;
+static int curx, cury;
+static long CountDown;
+static int Pass = 0;
+static int Interlace;
+
+/*
+ * Bump the 'curx' and 'cury' to point to the next pixel
+ */
+static void
+BumpPixel(void)
+{
+ /*
+ * Bump the current X position
+ */
+ ++curx;
+
+ /*
+ * If we are at the end of a scan line, set curx back to the beginning
+ * If we are interlaced, bump the cury to the appropriate spot,
+ * otherwise, just increment it.
+ */
+ if( curx == Width ) {
+ curx = 0;
+
+ if( !Interlace )
+ ++cury;
+ else {
+ switch( Pass ) {
+
+ case 0:
+ cury += 8;
+ if( cury >= Height ) {
+ ++Pass;
+ cury = 4;
+ }
+ break;
+
+ case 1:
+ cury += 8;
+ if( cury >= Height ) {
+ ++Pass;
+ cury = 2;
+ }
+ break;
+
+ case 2:
+ cury += 4;
+ if( cury >= Height ) {
+ ++Pass;
+ cury = 1;
+ }
+ break;
+
+ case 3:
+ cury += 2;
+ break;
+ }
+ }
+ }
+}
+
+/*
+ * Return the next pixel from the image
+ */
+static int
+GIFNextPixel(gdImagePtr im)
+{
+ int r;
+
+ if( CountDown == 0 )
+ return EOF;
+
+ --CountDown;
+
+ r = gdImageGetPixel(im, curx, cury);
+
+ BumpPixel();
+
+ return r;
+}
+
+/* public */
+
+static void
+GIFEncode(gdIOCtx *fp, int GWidth, int GHeight, int GInterlace, int Background, int Transparent, int BitsPerPixel, int *Red, int *Green, int *Blue, gdImagePtr im)
+{
+ int B;
+ int RWidth, RHeight;
+ int LeftOfs, TopOfs;
+ int Resolution;
+ int ColorMapSize;
+ int InitCodeSize;
+ int i;
+
+ Interlace = GInterlace;
+
+ ColorMapSize = 1 << BitsPerPixel;
+
+ RWidth = Width = GWidth;
+ RHeight = Height = GHeight;
+ LeftOfs = TopOfs = 0;
+
+ Resolution = BitsPerPixel;
+
+ /*
+ * Calculate number of bits we are expecting
+ */
+ CountDown = (long)Width * (long)Height;
+
+ /*
+ * Indicate which pass we are on (if interlace)
+ */
+ Pass = 0;
+
+ /*
+ * The initial code size
+ */
+ if( BitsPerPixel <= 1 )
+ InitCodeSize = 2;
+ else
+ InitCodeSize = BitsPerPixel;
+
+ /*
+ * Set up the current x and y position
+ */
+ curx = cury = 0;
+
+ /*
+ * Write the Magic header
+ */
+ gdPutBuf( Transparent < 0 ? "GIF87a" : "GIF89a", 6, fp );
+
+ /*
+ * Write out the screen width and height
+ */
+ Putword( RWidth, fp );
+ Putword( RHeight, fp );
+
+ /*
+ * Indicate that there is a global colour map
+ */
+ B = 0x80; /* Yes, there is a color map */
+
+ /*
+ * OR in the resolution
+ */
+ B |= (Resolution - 1) << 5;
+
+ /*
+ * OR in the Bits per Pixel
+ */
+ B |= (BitsPerPixel - 1);
+
+ /*
+ * Write it out
+ */
+ gdPutC( B, fp );
+
+ /*
+ * Write out the Background colour
+ */
+ gdPutC( Background, fp );
+
+ /*
+ * Byte of 0's (future expansion)
+ */
+ gdPutC( 0, fp );
+
+ /*
+ * Write out the Global Colour Map
+ */
+ for( i=0; i<ColorMapSize; ++i ) {
+ gdPutC( Red[i], fp );
+ gdPutC( Green[i], fp );
+ gdPutC( Blue[i], fp );
+ }
+
+ /*
+ * Write out extension for transparent colour index, if necessary.
+ */
+ if ( Transparent >= 0 ) {
+ gdPutC( '!', fp );
+ gdPutC( 0xf9, fp );
+ gdPutC( 4, fp );
+ gdPutC( 1, fp );
+ gdPutC( 0, fp );
+ gdPutC( 0, fp );
+ gdPutC( (unsigned char) Transparent, fp );
+ gdPutC( 0, fp );
+ }
+
+ /*
+ * Write an Image separator
+ */
+ gdPutC( ',', fp );
+
+ /*
+ * Write the Image header
+ */
+
+ Putword( LeftOfs, fp );
+ Putword( TopOfs, fp );
+ Putword( Width, fp );
+ Putword( Height, fp );
+
+ /*
+ * Write out whether or not the image is interlaced
+ */
+ if( Interlace )
+ gdPutC( 0x40, fp );
+ else
+ gdPutC( 0x00, fp );
+
+ /*
+ * Write out the initial code size
+ */
+ gdPutC( InitCodeSize, fp );
+
+ /*
+ * Go and actually compress the data
+ */
+ compress( InitCodeSize+1, fp, im );
+
+ /*
+ * Write out a Zero-length packet (to end the series)
+ */
+ gdPutC( 0, fp );
+
+ /*
+ * Write the GIF file terminator
+ */
+ gdPutC( ';', fp );
+}
+
+/* */
+/* * Write out a word to the GIF file */
+/* */
+/*static void */
+/*Putword(int w, FILE *fp) */
+/*{ */
+/* fputc( w & 0xff, fp ); */
+/* fputc( (w / 256) & 0xff, fp ); */
+/*} */
+
+
+/***************************************************************************
+ *
+ * GIFCOMPR.C - GIF Image compression routines
+ *
+ * Lempel-Ziv compression based on 'compress'. GIF modifications by
+ * David Rowley (mgardi@watdcsu.waterloo.edu)
+ *
+ ***************************************************************************/
+
+/*
+ * General DEFINEs
+ */
+
+#define GIFBITS 12
+
+#define HSIZE 5003 /* 80% occupancy */
+
+#ifdef NO_UCHAR
+ typedef char char_type;
+#else /*NO_UCHAR*/
+ typedef unsigned char char_type;
+#endif /*NO_UCHAR*/
+
+/*
+ *
+ * GIF Image compression - modified 'compress'
+ *
+ * Based on: compress.c - File compression ala IEEE Computer, June 1984.
+ *
+ * By Authors: Spencer W. Thomas (decvax!harpo!utah-cs!utah-gr!thomas)
+ * Jim McKie (decvax!mcvax!jim)
+ * Steve Davies (decvax!vax135!petsd!peora!srd)
+ * Ken Turkowski (decvax!decwrl!turtlevax!ken)
+ * James A. Woods (decvax!ihnp4!ames!jaw)
+ * Joe Orost (decvax!vax135!petsd!joe)
+ *
+ */
+#include <ctype.h>
+
+#define ARGVAL() (*++(*argv) || (--argc && *++argv))
+
+static int n_bits; /* number of bits/code */
+static int maxbits = GIFBITS; /* user settable max # bits/code */
+static code_int maxcode; /* maximum code, given n_bits */
+static code_int maxmaxcode = (code_int)1 << GIFBITS; /* should NEVER generate this code */
+#ifdef COMPATIBLE /* But wrong! */
+# define MAXCODE(n_bits) ((code_int) 1 << (n_bits) - 1)
+#else /*COMPATIBLE*/
+# define MAXCODE(n_bits) (((code_int) 1 << (n_bits)) - 1)
+#endif /*COMPATIBLE*/
+
+static count_int htab [HSIZE];
+static unsigned short codetab [HSIZE];
+#define HashTabOf(i) htab[i]
+#define CodeTabOf(i) codetab[i]
+
+static code_int hsize = HSIZE; /* for dynamic table sizing */
+
+/*
+ * To save much memory, we overlay the table used by compress() with those
+ * used by decompress(). The tab_prefix table is the same size and type
+ * as the codetab. The tab_suffix table needs 2**GIFBITS characters. We
+ * get this from the beginning of htab. The output stack uses the rest
+ * of htab, and contains characters. There is plenty of room for any
+ * possible stack (stack used to be 8000 characters).
+ */
+
+#define tab_prefixof(i) CodeTabOf(i)
+#define tab_suffixof(i) ((char_type*)(htab))[i]
+#define de_stack ((char_type*)&tab_suffixof((code_int)1<<GIFBITS))
+
+static code_int free_ent = 0; /* first unused entry */
+
+/*
+ * block compression parameters -- after all codes are used up,
+ * and compression rate changes, start over.
+ */
+static int clear_flg = 0;
+
+static int offset;
+static long int in_count = 1; /* length of input */
+static long int out_count = 0; /* # of codes output (for debugging) */
+
+/*
+ * compress stdin to stdout
+ *
+ * Algorithm: use open addressing double hashing (no chaining) on the
+ * prefix code / next character combination. We do a variant of Knuth's
+ * algorithm D (vol. 3, sec. 6.4) along with G. Knott's relatively-prime
+ * secondary probe. Here, the modular division first probe is gives way
+ * to a faster exclusive-or manipulation. Also do block compression with
+ * an adaptive reset, whereby the code table is cleared when the compression
+ * ratio decreases, but after the table fills. The variable-length output
+ * codes are re-sized at this point, and a special CLEAR code is generated
+ * for the decompressor. Late addition: construct the table according to
+ * file size for noticeable speed improvement on small files. Please direct
+ * questions about this implementation to ames!jaw.
+ */
+
+static int g_init_bits;
+static gdIOCtx* g_outfile;
+
+static int ClearCode;
+static int EOFCode;
+
+static void
+compress(int init_bits, gdIOCtx *outfile, gdImagePtr im)
+{
+ register long fcode;
+ register code_int i /* = 0 */;
+ register int c;
+ register code_int ent;
+ register code_int disp;
+ register code_int hsize_reg;
+ register int hshift;
+
+ /*
+ * Set up the globals: g_init_bits - initial number of bits
+ * g_outfile - pointer to output file
+ */
+ g_init_bits = init_bits;
+ g_outfile = outfile;
+
+ /*
+ * Set up the necessary values
+ */
+ offset = 0;
+ out_count = 0;
+ clear_flg = 0;
+ in_count = 1;
+ maxcode = MAXCODE(n_bits = g_init_bits);
+
+ ClearCode = (1 << (init_bits - 1));
+ EOFCode = ClearCode + 1;
+ free_ent = ClearCode + 2;
+
+ char_init();
+
+ ent = GIFNextPixel( im );
+
+ hshift = 0;
+ for ( fcode = (long) hsize; fcode < 65536L; fcode *= 2L )
+ ++hshift;
+ hshift = 8 - hshift; /* set hash code range bound */
+
+ hsize_reg = hsize;
+ cl_hash( (count_int) hsize_reg); /* clear hash table */
+
+ output( (code_int)ClearCode );
+
+#ifdef SIGNED_COMPARE_SLOW
+ while ( (c = GIFNextPixel( im )) != (unsigned) EOF ) {
+#else /*SIGNED_COMPARE_SLOW*/
+ while ( (c = GIFNextPixel( im )) != EOF ) { /* } */
+#endif /*SIGNED_COMPARE_SLOW*/
+
+ ++in_count;
+
+ fcode = (long) (((long) c << maxbits) + ent);
+ i = (((code_int)c << hshift) ^ ent); /* xor hashing */
+
+ if ( HashTabOf (i) == fcode ) {
+ ent = CodeTabOf (i);
+ continue;
+ } else if ( (long)HashTabOf (i) < 0 ) /* empty slot */
+ goto nomatch;
+ disp = hsize_reg - i; /* secondary hash (after G. Knott) */
+ if ( i == 0 )
+ disp = 1;
+probe:
+ if ( (i -= disp) < 0 )
+ i += hsize_reg;
+
+ if ( HashTabOf (i) == fcode ) {
+ ent = CodeTabOf (i);
+ continue;
+ }
+ if ( (long)HashTabOf (i) > 0 )
+ goto probe;
+nomatch:
+ output ( (code_int) ent );
+ ++out_count;
+ ent = c;
+#ifdef SIGNED_COMPARE_SLOW
+ if ( (unsigned) free_ent < (unsigned) maxmaxcode) {
+#else /*SIGNED_COMPARE_SLOW*/
+ if ( free_ent < maxmaxcode ) { /* } */
+#endif /*SIGNED_COMPARE_SLOW*/
+ CodeTabOf (i) = free_ent++; /* code -> hashtable */
+ HashTabOf (i) = fcode;
+ } else
+ cl_block();
+ }
+ /*
+ * Put out the final code.
+ */
+ output( (code_int)ent );
+ ++out_count;
+ output( (code_int) EOFCode );
+}
+
+/*****************************************************************
+ * TAG( output )
+ *
+ * Output the given code.
+ * Inputs:
+ * code: A n_bits-bit integer. If == -1, then EOF. This assumes
+ * that n_bits =< (long)wordsize - 1.
+ * Outputs:
+ * Outputs code to the file.
+ * Assumptions:
+ * Chars are 8 bits long.
+ * Algorithm:
+ * Maintain a GIFBITS character long buffer (so that 8 codes will
+ * fit in it exactly). Use the VAX insv instruction to insert each
+ * code in turn. When the buffer fills up empty it and start over.
+ */
+
+static unsigned long cur_accum = 0;
+static int cur_bits = 0;
+
+static unsigned long masks[] = { 0x0000, 0x0001, 0x0003, 0x0007, 0x000F,
+ 0x001F, 0x003F, 0x007F, 0x00FF,
+ 0x01FF, 0x03FF, 0x07FF, 0x0FFF,
+ 0x1FFF, 0x3FFF, 0x7FFF, 0xFFFF };
+
+static void
+output(code_int code)
+{
+ cur_accum &= masks[ cur_bits ];
+
+ if( cur_bits > 0 )
+ cur_accum |= ((long)code << cur_bits);
+ else
+ cur_accum = code;
+
+ cur_bits += n_bits;
+
+ while( cur_bits >= 8 ) {
+ char_out( (unsigned int)(cur_accum & 0xff) );
+ cur_accum >>= 8;
+ cur_bits -= 8;
+ }
+
+ /*
+ * If the next entry is going to be too big for the code size,
+ * then increase it, if possible.
+ */
+ if ( free_ent > maxcode || clear_flg ) {
+
+ if( clear_flg ) {
+
+ maxcode = MAXCODE (n_bits = g_init_bits);
+ clear_flg = 0;
+
+ } else {
+
+ ++n_bits;
+ if ( n_bits == maxbits )
+ maxcode = maxmaxcode;
+ else
+ maxcode = MAXCODE(n_bits);
+ }
+ }
+
+ if( code == EOFCode ) {
+ /*
+ * At EOF, write the rest of the buffer.
+ */
+ while( cur_bits > 0 ) {
+ char_out( (unsigned int)(cur_accum & 0xff) );
+ cur_accum >>= 8;
+ cur_bits -= 8;
+ }
+
+ flush_char();
+
+/* fflush( g_outfile ); */
+/* */
+/* if( ferror( g_outfile ) ) */
+/* return; */
+ }
+}
+
+/*
+ * Clear out the hash table
+ */
+static void
+cl_block (void) /* table clear for block compress */
+{
+
+ cl_hash ( (count_int) hsize );
+ free_ent = ClearCode + 2;
+ clear_flg = 1;
+
+ output( (code_int)ClearCode );
+}
+
+static void
+cl_hash(register count_int hsize) /* reset code table */
+
+{
+
+ register count_int *htab_p = htab+hsize;
+
+ register long i;
+ register long m1 = -1;
+
+ i = hsize - 16;
+ do { /* might use Sys V memset(3) here */
+ *(htab_p-16) = m1;
+ *(htab_p-15) = m1;
+ *(htab_p-14) = m1;
+ *(htab_p-13) = m1;
+ *(htab_p-12) = m1;
+ *(htab_p-11) = m1;
+ *(htab_p-10) = m1;
+ *(htab_p-9) = m1;
+ *(htab_p-8) = m1;
+ *(htab_p-7) = m1;
+ *(htab_p-6) = m1;
+ *(htab_p-5) = m1;
+ *(htab_p-4) = m1;
+ *(htab_p-3) = m1;
+ *(htab_p-2) = m1;
+ *(htab_p-1) = m1;
+ htab_p -= 16;
+ } while ((i -= 16) >= 0);
+
+ for ( i += 16; i > 0; --i )
+ *--htab_p = m1;
+}
+
+/******************************************************************************
+ *
+ * GIF Specific routines
+ *
+ ******************************************************************************/
+
+/*
+ * Number of characters so far in this 'packet'
+ */
+static int a_count;
+
+/*
+ * Set up the 'byte output' routine
+ */
+static void
+char_init(void)
+{
+ a_count = 0;
+}
+
+/*
+ * Define the storage for the packet accumulator
+ */
+static char accum[ 256 ];
+
+/*
+ * Add a character to the end of the current packet, and if it is 254
+ * characters, flush the packet to disk.
+ */
+static void
+char_out(int c)
+{
+ accum[ a_count++ ] = c;
+ if( a_count >= 254 )
+ flush_char();
+}
+
+/*
+ * Flush the packet to disk, and reset the accumulator
+ */
+static void
+flush_char(void)
+{
+ if( a_count > 0 ) {
+ gdPutC( a_count, g_outfile );
+ gdPutBuf( accum, a_count, g_outfile );
+ a_count = 0;
+ }
+}
+
+static void init_statics(void) {
+ /* Some of these are properly initialized later. What I'm doing
+ here is making sure code that depends on C's initialization
+ of statics doesn't break when the code gets called more
+ than once. */
+ Width = 0;
+ Height = 0;
+ curx = 0;
+ cury = 0;
+ CountDown = 0;
+ Pass = 0;
+ Interlace = 0;
+ a_count = 0;
+ cur_accum = 0;
+ cur_bits = 0;
+ g_init_bits = 0;
+ g_outfile = 0;
+ ClearCode = 0;
+ EOFCode = 0;
+ free_ent = 0;
+ clear_flg = 0;
+ offset = 0;
+ in_count = 1;
+ out_count = 0;
+ hsize = HSIZE;
+ n_bits = 0;
+ maxbits = GIFBITS;
+ maxcode = 0;
+ maxmaxcode = (code_int)1 << GIFBITS;
+}
+
+
+/* +-------------------------------------------------------------------+ */
+/* | Copyright 1990, 1991, 1993, David Koblas. (koblas@netcom.com) | */
+/* | Permission to use, copy, modify, and distribute this software | */
+/* | and its documentation for any purpose and without fee is hereby | */
+/* | granted, provided that the above copyright notice appear in all | */
+/* | copies and that both that copyright notice and this permission | */
+/* | notice appear in supporting documentation. This software is | */
+/* | provided "as is" without express or implied warranty. | */
+/* +-------------------------------------------------------------------+ */
diff --git a/graphics/gd/files/gdcmpgif.c b/graphics/gd/files/gdcmpgif.c
new file mode 100644
index 000000000000..13c243014d2b
--- /dev/null
+++ b/graphics/gd/files/gdcmpgif.c
@@ -0,0 +1,85 @@
+#include <stdio.h>
+#include <unistd.h> /* For unlink function */
+#include "gd.h"
+
+/* A short program which converts a .png file into a .gd file, for
+ your convenience in creating images on the fly from a
+ basis image that must be loaded quickly. The .gd format
+ is not intended to be a general-purpose format. */
+
+void CompareImages(char *msg, gdImagePtr im1, gdImagePtr im2);
+
+
+int main(int argc, char **argv)
+{
+ gdImagePtr im1, im2;
+ FILE *in;
+
+ if (argc != 3) {
+ fprintf(stderr, "Usage: gdcmpgif filename.gif filename.gif\n");
+ exit(1);
+ }
+ in = fopen(argv[1], "rb");
+ if (!in) {
+ fprintf(stderr, "Input file does not exist!\n");
+ exit(1);
+ }
+ im1 = gdImageCreateFromGif(in);
+ fclose(in);
+
+ if (!im1) {
+ fprintf(stderr, "Input is not in GIF format!\n");
+ exit(1);
+ }
+
+ in = fopen(argv[2], "rb");
+ if (!in) {
+ fprintf(stderr, "Input file 2 does not exist!\n");
+ exit(1);
+ }
+ im2 = gdImageCreateFromGif(in);
+ fclose(in);
+
+ if (!im2) {
+ fprintf(stderr, "Input 2 is not in GIF format!\n");
+ exit(1);
+ }
+
+ CompareImages("gdcmpgif", im1, im2);
+
+ gdImageDestroy(im1);
+ gdImageDestroy(im2);
+
+ return 0;
+}
+
+void CompareImages(char *msg, gdImagePtr im1, gdImagePtr im2)
+{
+ int cmpRes;
+
+ cmpRes = gdImageCompare(im1, im2);
+
+ if (cmpRes & GD_CMP_IMAGE) {
+ printf("%%%s: ERROR images differ: BAD\n",msg);
+ } else if (cmpRes != 0) {
+ printf("%%%s: WARNING images differ: WARNING - Probably OK\n",msg);
+ } else {
+ printf("%%%s: OK\n",msg);
+ return;
+ }
+
+ if (cmpRes & (GD_CMP_SIZE_X + GD_CMP_SIZE_Y)) {
+ printf("-%s: INFO image sizes differ\n",msg);
+ }
+
+ if (cmpRes & GD_CMP_NUM_COLORS) {
+ printf("-%s: INFO number of pallette entries differ %d Vs. %d\n",msg,
+ im1->colorsTotal, im2->colorsTotal);
+ }
+
+ if (cmpRes & GD_CMP_COLOR) {
+ printf("-%s: INFO actual colours of pixels differ\n",msg);
+ }
+}
+
+
diff --git a/graphics/gd/files/giftogd2.c b/graphics/gd/files/giftogd2.c
new file mode 100644
index 000000000000..3753b56ac4c6
--- /dev/null
+++ b/graphics/gd/files/giftogd2.c
@@ -0,0 +1,48 @@
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "gd.h"
+
+/* A short program which converts a .gif file into a .gd file, for
+ your convenience in creating images on the fly from a
+ basis image that must be loaded quickly. The .gd format
+ is not intended to be a general-purpose format. */
+
+int main(int argc, char **argv)
+{
+ gdImagePtr im;
+ FILE *in, *out;
+ int cs, fmt;
+
+ if (argc != 5) {
+ fprintf(stderr, "Usage: giftogd2 filename.gif filename.gd2 cs fmt\n");
+ fprintf(stderr, " where cs is the chunk size\n");
+ fprintf(stderr, " fmt is 1 for raw, 2 for compressed\n");
+ exit(1);
+ }
+ in = fopen(argv[1], "rb");
+ if (!in) {
+ fprintf(stderr, "Input file does not exist!\n");
+ exit(1);
+ }
+ im = gdImageCreateFromGif(in);
+ fclose(in);
+ if (!im) {
+ fprintf(stderr, "Input is not in GIF format!\n");
+ exit(1);
+ }
+ out = fopen(argv[2], "wb");
+ if (!out) {
+ fprintf(stderr, "Output file cannot be written to!\n");
+ gdImageDestroy(im);
+ exit(1);
+ }
+ cs = atoi(argv[3]);
+ fmt = atoi(argv[4]);
+ gdImageGd2(im, out, cs, fmt);
+ fclose(out);
+ gdImageDestroy(im);
+
+ return 0;
+}
+
diff --git a/graphics/gd/files/patch-gd.h b/graphics/gd/files/patch-gd.h
new file mode 100644
index 000000000000..026f87b14b30
--- /dev/null
+++ b/graphics/gd/files/patch-gd.h
@@ -0,0 +1,41 @@
+--- gd.h Thu Jan 16 11:28:09 2003
++++ gd.h Mon Mar 24 16:26:14 2003
+@@ -209,4 +209,8 @@
+ gdImagePtr gdImageCreateFromPngSource (gdSourcePtr in);
+
++ gdImagePtr gdImageCreateFromGif(FILE *fd);
++ gdImagePtr gdImageCreateFromGifCtx(gdIOCtxPtr in);
++ gdImagePtr gdImageCreateFromGifSource(gdSourcePtr in);
++
+ gdImagePtr gdImageCreateFromGd (FILE * in);
+ gdImagePtr gdImageCreateFromGdCtx (gdIOCtxPtr in);
+@@ -300,4 +304,5 @@
+
+ void gdImagePolygon (gdImagePtr im, gdPointPtr p, int n, int c);
++ void gdImageOpenPolygon(gdImagePtr im, gdPointPtr p, int n, int c);
+ void gdImageFilledPolygon (gdImagePtr im, gdPointPtr p, int n, int c);
+
+@@ -395,4 +400,13 @@
+ void *gdImageJpegPtr (gdImagePtr im, int *size, int quality);
+
++ void gdImageLzw(gdImagePtr im, FILE *out);
++ void* gdImageLzwPtr(gdImagePtr im, int *size);
++ void gdImageLzwCtx(gdImagePtr im, gdIOCtxPtr out);
++
++ void gdImageBigGif(gdImagePtr im, FILE *out);
++ void* gdImageBigGifPtr(gdImagePtr im, int *size);
++ void gdImageBigGifCtx(gdImagePtr im, gdIOCtxPtr out);
++
++
+ /* A custom data sink. For backwards compatibility. Use
+ gdIOCtx instead. */
+@@ -408,4 +422,9 @@
+
+ void gdImagePngToSink (gdImagePtr im, gdSinkPtr out);
++
++ void gdImageGif(gdImagePtr im, FILE *out);
++ void* gdImageGifPtr(gdImagePtr im, int *size);
++ void gdImageGifCtx(gdImagePtr im, gdIOCtxPtr out);
++ void gdImageGifToSink(gdImagePtr im, gdSinkPtr out);
+
+ void gdImageGd (gdImagePtr im, FILE * out);
diff --git a/graphics/gd/files/patch-gdcache.h b/graphics/gd/files/patch-gdcache.h
deleted file mode 100644
index 408a96443de6..000000000000
--- a/graphics/gd/files/patch-gdcache.h
+++ /dev/null
@@ -1,10 +0,0 @@
---- gdcache.h.orig Wed Feb 7 04:44:02 2001
-+++ gdcache.h Fri Jul 4 21:58:32 2003
-@@ -40,7 +40,6 @@
- /* header */
- /*********************************************************/
-
--#include <malloc.h>
- #ifndef NULL
- #define NULL (void *)0
- #endif
diff --git a/graphics/gd/files/patch-gdft.c b/graphics/gd/files/patch-gdft.c
new file mode 100644
index 000000000000..cdee3d88935b
--- /dev/null
+++ b/graphics/gd/files/patch-gdft.c
@@ -0,0 +1,92 @@
+--- gdft.c Thu Jan 16 13:29:32 2003
++++ gdft.c Mon Mar 24 17:09:54 2003
+@@ -546,8 +546,8 @@
+ a->tweencolor = gdTrueColorAlpha (gdTrueColorGetRed (fg),
+ gdTrueColorGetGreen (fg),
+ gdTrueColorGetBlue (fg),
+- gdAlphaMax -
+- (gdTrueColorGetAlpha (fg) *
++ gdAlphaMax - ((gdAlphaMax -
++ gdTrueColorGetAlpha (fg)) *
+ pixel / NUMCOLORS));
+ }
+ else
+@@ -680,10 +680,14 @@
+ if (y >= im->sy || y < 0)
+ continue;
+
+- for (col = 0; col < bitmap.width; col++, pc++)
+- {
+- if (bitmap.pixel_mode == ft_pixel_mode_grays)
+- {
++ for (col = 0; col < bitmap.width; col++, pc++) {
++ x = pen_x + col;
++ /* clip if out of bounds */
++ if (x >= im->sx || x < 0)
++ continue;
++
++ switch(bitmap.pixel_mode) {
++ case ft_pixel_mode_grays:
+ /*
+ * Round to NUMCOLORS levels of antialiasing for
+ * index color images since only 256 colors are
+@@ -692,44 +696,38 @@
+ tc_key.pixel = ((bitmap.buffer[pc] * NUMCOLORS)
+ + bitmap.num_grays / 2)
+ / (bitmap.num_grays - 1);
+- }
+- else if (bitmap.pixel_mode == ft_pixel_mode_mono)
+- {
+- tc_key.pixel = ((bitmap.buffer[pc / 8]
+- << (pc % 8)) & 128) ? NUMCOLORS : 0;
++ break;
++ case ft_pixel_mode_mono:
+ /* 2.0.5: mode_mono fix from Giuliano Pochini */
+ tc_key.pixel =
+ ((bitmap.
+ buffer[(col >> 3) +
+ pcr]) & (1 << (~col & 0x07))) ? NUMCOLORS : 0;
+- }
+- else
+- {
++ break;
++ default:
+ return "Unsupported ft_pixel_mode";
+- }
++ }
++
+ if (tc_key.pixel > 0) /* if not background */
+ {
+- x = pen_x + col;
+-
+- /* clip if out of bounds */
+- if (x >= im->sx || x < 0)
+- continue;
+- /* get pixel location in gd buffer */
+- pixel = &im->pixels[y][x];
+- if (tc_key.pixel == NUMCOLORS)
+- {
++ if (im->trueColor) {
++ tc_elem = (tweencolor_t *)gdCacheGet(tc_cache, &tc_key);
++ gdImageSetPixel(im, x, y, tc_elem->tweencolor);
++ } else {
++ /* get pixel location in gd buffer */
++ pixel = &im->pixels[y][x];
++ if (tc_key.pixel == NUMCOLORS)
+ /* use fg color directly. gd 2.0.2: watch out for
+ negative indexes (thanks to David Marwood). */
+ *pixel = (fg < 0) ? -fg : fg;
+- }
+- else
+- {
++ else {
+ /* find antialised color */
+
+ tc_key.bgcolor = *pixel;
+ tc_elem = (tweencolor_t *) gdCacheGet (tc_cache, &tc_key);
+ *pixel = tc_elem->tweencolor;
+ }
++ }
+ }
+ }
+ }
diff --git a/graphics/gd/files/patch-gdkanji.c b/graphics/gd/files/patch-gdkanji.c
deleted file mode 100644
index 2162a7e95c38..000000000000
--- a/graphics/gd/files/patch-gdkanji.c
+++ /dev/null
@@ -1,87 +0,0 @@
---- gdkanji.c.orig Fri Feb 2 05:23:56 2001
-+++ gdkanji.c Wed Feb 7 20:59:08 2001
-@@ -103,14 +103,18 @@
- unsigned char *str;
- #endif
- {
-- static int whatcode;
-+ static int whatcode = ASCII;
-+ int oldcode = ASCII;
- int c, i;
- char *lang = NULL;
-
- c = '\1';
- i = 0;
-
-- if (whatcode == 0) whatcode = ASCII;
-+ if (whatcode != EUCORSJIS && whatcode != ASCII) {
-+ oldcode = whatcode;
-+ whatcode = ASCII;
-+ }
-
- while ((whatcode == EUCORSJIS || whatcode == ASCII) && c != '\0') {
- if ((c = str[i++]) != '\0') {
-@@ -167,7 +171,7 @@
- if ((c >= 64 && c <= 126) || (c >= 128 && c <= 160))
- whatcode = SJIS;
- else
-- if (c >= 253 && c >= 254) whatcode = EUC;
-+ if (c >= 253 && c <= 254) whatcode = EUC;
- else
- if (c >= 161 && c <= 252) whatcode = EUCORSJIS;
- }
-@@ -184,6 +188,8 @@
- debug("Kanji code detected at %d byte.", i);
- #endif
-
-+ if (whatcode == EUCORSJIS && oldcode != ASCII) whatcode = oldcode;
-+
- if (whatcode == EUCORSJIS) {
- if (getenv ("LC_ALL")) lang = getenv ("LC_ALL");
- else
-@@ -310,7 +316,7 @@
- error("invalid code specification: \"%s\" or \"%s\"",
- EUCSTR, code);
- #endif
-- strcpy(to, from);
-+ ustrcpy(to, from);
- return;
- }
-
-@@ -328,7 +334,7 @@
- else
- #endif
- error("something happen");
-- strcpy(to, from);
-+ ustrcpy(to, from);
- return;
- }
-
-@@ -526,11 +532,10 @@
-
- t = (unsigned char *)gdMalloc(BUFSIZ);
- any2eucjp(t, s, BUFSIZ);
-- i = strlen(t);
-+ i = strlen((const char *)t);
- gdFree(t);
- return i;
- }
--#endif
-
- #ifdef DEBUG
- int main()
-@@ -543,7 +548,7 @@
- while ( (c = fgetc(stdin)) != '\n' && i < BUFSIZ ) input[i++] = c;
- input[i] = '\0';
-
-- printf("input : %d bytes\n", strlen(input));
-+ printf("input : %d bytes\n", strlen((const char *)input));
- printf("output: %d bytes\n", strwidth(input));
-
- output = (unsigned char *)gdMalloc(BUFSIZ);
-@@ -555,4 +560,5 @@
-
- return 0;
- }
-+#endif
- #endif
diff --git a/graphics/gd/files/patch-gdtest.c b/graphics/gd/files/patch-gdtest.c
new file mode 100644
index 000000000000..85c855d4db02
--- /dev/null
+++ b/graphics/gd/files/patch-gdtest.c
@@ -0,0 +1,81 @@
+--- gdtest.c.orig Thu Apr 25 14:16:47 2002
++++ gdtest.c Tue Nov 6 15:53:38 2001
+@@ -84,6 +84,35 @@
+ gdImageDestroy (im2);
+ ctx->gd_free (ctx);
+
++ /* */
++ /* Send to GIF File then Ptr */
++ /* */
++ sprintf(of, "%s.gif", argv[1]);
++ out = fopen(of, "wb");
++ gdImageGif(im, out);
++ fclose(out);
++
++ in = fopen(of, "rb");
++ if (!in) {
++ fprintf(stderr, "GIF Output file does not exist!\n");
++ exit(1);
++ }
++ im2 = gdImageCreateFromGif(in);
++ fclose(in);
++
++ CompareImages("GD->GIF File->GD", ref, im2);
++
++ unlink(of);
++ gdImageDestroy(im2);
++
++ iptr = gdImageGifPtr(im,&sz);
++ ctx = gdNewDynamicCtx(sz,iptr);
++ im2 = gdImageCreateFromGifCtx(ctx);
++
++ CompareImages("GD->GIF ptr->GD", ref, im2);
++
++ gdImageDestroy(im2);
++ ctx->gd_free(ctx);
+
+ /* */
+ /* Send to GD2 File then Ptr */
+@@ -200,7 +229,30 @@
+ gdImageDestroy (im2);
+ };
+
+- unlink (of);
++ /*
++ ** Test gdImageCreateFromGifSource
++ **/
++
++ in = fopen(of, "rb");
++
++ if (!in)
++ {
++ fprintf (stderr, "GD Source: ERROR - GD Source input file does not exist - Sink may have failed!\n");
++ };
++
++ imgsrc.source = freadWrapper;
++ imgsrc.context = in;
++ im2 = gdImageCreateFromGifSource(&imgsrc);
++ fclose(in);
++
++ if (im2 == NULL) {
++ printf("GD Source (GIF): ERROR Null returned by gdImageCreateFromGifSource\n");
++ } else {
++ CompareImages("GD Source (GIF)", ref, im2);
++ gdImageDestroy(im2);
++ };
++
++ unlink(of);
+
+ /* */
+ /* Test Extraction */
+@@ -266,6 +318,10 @@
+
+ printf ("[Merged Image has %d colours]\n", im2->colorsTotal);
+ CompareImages ("Merged (gdtest.png, gdtest_merge.png)", im2, im3);
++
++ out = fopen ("test/gdtest_merge_out.png", "wb");
++ gdImagePng(im2, out);
++ close(out);
+
+ gdImageDestroy (im2);
+ gdImageDestroy (im3);
diff --git a/graphics/gd/files/patch-gdttf.c b/graphics/gd/files/patch-gdttf.c
deleted file mode 100644
index c7b8768a725f..000000000000
--- a/graphics/gd/files/patch-gdttf.c
+++ /dev/null
@@ -1,17 +0,0 @@
---- gdttf.c.orig Fri Feb 2 05:23:56 2001
-+++ gdttf.c Wed Feb 7 20:57:34 2001
-@@ -221,11 +221,10 @@
- byte = *((unsigned char *) str);
- #ifdef JISX0208
- if (0xA1 <= byte && byte <= 0xFE) {
-- int jiscode, ku, ten;
-+ int ku, ten;
-
-- jiscode = 0x100 * (byte & 0x7F) + (str[1] & 0x7F);
-- ku = (jiscode >> 8) - 0x20;
-- ten = (jiscode % 256) - 0x20;
-+ ku = (byte & 0x7F) - 0x20;
-+ ten = (str[1] & 0x7F) - 0x20;
- if ( (ku < 1 || ku > 92) || (ten < 1 || ten > 94) ) {
- *chPtr = (Tcl_UniChar) byte;
- return 1;
diff --git a/graphics/gd/files/patch-gif b/graphics/gd/files/patch-gif
deleted file mode 100644
index e78b1e350e3f..000000000000
--- a/graphics/gd/files/patch-gif
+++ /dev/null
@@ -1,11 +0,0 @@
-This patch together with the old implementation (from gd-1.5) of
-gd_gif_in.c restore GD's ability to read GIF images. The writing of such
-images is troubled because of Unisys' zeal in patent enforcement.
-
---- gd.h Tue Feb 6 14:44:01 2001
-+++ gd.h Fri Jul 27 16:10:38 2001
-@@ -95,2 +95,4 @@
- gdImagePtr gdImageCreate(int sx, int sy);
-+gdImagePtr gdImageCreateFromGif(FILE *fd);
-+gdImagePtr gdImageCreateFromGifCtx(gdIOCtxPtr in);
- gdImagePtr gdImageCreateFromPng(FILE *fd);
diff --git a/graphics/gd/files/patch-index.html b/graphics/gd/files/patch-index.html
new file mode 100644
index 000000000000..da061462fe6c
--- /dev/null
+++ b/graphics/gd/files/patch-index.html
@@ -0,0 +1,71 @@
+--- index.html Mon Nov 25 11:39:31 2002
++++ index.html Wed Nov 27 12:47:38 2002
+@@ -35,4 +35,9 @@
+ modern image formats such as PNG and JPEG as soon as possible.
+
++<p>Note, that the FreeBSD port of gd2 includes support for GIF files
++ported from the earlier releases of gd. If the WITH_LZW was defined at
++build time, the software will also use LZW-compression when creating
++GIF files.
++
+ <p>
+ gd 2.0.8 <strong>requires</strong> that the following libraries
+@@ -116,4 +121,18 @@
+ Portions relating to WBMP copyright 2000, 2001, 2002 Maurice Szmurlo and Johan Van
+ den Brande.
++
++<p>
++GIF decompression code copyright 1990, 1991, 1993, by David Koblas
++(koblas@netcom.com).
++<p>
++Non-LZW-based GIF compression code copyright 1998, by Hutchison Avenue
++Software Corporation (<a href="http://www.hasc.com">http://www.hasc.com/</a>,
++info@hasc.com).
++<p>
++LZW-based GIF compression code David Rowley.
++Obtaining a license for the Unisys LZW compression patent is
++entirely between the user and Unisys. The authors of gd can provide
++NO assistance in this matter.
++
+ <p>
+ <strong>Permission has been granted to copy, distribute and modify gd in any
+@@ -192,5 +211,22 @@
+ <li><a href="http://martin.gleeson.com/fly/">fly</a>, by Martin Gleeson
+ </ul>
+-<P>
++
++<P><A NAME="gifpatch"><H3>What does the FreeBSD port add?</H3></A>
++
++<p>This version reinstates GIF support. Specifically, the following
++functions are added: gdImageGif, gdImageGifPtr, gdImageGifCtx,
++gdImageGifToSink, gdImageCreateFromGif, gdImageCreateFromGifCtx,
++gdImageCreateFromGifSource.
++The can be used just like the corresponding functions for the other
++image formats.
++
++<p>Other functions added, but not documented, are: gdImageLzw,
++gdImageLzwPtr, gdImageLzwCtx, gdImageBigGif, gdImageBigGifPtr,
++gdImageBigGifCtx.
++
++<p>The <a href=#gdImageOpenPolygon>gdImageOpenPolygon</a> is added.
++This is basically the same as <a href=#gdImagePolygon>gdImagePolygon</A>,
++but it does not join the start and end points. It is required by GD.pm.
++
+ <A NAME="whatsnew2.0.8"><H3>What's new in version 2.0.8?</H3></A>
+ <P>
+@@ -1058,5 +1094,6 @@
+ <DD>
+ Represents a point in the coordinate space of the image; used
+-by <A HREF="#gdImagePolygon">gdImagePolygon</A> and
++by <A HREF="#gdImagePolygon">gdImagePolygon</A>,
++<A HREF="#gdImageOpenPolygon">gdImageOpenPolygon</A>, and
+ <A HREF="#gdImageFilledPolygon">gdImageFilledPolygon</A>.
+ <PRE>
+@@ -1068,5 +1105,6 @@
+ <DD>
+ A pointer to a <A HREF="#gdPoint">gdPoint</A> structure; passed
+-as an argument to <A HREF="#gdImagePolygon">gdImagePolygon</A>
++as an argument to <A HREF="#gdImagePolygon">gdImagePolygon</A>,
++<A HREF="#gdImageOpenPolygon">gdImageOpenPolygon</A>,
+ and <A HREF="#gdImageFilledPolygon">gdImageFilledPolygon</A>.
+ </DL>
diff --git a/graphics/gd/pkg-descr b/graphics/gd/pkg-descr
index f6ec333a65c6..f7507cc8d13f 100644
--- a/graphics/gd/pkg-descr
+++ b/graphics/gd/pkg-descr
@@ -1,23 +1,16 @@
-DESCRIPTION
+gd is a graphics library. It allows your code to quickly draw images
+complete with lines, arcs, text, multiple colors, cut and paste from
+other images, and flood fills, and write out the result as a PNG, GIF
+or JPEG file. This is particularly useful in World Wide Web applications,
+where PNG, GIF and JPEG are three of the formats accepted for inline
+images by most browsers.
- gd is a graphics library. It allows your code to quickly draw images
- complete with lines, arcs, text, multiple colors, cut and paste from
- other images, and flood fills, and write out the result as a .PNG file.
- This is particularly useful in World Wide Web applications, where .PNG
- is the format used for inline images.
-
- gd is not a paint program. If you are looking for a paint program, you
- are looking in the wrong place. If you are not a programmer, you are
- looking in the wrong place.
-
- gd does not provide for every possible desirable graphics operation.
- It is not necessary or desirable for gd to become a kitchen-sink
- graphics package, but version 1.7.3 incorporates most of the commonly
- requested features for an 8-bit 2D package. Support for truecolor
- images, JPEG and truecolor PNG is planned for version 2.0.
-
-AUTHOR
- gd was written by Thomas Boutell and is currently distributed by
- boutell.com, Inc.
+gd does not provide for every possible desirable graphics operation,
+but version 2.0 does include most frequently requested features,
+including both truecolor and palette images, resampling (smooth
+resizing of truecolor images) and so forth.
WWW: http://www.boutell.com/gd/
+
+- Alex Dupre
+sysadmin@alexdupre.com
diff --git a/graphics/gd/pkg-plist b/graphics/gd/pkg-plist
index b0daddfa56ee..a8b71306fc99 100644
--- a/graphics/gd/pkg-plist
+++ b/graphics/gd/pkg-plist
@@ -1,12 +1,25 @@
-include/gd/gd.h
-include/gd/gd_io.h
-include/gd/gdcache.h
-include/gd/gdfontg.h
-include/gd/gdfontl.h
-include/gd/gdfontmb.h
-include/gd/gdfonts.h
-include/gd/gdfontt.h
-lib/libgd1.a
-lib/libgd1.so
-lib/libgd1.so.2
-@dirrm include/gd
+bin/annotate
+bin/bdftogd
+bin/gd2copypal
+bin/gd2togif
+bin/gd2topng
+bin/gdcmpgif
+bin/gdparttopng
+bin/gdtopng
+bin/giftogd2
+bin/pngtogd
+bin/pngtogd2
+bin/webpng
+include/gd.h
+include/gd_io.h
+include/gdcache.h
+include/gdfontg.h
+include/gdfontl.h
+include/gdfontmb.h
+include/gdfonts.h
+include/gdfontt.h
+lib/libgd.a
+lib/libgd.so
+lib/libgd.so.4
+%%PORTDOCS%%%%DOCSDIR%%/index.html
+%%PORTDOCS%%@dirrm %%DOCSDIR%%