Subject: pkg/6779: netpbm needs a shampooing
To: None <gnats-bugs@gnats.netbsd.org>
From: None <windsor@warthog.com>
List: netbsd-bugs
Date: 01/10/1999 01:44:34
>Number:         6779
>Category:       pkg
>Synopsis:       the netpbm package needs updated and tidyied
>Confidential:   no
>Severity:       serious
>Priority:       low
>Responsible:    gnats-admin (GNATS administrator)
>State:          open
>Class:          change-request
>Submitter-Id:   net
>Arrival-Date:   Sat Jan  9 23:50:01 1999
>Last-Modified:
>Originator:     Rob Windsor
>Organization:
Nose Pickers Anonymous
>Release:        1.3.3
>Environment:
System: NetBSD evolution 1.3.3 NetBSD 1.3.3 (EVOLUTION) #1: Thu Dec 17 17:22:29 CST 1998 windsor@evolution:/usr/src/sys/arch/sparc/compile/EVOLUTION sparc


>Description:
	pkgsrc/graphics/netpbm needs a makeover, and one of the tarballs
	specifically included in it is getting hard(er) to find since it
	was updated last year.
	For example, at least two of the patchfiles (patch-ac and patch-bg)
	touch pnm/Makefile.
	Also, the pkg Makefile does an .afterinstall which could be done
	during the install process by patching the `Makefile's.  Since we
	touch three of them already, we might as well touch all of them
	and spread some consistency.
>How-To-Repeat:
	Just look at it.
>Fix:
	Patch with following (reference root is pkgsrc/graphics/netpbm),
	please erase or rename the entire pkg directory "netpbm" since
	I just diffed mine against an empty dir.  (Alternatively, patch(1)
	this in /tmp/foo and diff it against your pkgsrc/graphics/netpbm
	and then apply your new patch to your netpbm pkg.)

diff -r -c -N /tmp/null/Makefile ./Makefile
*** /tmp/null/Makefile	Wed Dec 31 18:00:00 1969
--- ./Makefile	Sun Jan 10 01:24:13 1999
***************
*** 0 ****
--- 1,32 ----
+ # $NetBSD: Makefile,v 1.22 1998/11/30 19:42:02 tv Exp $
+ #
+ 
+ DISTNAME=	netpbm
+ PKGNAME=	netpbm-19940301
+ CATEGORIES=	graphics
+ MASTER_SITES=	ftp://ftp.wustl.edu/graphics/graphics/packages/NetPBM/ \
+ 		ftp://ftp.informatik.uni-oldenburg.de/pub/netpbm/ \
+ 		ftp://ftp.informatik.uni-oldenburg.de/pub/grafik/png/applications/
+ DISTFILES=	netpbm-1mar1994.tar.gz \
+ 		pcxtoppm.tar.gz \
+ 		rletopnm.tar.gz \
+ 		pnmtopng-2.37.1.tar.gz
+ 
+ MAINTAINER=	packages@netbsd.org
+ 
+ DEPENDS+=	tiff-3.4:../../graphics/tiff
+ DEPENDS+=	jpeg-6b:../../graphics/jpeg
+ DEPENDS+=	png-1.0.2:../../graphics/png
+ 
+ CONFLICTS=	netpbm-*
+ 
+ WRKSRC=		${WRKDIR}/netpbm
+ MAKE_ENV +=	PREFIX=${PREFIX} MANCP="${INSTALL_MAN}"
+ 
+ post-extract:
+ # move updates into source tree
+ 	cd ${WRKSRC};\
+ 	${MV} ../*pcx*.? ppm;\
+ 	${MV} ../*rle*.? ../*png*.? pnm;
+ 
+ .include "../../mk/bsd.pkg.mk"
diff -r -c -N /tmp/null/files/md5 ./files/md5
*** /tmp/null/files/md5	Wed Dec 31 18:00:00 1969
--- ./files/md5	Sun Jan 10 01:25:10 1999
***************
*** 0 ****
--- 1,6 ----
+ $NetBSD: md5,v 1.4 1998/08/07 13:21:37 agc Exp $
+ 
+ MD5 (netpbm-1mar1994.tar.gz) = 55f505b09e69a5db8f08844435282dfb
+ MD5 (pcxtoppm.tar.gz) = d9a37913ef2c2cd412b0e7f969487dc2
+ MD5 (rletopnm.tar.gz) = c0488f9918f506bf6a8d09870d5d115f
+ MD5 (pnmtopng-2.37.1.tar.gz) = 3addb1d14811c86169c4bb09ee8942d7
diff -r -c -N /tmp/null/patches/patch-aa ./patches/patch-aa
*** /tmp/null/patches/patch-aa	Wed Dec 31 18:00:00 1969
--- ./patches/patch-aa	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,201 ----
+ *** ../../src/netpbm-1mar94/./Makefile	Wed Jan 26 05:47:35 1994
+ --- ./Makefile	Sun Jan 10 00:32:36 1999
+ ***************
+ *** 9,14 ****
+ --- 9,15 ----
+   # documentation.  This software is provided "as is" without express or
+   # implied warranty.
+   
+ + PREFIX =	/usr/local
+   # CONFIGURE: gcc makes things go faster on some machines, but not everyone
+   # has it.  Warning: do not use gcc's -finline-functions or -fstrength-reduce
+   # flags, they can produce incorrect code.  (This is with gcc versions 1.35,
+ ***************
+ *** 21,27 ****
+   #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   
+   # CONFIGURE: cc flags go here.
+ ! CFLAGS =	-O
+   #CFLAGS =	-g
+   #CFLAGS =	-g -O
+   
+ --- 22,28 ----
+   #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   
+   # CONFIGURE: cc flags go here.
+ ! CFLAGS =	-O2
+   #CFLAGS =	-g
+   #CFLAGS =	-g -O
+   
+ ***************
+ *** 48,80 ****
+   # By the way, you must have at least version 2.4 of libtiff.  Earlier
+   # versions will not work.
+   TIFFDEF =	-DLIBTIFF
+ ! TIFFINC =	-I../libtiff
+ ! TIFFLIB =	../libtiff/libtiff.a
+   TIFFBINARIES =	tifftopnm pnmtotiff
+   TIFFOBJECTS =	tifftopnm.o pnmtotiff.o
+   
+   # CONFIGURE: Define the directory that you want the binaries copied to.
+   # If you need scripts and binaries to be in different directories, you
+   # can set that up too.
+ ! INSTALLBINARIES =	/usr/local/netpbm
+   INSTALLSCRIPTS =	$(INSTALLBINARIES)
+   
+   # CONFIGURE: Define the directories that you want the manual sources copied to,
+   # plus the suffix you want them to have.
+ ! INSTALLMANUALS1 =	/usr/local/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	/usr/local/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	/usr/local/man/man5
+   SUFFIXMANUALS5 =	5
+   
+   # CONFIGURE: Normally the man pages are installed using "cp".  By changing
+   # this define you can use something else, for example a script that calls
+   # compress or pack. The ../mantocat is used on systems which use man pages
+   # in the "cat" format.
+ ! MANCP =			cp
+   #MANCP =		../mantocat
+   
+   # CONFIGURE: Normally the Makefiles build and install separate binaries for
+   # each program.  However, on some systems (especially those without shared
+   # libraries) this can mean a lot of space.  In this case you might try
+ --- 49,84 ----
+   # By the way, you must have at least version 2.4 of libtiff.  Earlier
+   # versions will not work.
+   TIFFDEF =	-DLIBTIFF
+ ! TIFFINC =	-I$(PREFIX)/include
+ ! TIFFLIB =	-L$(PREFIX)/lib -ltiff -ljpeg
+   TIFFBINARIES =	tifftopnm pnmtotiff
+   TIFFOBJECTS =	tifftopnm.o pnmtotiff.o
+   
+   # CONFIGURE: Define the directory that you want the binaries copied to.
+   # If you need scripts and binaries to be in different directories, you
+   # can set that up too.
+ ! INSTALLBINARIES =	$(PREFIX)/bin
+   INSTALLSCRIPTS =	$(INSTALLBINARIES)
+   
+   # CONFIGURE: Define the directories that you want the manual sources copied to,
+   # plus the suffix you want them to have.
+ ! INSTALLMANUALS1 =	$(PREFIX)/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	$(PREFIX)/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	$(PREFIX)/man/man5
+   SUFFIXMANUALS5 =	5
+   
+   # CONFIGURE: Normally the man pages are installed using "cp".  By changing
+   # this define you can use something else, for example a script that calls
+   # compress or pack. The ../mantocat is used on systems which use man pages
+   # in the "cat" format.
+ ! MANCP =			install -c -m 0644
+   #MANCP =		../mantocat
+   
+ + INSTALLLIBS =		$(PREFIX)/lib
+ + INSTALLDEFS =		$(PREFIX)/include
+ + 
+   # CONFIGURE: Normally the Makefiles build and install separate binaries for
+   # each program.  However, on some systems (especially those without shared
+   # libraries) this can mean a lot of space.  In this case you might try
+ ***************
+ *** 87,96 ****
+   #
+   # Note that if you make a "merge", the executables don't get created
+   # until you do the install.
+ ! #all:		binaries
+ ! #install:	install.bin install.man
+ ! all:		merge
+ ! install:	install.merge install.man
+   
+   # End of configurable definitions.
+   
+ --- 91,100 ----
+   #
+   # Note that if you make a "merge", the executables don't get created
+   # until you do the install.
+ ! all:		binaries
+ ! install:	install.bin install.man
+ ! #all:		merge
+ ! #install:	install.merge install.man
+   
+   # End of configurable definitions.
+   
+ ***************
+ *** 99,108 ****
+   SUBDIRS =	pbm pgm ppm pnm
+   
+   binaries:
+ ! 	./stamp-date
+ ! 	( echo "libtiff" ; cd libtiff ; make )
+   	for i in $(SUBDIRS) ; do \
+ ! 	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'TIFFDEF=$(TIFFDEF)' 'TIFFINC=$(TIFFINC)' 'TIFFLIB=$(TIFFLIB)' 'TIFFBINARIES=$(TIFFBINARIES)' 'TIFFOBJECTS=$(TIFFOBJECTS)' 'LDFLAGS=$(LDFLAGS)' binaries ); \
+   	done
+   
+   merge:
+ --- 103,112 ----
+   SUBDIRS =	pbm pgm ppm pnm
+   
+   binaries:
+ ! #	./stamp-date
+ ! #	( echo "libtiff" ; cd libtiff ; make )
+   	for i in $(SUBDIRS) ; do \
+ ! 	    ( echo "===> $$i" ; cd $$i ; $(MAKE) $(MFLAGS) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'TIFFDEF=$(TIFFDEF)' 'TIFFINC=$(TIFFINC)' 'TIFFLIB=$(TIFFLIB)' 'TIFFBINARIES=$(TIFFBINARIES)' 'TIFFOBJECTS=$(TIFFOBJECTS)' 'LDFLAGS=$(LDFLAGS)' binaries ); \
+   	done
+   
+   merge:
+ ***************
+ *** 113,127 ****
+   	done
+   
+   install.bin:
+ ! 	-mkdir $(INSTALLBINARIES)
+   	for i in $(SUBDIRS) ; do \
+ ! 	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'TIFFDEF=$(TIFFDEF)' 'TIFFINC=$(TIFFINC)' 'TIFFLIB=$(TIFFLIB)' 'TIFFBINARIES=$(TIFFBINARIES)' 'TIFFOBJECTS=$(TIFFOBJECTS)' 'LDFLAGS=$(LDFLAGS)' 'INSTALLBINARIES=$(INSTALLBINARIES)' 'INSTALLSCRIPTS=$(INSTALLSCRIPTS)' install.bin ); \
+   	done
+   
+   install.merge:
+ ! 	-mkdir $(INSTALLBINARIES)
+   	for i in $(SUBDIRS) ; do \
+ ! 	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'TIFFDEF=$(TIFFDEF)' 'TIFFINC=$(TIFFINC)' 'TIFFLIB=$(TIFFLIB)' 'TIFFBINARIES=$(TIFFBINARIES)' 'TIFFOBJECTS=$(TIFFOBJECTS)' 'LDFLAGS=$(LDFLAGS)' 'INSTALLBINARIES=$(INSTALLBINARIES)' 'INSTALLSCRIPTS=$(INSTALLSCRIPTS)' install.merge ); \
+   	done
+   
+   install.man:
+ --- 117,135 ----
+   	done
+   
+   install.bin:
+ ! #	-mkdir $(INSTALLBINARIES)
+ ! #	-mkdir $(INSTALLLIBS)
+ ! #	-mkdir $(INSTALLDEFS)
+   	for i in $(SUBDIRS) ; do \
+ ! 	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'TIFFDEF=$(TIFFDEF)' 'TIFFINC=$(TIFFINC)' 'TIFFLIB=$(TIFFLIB)' 'TIFFBINARIES=$(TIFFBINARIES)' 'TIFFOBJECTS=$(TIFFOBJECTS)' 'LDFLAGS=$(LDFLAGS)' 'INSTALLBINARIES=$(INSTALLBINARIES)' 'INSTALLSCRIPTS=$(INSTALLSCRIPTS)' 'INSTALLLIBS=$(INSTALLLIBS)' 'INSTALLDEFS=$(INSTALLDEFS)' install.bin ); \
+   	done
+   
+   install.merge:
+ ! #	-mkdir $(INSTALLBINARIES)
+ ! #	-mkdir $(INSTALLLIBS)
+ ! #	-mkdir $(INSTALLDEFS)
+   	for i in $(SUBDIRS) ; do \
+ ! 	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) 'CC=$(CC)' 'CFLAGS=$(CFLAGS)' 'TIFFDEF=$(TIFFDEF)' 'TIFFINC=$(TIFFINC)' 'TIFFLIB=$(TIFFLIB)' 'TIFFBINARIES=$(TIFFBINARIES)' 'TIFFOBJECTS=$(TIFFOBJECTS)' 'LDFLAGS=$(LDFLAGS)' 'INSTALLBINARIES=$(INSTALLBINARIES)' 'INSTALLSCRIPTS=$(INSTALLSCRIPTS)' 'INSTALLLIBS=$(INSTALLLIBS)' 'INSTALLDEFS=$(INSTALLDEFS)' install.merge ); \
+   	done
+   
+   install.man:
+ ***************
+ *** 131,137 ****
+   
+   clean:
+   	rm -f *.shar *.shar? art.* *~
+ ! 	echo "" > compile.h
+ ! 	for i in $(SUBDIRS) libtiff ; do \
+   	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) clean ); \
+   	done
+ --- 139,145 ----
+   
+   clean:
+   	rm -f *.shar *.shar? art.* *~
+ ! 	rm -f compile.h ; echo "" > compile.h
+ ! 	for i in $(SUBDIRS) ; do \
+   	    ( echo $$i ; cd $$i ; $(MAKE) $(MFLAGS) clean ); \
+   	done
diff -r -c -N /tmp/null/patches/patch-ab ./patches/patch-ab
*** /tmp/null/patches/patch-ab	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ab	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,182 ----
+ *** ../../src/netpbm-1mar94/./pbm/Makefile	Sat Nov 20 08:59:20 1993
+ --- ./pbm/Makefile	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 10,37 ****
+   # implied warranty.
+   
+   # Default values, usually overridden by top-level Makefile.
+ ! CC =		cc
+   #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   #CFLAGS =	-O
+ ! CFLAGS =	-g
+   #CFLAGS =	-g -O
+   TIFFDEF =       -DLIBTIFF
+   #LDFLAGS =	-s
+   LDFLAGS =	
+ ! INSTALLBINARIES =	/usr/new/pbm
+ ! INSTALLMANUALS1 =	/usr/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	/usr/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	/usr/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			cp
+   
+   SHELL =		/bin/sh
+   INCLUDE =	-I..
+   ALLCFLAGS =	$(CFLAGS) $(TIFFDEF) $(INCLUDE)
+   LIBPBM =	libpbm.a
+ ! DEFPBM =	pbm.h ../pbmplus.h
+   
+   PORTBINARIES =	atktopbm brushtopbm cmuwmtopbm g3topbm \
+   		icontopbm gemtopbm macptopbm mgrtopbm \
+ --- 10,41 ----
+   # implied warranty.
+   
+   # Default values, usually overridden by top-level Makefile.
+ ! PREFIX =	/usr/local
+ ! CC =		gcc
+   #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   #CFLAGS =	-O
+ ! CFLAGS =	-O2
+   #CFLAGS =	-g -O
+   TIFFDEF =       -DLIBTIFF
+   #LDFLAGS =	-s
+   LDFLAGS =	
+ ! INSTALLBINARIES =	$(PREFIX)/bin
+ ! INSTALLMANUALS1 =	$(PREFIX)/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	$(PREFIX)/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	$(PREFIX)/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			install -c -m 0644
+ ! INSTALLLIBS =		$(PREFIX)/lib
+ ! INSTALLDEFS =		$(PREFIX)/include
+   
+   SHELL =		/bin/sh
+   INCLUDE =	-I..
+   ALLCFLAGS =	$(CFLAGS) $(TIFFDEF) $(INCLUDE)
+   LIBPBM =	libpbm.a
+ ! DEFPBM =	pbm.h
+ ! DEFPBMPLUS =	../pbmplus.h
+   
+   PORTBINARIES =	atktopbm brushtopbm cmuwmtopbm g3topbm \
+   		icontopbm gemtopbm macptopbm mgrtopbm \
+ ***************
+ *** 67,84 ****
+   MANUALS5 =	pbm
+   
+   
+ ! #all:		binaries
+ ! all:		merge
+ ! #install:	install.bin
+ ! install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	cp $(BINARIES) $(INSTALLBINARIES)
+ ! 
+   
+   merge:		pbmmerge
+   pbmmerge:	pbmmerge.c $(OBJECTS) $(LIBPBM)
+ --- 71,89 ----
+   MANUALS5 =	pbm
+   
+   
+ ! all:		binaries
+ ! #all:		merge
+ ! install:	install.bin
+ ! #install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	install -c -s -m 0755 $(BINARIES) $(INSTALLBINARIES)
+ ! 	install -c -m 0644 $(LIBPBM) $(INSTALLLIBS)
+ ! 	install -c -m 0644 $(DEFPBM) $(INSTALLDEFS)
+   
+   merge:		pbmmerge
+   pbmmerge:	pbmmerge.c $(OBJECTS) $(LIBPBM)
+ ***************
+ *** 107,121 ****
+   	done
+   
+   # Rule for plain programs.
+ ! $(PORTBINARIES):	$(DEFPBM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPBM)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):	$(DEFPBM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	$(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And library.
+ --- 112,126 ----
+   	done
+   
+   # Rule for plain programs.
+ ! $(PORTBINARIES):	$(DEFPBM) $(DEFPBMPLUS) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPBM)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):	$(DEFPBM) $(DEFPBMPLUS) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	$(DEFPBM) $(DEFPBMPLUS)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And library.
+ ***************
+ *** 125,139 ****
+   	ar rc $(LIBPBM) libpbm1.o libpbm2.o libpbm3.o libpbm4.o libpbm5.o
+   	-ranlib $(LIBPBM)
+   
+ ! libpbm1.o:	$(DEFPBM) ../version.h ../compile.h libpbm.h libpbm1.c
+   	$(CC) $(ALLCFLAGS) -c libpbm1.c
+ ! libpbm2.o:	$(DEFPBM) libpbm.h libpbm2.c
+   	$(CC) $(ALLCFLAGS) -c libpbm2.c
+ ! libpbm3.o:	$(DEFPBM) libpbm.h libpbm3.c
+   	$(CC) $(ALLCFLAGS) -c libpbm3.c
+ ! libpbm4.o:	$(DEFPBM) libpbm.h libpbm4.c
+   	$(CC) $(ALLCFLAGS) -c libpbm4.c
+ ! libpbm5.o:	$(DEFPBM) pbmfont.h libpbm5.c
+   	$(CC) $(ALLCFLAGS) -c libpbm5.c
+   
+   # Other dependencies.
+ --- 130,144 ----
+   	ar rc $(LIBPBM) libpbm1.o libpbm2.o libpbm3.o libpbm4.o libpbm5.o
+   	-ranlib $(LIBPBM)
+   
+ ! libpbm1.o:	$(DEFPBM) $(DEFPBMPLUS) ../version.h ../compile.h libpbm.h libpbm1.c
+   	$(CC) $(ALLCFLAGS) -c libpbm1.c
+ ! libpbm2.o:	$(DEFPBM) $(DEFPBMPLUS) libpbm.h libpbm2.c
+   	$(CC) $(ALLCFLAGS) -c libpbm2.c
+ ! libpbm3.o:	$(DEFPBM) $(DEFPBMPLUS) libpbm.h libpbm3.c
+   	$(CC) $(ALLCFLAGS) -c libpbm3.c
+ ! libpbm4.o:	$(DEFPBM) $(DEFPBMPLUS) libpbm.h libpbm4.c
+   	$(CC) $(ALLCFLAGS) -c libpbm4.c
+ ! libpbm5.o:	$(DEFPBM) $(DEFPBMPLUS) pbmfont.h libpbm5.c
+   	$(CC) $(ALLCFLAGS) -c libpbm5.c
+   
+   # Other dependencies.
+ ***************
+ *** 184,187 ****
+   pbmtoepsi pbmtoepsi.o:		pbmtoepsi.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core $(BINARIES) pbmmerge
+ --- 189,192 ----
+   pbmtoepsi pbmtoepsi.o:		pbmtoepsi.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core *.core $(BINARIES) pbmmerge
diff -r -c -N /tmp/null/patches/patch-ac ./patches/patch-ac
*** /tmp/null/patches/patch-ac	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ac	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,19 ----
+ *** ../../src/netpbm-1mar94/./pbm/libpbm1.c	Mon Jan 10 11:37:22 1994
+ --- ./pbm/libpbm1.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 132,138 ****
+           if ( isupper( c1 ) )
+               c1 = tolower( c1 );
+           if ( isupper( c2 ) )
+ !             c1 = tolower( c2 );
+           if ( c1 != c2 )
+               return 0;
+           }
+ --- 132,138 ----
+           if ( isupper( c1 ) )
+               c1 = tolower( c1 );
+           if ( isupper( c2 ) )
+ !             c2 = tolower( c2 );
+           if ( c1 != c2 )
+               return 0;
+           }
diff -r -c -N /tmp/null/patches/patch-ad ./patches/patch-ad
*** /tmp/null/patches/patch-ad	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ad	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,15 ----
+ *** ../../src/netpbm-1mar94/./pbm/pbmmerge.c	Wed Nov  3 03:28:55 1993
+ --- ./pbm/pbmmerge.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 29,34 ****
+ --- 29,38 ----
+   	{
+   	++argv;
+   	--argc;
+ + 	if(!*argv)	{
+ + 		fprintf(stderr, "Usage: pbmmerge pbm_program_name [args ...]\n");
+ + 		exit(1);
+ + 		}
+   	goto again;
+   	}
+   
diff -r -c -N /tmp/null/patches/patch-ae ./patches/patch-ae
*** /tmp/null/patches/patch-ae	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ae	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,27 ----
+ *** ../../src/netpbm-1mar94/./pbm/pbmtext.c	Wed Oct 27 02:27:04 1993
+ --- ./pbm/pbmtext.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 105,114 ****
+       else
+   	{ /* Read text from stdin. */
+   	lines = 0;
+ ! 	while ( gets( buf ) != NULL )
+   	    {
+   	    int l;
+   
+   	    fix_control_chars( buf );
+   	    l = strlen( buf );
+   	    if ( lines >= maxlines )
+ --- 105,116 ----
+       else
+   	{ /* Read text from stdin. */
+   	lines = 0;
+ ! 	while ( fgets( buf, sizeof(buf), stdin ) != NULL )
+   	    {
+   	    int l;
+ +             char *nl = strchr(buf, '\n');
+   
+ +             if (nl) *nl = 0;
+   	    fix_control_chars( buf );
+   	    l = strlen( buf );
+   	    if ( lines >= maxlines )
diff -r -c -N /tmp/null/patches/patch-af ./patches/patch-af
*** /tmp/null/patches/patch-af	Wed Dec 31 18:00:00 1969
--- ./patches/patch-af	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,208 ----
+ *** ../../src/netpbm-1mar94/./pbm/pbmto10x.c	Mon Oct  4 04:10:42 1993
+ --- ./pbm/pbmto10x.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 1,6 ****
+   /* pbmto10x.c - read a portable bitmap and produce a Gemini 10X printer file
+   **
+ ! ** Copyright (C) 1990 by Ken Yap
+   **
+   ** Permission to use, copy, modify, and distribute this software and its
+   ** documentation for any purpose and without fee is hereby granted, provided
+ --- 1,6 ----
+   /* pbmto10x.c - read a portable bitmap and produce a Gemini 10X printer file
+   **
+ ! ** Copyright (C) 1990, 1994 by Ken Yap
+   **
+   ** Permission to use, copy, modify, and distribute this software and its
+   ** documentation for any purpose and without fee is hereby granted, provided
+ ***************
+ *** 8,13 ****
+ --- 8,15 ----
+   ** copyright notice and this permission notice appear in supporting
+   ** documentation.  This software is provided "as is" without express or
+   ** implied warranty.
+ + **
+ + ** Modified to shorten stripes and eliminate blank stripes. Dec 1994.
+   */
+   
+   #include "pbm.h"
+ ***************
+ *** 52,66 ****
+   }
+   
+   static void
+   res_60x72()
+   {
+   	register int	i, item, npins, row, col;
+   	bit		*bitrows[LOW_RES_ROWS], *bP[LOW_RES_ROWS];
+   
+   	for (i = 0; i < LOW_RES_ROWS; ++i)
+   		bitrows[i] = pbm_allocrow(cols);
+   	printf("\033A\010");		/* '\n' = 8/72 */
+ ! 	for (row = 0; row < rows; row += LOW_RES_ROWS)
+   	{
+   		if (row + LOW_RES_ROWS <= rows)
+   			npins = LOW_RES_ROWS;
+ --- 54,93 ----
+   }
+   
+   static void
+ + outstripe(stripe, sP, reschar)
+ + 	register char	*stripe, *sP;
+ + 	register int	reschar;
+ + {
+ + 	register int	ncols;
+ + 
+ + 	/* scan backwards, removing empty columns */
+ + 	while (sP != stripe)
+ + 		if (*--sP != 0)
+ + 		{
+ + 			++sP;
+ + 			break;
+ + 		}
+ + 	ncols = sP - stripe;
+ + 	if (ncols > 0)
+ + 	{
+ + 		printf("\033%c%c%c", reschar, ncols % 256, ncols / 256);
+ + 		fwrite(stripe, sizeof(char), ncols, stdout);
+ + 	}
+ + 	putchar('\n');			/* flush buffer */
+ + }
+ + 
+ + static void
+   res_60x72()
+   {
+   	register int	i, item, npins, row, col;
+   	bit		*bitrows[LOW_RES_ROWS], *bP[LOW_RES_ROWS];
+ + 	char		*stripe, *sP;
+   
+ + 	stripe = malloc(cols);
+   	for (i = 0; i < LOW_RES_ROWS; ++i)
+   		bitrows[i] = pbm_allocrow(cols);
+   	printf("\033A\010");		/* '\n' = 8/72 */
+ ! 	for (row = 0, sP = stripe; row < rows; row += LOW_RES_ROWS, sP = stripe)
+   	{
+   		if (row + LOW_RES_ROWS <= rows)
+   			npins = LOW_RES_ROWS;
+ ***************
+ *** 68,84 ****
+   			npins = rows - row;
+   		for (i = 0; i < npins; ++i)
+   			pbm_readpbmrow(ifp, bP[i] = bitrows[i], cols, format);
+ - 		printf("\033K%c%c", cols % 256, cols / 256);
+   		for (col = 0; col < cols; ++col)
+   		{
+   			item = 0;
+   			for (i = 0; i < npins; ++i)
+   				if (*(bP[i]++) == PBM_BLACK)
+   					item |= 1 << (7 - i);
+ ! 			putchar(item);
+   		}
+ ! 		putchar('\n');
+   	}
+   }
+   
+   static void
+ --- 95,112 ----
+   			npins = rows - row;
+   		for (i = 0; i < npins; ++i)
+   			pbm_readpbmrow(ifp, bP[i] = bitrows[i], cols, format);
+   		for (col = 0; col < cols; ++col)
+   		{
+   			item = 0;
+   			for (i = 0; i < npins; ++i)
+   				if (*(bP[i]++) == PBM_BLACK)
+   					item |= 1 << (7 - i);
+ ! 			*sP++ = item;
+   		}
+ ! 		outstripe(stripe, sP, 'K');
+   	}
+ + 	printf("\033@");
+ + 	free(stripe);
+   }
+   
+   static void
+ ***************
+ *** 86,96 ****
+   {
+   	register int	i, pin, item, npins, row, col;
+   	bit		*bitrows[HIGH_RES_ROWS], *bP[HIGH_RES_ROWS];
+   
+   	for (i = 0; i < HIGH_RES_ROWS; ++i)
+   		bitrows[i] = pbm_allocrow(cols);
+ ! 	putchar('\033'); putchar('3'); putchar('\0');
+ ! 	for (row = 0; row < rows; row += HIGH_RES_ROWS)
+   	{
+   		if (row + HIGH_RES_ROWS <= rows)
+   			npins = HIGH_RES_ROWS;
+ --- 114,126 ----
+   {
+   	register int	i, pin, item, npins, row, col;
+   	bit		*bitrows[HIGH_RES_ROWS], *bP[HIGH_RES_ROWS];
+ + 	char		*stripe, *sP;
+   
+ + 	stripe = malloc(cols);
+   	for (i = 0; i < HIGH_RES_ROWS; ++i)
+   		bitrows[i] = pbm_allocrow(cols);
+ ! 	printf("\0333\001");			/* \n = 1/144" */
+ ! 	for (row = 0, sP = stripe; row < rows; row += HIGH_RES_ROWS, sP = stripe)
+   	{
+   		if (row + HIGH_RES_ROWS <= rows)
+   			npins = HIGH_RES_ROWS;
+ ***************
+ *** 98,104 ****
+   			npins = rows - row;
+   		for (i = 0; i < npins; ++i)
+   			pbm_readpbmrow(ifp, bP[i] = bitrows[i], cols, format);
+ - 		printf("\033L%c%c", cols % 256, cols / 256);
+   		for (col = 0; col < cols; ++col)
+   		{
+   			item = 0;
+ --- 128,133 ----
+ ***************
+ *** 106,116 ****
+   			for (pin = i = 0; i < npins; i += 2, ++pin)
+   				if (*(bP[i]++) == PBM_BLACK)
+   					item |= 1 << (7 - pin);
+ ! 			putchar(item);
+   		}
+ ! 		putchar('\n');			/* flush buffer */
+ ! 		printf("\033J\001");		/* 1/144 down */
+ ! 		printf("\033L%c%c", cols % 256, cols / 256);
+   		for (col = 0; col < cols; ++col)
+   		{
+   			item = 0;
+ --- 135,144 ----
+   			for (pin = i = 0; i < npins; i += 2, ++pin)
+   				if (*(bP[i]++) == PBM_BLACK)
+   					item |= 1 << (7 - pin);
+ ! 			*sP++ = item;
+   		}
+ ! 		outstripe(stripe, sP, 'L');
+ ! 		sP = stripe;
+   		for (col = 0; col < cols; ++col)
+   		{
+   			item = 0;
+ ***************
+ *** 118,126 ****
+   			for (i = 1, pin = 0; i < npins; i += 2, ++pin)
+   				if (*(bP[i]++) == PBM_BLACK)
+   					item |= 1 << (7 - pin);
+ ! 			putchar(item);
+   		}
+ ! 		putchar('\n');			/* flush buffer */
+ ! 		printf("\033J\017");		/* 15/144 down */
+   	}
+   }
+ --- 146,156 ----
+   			for (i = 1, pin = 0; i < npins; i += 2, ++pin)
+   				if (*(bP[i]++) == PBM_BLACK)
+   					item |= 1 << (7 - pin);
+ ! 			*sP++ = item;
+   		}
+ ! 		outstripe(stripe, sP, 'L');
+ ! 		printf("\033J\016");		/* 14/144 down, \n did 1/144 */
+   	}
+ + 	printf("\033@");
+ + 	free(stripe);
+   }
diff -r -c -N /tmp/null/patches/patch-ag ./patches/patch-ag
*** /tmp/null/patches/patch-ag	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ag	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,17 ----
+ *** ../../src/netpbm-1mar94/./pbmplus.h	Tue Mar  1 03:46:36 1994
+ --- ./pbmplus.h	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 119,128 ****
+ --- 119,130 ----
+   #ifndef VMS
+   #include <unistd.h>
+   #endif
+ + #ifndef __NetBSD__
+   extern int atoi();
+   extern void exit();
+   extern long time();
+   extern int write();
+ + #endif /* NetBSD */
+   #endif
+   
+   /* CONFIGURE: On most BSD systems, malloc() gets declared in stdlib.h, on
diff -r -c -N /tmp/null/patches/patch-ah ./patches/patch-ah
*** /tmp/null/patches/patch-ah	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ah	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,188 ----
+ *** ../../src/netpbm-1mar94/./pgm/Makefile	Fri Jan 28 04:14:02 1994
+ --- ./pgm/Makefile	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 10,15 ****
+ --- 10,16 ----
+   # implied warranty.
+   
+   # Default values, usually overridden by top-level Makefile.
+ + PREFIX =	/usr/local
+   #CC =		cc
+   CC =		gcc
+   #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+ ***************
+ *** 18,31 ****
+   #CFLAGS =	-g -O
+   LDFLAGS =	-s
+   #LDFLAGS =	
+ ! INSTALLBINARIES =	/usr/new/pbm
+ ! INSTALLMANUALS1 =	/usr/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	/usr/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	/usr/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			cp
+   
+   PBMDIR =	../pbm
+   INCLUDEPBM =	-I$(PBMDIR)
+ --- 19,34 ----
+   #CFLAGS =	-g -O
+   LDFLAGS =	-s
+   #LDFLAGS =	
+ ! INSTALLBINARIES =	$(PREFIX)/bin
+ ! INSTALLMANUALS1 =	$(PREFIX)/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	$(PREFIX)/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	$(PREFIX)/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			install -c -m 0644
+ ! INSTALLLIBS =		$(PREFIX)/lib
+ ! INSTALLDEFS =		$(PREFIX)/include
+   
+   PBMDIR =	../pbm
+   INCLUDEPBM =	-I$(PBMDIR)
+ ***************
+ *** 37,48 ****
+   INCLUDE =	-I.. $(INCLUDEPBM)
+   ALLCFLAGS =	$(CFLAGS) $(INCLUDE)
+   LIBPGM =	libpgm.a
+   
+   PORTBINARIES =	asciitopgm bioradtopgm fstopgm hipstopgm \
+ ! 		lispmtopgm pbmtopgm pgmbentley pgmenhance pgmhist pgmkernel \
+   		pgmnoise pgmnorm pgmoil pgmramp pgmtofs pgmtolispm \
+   		pgmtopbm psidtopgm spottopgm
+ ! MATHBINARIES =	pgmcrater pgmedge pgmtexture rawtopgm
+   BINARIES =	$(PORTBINARIES) $(MATHBINARIES)
+   
+   OBJECTS =	asciitopgm.o bioradtopgm.o fstopgm.o hipstopgm.o \
+ --- 40,52 ----
+   INCLUDE =	-I.. $(INCLUDEPBM)
+   ALLCFLAGS =	$(CFLAGS) $(INCLUDE)
+   LIBPGM =	libpgm.a
+ + DEFPGM =	pgm.h
+   
+   PORTBINARIES =	asciitopgm bioradtopgm fstopgm hipstopgm \
+ ! 		lispmtopgm pbmtopgm pgmbentley pgmenhance pgmhist \
+   		pgmnoise pgmnorm pgmoil pgmramp pgmtofs pgmtolispm \
+   		pgmtopbm psidtopgm spottopgm
+ ! MATHBINARIES =	pgmcrater pgmedge pgmtexture rawtopgm pgmkernel
+   BINARIES =	$(PORTBINARIES) $(MATHBINARIES)
+   
+   OBJECTS =	asciitopgm.o bioradtopgm.o fstopgm.o hipstopgm.o \
+ ***************
+ *** 56,73 ****
+   MANUALS5 =	pgm
+   
+   
+ ! #all:		binaries
+ ! all:		merge
+ ! #install:	install.bin
+ ! install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	cp $(BINARIES) $(INSTALLBINARIES)
+ ! 
+   
+   merge:		pgmmerge
+   pgmmerge:	pgmmerge.c $(OBJECTS) $(LIBPGM) $(LIBPBM)
+ --- 60,78 ----
+   MANUALS5 =	pgm
+   
+   
+ ! all:		binaries
+ ! #all:		merge
+ ! install:	install.bin
+ ! #install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	install -c -s -m 0755 $(BINARIES) $(INSTALLBINARIES)
+ ! 	install -c -m 0644 $(LIBPGM) $(INSTALLLIBS)
+ ! 	install -c -m 0644 $(DEFPGM) $(INSTALLDEFS)
+   
+   merge:		pgmmerge
+   pgmmerge:	pgmmerge.c $(OBJECTS) $(LIBPGM) $(LIBPBM)
+ ***************
+ *** 97,111 ****
+   
+   
+   # Rule for plain programs.
+ ! $(PORTBINARIES):	pgm.h $(DEFPBM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPGM) $(LIBPBM)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):	pgm.h $(DEFPBM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPGM) $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	pgm.h $(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And libraries.
+ --- 102,116 ----
+   
+   
+   # Rule for plain programs.
+ ! $(PORTBINARIES):	$(DEFPGM) $(DEFPBM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPGM) $(LIBPBM)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):	$(DEFPGM) $(DEFPBM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPGM) $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	$(DEFPGM) $(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And libraries.
+ ***************
+ *** 117,125 ****
+   	ar rc $(LIBPGM) libpgm1.o libpgm2.o
+   	-ranlib $(LIBPGM)
+   
+ ! libpgm1.o:	pgm.h $(DEFPBM) libpgm.h libpgm1.c
+   	$(CC) $(ALLCFLAGS) -c libpgm1.c
+ ! libpgm2.o:	pgm.h $(DEFPBM) libpgm.h libpgm2.c $(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libpgm2.c
+   
+   # Other dependencies.
+ --- 122,130 ----
+   	ar rc $(LIBPGM) libpgm1.o libpgm2.o
+   	-ranlib $(LIBPGM)
+   
+ ! libpgm1.o:	$(DEFPGM) $(DEFPBM) lib$(DEFPGM) libpgm1.c
+   	$(CC) $(ALLCFLAGS) -c libpgm1.c
+ ! libpgm2.o:	$(DEFPGM) $(DEFPBM) lib$(DEFPGM) libpgm2.c $(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libpgm2.c
+   
+   # Other dependencies.
+ ***************
+ *** 134,140 ****
+   pgmedge pgmedge.o:		pgmedge.c
+   pgmenhance pgmenhance.o:	pgmenhance.c
+   pgmhist pgmhist.o:		pgmhist.c
+ - pgmkernel pgmkernel.o:		pgmkernel.c
+   pgmnoise pgmnoise.o:		pgmnoise.c
+   pgmnorm pgmnorm.o:		pgmnorm.c
+   pgmoil pgmoil.o:		pgmoil.c
+ --- 139,144 ----
+ ***************
+ *** 148,151 ****
+   spottopgm spottopgm.o:		spottopgm.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core $(BINARIES) pgmmerge
+ --- 152,155 ----
+   spottopgm spottopgm.o:		spottopgm.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core *.core $(BINARIES) pgmmerge
diff -r -c -N /tmp/null/patches/patch-ai ./patches/patch-ai
*** /tmp/null/patches/patch-ai	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ai	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,15 ----
+ *** ../../src/netpbm-1mar94/./pgm/pgmmerge.c	Fri Jan 28 04:17:38 1994
+ --- ./pgm/pgmmerge.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 29,34 ****
+ --- 29,38 ----
+   	{
+   	++argv;
+   	--argc;
+ + 	if(!*argv)	{
+ + 		fprintf(stderr, "Usage: pgmmerge pgm_program_name [args ...]\n");
+ + 		exit(1);
+ + 		}
+   	goto again;
+   	}
+   
diff -r -c -N /tmp/null/patches/patch-aj ./patches/patch-aj
*** /tmp/null/patches/patch-aj	Wed Dec 31 18:00:00 1969
--- ./patches/patch-aj	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,258 ----
+ *** ../../src/netpbm-1mar94/./pnm/Makefile	Mon Jan 31 10:47:32 1994
+ --- ./pnm/Makefile	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 9,36 ****
+   # documentation.  This software is provided "as is" without express or
+   # implied warranty.
+   
+   # Default values, usually overridden by top-level Makefile.
+ ! #CC =		cc
+ ! CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   #CFLAGS =	-O
+ ! CFLAGS =	-g
+   #CFLAGS =	-g -O
+   TIFFDEF =	-DLIBTIFF
+ ! TIFFINC =       -I../libtiff
+ ! TIFFLIB =       ../libtiff/libtiff.a
+   TIFFBINARIES =  tifftopnm pnmtotiff
+   TIFFOBJECTS =   tifftopnm.o pnmtotiff.o
+ ! #LDFLAGS =	-s
+ ! LDFLAGS =	
+ ! INSTALLBINARIES =	/usr/new/pbm
+   INSTALLSCRIPTS =	$(INSTALLBINARIES)
+ ! INSTALLMANUALS1 =	/usr/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	/usr/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	/usr/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			cp
+   
+   PPMDIR =	../ppm
+   INCLUDEPPM =	-I$(PPMDIR)
+ --- 9,39 ----
+   # documentation.  This software is provided "as is" without express or
+   # implied warranty.
+   
+ + PREFIX =	/usr/local
+   # Default values, usually overridden by top-level Makefile.
+ ! CC =		gcc
+ ! #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   #CFLAGS =	-O
+ ! CFLAGS =	-O2
+   #CFLAGS =	-g -O
+   TIFFDEF =	-DLIBTIFF
+ ! TIFFINC =       -I$(PREFIX)/include
+ ! TIFFLIB =       -L$(PREFIX)/lib -ltiff -ljpeg
+   TIFFBINARIES =  tifftopnm pnmtotiff
+   TIFFOBJECTS =   tifftopnm.o pnmtotiff.o
+ ! LDFLAGS =	-s
+ ! #LDFLAGS =	
+ ! INSTALLBINARIES =	$(PREFIX)/bin
+   INSTALLSCRIPTS =	$(INSTALLBINARIES)
+ ! INSTALLMANUALS1 =	$(PREFIX)/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	$(PREFIX)/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	$(PREFIX)/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			install -c -m 0644
+ ! INSTALLLIBS =		$(PREFIX)/lib
+ ! INSTALLDEFS =		$(PREFIX)/include
+   
+   PPMDIR =	../ppm
+   INCLUDEPPM =	-I$(PPMDIR)
+ ***************
+ *** 54,101 ****
+   INCLUDE =	-I.. $(INCLUDEPPM) $(INCLUDEPGM) $(INCLUDEPBM)
+   ALLCFLAGS =	$(CFLAGS) $(INCLUDE) $(TIFFDEF) $(TIFFINC)
+   LIBPNM =	libpnm.a
+   
+   PORTBINARIES =	fitstopnm giftopnm \
+   		pnmalias pnmarith pnmcat pnmcomp pnmconvol pnmcrop \
+   		pnmcut pnmdepth pnmenlarge pnmfile pnmflip pnmhistmap \
+   		pnminvert pnmnoraw pnmpad pnmpaste \
+   		pnmtile pnmtoddif pnmtofits pnmtops pnmtorast \
+ ! 		pnmtosgi pnmtosir pnmtoxwd \
+ ! 		rasttopnm sgitopnm sirtopnm xwdtopnm zeisstopnm
+   MATHBINARIES =	pnmgamma pnmnlfilt pnmrotate pnmscale pnmshear
+ ! BINARIES =      $(PORTBINARIES) $(MATHBINARIES) $(TIFFBINARIES)
+ ! SCRIPTS =	anytopnm pnmindex pnmmargin pnmsmooth pstopnm
+   
+   PORTOBJECTS =	fitstopnm.o giftopnm.o \
+   		pnmalias.o pnmarith.o pnmcat.o pnmcomp.o pnmconvol.o pnmcrop.o \
+   		pnmcut.o pnmdepth.o pnmenlarge.o pnmfile.o pnmflip.o pnmhistmap.o \
+ ! 		pnminvert.o pnmnoraw.o pnmpad.o pnmpaste.o \
+   		pnmtile.o pnmtoddif.o pnmtofits.o pnmtops.o pnmtorast.o \
+   		pnmtosgi.o pnmtosir.o pnmtoxwd.o \
+   		rasttopnm.o sgitopnm.o sirtopnm.o xwdtopnm.o zeisstopnm.o \
+   		pnmgamma.o pnmnlfilt.o pnmrotate.o pnmscale.o pnmshear.o
+ ! OBJECTS =	$(PORTOBJECTS) $(TIFFOBJECTS)
+   
+   MANUALS1 =	$(BINARIES) $(SCRIPTS)
+   MANUALS3 =	libpnm
+   MANUALS5 =	pnm
+   
+   
+ ! #all:		binaries
+ ! all:		merge
+ ! #install:	install.bin
+ ! install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries $(SCRIPTS)
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	cp $(BINARIES) $(INSTALLBINARIES)
+   	cd $(INSTALLSCRIPTS) ; rm -f $(SCRIPTS)
+ ! 	cp $(SCRIPTS) $(INSTALLSCRIPTS)
+ ! 	cd $(INSTALLSCRIPTS) ; chmod +x $(SCRIPTS)
+ ! 
+   
+   merge:		pnmmerge
+   pnmmerge:	pnmmerge.c $(OBJECTS) $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ --- 57,108 ----
+   INCLUDE =	-I.. $(INCLUDEPPM) $(INCLUDEPGM) $(INCLUDEPBM)
+   ALLCFLAGS =	$(CFLAGS) $(INCLUDE) $(TIFFDEF) $(TIFFINC)
+   LIBPNM =	libpnm.a
+ + DEFPNM =	pnm.h
+   
+   PORTBINARIES =	fitstopnm giftopnm \
+   		pnmalias pnmarith pnmcat pnmcomp pnmconvol pnmcrop \
+   		pnmcut pnmdepth pnmenlarge pnmfile pnmflip pnmhistmap \
+   		pnminvert pnmnoraw pnmpad pnmpaste \
+   		pnmtile pnmtoddif pnmtofits pnmtops pnmtorast \
+ ! 		pnmtorle pnmtosgi pnmtosir pnmtoxwd \
+ ! 		rasttopnm rletopnm sgitopnm sirtopnm xwdtopnm zeisstopnm \
+ ! 		pnmsmooth pnmhisteq
+   MATHBINARIES =	pnmgamma pnmnlfilt pnmrotate pnmscale pnmshear
+ ! PNGBINARIES =	pngtopnm pnmtopng
+ ! BINARIES =      $(PORTBINARIES) $(MATHBINARIES) $(PNGBINARIES) $(TIFFBINARIES)
+ ! SCRIPTS =	anytopnm pnmindex pnmmargin pstopnm
+   
+   PORTOBJECTS =	fitstopnm.o giftopnm.o \
+   		pnmalias.o pnmarith.o pnmcat.o pnmcomp.o pnmconvol.o pnmcrop.o \
+   		pnmcut.o pnmdepth.o pnmenlarge.o pnmfile.o pnmflip.o pnmhistmap.o \
+ ! 		pnmhisteq.o pnminvert.o pnmnoraw.o pnmpad.o pnmpaste.o\
+   		pnmtile.o pnmtoddif.o pnmtofits.o pnmtops.o pnmtorast.o \
+   		pnmtosgi.o pnmtosir.o pnmtoxwd.o \
+   		rasttopnm.o sgitopnm.o sirtopnm.o xwdtopnm.o zeisstopnm.o \
+ + 		pnmsmooth.o pnmhisteq.o \
+   		pnmgamma.o pnmnlfilt.o pnmrotate.o pnmscale.o pnmshear.o
+ ! OBJECTS =	$(PORTOBJECTS)
+   
+   MANUALS1 =	$(BINARIES) $(SCRIPTS)
+   MANUALS3 =	libpnm
+   MANUALS5 =	pnm
+   
+   
+ ! all:		binaries
+ ! #all:		merge
+ ! install:	install.bin
+ ! #install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries $(SCRIPTS)
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	install -c -s -m 0755 $(BINARIES) $(INSTALLBINARIES)
+   	cd $(INSTALLSCRIPTS) ; rm -f $(SCRIPTS)
+ ! 	install -c -m 0755 $(SCRIPTS) $(INSTALLSCRIPTS)
+ ! 	install -c -m 0644 $(LIBPNM) $(INSTALLLIBS)
+ ! 	install -c -m 0644 $(DEFPNM) $(INSTALLDEFS)
+   
+   merge:		pnmmerge
+   pnmmerge:	pnmmerge.c $(OBJECTS) $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ ***************
+ *** 128,143 ****
+   
+   
+   # Rules for plain programs.
+ ! $(PORTBINARIES) $(TIFFBINARIES):	pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM) $(TIFFLIB)
+ ! 	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM) $(TIFFLIB)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):        pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPNM) \
+   			$(LIBPPM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And libraries.
+ --- 135,156 ----
+   
+   
+   # Rules for plain programs.
+ ! $(PORTBINARIES):	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ ! 	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ ! 
+ ! $(PNGBINARIES):	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ ! 	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM) -L${LOCALBASE}/lib -lpng -lz -lm
+ ! 
+ ! $(TIFFBINARIES):	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ ! 	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM) $(TIFFLIB) -lm -lz
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):        $(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPNM) \
+   			$(LIBPPM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPNM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And libraries.
+ ***************
+ *** 153,167 ****
+   	ar rc $(LIBPNM) libpnm1.o libpnm2.o libpnm3.o libpnm4.o
+   	-ranlib $(LIBPNM)
+   
+ ! libpnm1.o:	pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM) libpnm1.c
+   	$(CC) $(ALLCFLAGS) -c libpnm1.c
+ ! libpnm2.o:	pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM) libpnm2.c $(DEFLIBPPM) \
+   		$(DEFLIBPGM) $(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libpnm2.c
+ ! libpnm3.o:	pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM) libpnm3.c $(DEFLIBPPM) \
+   		$(DEFLIBPGM) $(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libpnm3.c
+ ! libpnm4.o:	pnm.h $(DEFPPM) $(DEFPGM) $(DEFPBM) rast.h libpnm4.c
+   	$(CC) $(ALLCFLAGS) -c libpnm4.c
+   
+   # Other dependencies.
+ --- 166,180 ----
+   	ar rc $(LIBPNM) libpnm1.o libpnm2.o libpnm3.o libpnm4.o
+   	-ranlib $(LIBPNM)
+   
+ ! libpnm1.o:	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) libpnm1.c
+   	$(CC) $(ALLCFLAGS) -c libpnm1.c
+ ! libpnm2.o:	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) libpnm2.c $(DEFLIBPPM) \
+   		$(DEFLIBPGM) $(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libpnm2.c
+ ! libpnm3.o:	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) libpnm3.c $(DEFLIBPPM) \
+   		$(DEFLIBPGM) $(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libpnm3.c
+ ! libpnm4.o:	$(DEFPNM) $(DEFPPM) $(DEFPGM) $(DEFPBM) rast.h libpnm4.c
+   	$(CC) $(ALLCFLAGS) -c libpnm4.c
+   
+   # Other dependencies.
+ ***************
+ *** 202,207 ****
+   tifftopnm tifftopnm.o:		tifftopnm.c
+   xwdtopnm xwdtopnm.o:		xwdtopnm.c x10wd.h x11wd.h
+   zeisstopnm zeisstopnm.o:	zeisstopnm.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core $(BINARIES) pnmmerge
+ --- 215,222 ----
+   tifftopnm tifftopnm.o:		tifftopnm.c
+   xwdtopnm xwdtopnm.o:		xwdtopnm.c x10wd.h x11wd.h
+   zeisstopnm zeisstopnm.o:	zeisstopnm.c
+ + pnmhisteq pnmhisteq.o:		pnmhisteq.c
+ + pnmsmooth pnmsmooth.o:          pnmsmooth.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core *.core $(BINARIES) pnmmerge
diff -r -c -N /tmp/null/patches/patch-ak ./patches/patch-ak
*** /tmp/null/patches/patch-ak	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ak	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,70 ----
+ *** ../../src/netpbm-1mar94/./pnm/anytopnm	Mon Oct  4 04:11:29 1993
+ --- ./pnm/anytopnm	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 53,59 ****
+   	;;
+   
+   	*GIF* )
+ ! 	giftoppm "$file"
+   	break
+   	;;
+   
+ --- 53,59 ----
+   	;;
+   
+   	*GIF* )
+ ! 	giftopnm "$file"
+   	break
+   	;;
+   
+ ***************
+ *** 82,87 ****
+ --- 82,96 ----
+   	break
+   	;;
+   
+ +         *JPEG* | *JFIF* )
+ +         djpeg "$file"
+ +         ;;
+ + 
+ +         *PNG* )
+ +         pngtopnm "$file"
+ +         break
+ +         ;;
+ + 
+   	* )
+   	# Can't figure out the file type from the magic number,
+   	# try the extension.
+ ***************
+ *** 130,136 ****
+   	    fitstopgm "$file"
+   	    ;;
+   	    *.gif | *.gif.* )
+ ! 	    giftoppm "$file"
+   	    ;;
+   	    *.iff | *.iff.* | *.ilbm | *.ilbm.* )
+   	    ilbmtoppm "$file"
+ --- 139,145 ----
+   	    fitstopgm "$file"
+   	    ;;
+   	    *.gif | *.gif.* )
+ ! 	    giftopnm "$file"
+   	    ;;
+   	    *.iff | *.iff.* | *.ilbm | *.ilbm.* )
+   	    ilbmtoppm "$file"
+ ***************
+ *** 168,173 ****
+ --- 177,189 ----
+   	    *.ybm | *.ybm.* | *.face | *.face.* )
+   	    ybmtopbm "$file"
+   	    ;;
+ +             *.JPEG | *.jpeg | *.jpg | *.JPG )
+ +             djpeg "$file"
+ +             ;;
+ +             *.png | *.PNG )
+ +             pngtopnm "$file"
+ +             break
+ +             ;;
+   	    * )
+   	    echo "$0: unknown file type" 1>&2
+   	    exit 1
diff -r -c -N /tmp/null/patches/patch-al ./patches/patch-al
*** /tmp/null/patches/patch-al	Wed Dec 31 18:00:00 1969
--- ./patches/patch-al	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,19 ----
+ *** ../../src/netpbm-1mar94/./pnm/pnmarith.1	Mon Oct  4 04:11:34 1993
+ --- ./pnm/pnmarith.1	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 4,10 ****
+   pnmarith - perform arithmetic on two portable anymaps
+   .SH SYNOPSIS
+   .B pnmarith
+ ! .BR -add | -subtract | -multiply | -difference
+   .I pnmfile1 pnmfile2
+   .SH DESCRIPTION
+   Reads two portable anymaps as input.
+ --- 4,10 ----
+   pnmarith - perform arithmetic on two portable anymaps
+   .SH SYNOPSIS
+   .B pnmarith
+ ! .BR -add | -subtract | -multiply | -difference | -minimum | -maximum.
+   .I pnmfile1 pnmfile2
+   .SH DESCRIPTION
+   Reads two portable anymaps as input.
diff -r -c -N /tmp/null/patches/patch-am ./patches/patch-am
*** /tmp/null/patches/patch-am	Wed Dec 31 18:00:00 1969
--- ./patches/patch-am	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,88 ----
+ *** ../../src/netpbm-1mar94/./pnm/pnmarith.c	Wed Jan  5 04:04:53 1994
+ --- ./pnm/pnmarith.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 29,35 ****
+       xelval maxval1, maxval2, maxval3;
+       int argn, rows1, cols1, format1, rows2, cols2, format2, format3, row, col;
+       char function;
+ !     char* usage = "-add|-subtract|-multiply|-difference pnmfile1 pnmfile2";
+   
+   
+       pnm_init( &argc, argv );
+ --- 29,36 ----
+       xelval maxval1, maxval2, maxval3;
+       int argn, rows1, cols1, format1, rows2, cols2, format2, format3, row, col;
+       char function;
+ !     char* usage =
+ ! "-add|-subtract|-multiply|-difference|-minimum|-maximum pnmfile1 pnmfile2";
+   
+   
+       pnm_init( &argc, argv );
+ ***************
+ *** 48,53 ****
+ --- 49,58 ----
+   	    function = '*';
+   	else if ( pm_keymatch( argv[argn], "-difference", 2 ) )
+   	    function = 'D';
+ + 	else if ( pm_keymatch( argv[argn], "-minimum", 2 ) )
+ + 	    function = 'N';
+ + 	else if ( pm_keymatch( argv[argn], "-maximum", 2 ) )
+ + 	    function = 'X';
+   	else
+   	    pm_usage( usage );
+   	++argn;
+ ***************
+ *** 112,118 ****
+   	    pnm_promoteformatrow(
+   		xelrow2, cols1, maxval2, format2, maxval3, format3 );
+   
+ !         for ( col = 0, x1P = xelrow1, x2P = xelrow2;
+   	      col < cols1; ++col, ++x1P, ++x2P )
+   	    {
+   	    switch ( PNM_FORMAT_TYPE(format3) )
+ --- 117,123 ----
+   	    pnm_promoteformatrow(
+   		xelrow2, cols1, maxval2, format2, maxval3, format3 );
+   
+ ! 	for ( col = 0, x1P = xelrow1, x2P = xelrow2;
+   	      col < cols1; ++col, ++x1P, ++x2P )
+   	    {
+   	    switch ( PNM_FORMAT_TYPE(format3) )
+ ***************
+ *** 153,158 ****
+ --- 158,175 ----
+   		    b1 = (b1>b2)?(b1-b2):(b2-b1);
+   		    break;
+   
+ + 		    case 'N':
+ + 		    r1 = (r1>r2)?(r2):(r1);
+ + 		    g1 = (g1>g2)?(g2):(g1);
+ + 		    b1 = (b1>b2)?(b2):(b1);
+ + 		    break;
+ +   
+ + 		    case 'X':
+ + 		    r1 = (r1>r2)?(r1):(r2);
+ + 		    g1 = (g1>g2)?(g1):(g2);
+ + 		    b1 = (b1>b2)?(b1):(b2);
+ + 		    break;
+ + 
+   		    default:
+   		    pm_error( "can't happen" );
+   		    }
+ ***************
+ *** 188,193 ****
+ --- 205,218 ----
+   
+   		    case 'D':
+   		    g1 = (g1>g2)?(g1-g2):(g2-g1);
+ + 		    break;
+ + 
+ + 		    case 'N':
+ + 		    g1 = (g1>g2)?(g2):(g1);
+ + 		    break;
+ +   
+ + 		    case 'X':
+ + 		    g1 = (g1>g2)?(g1):(g2);
+   		    break;
+   
+   		    default:
diff -r -c -N /tmp/null/patches/patch-an ./patches/patch-an
*** /tmp/null/patches/patch-an	Wed Dec 31 18:00:00 1969
--- ./patches/patch-an	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,1925 ----
+ *** ../../src/netpbm-1mar94/./pnm/pnmconvol.c	Mon Oct  4 04:11:36 1993
+ --- ./pnm/pnmconvol.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 1,5 ****
+ --- 1,10 ----
+   /* pnmconvol.c - general MxN convolution on a portable anymap
+   **
+ + ** Version 2.0.1 January 30, 1995
+ + **
+ + ** Major rewriting by Mike Burns
+ + ** Copyright (C) 1994, 1995 by Mike Burns (burns@chem.psu.edu)
+ + **
+   ** Copyright (C) 1989, 1991 by Jef Poskanzer.
+   **
+   ** Permission to use, copy, modify, and distribute this software and its
+ ***************
+ *** 10,40 ****
+   ** implied warranty.
+   */
+   
+   #include "pnm.h"
+   
+   int
+   main( argc, argv )
+       int argc;
+       char* argv[];
+       {
+       FILE* cifp;
+ -     FILE* ifp;
+       xel** cxels;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xel x;
+ !     int argn, crows, ccols, cformat, ccolso2, crowso2;
+ !     int rows, cols, format, newformat, crow, row;
+       register int ccol, col;
+ !     xelval cmaxval, maxval;
+       xelval g;
+ -     float** gweights;
+       float gsum;
+ -     xelval r, b;
+ -     float** rweights;
+ -     float** bweights;
+       float rsum, bsum;
+       char* usage = "<convolutionfile> [pnmfile]";
+   
+       pnm_init( &argc, argv );
+   
+ --- 15,123 ----
+   ** implied warranty.
+   */
+   
+ + /* Version 2.0.1 Changes
+ + ** ---------------------
+ + ** Fixed four lines that were improperly allocated as sizeof( float ) when they
+ + ** should have been sizeof( long ).
+ + **
+ + ** Version 2.0 Changes
+ + ** -------------------
+ + ** Reduce run time by general optimizations and handling special cases of
+ + ** convolution matrices.  Program automatically determines if convolution 
+ + ** matrix is one of the types it can make use of so no extra command line
+ + ** arguments are necessary.
+ + **
+ + ** Examples of convolution matrices for the special cases are
+ + **
+ + **    Mean       Horizontal    Vertical
+ + **    x x x        x x x        x y z
+ + **    x x x        y y y        x y z
+ + **    x x x        z z z        x y z
+ + **
+ + ** I don't know if the horizontal and vertical ones are of much use, but
+ + ** after working on the mean convolution, it gave me ideas for the other two.
+ + **
+ + ** Some other compiler dependent optimizations
+ + ** -------------------------------------------
+ + ** Created separate functions as code was getting too large to put keep both
+ + ** PGM and PPM cases in same function and also because SWITCH statement in
+ + ** inner loop can take progressively more time the larger the size of the 
+ + ** convolution matrix.  GCC is affected this way.
+ + **
+ + ** Removed use of MOD (%) operator from innermost loop by modifying manner in
+ + ** which the current xelbuf[] is chosen.
+ + ** 
+ + */
+ + 
+   #include "pnm.h"
+   
+ + /* Macros to verify that r,g,b values are within proper range */
+ + 
+ + #define CHECK_GRAY \
+ +     if ( tempgsum < 0L ) g = 0; \
+ +     else if ( tempgsum > maxval ) g = maxval; \
+ +     else g = tempgsum;
+ + 
+ + #define CHECK_RED \
+ +     if ( temprsum < 0L ) r = 0; \
+ +     else if ( temprsum > maxval ) r = maxval; \
+ +     else r = temprsum;
+ + 
+ + #define CHECK_GREEN \
+ +     if ( tempgsum < 0L ) g = 0; \
+ +     else if ( tempgsum > maxval ) g = maxval; \
+ +     else g = tempgsum;
+ + 
+ + #define CHECK_BLUE \
+ +     if ( tempbsum < 0L ) b = 0; \
+ +     else if ( tempbsum > maxval ) b = maxval; \
+ +     else b = tempbsum;
+ + 
+ + 
+ + static int check_convolve_type ARGS((xel **cxels));
+ + static void pgm_general_convolve ARGS((void));
+ + static void ppm_general_convolve ARGS((void));
+ + static void pgm_mean_convolve ARGS((void));
+ + static void ppm_mean_convolve ARGS((void));
+ + static void pgm_vertical_convolve ARGS((void));
+ + static void ppm_vertical_convolve ARGS((void));
+ + static void pgm_horizontal_convolve ARGS((void));
+ + static void ppm_horizontal_convolve ARGS((void));
+ + 
+ + #define TRUE	1
+ + #define FALSE	0
+ + 
+ + #define GENERAL_CONVOLVE	0
+ + #define MEAN_CONVOLVE		1
+ + #define HORIZONTAL_CONVOLVE	2
+ + #define VERTICAL_CONVOLVE	3
+ + 
+ + static FILE* ifp;
+ + static float** rweights;
+ + static float** gweights;
+ + static float** bweights;
+ + static int crows, ccols, ccolso2, crowso2;
+ + static int cols, rows;
+ + static xelval maxval;
+ + static int format, newformat;
+ + static float rmeanweight, gmeanweight, bmeanweight;
+ + 
+   int
+   main( argc, argv )
+       int argc;
+       char* argv[];
+       {
+       FILE* cifp;
+       xel** cxels;
+ !     int argn, cformat;
+ !     int crow, row;
+       register int ccol, col;
+ !     xelval cmaxval;
+       xelval g;
+       float gsum;
+       float rsum, bsum;
+       char* usage = "<convolutionfile> [pnmfile]";
+ +     int convolve_type;
+   
+       pnm_init( &argc, argv );
+   
+ ***************
+ *** 90,95 ****
+ --- 173,179 ----
+               }
+           }
+   
+ + 
+       /* Set up the normalized weights. */
+       rweights = (float**) pm_allocarray( ccols, crows, sizeof(float) );
+       gweights = (float**) pm_allocarray( ccols, crows, sizeof(float) );
+ ***************
+ *** 115,120 ****
+ --- 199,212 ----
+   		break;
+   		}
+   	    }
+ + 
+ +     /* For mean_convolve routines.  All weights of a single color are the same
+ +     ** so just grab any one of them.
+ +     */
+ +     rmeanweight = rweights[0][0];
+ +     gmeanweight = gweights[0][0];
+ +     bmeanweight = bweights[0][0];
+ + 
+       switch ( PNM_FORMAT_TYPE(format) )
+   	{
+   	case PPM_TYPE:
+ ***************
+ *** 131,141 ****
+ --- 223,421 ----
+   	break;
+   	}
+   
+ +     /* Handle certain special cases when runtime can be improved. */
+ + 
+ +     convolve_type = check_convolve_type(cxels);
+ + 
+ +     switch ( PNM_FORMAT_TYPE(format) )
+ + 	{
+ + 	case PPM_TYPE:
+ + 	switch (convolve_type)
+ + 	    {
+ + 	    case MEAN_CONVOLVE:
+ + 	    ppm_mean_convolve();
+ + 	    break;
+ + 
+ + 	    case HORIZONTAL_CONVOLVE:
+ + 	    ppm_horizontal_convolve();
+ + 	    break;
+ + 
+ + 	    case VERTICAL_CONVOLVE:
+ + 	    ppm_vertical_convolve();
+ + 	    break;
+ + 
+ + 	    default: /* GENERAL_CONVOLVE */
+ + 	    ppm_general_convolve();
+ + 	    break;  
+ + 	    }
+ + 	break;
+ + 
+ + 	default:
+ + 	switch (convolve_type)
+ + 	    {
+ + 	    case MEAN_CONVOLVE:
+ + 	    pgm_mean_convolve();
+ + 	    break;
+ + 
+ + 	    case HORIZONTAL_CONVOLVE:
+ + 	    pgm_horizontal_convolve();
+ + 	    break;
+ + 
+ + 	    case VERTICAL_CONVOLVE:
+ + 	    pgm_vertical_convolve();
+ + 	    break;
+ + 
+ + 	    default: /* GENERAL_CONVOLVE */
+ + 	    pgm_general_convolve();
+ + 	    break;  
+ + 	    }
+ + 	break;
+ + 	} /* PNM_TYPE */
+ + 
+ +     pm_close( ifp );
+ +     exit( 0 );
+ +     }
+ + 
+ + 
+ + 
+ + /* check_convolve_type
+ + **
+ + ** Determine if the convolution matrix is one of the special cases that
+ + ** can be processed faster than the general form.
+ + **
+ + ** Does not check for the case where one of the PPM colors can have differing 
+ + ** types.  Only handles cases where all PPM's are of the same special case.
+ + */
+ + 
+ + static int
+ + check_convolve_type (cxels)
+ +     xel **cxels;
+ +     {
+ +     int convolve_type;
+ +     int horizontal, vertical;
+ +     int tempcxel, rtempcxel, gtempcxel, btempcxel;
+ +     int crow, ccol;
+ + 
+ +     switch ( PNM_FORMAT_TYPE(format) )
+ + 	{
+ + 	case PPM_TYPE:
+ + 	horizontal = TRUE;
+ + 	crow = 0;
+ + 	while ( horizontal && (crow < crows) )
+ + 	    {
+ + 	    ccol = 1;
+ + 	    rtempcxel = PPM_GETR(cxels[crow][0]);
+ + 	    gtempcxel = PPM_GETG(cxels[crow][0]);
+ + 	    btempcxel = PPM_GETB(cxels[crow][0]);
+ + 	    while ( horizontal && (ccol < ccols) )
+ + 		{
+ + 		if (( PPM_GETR(cxels[crow][ccol]) != rtempcxel ) |
+ + 		    ( PPM_GETG(cxels[crow][ccol]) != gtempcxel ) |
+ + 		    ( PPM_GETB(cxels[crow][ccol]) != btempcxel )) 
+ + 		    horizontal = FALSE;
+ + 		++ccol;
+ + 		}
+ + 	    ++crow;
+ + 	    }
+ + 
+ + 	vertical = TRUE;
+ + 	ccol = 0;
+ + 	while ( vertical && (ccol < ccols) )
+ + 	    {
+ + 	    crow = 1;
+ + 	    rtempcxel = PPM_GETR(cxels[0][ccol]);
+ + 	    gtempcxel = PPM_GETG(cxels[0][ccol]);
+ + 	    btempcxel = PPM_GETB(cxels[0][ccol]);
+ + 	    while ( vertical && (crow < crows) )
+ + 		{
+ + 		if (( PPM_GETR(cxels[crow][ccol]) != rtempcxel ) |
+ + 		    ( PPM_GETG(cxels[crow][ccol]) != gtempcxel ) |
+ + 		    ( PPM_GETB(cxels[crow][ccol]) != btempcxel ))
+ + 		    vertical = FALSE;
+ + 		++crow;
+ + 		}
+ + 	    ++ccol;
+ + 	    }
+ + 	break;
+ + 
+ + 	default:
+ + 	horizontal = TRUE;
+ + 	crow = 0;
+ + 	while ( horizontal && (crow < crows) )
+ + 	    {
+ + 	    ccol = 1;
+ + 	    tempcxel = PNM_GET1(cxels[crow][0]);
+ + 	    while ( horizontal && (ccol < ccols) )
+ + 		{
+ + 		if ( PNM_GET1(cxels[crow][ccol]) != tempcxel )
+ + 		    horizontal = FALSE;
+ + 		++ccol;
+ + 		}
+ + 	    ++crow;
+ + 	    }
+ + 
+ + 	vertical = TRUE;
+ + 	ccol = 0;
+ + 	while ( vertical && (ccol < ccols) )
+ + 	    {
+ + 	    crow = 1;
+ + 	    tempcxel = PNM_GET1(cxels[0][ccol]);
+ + 	    while ( vertical && (crow < crows) )
+ + 		{
+ + 		if ( PNM_GET1(cxels[crow][ccol]) != tempcxel )
+ + 		    vertical = FALSE;
+ + 		++crow;
+ + 		}
+ + 	    ++ccol;
+ + 	    }
+ + 	break;
+ + 	}
+ + 
+ +     /* Which type do we have? */
+ +     if ( horizontal && vertical )
+ + 	convolve_type = MEAN_CONVOLVE;
+ +     else if ( horizontal )
+ + 	convolve_type = HORIZONTAL_CONVOLVE;
+ +     else if ( vertical )
+ + 	convolve_type = VERTICAL_CONVOLVE;
+ +     else
+ + 	convolve_type = GENERAL_CONVOLVE;
+ + 
+ +     return (convolve_type);
+ +     }
+ + 
+ + 
+ + 
+ + 
+ + /* General PGM Convolution
+ + **
+ + ** No useful redundancy in convolution matrix.
+ + */
+ + 
+ + static void
+ + pgm_general_convolve()
+ +     {
+ +     register int ccol, col;
+ +     xel** xelbuf;
+ +     xel* outputrow;
+ +     xel x, y;
+ +     xelval g;
+ +     int row, crow;
+ +     float gsum;
+ +     xel **rowptr, *temprptr;
+ +     int toprow, temprow;
+ +     int i, irow;
+ +     int leftcol;
+ +     long tempgsum;
+ + 
+       /* Allocate space for one convolution-matrix's worth of rows, plus
+       ** a row output buffer. */
+       xelbuf = pnm_allocarray( cols, crows );
+       outputrow = pnm_allocrow( cols );
+   
+ +     /* Allocate array of pointers to xelbuf */
+ +     rowptr = (xel **) pnm_allocarray( 1, crows );
+ + 
+       pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+   
+       /* Read in one convolution-matrix's worth of image, less one row. */
+ ***************
+ *** 155,219 ****
+       */
+       for ( ; row < rows; ++row )
+   	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row % crows], cols, maxval, format );
+   	if ( PNM_FORMAT_TYPE(format) != newformat )
+   	    pnm_promoteformatrow(
+ ! 		xelbuf[row % crows], cols, maxval, format, maxval, newformat );
+   
+   	for ( col = 0; col < cols; ++col )
+   	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = xelbuf[(row - crowso2) % crows][col];
+   	    else
+   		{
+ !                 switch ( PNM_FORMAT_TYPE(format) )
+ !                     {
+ !                     case PPM_TYPE:
+ ! 		    rsum = gsum = bsum = 0.0;
+ ! 		    for ( crow = 0; crow < crows; ++crow )
+ ! 			for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 			    {
+ ! 			    x = xelbuf[(row+1+crow) % crows][col-ccolso2+ccol];
+ ! 			    rsum += PPM_GETR( x ) * rweights[crow][ccol];
+ ! 			    gsum += PPM_GETG( x ) * gweights[crow][ccol];
+ ! 			    bsum += PPM_GETB( x ) * bweights[crow][ccol];
+ ! 			    }
+ ! 		    if ( rsum < 0.0 ) r = 0;
+ ! 		    else if ( rsum > maxval ) r = maxval;
+ ! 		    else r = rsum + 0.5;
+ ! 		    if ( gsum < 0.0 ) g = 0;
+ ! 		    else if ( gsum > maxval ) g = maxval;
+ ! 		    else g = gsum + 0.5;
+ ! 		    if ( bsum < 0.0 ) b = 0;
+ ! 		    else if ( bsum > maxval ) b = maxval;
+ ! 		    else b = bsum + 0.5;
+ ! 		    PPM_ASSIGN( outputrow[col], r, g, b );
+ !                     break;
+ ! 
+ !                     default:
+ ! 		    gsum = 0.0;
+ ! 		    for ( crow = 0; crow < crows; ++crow )
+ ! 			for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 			    {
+ ! 			    x = xelbuf[(row+1+crow) % crows][col-ccolso2+ccol];
+ ! 			    gsum += PNM_GET1( x ) * gweights[crow][ccol];
+ ! 			    }
+ ! 		    if ( gsum < 0.0 ) g = 0;
+ ! 		    else if ( gsum > maxval ) g = maxval;
+ ! 		    else g = gsum + 0.5;
+   		    PNM_ASSIGN1( outputrow[col], g );
+ -                     break;
+ -                     }
+   		}
+   
+   	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+   	}
+ -     pm_close( ifp );
+   
+       /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( ; row < rows + crowso2; ++row )
+   	pnm_writepnmrow(
+ !             stdout, xelbuf[(row-crowso2) % crows], cols, maxval, newformat, 0 );
+   
+       pm_close( stdout );
+ -     exit( 0 );
+       }
+ --- 435,1904 ----
+       */
+       for ( ; row < rows; ++row )
+   	{
+ ! 	toprow = row + 1;
+ ! 	temprow = row % crows;
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+   	if ( PNM_FORMAT_TYPE(format) != newformat )
+   	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	/* Arrange rowptr to eliminate the use of mod function to determine
+ ! 	** which row of xelbuf is 0...crows.  Mod function can be very costly.
+ ! 	*/
+ ! 	temprow = toprow % crows;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    rowptr[i] = xelbuf[irow];
+   
+   	for ( col = 0; col < cols; ++col )
+ + 	    {
+   	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+   	    else
+   		{
+ ! 		leftcol = col - ccolso2;
+ ! 		gsum = 0.0;
+ ! 		for ( crow = 0; crow < crows; ++crow )
+ ! 		    {
+ ! 		    temprptr = rowptr[crow] + leftcol;
+ ! 		    for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 			gsum += PNM_GET1( *(temprptr + ccol) )
+ ! 			    * gweights[crow][ccol];
+ ! 		    }
+ ! 		    tempgsum = gsum + 0.5;
+ ! 		    CHECK_GRAY;
+   		    PNM_ASSIGN1( outputrow[col], g );
+   		}
+ + 	    }
+ + 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ + 	}
+ + 
+ +     /* Now write out the remaining unconvolved rows in xelbuf. */
+ +     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ + 	pnm_writepnmrow(
+ +             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ + 
+ +     pm_close( stdout );
+ +     }
+ + 
+ + 
+ + /* PGM Mean Convolution
+ + **
+ + ** This is the common case where you just want the target pixel replaced with
+ + ** the average value of its neighbors.  This can work much faster than the
+ + ** general case because you can reduce the number of floating point operations
+ + ** that are required since all the weights are the same.  You will only need
+ + ** to multiply by the weight once, not for every pixel in the convolution
+ + ** matrix.
+ + **
+ + ** This algorithm works by creating sums for each column of crows height for
+ + ** the whole width of the image.  Then add ccols column sums together to obtain
+ + ** the total sum of the neighbors and multiply that sum by the weight.  As you
+ + ** move right to left to calculate the next pixel, take the total sum you just
+ + ** generated, add in the value of the next column and subtract the value of the
+ + ** leftmost column.  Multiply that by the weight and that's it.  As you move
+ + ** down a row, calculate new column sums by using previous sum for that column
+ + ** and adding in pixel on current row and subtracting pixel in top row.
+ + **
+ + */
+ + 
+ + 
+ + static void
+ + pgm_mean_convolve()
+ +     {
+ +     register int ccol, col;
+ +     xel** xelbuf;
+ +     xel* outputrow;
+ +     xelval g;
+ +     int row, crow;
+ +     xel **rowptr, *temprptr;
+ +     int leftcol;
+ +     int i, irow;
+ +     int toprow, temprow;
+ +     int subrow, addrow;
+ +     int subcol, addcol;
+ +     long gisum;
+ +     int tempcol, crowsp1;
+ +     long tempgsum;
+ +     long *gcolumnsum;
+ + 
+ +     /* Allocate space for one convolution-matrix's worth of rows, plus
+ +     ** a row output buffer.  MEAN uses an extra row. */
+ +     xelbuf = pnm_allocarray( cols, crows + 1 );
+ +     outputrow = pnm_allocrow( cols );
+ + 
+ +     /* Allocate array of pointers to xelbuf. MEAN uses an extra row. */
+ +     rowptr = (xel **) pnm_allocarray( 1, crows + 1);
+ + 
+ +     /* Allocate space for intermediate column sums */
+ +     gcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ +     for ( col = 0; col < cols; ++col )
+ + 	gcolumnsum[col] = 0L;
+ + 
+ +     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ + 
+ +     /* Read in one convolution-matrix's worth of image, less one row. */
+ +     for ( row = 0; row < crows - 1; ++row )
+ + 	{
+ + 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ + 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ + 	    pnm_promoteformatrow(
+ + 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ + 	/* Write out just the part we're not going to convolve. */
+ + 	if ( row < crowso2 )
+ + 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ + 	}
+ + 
+ +     /* Do first real row only */
+ +     subrow = crows;
+ +     addrow = crows - 1;
+ +     toprow = row + 1;
+ +     temprow = row % crows;
+ +     pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ +     if ( PNM_FORMAT_TYPE(format) != newformat )
+ + 	pnm_promoteformatrow(
+ + 	    xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ + 
+ +     temprow = toprow % crows;
+ +     i = 0;
+ +     for (irow = temprow; irow < crows; ++i, ++irow)
+ + 	rowptr[i] = xelbuf[irow];
+ +     for (irow = 0; irow < temprow; ++irow, ++i)
+ + 	rowptr[i] = xelbuf[irow];
+ + 
+ +     gisum = 0L;
+ +     for ( col = 0; col < cols; ++col )
+ + 	{
+ + 	if ( col < ccolso2 || col >= cols - ccolso2 )
+ + 	    outputrow[col] = rowptr[crowso2][col];
+ + 	else if ( col == ccolso2 )
+ + 	    {
+ + 	    leftcol = col - ccolso2;
+ + 	    for ( crow = 0; crow < crows; ++crow )
+ + 		{
+ + 		temprptr = rowptr[crow] + leftcol;
+ + 		for ( ccol = 0; ccol < ccols; ++ccol )
+ + 		    gcolumnsum[leftcol + ccol] += 
+ + 			PNM_GET1( *(temprptr + ccol) );
+ + 		}
+ + 	    for ( ccol = 0; ccol < ccols; ++ccol)
+ + 		gisum += gcolumnsum[leftcol + ccol];
+ + 	    tempgsum = (float) gisum * gmeanweight + 0.5;
+ + 	    CHECK_GRAY;
+ + 	    PNM_ASSIGN1( outputrow[col], g );
+ + 	    }
+ + 	else
+ + 	    {
+ + 	    /* Column numbers to subtract or add to isum */
+ + 	    subcol = col - ccolso2 - 1;
+ + 	    addcol = col + ccolso2;  
+ + 	    for ( crow = 0; crow < crows; ++crow )
+ + 		gcolumnsum[addcol] += PNM_GET1( rowptr[crow][addcol] );
+ + 	    gisum = gisum - gcolumnsum[subcol] + gcolumnsum[addcol];
+ + 	    tempgsum = (float) gisum * gmeanweight + 0.5;
+ + 	    CHECK_GRAY;
+ + 	    PNM_ASSIGN1( outputrow[col], g );
+ + 	    }
+ + 	}
+ +     pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+   
+ +     ++row;
+ +     /* For all subsequent rows do it this way as the columnsums have been
+ +     ** generated.  Now we can use them to reduce further calculations.
+ +     */
+ +     crowsp1 = crows + 1;
+ +     for ( ; row < rows; ++row )
+ + 	{
+ + 	toprow = row + 1;
+ + 	temprow = row % (crows + 1);
+ + 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ + 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ + 	    pnm_promoteformatrow(
+ + 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ + 
+ + 	/* This rearrangement using crows+1 rowptrs and xelbufs will cause
+ + 	** rowptr[0..crows-1] to always hold active xelbufs and for 
+ + 	** rowptr[crows] to always hold the oldest (top most) xelbuf.
+ + 	*/
+ + 	temprow = (toprow + 1) % crowsp1;
+ + 	i = 0;
+ + 	for (irow = temprow; irow < crowsp1; ++i, ++irow)
+ + 	    rowptr[i] = xelbuf[irow];
+ + 	for (irow = 0; irow < temprow; ++irow, ++i)
+ + 	    rowptr[i] = xelbuf[irow];
+ + 
+ + 	gisum = 0L;
+ + 	for ( col = 0; col < cols; ++col )
+ + 	    {
+ + 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ + 		outputrow[col] = rowptr[crowso2][col];
+ + 	    else if ( col == ccolso2 )
+ + 		{
+ + 		leftcol = col - ccolso2;
+ + 		for ( ccol = 0; ccol < ccols; ++ccol )
+ + 		    {
+ + 		    tempcol = leftcol + ccol;
+ + 		    gcolumnsum[tempcol] = gcolumnsum[tempcol]
+ + 			- PNM_GET1( rowptr[subrow][ccol] )
+ + 			+ PNM_GET1( rowptr[addrow][ccol] );
+ + 		    gisum += gcolumnsum[tempcol];
+ + 		    }
+ + 		tempgsum = (float) gisum * gmeanweight + 0.5;
+ + 		CHECK_GRAY;
+ + 		PNM_ASSIGN1( outputrow[col], g );
+ + 		}
+ + 	    else
+ + 		{
+ + 		/* Column numbers to subtract or add to isum */
+ + 		subcol = col - ccolso2 - 1;
+ + 		addcol = col + ccolso2;  
+ + 		gcolumnsum[addcol] = gcolumnsum[addcol]
+ + 		    - PNM_GET1( rowptr[subrow][addcol] )
+ + 		    + PNM_GET1( rowptr[addrow][addcol] );
+ + 		gisum = gisum - gcolumnsum[subcol] + gcolumnsum[addcol];
+ + 		tempgsum = (float) gisum * gmeanweight + 0.5;
+ + 		CHECK_GRAY;
+ + 		PNM_ASSIGN1( outputrow[col], g );
+ + 		}
+ + 	    }
+   	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+   	}
+   
+       /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+   	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ ! 
+ !     pm_close( stdout );
+ !     }
+ ! 
+ ! 
+ ! /* PGM Horizontal Convolution
+ ! **
+ ! ** Similar idea to using columnsums of the Mean and Vertical convolution,
+ ! ** but uses temporary sums of row values.  Need to multiply by weights crows
+ ! ** number of times.  Each time a new line is started, must recalculate the
+ ! ** initials rowsums for the newest row only.  Uses queue to still access
+ ! ** previous row sums.
+ ! **
+ ! */
+ ! 
+ ! static void
+ ! pgm_horizontal_convolve()
+ !     {
+ !     register int ccol, col;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xel x;
+ !     xelval g;
+ !     int row, crow;
+ !     xel **rowptr, *temprptr;
+ !     int leftcol;
+ !     int i, irow;
+ !     int temprow;
+ !     int subcol, addcol;
+ !     float gsum;
+ !     int addrow, subrow;
+ !     long **growsum, **growsumptr;
+ !     int crowsp1;
+ !     long tempgsum;
+ ! 
+ !     /* Allocate space for one convolution-matrix's worth of rows, plus
+ !     ** a row output buffer. */
+ !     xelbuf = pnm_allocarray( cols, crows + 1 );
+ !     outputrow = pnm_allocrow( cols );
+ ! 
+ !     /* Allocate array of pointers to xelbuf */
+ !     rowptr = (xel **) pnm_allocarray( 1, crows + 1);
+ ! 
+ !     /* Allocate intermediate row sums.  HORIZONTAL uses an extra row. */
+ !     /* crows current rows and 1 extra for newest added row.           */
+ !     growsum = (long **) pm_allocarray( cols, crows + 1, sizeof(long) );
+ !     growsumptr = (long **) pnm_allocarray( 1, crows + 1);
+ ! 
+ !     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ ! 
+ !     /* Read in one convolution-matrix's worth of image, less one row. */
+ !     for ( row = 0; row < crows - 1; ++row )
+ ! 	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ ! 	/* Write out just the part we're not going to convolve. */
+ ! 	if ( row < crowso2 )
+ ! 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* First row only */
+ !     temprow = row % crows;
+ !     pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ !     if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	pnm_promoteformatrow(
+ ! 	    xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ !     temprow = (row + 1) % crows;
+ !     i = 0;
+ !     for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	rowptr[i] = xelbuf[irow];
+ !     for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	rowptr[i] = xelbuf[irow];
+ ! 
+ !     for ( crow = 0; crow < crows; ++crow )
+ ! 	growsumptr[crow] = growsum[crow];
+ !  
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 	    outputrow[col] = rowptr[crowso2][col];
+ ! 	else if ( col == ccolso2 )
+ ! 	    {
+ ! 	    leftcol = col - ccolso2;
+ ! 	    gsum = 0.0;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		temprptr = rowptr[crow] + leftcol;
+ ! 		growsumptr[crow][leftcol] = 0L;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    growsumptr[crow][leftcol] += 
+ ! 		        PNM_GET1( *(temprptr + ccol) );
+ ! 		gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		}
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    CHECK_GRAY;
+ ! 	    PNM_ASSIGN1( outputrow[col], g );
+ ! 	    }
+ ! 	else
+ ! 	    {
+ ! 	    gsum = 0.0;
+ ! 	    leftcol = col - ccolso2;
+ ! 	    subcol = col - ccolso2 - 1;
+ ! 	    addcol = col + ccolso2;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		growsumptr[crow][leftcol] = growsumptr[crow][subcol]
+ ! 		    - PNM_GET1( rowptr[crow][subcol] )
+ ! 		    + PNM_GET1( rowptr[crow][addcol] );
+ ! 		gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		}
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    CHECK_GRAY;
+ ! 	    PNM_ASSIGN1( outputrow[col], g );
+ ! 	    }
+ !         }
+ !     pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 
+ ! 
+ !     /* For all subsequent rows */
+ ! 
+ !     subrow = crows;
+ !     addrow = crows - 1;
+ !     crowsp1 = crows + 1;
+ !     ++row;
+ !     for ( ; row < rows; ++row )
+ ! 	{
+ ! 	temprow = row % crowsp1;
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	temprow = (row + 2) % crowsp1;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crowsp1; ++i, ++irow)
+ ! 	    {
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	    growsumptr[i] = growsum[irow];
+ ! 	    }
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    {
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	    growsumptr[i] = growsum[irow];
+ ! 	    }
+ ! 
+ ! 	for ( col = 0; col < cols; ++col )
+ ! 	    {
+ ! 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+ ! 	    else if ( col == ccolso2 )
+ ! 		{
+ ! 		gsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		growsumptr[addrow][leftcol] = 0L;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    growsumptr[addrow][leftcol] += 
+ ! 			PNM_GET1( rowptr[addrow][leftcol + ccol] );
+ ! 		for ( crow = 0; crow < crows; ++crow )
+ ! 		    gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		tempgsum = gsum + 0.5;
+ ! 		CHECK_GRAY;
+ ! 		PNM_ASSIGN1( outputrow[col], g );
+ ! 		}
+ ! 	    else
+ ! 		{
+ ! 		gsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		subcol = col - ccolso2 - 1;
+ ! 		addcol = col + ccolso2;  
+ ! 		growsumptr[addrow][leftcol] = growsumptr[addrow][subcol]
+ ! 		    - PNM_GET1( rowptr[addrow][subcol] )
+ ! 		    + PNM_GET1( rowptr[addrow][addcol] );
+ ! 		for ( crow = 0; crow < crows; ++crow )
+ ! 		    gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		tempgsum = gsum + 0.5;
+ ! 		CHECK_GRAY;
+ ! 		PNM_ASSIGN1( outputrow[col], g );
+ ! 		}
+ ! 	    }
+ ! 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ ! 	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ ! 
+ !     pm_close( stdout );
+ !     }
+ ! 
+ ! 
+ ! /* PGM Vertical Convolution
+ ! **
+ ! ** Uses column sums as in Mean Convolution.
+ ! **
+ ! */
+ ! 
+ ! 
+ ! static void
+ ! pgm_vertical_convolve()
+ !     {
+ !     register int ccol, col;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xelval g;
+ !     int row, crow;
+ !     xel **rowptr, *temprptr;
+ !     int leftcol;
+ !     int i, irow;
+ !     int toprow, temprow;
+ !     int subrow, addrow;
+ !     int tempcol;
+ !     float gsum;
+ !     long *gcolumnsum;
+ !     int crowsp1;
+ !     int addcol;
+ !     long tempgsum;
+ ! 
+ !     /* Allocate space for one convolution-matrix's worth of rows, plus
+ !     ** a row output buffer. VERTICAL uses an extra row. */
+ !     xelbuf = pnm_allocarray( cols, crows + 1 );
+ !     outputrow = pnm_allocrow( cols );
+ ! 
+ !     /* Allocate array of pointers to xelbuf */
+ !     rowptr = (xel **) pnm_allocarray( 1, crows + 1 );
+ ! 
+ !     /* Allocate space for intermediate column sums */
+ !     gcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     for ( col = 0; col < cols; ++col )
+ ! 	gcolumnsum[col] = 0L;
+ ! 
+ !     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ ! 
+ !     /* Read in one convolution-matrix's worth of image, less one row. */
+ !     for ( row = 0; row < crows - 1; ++row )
+ ! 	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ ! 	/* Write out just the part we're not going to convolve. */
+ ! 	if ( row < crowso2 )
+ ! 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now the rest of the image - read in the row at the end of
+ !     ** xelbuf, and convolve and write out the row in the middle.
+ !     */
+ !     /* For first row only */
+ ! 
+ !     toprow = row + 1;
+ !     temprow = row % crows;
+ !     pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ !     if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	pnm_promoteformatrow(
+ ! 	    xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ !     /* Arrange rowptr to eliminate the use of mod function to determine
+ !     ** which row of xelbuf is 0...crows.  Mod function can be very costly.
+ !     */
+ !     temprow = toprow % crows;
+ !     i = 0;
+ !     for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	rowptr[i] = xelbuf[irow];
+ !     for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	rowptr[i] = xelbuf[irow];
+ ! 
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 	    outputrow[col] = rowptr[crowso2][col];
+ ! 	else if ( col == ccolso2 )
+ ! 	    {
+ ! 	    gsum = 0.0;
+ ! 	    leftcol = col - ccolso2;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		temprptr = rowptr[crow] + leftcol;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    gcolumnsum[leftcol + ccol] += 
+ ! 			PNM_GET1( *(temprptr + ccol) );
+ ! 		}
+ ! 	    for ( ccol = 0; ccol < ccols; ++ccol)
+ ! 		gsum += gcolumnsum[leftcol + ccol] * gweights[0][ccol];
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    CHECK_GRAY;
+ ! 	    PNM_ASSIGN1( outputrow[col], g );
+ ! 	    }
+ ! 	else
+ ! 	    {
+ ! 	    gsum = 0.0;
+ ! 	    leftcol = col - ccolso2;
+ ! 	    addcol = col + ccolso2;  
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		gcolumnsum[addcol] += PNM_GET1( rowptr[crow][addcol] );
+ ! 	    for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		gsum += gcolumnsum[leftcol + ccol] * gweights[0][ccol];
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    CHECK_GRAY;
+ ! 	    PNM_ASSIGN1( outputrow[col], g );
+ ! 	    }
+ ! 	}
+ !     pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 
+ !     /* For all subsequent rows */
+ !     subrow = crows;
+ !     addrow = crows - 1;
+ !     crowsp1 = crows + 1;
+ !     ++row;
+ !     for ( ; row < rows; ++row )
+ ! 	{
+ ! 	toprow = row + 1;
+ ! 	temprow = row % (crows +1);
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	/* Arrange rowptr to eliminate the use of mod function to determine
+ ! 	** which row of xelbuf is 0...crows.  Mod function can be very costly.
+ ! 	*/
+ ! 	temprow = (toprow + 1) % crowsp1;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crowsp1; ++i, ++irow)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 
+ ! 	for ( col = 0; col < cols; ++col )
+ ! 	    {
+ ! 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+ ! 	    else if ( col == ccolso2 )
+ ! 		{
+ ! 		gsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    tempcol = leftcol + ccol;
+ ! 		    gcolumnsum[tempcol] = gcolumnsum[tempcol] 
+ ! 			- PNM_GET1( rowptr[subrow][ccol] )
+ ! 			+ PNM_GET1( rowptr[addrow][ccol] );
+ ! 		    gsum = gsum + gcolumnsum[tempcol] * gweights[0][ccol];
+ ! 		    }
+ ! 		tempgsum = gsum + 0.5;
+ ! 		CHECK_GRAY;
+ ! 		PNM_ASSIGN1( outputrow[col], g );
+ ! 		}
+ ! 	    else
+ ! 		{
+ ! 		gsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		addcol = col + ccolso2;
+ ! 		gcolumnsum[addcol] = gcolumnsum[addcol]
+ ! 		    - PNM_GET1( rowptr[subrow][addcol] )
+ ! 		    + PNM_GET1( rowptr[addrow][addcol] );
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    gsum += gcolumnsum[leftcol + ccol] * gweights[0][ccol];
+ ! 		tempgsum = gsum + 0.5;
+ ! 		CHECK_GRAY;
+ ! 		PNM_ASSIGN1( outputrow[col], g );
+ ! 		}
+ ! 	    }
+ ! 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ ! 	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ ! 
+ !     pm_close( stdout );
+ !     }
+ ! 
+ ! 
+ ! 
+ ! 
+ ! /* PPM General Convolution Algorithm
+ ! **
+ ! ** No redundancy in convolution matrix.  Just use brute force.
+ ! ** See pgm_general_convolve() for more details.
+ ! */
+ ! 
+ ! static void
+ ! ppm_general_convolve()
+ !     {
+ !     register int ccol, col;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xel x, y;
+ !     xelval r, g, b;
+ !     int row, crow;
+ !     float rsum, gsum, bsum;
+ !     xel **rowptr, *temprptr;
+ !     int toprow, temprow;
+ !     int i, irow;
+ !     int leftcol;
+ !     long temprsum, tempgsum, tempbsum;
+ ! 
+ !     /* Allocate space for one convolution-matrix's worth of rows, plus
+ !     ** a row output buffer. */
+ !     xelbuf = pnm_allocarray( cols, crows );
+ !     outputrow = pnm_allocrow( cols );
+ ! 
+ !     /* Allocate array of pointers to xelbuf */
+ !     rowptr = (xel **) pnm_allocarray( 1, crows );
+ ! 
+ !     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ ! 
+ !     /* Read in one convolution-matrix's worth of image, less one row. */
+ !     for ( row = 0; row < crows - 1; ++row )
+ ! 	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ ! 	/* Write out just the part we're not going to convolve. */
+ ! 	if ( row < crowso2 )
+ ! 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now the rest of the image - read in the row at the end of
+ !     ** xelbuf, and convolve and write out the row in the middle.
+ !     */
+ !     for ( ; row < rows; ++row )
+ ! 	{
+ ! 	toprow = row + 1;
+ ! 	temprow = row % crows;
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	/* Arrange rowptr to eliminate the use of mod function to determine
+ ! 	** which row of xelbuf is 0...crows.  Mod function can be very costly.
+ ! 	*/
+ ! 	temprow = toprow % crows;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 
+ ! 	for ( col = 0; col < cols; ++col )
+ ! 	    {
+ ! 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+ ! 	    else
+ ! 		{
+ ! 		leftcol = col - ccolso2;
+ ! 		rsum = gsum = bsum = 0.0;
+ ! 		for ( crow = 0; crow < crows; ++crow )
+ ! 		    {
+ ! 		    temprptr = rowptr[crow] + leftcol;
+ ! 		    for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 			{
+ ! 			rsum += PPM_GETR( *(temprptr + ccol) )
+ ! 			    * rweights[crow][ccol];
+ ! 			gsum += PPM_GETG( *(temprptr + ccol) )
+ ! 			    * gweights[crow][ccol];
+ ! 			bsum += PPM_GETB( *(temprptr + ccol) )
+ ! 			    * bweights[crow][ccol];
+ ! 			}
+ ! 		    }
+ ! 		    temprsum = rsum + 0.5;
+ ! 		    tempgsum = gsum + 0.5;
+ ! 		    tempbsum = bsum + 0.5;
+ ! 		    CHECK_RED;
+ ! 		    CHECK_GREEN;
+ ! 		    CHECK_BLUE;
+ ! 		    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    }
+ ! 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ ! 	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ ! 
+ !     pm_close( stdout );
+ !     }
+ ! 
+ ! 
+ ! /* PPM Mean Convolution
+ ! **
+ ! ** Same as pgm_mean_convolve() but for PPM.
+ ! **
+ ! */
+ ! 
+ ! static void
+ ! ppm_mean_convolve()
+ !     {
+ !     register int ccol, col;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xelval r, g, b;
+ !     int row, crow;
+ !     xel **rowptr, *temprptr;
+ !     int leftcol;
+ !     int i, irow;
+ !     int toprow, temprow;
+ !     int subrow, addrow;
+ !     int subcol, addcol;
+ !     long risum, gisum, bisum;
+ !     float rsum, gsum, bsum;
+ !     long temprsum, tempgsum, tempbsum;
+ !     int tempcol, crowsp1;
+ !     long *rcolumnsum, *gcolumnsum, *bcolumnsum;
+ ! 
+ !     /* Allocate space for one convolution-matrix's worth of rows, plus
+ !     ** a row output buffer.  MEAN uses an extra row. */
+ !     xelbuf = pnm_allocarray( cols, crows + 1 );
+ !     outputrow = pnm_allocrow( cols );
+ ! 
+ !     /* Allocate array of pointers to xelbuf. MEAN uses an extra row. */
+ !     rowptr = (xel **) pnm_allocarray( 1, crows + 1);
+ ! 
+ !     /* Allocate space for intermediate column sums */
+ !     rcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     gcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     bcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	rcolumnsum[col] = 0L;
+ ! 	gcolumnsum[col] = 0L;
+ ! 	bcolumnsum[col] = 0L;
+ ! 	}
+ ! 
+ !     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ ! 
+ !     /* Read in one convolution-matrix's worth of image, less one row. */
+ !     for ( row = 0; row < crows - 1; ++row )
+ ! 	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ ! 	/* Write out just the part we're not going to convolve. */
+ ! 	if ( row < crowso2 )
+ ! 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Do first real row only */
+ !     subrow = crows;
+ !     addrow = crows - 1;
+ !     toprow = row + 1;
+ !     temprow = row % crows;
+ !     pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ !     if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	pnm_promoteformatrow(
+ ! 	    xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ !     temprow = toprow % crows;
+ !     i = 0;
+ !     for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	rowptr[i] = xelbuf[irow];
+ !     for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	rowptr[i] = xelbuf[irow];
+ ! 
+ !     risum = 0L;
+ !     gisum = 0L;
+ !     bisum = 0L;
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 	    outputrow[col] = rowptr[crowso2][col];
+ ! 	else if ( col == ccolso2 )
+ ! 	    {
+ ! 	    leftcol = col - ccolso2;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		temprptr = rowptr[crow] + leftcol;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    rcolumnsum[leftcol + ccol] += 
+ ! 			PPM_GETR( *(temprptr + ccol) );
+ ! 		    gcolumnsum[leftcol + ccol] += 
+ ! 			PPM_GETG( *(temprptr + ccol) );
+ ! 		    bcolumnsum[leftcol + ccol] += 
+ ! 			PPM_GETB( *(temprptr + ccol) );
+ ! 		    }
+ ! 		}
+ ! 	    for ( ccol = 0; ccol < ccols; ++ccol)
+ ! 		{
+ ! 		risum += rcolumnsum[leftcol + ccol];
+ ! 		gisum += gcolumnsum[leftcol + ccol];
+ ! 		bisum += bcolumnsum[leftcol + ccol];
+ ! 		}
+ ! 	    temprsum = (float) risum * rmeanweight + 0.5;
+ ! 	    tempgsum = (float) gisum * gmeanweight + 0.5;
+ ! 	    tempbsum = (float) bisum * bmeanweight + 0.5;
+ ! 	    CHECK_RED;
+ ! 	    CHECK_GREEN;
+ ! 	    CHECK_BLUE;
+ ! 	    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 	    }
+ ! 	else
+ ! 	    {
+ ! 	    /* Column numbers to subtract or add to isum */
+ ! 	    subcol = col - ccolso2 - 1;
+ ! 	    addcol = col + ccolso2;  
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		rcolumnsum[addcol] += PPM_GETR( rowptr[crow][addcol] );
+ ! 		gcolumnsum[addcol] += PPM_GETG( rowptr[crow][addcol] );
+ ! 		bcolumnsum[addcol] += PPM_GETB( rowptr[crow][addcol] );
+ ! 		}
+ ! 	    risum = risum - rcolumnsum[subcol] + rcolumnsum[addcol];
+ ! 	    gisum = gisum - gcolumnsum[subcol] + gcolumnsum[addcol];
+ ! 	    bisum = bisum - bcolumnsum[subcol] + bcolumnsum[addcol];
+ ! 	    temprsum = (float) risum * rmeanweight + 0.5;
+ ! 	    tempgsum = (float) gisum * gmeanweight + 0.5;
+ ! 	    tempbsum = (float) bisum * bmeanweight + 0.5;
+ ! 	    CHECK_RED;
+ ! 	    CHECK_GREEN;
+ ! 	    CHECK_BLUE;
+ ! 	    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 	    }
+ ! 	}
+ !     pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 
+ !     ++row;
+ !     /* For all subsequent rows do it this way as the columnsums have been
+ !     ** generated.  Now we can use them to reduce further calculations.
+ !     */
+ !     crowsp1 = crows + 1;
+ !     for ( ; row < rows; ++row )
+ ! 	{
+ ! 	toprow = row + 1;
+ ! 	temprow = row % (crows + 1);
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	/* This rearrangement using crows+1 rowptrs and xelbufs will cause
+ ! 	** rowptr[0..crows-1] to always hold active xelbufs and for 
+ ! 	** rowptr[crows] to always hold the oldest (top most) xelbuf.
+ ! 	*/
+ ! 	temprow = (toprow + 1) % crowsp1;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crowsp1; ++i, ++irow)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 
+ ! 	risum = 0L;
+ ! 	gisum = 0L;
+ ! 	bisum = 0L;
+ ! 	for ( col = 0; col < cols; ++col )
+ ! 	    {
+ ! 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+ ! 	    else if ( col == ccolso2 )
+ ! 		{
+ ! 		leftcol = col - ccolso2;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    tempcol = leftcol + ccol;
+ ! 		    rcolumnsum[tempcol] = rcolumnsum[tempcol]
+ ! 			- PPM_GETR( rowptr[subrow][ccol] )
+ ! 			+ PPM_GETR( rowptr[addrow][ccol] );
+ ! 		    risum += rcolumnsum[tempcol];
+ ! 		    gcolumnsum[tempcol] = gcolumnsum[tempcol]
+ ! 			- PPM_GETG( rowptr[subrow][ccol] )
+ ! 			+ PPM_GETG( rowptr[addrow][ccol] );
+ ! 		    gisum += gcolumnsum[tempcol];
+ ! 		    bcolumnsum[tempcol] = bcolumnsum[tempcol]
+ ! 			- PPM_GETB( rowptr[subrow][ccol] )
+ ! 			+ PPM_GETB( rowptr[addrow][ccol] );
+ ! 		    bisum += bcolumnsum[tempcol];
+ ! 		    }
+ ! 		temprsum = (float) risum * rmeanweight + 0.5;
+ ! 		tempgsum = (float) gisum * gmeanweight + 0.5;
+ ! 		tempbsum = (float) bisum * bmeanweight + 0.5;
+ ! 		CHECK_RED;
+ ! 		CHECK_GREEN;
+ ! 		CHECK_BLUE;
+ ! 		PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    else
+ ! 		{
+ ! 		/* Column numbers to subtract or add to isum */
+ ! 		subcol = col - ccolso2 - 1;
+ ! 		addcol = col + ccolso2;  
+ ! 		rcolumnsum[addcol] = rcolumnsum[addcol]
+ ! 		    - PPM_GETR( rowptr[subrow][addcol] )
+ ! 		    + PPM_GETR( rowptr[addrow][addcol] );
+ ! 		risum = risum - rcolumnsum[subcol] + rcolumnsum[addcol];
+ ! 		gcolumnsum[addcol] = gcolumnsum[addcol]
+ ! 		    - PPM_GETG( rowptr[subrow][addcol] )
+ ! 		    + PPM_GETG( rowptr[addrow][addcol] );
+ ! 		gisum = gisum - gcolumnsum[subcol] + gcolumnsum[addcol];
+ ! 		bcolumnsum[addcol] = bcolumnsum[addcol]
+ ! 		    - PPM_GETB( rowptr[subrow][addcol] )
+ ! 		    + PPM_GETB( rowptr[addrow][addcol] );
+ ! 		bisum = bisum - bcolumnsum[subcol] + bcolumnsum[addcol];
+ ! 		temprsum = (float) risum * rmeanweight + 0.5;
+ ! 		tempgsum = (float) gisum * gmeanweight + 0.5;
+ ! 		tempbsum = (float) bisum * bmeanweight + 0.5;
+ ! 		CHECK_RED;
+ ! 		CHECK_GREEN;
+ ! 		CHECK_BLUE;
+ ! 		PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    }
+ ! 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ ! 	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ ! 
+ !     pm_close( stdout );
+ !     }
+ ! 
+ ! 
+ ! /* PPM Horizontal Convolution
+ ! **
+ ! ** Same as pgm_horizontal_convolve()
+ ! **
+ ! **/
+ ! 
+ ! static void
+ ! ppm_horizontal_convolve()
+ !     {
+ !     register int ccol, col;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xel x;
+ !     xelval r, g, b;
+ !     int row, crow;
+ !     xel **rowptr, *temprptr;
+ !     int leftcol;
+ !     int i, irow;
+ !     int temprow;
+ !     int subcol, addcol;
+ !     float rsum, gsum, bsum;
+ !     int addrow, subrow;
+ !     long **rrowsum, **rrowsumptr;
+ !     long **growsum, **growsumptr;
+ !     long **browsum, **browsumptr;
+ !     int crowsp1;
+ !     long temprsum, tempgsum, tempbsum;
+ ! 
+ !     /* Allocate space for one convolution-matrix's worth of rows, plus
+ !     ** a row output buffer. */
+ !     xelbuf = pnm_allocarray( cols, crows + 1 );
+ !     outputrow = pnm_allocrow( cols );
+ ! 
+ !     /* Allocate array of pointers to xelbuf */
+ !     rowptr = (xel **) pnm_allocarray( 1, crows + 1);
+ ! 
+ !     /* Allocate intermediate row sums.  HORIZONTAL uses an extra row */
+ !     rrowsum = (long **) pm_allocarray( cols, crows + 1, sizeof(long) );
+ !     rrowsumptr = (long **) pnm_allocarray( 1, crows + 1);
+ !     growsum = (long **) pm_allocarray( cols, crows + 1, sizeof(long) );
+ !     growsumptr = (long **) pnm_allocarray( 1, crows + 1);
+ !     browsum = (long **) pm_allocarray( cols, crows + 1, sizeof(long) );
+ !     browsumptr = (long **) pnm_allocarray( 1, crows + 1);
+ ! 
+ !     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ ! 
+ !     /* Read in one convolution-matrix's worth of image, less one row. */
+ !     for ( row = 0; row < crows - 1; ++row )
+ ! 	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ ! 	/* Write out just the part we're not going to convolve. */
+ ! 	if ( row < crowso2 )
+ ! 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* First row only */
+ !     temprow = row % crows;
+ !     pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ !     if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	pnm_promoteformatrow(
+ ! 	    xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ !     temprow = (row + 1) % crows;
+ !     i = 0;
+ !     for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	rowptr[i] = xelbuf[irow];
+ !     for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	rowptr[i] = xelbuf[irow];
+ ! 
+ !     for ( crow = 0; crow < crows; ++crow )
+ ! 	{
+ ! 	rrowsumptr[crow] = rrowsum[crow];
+ ! 	growsumptr[crow] = growsum[crow];
+ ! 	browsumptr[crow] = browsum[crow];
+ ! 	}
+ !  
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 	    outputrow[col] = rowptr[crowso2][col];
+ ! 	else if ( col == ccolso2 )
+ ! 	    {
+ ! 	    leftcol = col - ccolso2;
+ ! 	    rsum = 0.0;
+ ! 	    gsum = 0.0;
+ ! 	    bsum = 0.0;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		temprptr = rowptr[crow] + leftcol;
+ ! 		rrowsumptr[crow][leftcol] = 0L;
+ ! 		growsumptr[crow][leftcol] = 0L;
+ ! 		browsumptr[crow][leftcol] = 0L;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    rrowsumptr[crow][leftcol] += 
+ ! 		        PPM_GETR( *(temprptr + ccol) );
+ ! 		    growsumptr[crow][leftcol] += 
+ ! 		        PPM_GETG( *(temprptr + ccol) );
+ ! 		    browsumptr[crow][leftcol] += 
+ ! 		        PPM_GETB( *(temprptr + ccol) );
+ ! 		    }
+ ! 		rsum += rrowsumptr[crow][leftcol] * rweights[crow][0];
+ ! 		gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		bsum += browsumptr[crow][leftcol] * bweights[crow][0];
+ ! 		}
+ ! 	    temprsum = rsum + 0.5;
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    tempbsum = bsum + 0.5;
+ ! 	    CHECK_RED;
+ ! 	    CHECK_GREEN;
+ ! 	    CHECK_BLUE;
+ ! 	    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 	    }
+ ! 	else
+ ! 	    {
+ ! 	    rsum = 0.0;
+ ! 	    gsum = 0.0;
+ ! 	    bsum = 0.0;
+ ! 	    leftcol = col - ccolso2;
+ ! 	    subcol = col - ccolso2 - 1;
+ ! 	    addcol = col + ccolso2;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		rrowsumptr[crow][leftcol] = rrowsumptr[crow][subcol]
+ ! 		    - PPM_GETR( rowptr[crow][subcol] )
+ ! 		    + PPM_GETR( rowptr[crow][addcol] );
+ ! 		rsum += rrowsumptr[crow][leftcol] * rweights[crow][0];
+ ! 		growsumptr[crow][leftcol] = growsumptr[crow][subcol]
+ ! 		    - PPM_GETG( rowptr[crow][subcol] )
+ ! 		    + PPM_GETG( rowptr[crow][addcol] );
+ ! 		gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		browsumptr[crow][leftcol] = browsumptr[crow][subcol]
+ ! 		    - PPM_GETB( rowptr[crow][subcol] )
+ ! 		    + PPM_GETB( rowptr[crow][addcol] );
+ ! 		bsum += browsumptr[crow][leftcol] * bweights[crow][0];
+ ! 		}
+ ! 	    temprsum = rsum + 0.5;
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    tempbsum = bsum + 0.5;
+ ! 	    CHECK_RED;
+ ! 	    CHECK_GREEN;
+ ! 	    CHECK_BLUE;
+ ! 	    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 	    }
+ !         }
+ !     pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 
+ ! 
+ !     /* For all subsequent rows */
+ ! 
+ !     subrow = crows;
+ !     addrow = crows - 1;
+ !     crowsp1 = crows + 1;
+ !     ++row;
+ !     for ( ; row < rows; ++row )
+ ! 	{
+ ! 	temprow = row % crowsp1;
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	temprow = (row + 2) % crowsp1;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crowsp1; ++i, ++irow)
+ ! 	    {
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	    rrowsumptr[i] = rrowsum[irow];
+ ! 	    growsumptr[i] = growsum[irow];
+ ! 	    browsumptr[i] = browsum[irow];
+ ! 	    }
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    {
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	    rrowsumptr[i] = rrowsum[irow];
+ ! 	    growsumptr[i] = growsum[irow];
+ ! 	    browsumptr[i] = browsum[irow];
+ ! 	    }
+ ! 
+ ! 	for ( col = 0; col < cols; ++col )
+ ! 	    {
+ ! 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+ ! 	    else if ( col == ccolso2 )
+ ! 		{
+ ! 		rsum = 0.0;
+ ! 		gsum = 0.0;
+ ! 		bsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		rrowsumptr[addrow][leftcol] = 0L;
+ ! 		growsumptr[addrow][leftcol] = 0L;
+ ! 		browsumptr[addrow][leftcol] = 0L;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    rrowsumptr[addrow][leftcol] += 
+ ! 			PPM_GETR( rowptr[addrow][leftcol + ccol] );
+ ! 		    growsumptr[addrow][leftcol] += 
+ ! 			PPM_GETG( rowptr[addrow][leftcol + ccol] );
+ ! 		    browsumptr[addrow][leftcol] += 
+ ! 			PPM_GETB( rowptr[addrow][leftcol + ccol] );
+ ! 		    }
+ ! 		for ( crow = 0; crow < crows; ++crow )
+ ! 		    {
+ ! 		    rsum += rrowsumptr[crow][leftcol] * rweights[crow][0];
+ ! 		    gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		    bsum += browsumptr[crow][leftcol] * bweights[crow][0];
+ ! 		    }
+ ! 		temprsum = rsum + 0.5;
+ ! 		tempgsum = gsum + 0.5;
+ ! 		tempbsum = bsum + 0.5;
+ ! 		CHECK_RED;
+ ! 		CHECK_GREEN;
+ ! 		CHECK_BLUE;
+ ! 		PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    else
+ ! 		{
+ ! 		rsum = 0.0;
+ ! 		gsum = 0.0;
+ ! 		bsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		subcol = col - ccolso2 - 1;
+ ! 		addcol = col + ccolso2;  
+ ! 		rrowsumptr[addrow][leftcol] = rrowsumptr[addrow][subcol]
+ ! 		    - PPM_GETR( rowptr[addrow][subcol] )
+ ! 		    + PPM_GETR( rowptr[addrow][addcol] );
+ ! 		growsumptr[addrow][leftcol] = growsumptr[addrow][subcol]
+ ! 		    - PPM_GETG( rowptr[addrow][subcol] )
+ ! 		    + PPM_GETG( rowptr[addrow][addcol] );
+ ! 		browsumptr[addrow][leftcol] = browsumptr[addrow][subcol]
+ ! 		    - PPM_GETB( rowptr[addrow][subcol] )
+ ! 		    + PPM_GETB( rowptr[addrow][addcol] );
+ ! 		for ( crow = 0; crow < crows; ++crow )
+ ! 		    {
+ ! 		    rsum += rrowsumptr[crow][leftcol] * rweights[crow][0];
+ ! 		    gsum += growsumptr[crow][leftcol] * gweights[crow][0];
+ ! 		    bsum += browsumptr[crow][leftcol] * bweights[crow][0];
+ ! 		    }
+ ! 		temprsum = rsum + 0.5;
+ ! 		tempgsum = gsum + 0.5;
+ ! 		tempbsum = bsum + 0.5;
+ ! 		CHECK_RED;
+ ! 		CHECK_GREEN;
+ ! 		CHECK_BLUE;
+ ! 		PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    }
+ ! 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ ! 	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+ ! 
+ !     pm_close( stdout );
+ !     }
+ ! 
+ ! 
+ ! /* PPM Vertical Convolution
+ ! **
+ ! ** Same as pgm_vertical_convolve()
+ ! **
+ ! */
+ ! 
+ ! static void
+ ! ppm_vertical_convolve()
+ !     {
+ !     register int ccol, col;
+ !     xel** xelbuf;
+ !     xel* outputrow;
+ !     xelval r, g, b;
+ !     int row, crow;
+ !     xel **rowptr, *temprptr;
+ !     int leftcol;
+ !     int i, irow;
+ !     int toprow, temprow;
+ !     int subrow, addrow;
+ !     int tempcol;
+ !     float rsum, gsum, bsum;
+ !     long *rcolumnsum, *gcolumnsum, *bcolumnsum;
+ !     int crowsp1;
+ !     int addcol;
+ !     long temprsum, tempgsum, tempbsum;
+ ! 
+ !     /* Allocate space for one convolution-matrix's worth of rows, plus
+ !     ** a row output buffer. VERTICAL uses an extra row. */
+ !     xelbuf = pnm_allocarray( cols, crows + 1 );
+ !     outputrow = pnm_allocrow( cols );
+ ! 
+ !     /* Allocate array of pointers to xelbuf */
+ !     rowptr = (xel **) pnm_allocarray( 1, crows + 1 );
+ ! 
+ !     /* Allocate space for intermediate column sums */
+ !     rcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     gcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     bcolumnsum = (long *) pm_allocrow( cols, sizeof(long) );
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	rcolumnsum[col] = 0L;
+ ! 	gcolumnsum[col] = 0L;
+ ! 	bcolumnsum[col] = 0L;
+ ! 	}
+ ! 
+ !     pnm_writepnminit( stdout, cols, rows, maxval, newformat, 0 );
+ ! 
+ !     /* Read in one convolution-matrix's worth of image, less one row. */
+ !     for ( row = 0; row < crows - 1; ++row )
+ ! 	{
+ ! 	pnm_readpnmrow( ifp, xelbuf[row], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[row], cols, maxval, format, maxval, newformat );
+ ! 	/* Write out just the part we're not going to convolve. */
+ ! 	if ( row < crowso2 )
+ ! 	    pnm_writepnmrow( stdout, xelbuf[row], cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now the rest of the image - read in the row at the end of
+ !     ** xelbuf, and convolve and write out the row in the middle.
+ !     */
+ !     /* For first row only */
+ ! 
+ !     toprow = row + 1;
+ !     temprow = row % crows;
+ !     pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ !     if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	pnm_promoteformatrow(
+ ! 	    xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ !     /* Arrange rowptr to eliminate the use of mod function to determine
+ !     ** which row of xelbuf is 0...crows.  Mod function can be very costly.
+ !     */
+ !     temprow = toprow % crows;
+ !     i = 0;
+ !     for (irow = temprow; irow < crows; ++i, ++irow)
+ ! 	rowptr[i] = xelbuf[irow];
+ !     for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	rowptr[i] = xelbuf[irow];
+ ! 
+ !     for ( col = 0; col < cols; ++col )
+ ! 	{
+ ! 	if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 	    outputrow[col] = rowptr[crowso2][col];
+ ! 	else if ( col == ccolso2 )
+ ! 	    {
+ ! 	    rsum = 0.0;
+ ! 	    gsum = 0.0;
+ ! 	    bsum = 0.0;
+ ! 	    leftcol = col - ccolso2;
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		temprptr = rowptr[crow] + leftcol;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    rcolumnsum[leftcol + ccol] += 
+ ! 			PPM_GETR( *(temprptr + ccol) );
+ ! 		    gcolumnsum[leftcol + ccol] += 
+ ! 			PPM_GETG( *(temprptr + ccol) );
+ ! 		    bcolumnsum[leftcol + ccol] += 
+ ! 			PPM_GETB( *(temprptr + ccol) );
+ ! 		    }
+ ! 		}
+ ! 	    for ( ccol = 0; ccol < ccols; ++ccol)
+ ! 		{
+ ! 		rsum += rcolumnsum[leftcol + ccol] * rweights[0][ccol];
+ ! 		gsum += gcolumnsum[leftcol + ccol] * gweights[0][ccol];
+ ! 		bsum += bcolumnsum[leftcol + ccol] * bweights[0][ccol];
+ ! 		}
+ ! 	    temprsum = rsum + 0.5;
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    tempbsum = bsum + 0.5;
+ ! 	    CHECK_RED;
+ ! 	    CHECK_GREEN;
+ ! 	    CHECK_BLUE;
+ ! 	    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 	    }
+ ! 	else
+ ! 	    {
+ ! 	    rsum = 0.0;
+ ! 	    gsum = 0.0;
+ ! 	    bsum = 0.0;
+ ! 	    leftcol = col - ccolso2;
+ ! 	    addcol = col + ccolso2;  
+ ! 	    for ( crow = 0; crow < crows; ++crow )
+ ! 		{
+ ! 		rcolumnsum[addcol] += PPM_GETR( rowptr[crow][addcol] );
+ ! 		gcolumnsum[addcol] += PPM_GETG( rowptr[crow][addcol] );
+ ! 		bcolumnsum[addcol] += PPM_GETB( rowptr[crow][addcol] );
+ ! 		}
+ ! 	    for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		{
+ ! 		rsum += rcolumnsum[leftcol + ccol] * rweights[0][ccol];
+ ! 		gsum += gcolumnsum[leftcol + ccol] * gweights[0][ccol];
+ ! 		bsum += bcolumnsum[leftcol + ccol] * bweights[0][ccol];
+ ! 		}
+ ! 	    temprsum = rsum + 0.5;
+ ! 	    tempgsum = gsum + 0.5;
+ ! 	    tempbsum = bsum + 0.5;
+ ! 	    CHECK_RED;
+ ! 	    CHECK_GREEN;
+ ! 	    CHECK_BLUE;
+ ! 	    PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 	    }
+ ! 	}
+ !     pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 
+ !     /* For all subsequent rows */
+ !     subrow = crows;
+ !     addrow = crows - 1;
+ !     crowsp1 = crows + 1;
+ !     ++row;
+ !     for ( ; row < rows; ++row )
+ ! 	{
+ ! 	toprow = row + 1;
+ ! 	temprow = row % (crows +1);
+ ! 	pnm_readpnmrow( ifp, xelbuf[temprow], cols, maxval, format );
+ ! 	if ( PNM_FORMAT_TYPE(format) != newformat )
+ ! 	    pnm_promoteformatrow(
+ ! 		xelbuf[temprow], cols, maxval, format, maxval, newformat );
+ ! 
+ ! 	/* Arrange rowptr to eliminate the use of mod function to determine
+ ! 	** which row of xelbuf is 0...crows.  Mod function can be very costly.
+ ! 	*/
+ ! 	temprow = (toprow + 1) % crowsp1;
+ ! 	i = 0;
+ ! 	for (irow = temprow; irow < crowsp1; ++i, ++irow)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 	for (irow = 0; irow < temprow; ++irow, ++i)
+ ! 	    rowptr[i] = xelbuf[irow];
+ ! 
+ ! 	for ( col = 0; col < cols; ++col )
+ ! 	    {
+ ! 	    if ( col < ccolso2 || col >= cols - ccolso2 )
+ ! 		outputrow[col] = rowptr[crowso2][col];
+ ! 	    else if ( col == ccolso2 )
+ ! 		{
+ ! 		rsum = 0.0;
+ ! 		gsum = 0.0;
+ ! 		bsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    tempcol = leftcol + ccol;
+ ! 		    rcolumnsum[tempcol] = rcolumnsum[tempcol] 
+ ! 			- PPM_GETR( rowptr[subrow][ccol] )
+ ! 			+ PPM_GETR( rowptr[addrow][ccol] );
+ ! 		    rsum = rsum + rcolumnsum[tempcol] * rweights[0][ccol];
+ ! 		    gcolumnsum[tempcol] = gcolumnsum[tempcol] 
+ ! 			- PPM_GETG( rowptr[subrow][ccol] )
+ ! 			+ PPM_GETG( rowptr[addrow][ccol] );
+ ! 		    gsum = gsum + gcolumnsum[tempcol] * gweights[0][ccol];
+ ! 		    bcolumnsum[tempcol] = bcolumnsum[tempcol] 
+ ! 			- PPM_GETB( rowptr[subrow][ccol] )
+ ! 			+ PPM_GETB( rowptr[addrow][ccol] );
+ ! 		    bsum = bsum + bcolumnsum[tempcol] * bweights[0][ccol];
+ ! 		    }
+ ! 		temprsum = rsum + 0.5;
+ ! 		tempgsum = gsum + 0.5;
+ ! 		tempbsum = bsum + 0.5;
+ ! 		CHECK_RED;
+ ! 		CHECK_GREEN;
+ ! 		CHECK_BLUE;
+ ! 		PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    else
+ ! 		{
+ ! 		rsum = 0.0;
+ ! 		gsum = 0.0;
+ ! 		bsum = 0.0;
+ ! 		leftcol = col - ccolso2;
+ ! 		addcol = col + ccolso2;
+ ! 		rcolumnsum[addcol] = rcolumnsum[addcol]
+ ! 		    - PPM_GETR( rowptr[subrow][addcol] )
+ ! 		    + PPM_GETR( rowptr[addrow][addcol] );
+ ! 		gcolumnsum[addcol] = gcolumnsum[addcol]
+ ! 		    - PPM_GETG( rowptr[subrow][addcol] )
+ ! 		    + PPM_GETG( rowptr[addrow][addcol] );
+ ! 		bcolumnsum[addcol] = bcolumnsum[addcol]
+ ! 		    - PPM_GETB( rowptr[subrow][addcol] )
+ ! 		    + PPM_GETB( rowptr[addrow][addcol] );
+ ! 		for ( ccol = 0; ccol < ccols; ++ccol )
+ ! 		    {
+ ! 		    rsum += rcolumnsum[leftcol + ccol] * rweights[0][ccol];
+ ! 		    gsum += gcolumnsum[leftcol + ccol] * gweights[0][ccol];
+ ! 		    bsum += bcolumnsum[leftcol + ccol] * bweights[0][ccol];
+ ! 		    }
+ ! 		temprsum = rsum + 0.5;
+ ! 		tempgsum = gsum + 0.5;
+ ! 		tempbsum = bsum + 0.5;
+ ! 		CHECK_RED;
+ ! 		CHECK_GREEN;
+ ! 		CHECK_BLUE;
+ ! 		PPM_ASSIGN( outputrow[col], r, g, b );
+ ! 		}
+ ! 	    }
+ ! 	pnm_writepnmrow( stdout, outputrow, cols, maxval, newformat, 0 );
+ ! 	}
+ ! 
+ !     /* Now write out the remaining unconvolved rows in xelbuf. */
+ !     for ( irow = crowso2 + 1; irow < crows; ++irow )
+ ! 	pnm_writepnmrow(
+ !             stdout, rowptr[irow], cols, maxval, newformat, 0 );
+   
+       pm_close( stdout );
+       }
diff -r -c -N /tmp/null/patches/patch-ao ./patches/patch-ao
*** /tmp/null/patches/patch-ao	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ao	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,35 ----
+ *** ../../src/netpbm-1mar94/./pnm/pnmmerge.c	Mon Jan 31 05:31:47 1994
+ --- ./pnm/pnmmerge.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 30,35 ****
+ --- 30,39 ----
+   	{
+   	++argv;
+   	--argc;
+ + 	if(!*argv)	{
+ + 		fprintf(stderr, "Usage: pnmmerge pnm_program_name [args ...]\n");
+ + 		exit(1);
+ + 		}
+   	goto again;
+   	}
+   
+ ***************
+ *** 51,56 ****
+ --- 55,61 ----
+       TRY("pnmgamma", pnmgamma_main);
+       TRY("pnminvert", pnminvert_main);
+       TRY("pnmhistmap", pnmhistmap_main);
+ +     TRY("pnmhisteq", pnmhisteq_main);
+       TRY("pnmnlfilt", pnmnlfilt_main);
+       TRY("pnmnoraw", pnmnoraw_main);
+       TRY("pnmpaste", pnmpaste_main);
+ ***************
+ *** 76,81 ****
+ --- 81,87 ----
+   #endif /*LIBTIFF*/
+       TRY("xwdtopnm", xwdtopnm_main);
+       TRY("zeisstopnm", zeisstopnm_main);
+ +     TRY("pnmsmooth", pnmsmooth_main);
+   
+       (void) fprintf(
+   	stderr, "pnmmerge: \"%s\" is an unknown PNM program!\n", cp );
diff -r -c -N /tmp/null/patches/patch-ap ./patches/patch-ap
*** /tmp/null/patches/patch-ap	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ap	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,72 ----
+ *** ../../src/netpbm-1mar94/./pnm/pnmsmooth.1	Mon Oct  4 04:11:56 1993
+ --- ./pnm/pnmsmooth.1	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 1,25 ****
+ ! .TH pnmsmooth 1 "13 January 1991"
+   .IX pnmsmooth
+   .SH NAME
+   pnmsmooth - smooth out an image
+   .SH SYNOPSIS
+   .B pnmsmooth
+   .RI [ pnmfile ]
+   .SH DESCRIPTION
+   Smooths out an image by replacing each pixel with the
+ ! average of its nine immediate neighbors.
+   .IX smoothing
+   .IX anti-aliasing
+ ! It is implemented as a simple script using
+   .IR pnmconvol .
+   .IX pnmconvol
+   .SH "SEE ALSO"
+   pnmconvol(1), pnm(5)
+ ! .SH BUGS
+ ! It's a script.
+ ! Scripts are not portable to non-Unix environments.
+ ! .SH AUTHOR
+   Copyright (C) 1989, 1991 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
+ --- 1,42 ----
+ ! .TH pnmsmooth 1 "4 December 1994"
+   .IX pnmsmooth
+   .SH NAME
+   pnmsmooth - smooth out an image
+   .SH SYNOPSIS
+   .B pnmsmooth
+ + .RB [ -size
+ + .IR width
+ + .IR height ]
+ + .RB [ -dump
+ + .IR dumpfile ]
+   .RI [ pnmfile ]
+   .SH DESCRIPTION
+   Smooths out an image by replacing each pixel with the
+ ! average of its width X height neighbors.
+   .IX smoothing
+   .IX anti-aliasing
+ ! It is implemented as a C progam that generates a PGM convolution matrix
+ ! and then invokes
+   .IR pnmconvol .
+   .IX pnmconvol
+ + .SH OPTIONS
+ + .TP
+ + .B -size width height
+ + Specifies the size of the convolution matrix.  
+ + Default size is a 3x3 matrix.
+ + Width and height sizes must be odd.  
+ + Maximum size of convolution matrix is limited by the maximum value for a 
+ + pixel such that (width * height * 2) must not exceed the maximum pixel value.
+ + .TP
+ + .B -dump dumpfile
+ + Generates and saves the convolution file only.
+ + Use of this option does not invoke pnmconvol.
+   .SH "SEE ALSO"
+   pnmconvol(1), pnm(5)
+ ! .SH AUTHORS
+   Copyright (C) 1989, 1991 by Jef Poskanzer.
+ + .br
+ + Converted from script to C program December 1994 by Mike Burns (burns@chem.psu.edu).
+   .\" 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
diff -r -c -N /tmp/null/patches/patch-aq ./patches/patch-aq
*** /tmp/null/patches/patch-aq	Wed Dec 31 18:00:00 1969
--- ./patches/patch-aq	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,55 ----
+ *** ../../src/netpbm-1mar94/./pnm/pnmtotiff.c	Thu Jan 27 10:59:25 1994
+ --- ./pnm/pnmtotiff.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 196,201 ****
+ --- 196,202 ----
+   	    samplesperpixel = 1;
+   	    bitspersample = pm_maxvaltobits( maxval );
+   	    photometric = PHOTOMETRIC_MINISBLACK;
+ + 	    i = 8 / bitspersample;
+   	    bytesperrow = ( cols + i - 1 ) / i;
+   	    }
+   	else
+ ***************
+ *** 276,295 ****
+   		for ( col = 0, xP = xels[row], tP = buf;
+   		      col < cols; ++col, ++xP )
+   		    {
+ ! 		    register unsigned char s;
+   
+   		    s = PPM_GETR( *xP );
+   		    if ( maxval != 255 )
+ ! 			s = (long) s * 255 / maxval;
+ ! 		    *tP++ = s;
+   		    s = PPM_GETG( *xP );
+   		    if ( maxval != 255 )
+ ! 			s = (long) s * 255 / maxval;
+ ! 		    *tP++ = s;
+   		    s = PPM_GETB( *xP );
+   		    if ( maxval != 255 )
+ ! 			s = (long) s * 255 / maxval;
+ ! 		    *tP++ = s;
+   		    }
+   		}
+   	    else
+ --- 277,296 ----
+   		for ( col = 0, xP = xels[row], tP = buf;
+   		      col < cols; ++col, ++xP )
+   		    {
+ ! 		    register xelval s;
+   
+   		    s = PPM_GETR( *xP );
+   		    if ( maxval != 255 )
+ ! 			s = s * 255 / maxval;
+ ! 		    *tP++ = (unsigned char)s;
+   		    s = PPM_GETG( *xP );
+   		    if ( maxval != 255 )
+ ! 			s = s * 255 / maxval;
+ ! 		    *tP++ = (unsigned char)s;
+   		    s = PPM_GETB( *xP );
+   		    if ( maxval != 255 )
+ ! 			s = s * 255 / maxval;
+ ! 		    *tP++ = (unsigned char)s;
+   		    }
+   		}
+   	    else
diff -r -c -N /tmp/null/patches/patch-ar ./patches/patch-ar
*** /tmp/null/patches/patch-ar	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ar	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,133 ----
+ *** ../../src/netpbm-1mar94/./pnm/tifftopnm.c	Mon Oct  4 04:12:01 1993
+ --- ./pnm/tifftopnm.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 54,60 ****
+       int headerdump;
+       register u_char sample;
+       register int bitsleft;
+ !     unsigned short bps, spp, photomet;
+       unsigned short* redcolormap;
+       unsigned short* greencolormap;
+       unsigned short* bluecolormap;
+ --- 54,60 ----
+       int headerdump;
+       register u_char sample;
+       register int bitsleft;
+ !     unsigned short bps, spp, photomet, planarconfig;
+       unsigned short* redcolormap;
+       unsigned short* greencolormap;
+       unsigned short* bluecolormap;
+ ***************
+ *** 101,106 ****
+ --- 101,113 ----
+   	spp = 1;
+       if ( ! TIFFGetField( tif, TIFFTAG_PHOTOMETRIC, &photomet ) )
+   	pm_error( "error getting photometric" );
+ +     if( spp > 1 ){
+ + 	if ( ! TIFFGetField( tif, TIFFTAG_PLANARCONFIG, &planarconfig ) )
+ + 	    pm_error( "error getting planarconfig" );
+ +     }else{
+ + 	planarconfig = PLANARCONFIG_CONTIG;
+ +     }
+ + 
+   
+       switch ( spp )
+   	{
+ ***************
+ *** 114,119 ****
+ --- 121,138 ----
+   	    "can only handle 1-channel gray scale or 1- or 3-channel color" );
+   	}
+   
+ +     switch( planarconfig )
+ + 	{
+ + 	case PLANARCONFIG_CONTIG:
+ + 	    break;
+ + 	case PLANARCONFIG_SEPARATE:
+ + 	    if( photomet != PHOTOMETRIC_RGB )
+ + 		pm_error( "can only handle separate planes with RGB data" );
+ + 	    break;
+ + 	default:
+ + 	    pm_error("Unrecongnized PLANARCONFIG tag!\n");
+ + 	}
+ + 
+       (void) TIFFGetField( tif, TIFFTAG_IMAGEWIDTH, &cols );
+       (void) TIFFGetField( tif, TIFFTAG_IMAGELENGTH, &rows );
+   
+ ***************
+ *** 259,278 ****
+   	    break;
+   
+   	    case PHOTOMETRIC_RGB:
+ ! 	    for ( col = 0; col < cols; ++col, ++xP )
+ ! 		{
+ ! 		register xelval r, g, b;
+ ! 
+ ! 		NEXTSAMPLE
+ ! 		r = sample;
+ ! 		NEXTSAMPLE
+ ! 		g = sample;
+ ! 		NEXTSAMPLE
+ ! 		b = sample;
+ ! 		if ( spp == 4 )
+ ! 		    NEXTSAMPLE		/* skip alpha channel */
+ ! 		PPM_ASSIGN( *xP, r, g, b );
+ ! 		}
+   	    break;
+   
+   	    default:
+ --- 278,331 ----
+   	    break;
+   
+   	    case PHOTOMETRIC_RGB:
+ ! 	    if( planarconfig == PLANARCONFIG_CONTIG ){
+ ! 		for ( col = 0; col < cols; ++col, ++xP )
+ ! 		    {
+ ! 		    register xelval r, g, b;
+ ! 
+ ! 		    NEXTSAMPLE
+ ! 		    r = sample;
+ ! 		    NEXTSAMPLE
+ ! 		    g = sample;
+ ! 		    NEXTSAMPLE
+ ! 		    b = sample;
+ ! 		    if ( spp == 4 )
+ ! 		        NEXTSAMPLE /* skip alpha channel */
+ ! 		    PPM_ASSIGN( *xP, r, g, b );
+ ! 		    }
+ ! 	    }else{
+ ! 		/* First clear the value and assign the reds */
+ ! 		for ( col = 0; col < cols; ++col, ++xP )
+ ! 		    {
+ ! 			NEXTSAMPLE
+ ! 			PPM_ASSIGN( *xP, 0, 0, 0 );
+ ! 			PPM_PUTR( *xP, sample );
+ ! 		    }
+ ! 
+ ! 		/* Next the greens */
+ ! 		if ( TIFFReadScanline( tif, buf, row, 1 ) < 0 )
+ ! 		    pm_error( "bad data read on green line %d", row );
+ ! 		xP = xelrow;
+ ! 		inP = buf;
+ ! 		bitsleft = 8;
+ ! 		for ( col = 0; col < cols; ++col, ++xP )
+ ! 		    {
+ ! 			NEXTSAMPLE
+ ! 			PPM_PUTG( *xP, sample );
+ ! 		    }
+ ! 
+ ! 		/* And finally the blues */
+ ! 		if ( TIFFReadScanline( tif, buf, row, 2 ) < 0 )
+ ! 		    pm_error( "bad data read on green line %d", row );
+ ! 		xP = xelrow;
+ ! 		inP = buf;
+ ! 		bitsleft = 8;
+ ! 		for ( col = 0; col < cols; ++col, ++xP )
+ ! 		    {
+ ! 			NEXTSAMPLE
+ ! 			PPM_PUTB( *xP, sample );
+ ! 		    }
+ ! 	    }		
+   	    break;
+   
+   	    default:
diff -r -c -N /tmp/null/patches/patch-as ./patches/patch-as
*** /tmp/null/patches/patch-as	Wed Dec 31 18:00:00 1969
--- ./patches/patch-as	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,166 ----
+ *** /dev/null	Sat Jan  9 13:03:49 1999
+ --- ./pnm/pnmhisteq.1	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 0 ****
+ --- 1,161 ----
+ + .TH pnmhisteq 1 "19 March 1995"
+ + .IX "pnmhisteq command"
+ + .IX histogram
+ + .SH NAME
+ + pnmhisteq \- histogram equalise a portable anymap
+ + .SH SYNOPSIS
+ + .na
+ + .B pnmhisteq
+ + 'ti 15
+ + .RB [ \-gray ]
+ + .RB [ \-rmap
+ + .IR pgmfile ]
+ + .RB [ \-wmap
+ + .IR pgmfile ]
+ + .RB [ \-verbose ]
+ + .RI [ pnmfile ]
+ + .ad
+ + .SH DESCRIPTION
+ + .B pnmhisteq
+ + increases the contrast of a portable graymap or pixmap through the
+ + technique of
+ + .IR "histogram equalisation" [1].
+ + A histogram of the luminance of pixels in the map is computed, from
+ + which a transfer function is calculated which spreads out intensity levels
+ + around histogram peaks and compresses them at troughs.  This has the
+ + effect of using the available levels of intensity more efficiently and
+ + thereby increases the detail visible in the image.
+ + .PP
+ + Mathematically, if
+ + .I N[i]
+ + is the number of pixels of luminosity
+ + .I i
+ + in the image and
+ + .I T
+ + is the total number of pixels, luminosity
+ + .I j
+ + is replaced by:
+ + .PP
+ + .NF
+ + .vs 9p
+ +          j
+ +         ---
+ +         \\
+ +          \>   N[i] / T
+ +         \/
+ +         ---
+ +         i=0
+ + .vs
+ + .FI
+ + .PP
+ + If you're processing a related set of images, for example frames of an
+ + animation, it's generally best to apply the same intensity map to
+ + every frame, since otherwise you'll get distracting frame-to-frame
+ + changes in the brightness of objects.
+ + .BR pnmhisteq 's
+ + .B \-wmap
+ + option
+ + allows you to save, as a portable graymap, the luminosity map computed
+ + from an image (usually a composite of the images you intend
+ + to process created with
+ + .BR pnmcat ).
+ + Then, you can subsequently process each of the individual images using
+ + the luminosity map saved in the file, supplied with the
+ + .B \-rmap
+ + option.
+ + .SH OPTIONS
+ + .TP 10
+ + .B \-gray
+ + When processing a pixmap, only gray pixels (those with identical red,
+ + green, and blue values) are included in the histogram and modified
+ + in the output image.  This is a special purpose option intended
+ + for images where the actual data are gray scale, with
+ + colour annotations you don't want modified.  Weather
+ + satellite images that show continent outlines in colour are best
+ + processed using this option.  The option has no effect when the input
+ + is a graymap.
+ + .TP
+ + .BI \-rmap " mapfile"
+ + Process the image using the luminosity map specified by the portable
+ + graymap
+ + .I mapfile.
+ + The graymap, usually created by an earlier run of
+ + .B pnmhisteq
+ + with the 
+ + .B \-wmap
+ + option, contains a single row with number of columns equal to
+ + the
+ + .I maxval
+ + (greatest intensity) of the image.  Each pixel in the image is
+ + transformed by looking up its luminosity in the corresponding
+ + column in the map file and changing it to the value
+ + given by that column.
+ + .TP
+ + .BI \-wmap " mapfile"
+ + Creates a portable graymap,
+ + .I mapfile,
+ + containing the luminosity map computed from the histogram of the
+ + input image.  This map file can be read on subsequent runs of
+ + .B pnmhisteq
+ + with the
+ + .B \-rmap
+ + option, allowing a group of images to be processed with
+ + an identical map.
+ + .TP
+ + .B \-verbose
+ + Prints the histogram and luminosity map on standard error.
+ + .PP
+ + All flags can be abbreviated to their shortest unique prefix.
+ + .SH BUGS
+ + Histogram equalisation is effective for increasing the visible detail
+ + in scientific imagery and in some continuous-tone pictures.  It is
+ + often too drastic, however, for scanned halftone images, where it
+ + does an excellent job of making halftone artifacts apparent.  You
+ + might want to experiment with
+ + .BR pgnnorm ,
+ + .BR ppmnorm ,
+ + and
+ + .B pnmgamma
+ + for more subtle contrast enhancement.
+ + .PP
+ + The luminosity map file supplied by the
+ + .B \-rmap
+ + option must have the same
+ + .I maxval
+ + as the input image.  This is always the case when the
+ + map file was created by the
+ + .B \-wmap
+ + option of 
+ + .BR pnmhisteq .
+ + If this restriction causes a problem, simply adjust the
+ + .I maxval
+ + of the map with
+ + .B pnmdepth
+ + to agree with the input image.
+ + .PP
+ + If the input is a PBM file (on which histogram equalisation is an
+ + identity operation), the only effect of passing the file through
+ + .B pnmhisteq
+ + will be the passage of time.
+ + .SH "SEE ALSO"
+ + .PD
+ + .BR pgmnorm (1),
+ + .BR pnm (5),
+ + .BR pnmcat (1),
+ + .BR pnmdepth (1),
+ + .BR pnmgamma (1),
+ + .BR pnmnorm (1)
+ + .TP 5
+ + [1]
+ + Russ, John C.  The Image Processing Handbook.
+ + Boca Raton: CRC Press, 1992.  Pages 105-110.
+ + .ne 10
+ + .SH AUTHOR
+ + .ce 2
+ + Copyright (C) 1995 by John Walker (kelvin@fourmilab.ch).
+ + WWW home page: http://www.fourmilab.ch/
+ + .PP
+ + Permission to use, copy, modify, and distribute this software and its
+ + documentation for any purpose and without fee is hereby granted,
+ + without any conditions or restrictions.  This software is provided ``as
+ + is'' without express or implied warranty.
diff -r -c -N /tmp/null/patches/patch-at ./patches/patch-at
*** /tmp/null/patches/patch-at	Wed Dec 31 18:00:00 1969
--- ./patches/patch-at	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,376 ----
+ *** /dev/null	Sat Jan  9 13:03:49 1999
+ --- ./pnm/pnmhisteq.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 0 ****
+ --- 1,371 ----
+ + /*
+ + 			     pnmhisteq.c
+ + 
+ + 	       Equalise histogram for a PGM or PPM file
+ + 
+ +    Options:	-gray:	  modify gray pixels only; leave colours unchanged
+ + 		-rmap fn: read luminosity map from PGM file fn
+ + 		-wmap wn: write luminosity map to PGM file fn
+ + 		-verbose: print histogram and luminosity map
+ + 
+ +     Accepts PGM and PPM as input.  PBM input is allowed, but histogram
+ +     equalisation does not modify a PBM file.
+ + 
+ + 	  by John Walker (kelvin@fourmilab.ch) -- March MVM.
+ + 	       WWW home page: http://www.fourmilab.ch/
+ + 
+ + 		  Copyright (C) 1995 by John Walker
+ + 
+ +     Permission	to use, copy, modify, and distribute this software and
+ +     its documentation for  any	purpose  and  without  fee  is	hereby
+ +     granted, without any conditions or restrictions.  This software is
+ +     provided "as is" without express or implied warranty.
+ + 
+ + */
+ + 
+ + #include "pnm.h"
+ + 
+ + /* Prototypes */
+ + 
+ + static void hsv_rgb ARGS((double h, double s, double v,
+ + 			  double *r, double *g, double *b));
+ + static void rgb_hsv ARGS((double r, double g, double b,
+ + 			  double *h, double *s, double *v));
+ + 
+ + /*  HSV_RGB  --  Convert HSV colour specification to RGB  intensities.
+ + 		 Hue is specified as a	real  value  from  0  to  360,
+ + 		 Saturation  and  Intensity as reals from 0 to 1.  The
+ + 		 RGB components are returned as reals from 0 to 1. */
+ + 
+ + static void hsv_rgb(h, s, v, r, g, b)
+ +   double h, s, v;
+ +   double *r, *g, *b;
+ + {
+ +     int i;
+ +     double f, p, q, t;
+ + 
+ +     if (s == 0) {
+ + 	*r = *g = *b = v;
+ +     } else {
+ + 	if (h == 360.0) {
+ + 	    h = 0;
+ + 	}
+ + 	h /= 60.0;
+ + 
+ + 	i = h;
+ + 	f = h - i;
+ + 	p = v * (1.0 - s);
+ + 	q = v * (1.0 - (s * f));
+ + 	t = v * (1.0 - (s * (1.0 - f)));
+ + 	switch (i) {
+ + 
+ + 	    case 0:
+ + 		*r = v;
+ + 		*g = t;
+ + 		*b = p;
+ + 		break;
+ + 
+ + 	    case 1:
+ + 		*r = q;
+ + 		*g = v;
+ + 		*b = p;
+ + 		break;
+ + 
+ + 	    case 2:
+ + 		*r = p;
+ + 		*g = v;
+ + 		*b = t;
+ + 		break;
+ + 
+ + 	    case 3:
+ + 		*r = p;
+ + 		*g = q;
+ + 		*b = v;
+ + 		break;
+ + 
+ + 	    case 4:
+ + 		*r = t;
+ + 		*g = p;
+ + 		*b = v;
+ + 		break;
+ + 
+ + 	    case 5:
+ + 		*r = v;
+ + 		*g = p;
+ + 		*b = q;
+ + 		break;
+ + 	 }
+ +     }
+ + }
+ + 
+ + /*  RGB_HSV  --  Map R, G, B intensities in the range from 0 to 1 into
+ + 		 Hue, Saturation,  and	Value:	Hue  from  0  to  360,
+ + 		 Saturation  from  0  to  1,  and  Value  from 0 to 1.
+ +                  Special case: if Saturation is 0 (it's a  grey  scale
+ + 		 tone), Hue is undefined and is returned as -1.
+ + 
+ + 		 This follows Foley & van Dam, section 17.4.4. */
+ + 
+ + static void rgb_hsv(r, g, b, h, s, v)
+ +   double r, g, b;
+ +   double *h, *s, *v;
+ + {
+ +     double imax = max(r, max(g, b)),
+ + 	   imin = min(r, min(g, b)),
+ + 	   rc, gc, bc;
+ + 
+ +     *v = imax;
+ +     if (imax != 0) {
+ + 	*s = (imax - imin) / imax;
+ +     } else {
+ + 	*s = 0;
+ +     }
+ + 
+ +     if (*s == 0) {
+ + 	*h = -1;
+ +     } else {
+ + 	rc = (imax - r) / (imax - imin);
+ + 	gc = (imax - g) / (imax - imin);
+ + 	bc = (imax - b) / (imax - imin);
+ + 	if (r == imax) {
+ + 	    *h = bc - gc;
+ + 	} else if (g == imax) {
+ + 	    *h = 2.0 + rc - bc;
+ + 	} else {
+ + 	    *h = 4.0 + gc - rc;
+ + 	}
+ + 	*h *= 60.0;
+ + 	if (*h < 0.0) {
+ + 	    *h += 360.0;
+ + 	}
+ +     }
+ + }
+ + 
+ + int main(argc, argv)
+ +   int argc;
+ +   char *argv[];
+ + {
+ +     FILE *ifp;
+ +     int argn = 1, i, j, verbose = 0, mono_only = 0;
+ +     gray lmin, lmax;
+ +     gray **lumamap;		      /* Luminosity map */
+ +     long *lumahist;		      /* Histogram of luminosity values */
+ +     int rows, hist_cols;	      /* Rows, columns of input image */
+ +     xelval maxval;		      /* Maxval of input image */
+ +     int format; 		      /* Format indicator (PBM/PGM/PPM) */
+ +     xel** xels; 		      /* Pixel array */
+ +     unsigned long pixels = 0, pixsum = 0, maxluma = 0;
+ +     double lscale;
+ +     xel *grayrow;
+ +     pixel *pixrow;
+ +     FILE *rmap = NULL, *wmap = NULL;
+ +     char *usage = "[-gray] [-verbose] [-rmap pgmfile] [-wmap pgmfile] [pnmfile]";
+ + 
+ +     pnm_init(&argc, argv);
+ + 
+ +     /* Check for flags. */
+ + 
+ +     while (argn < argc && argv[argn][0] == '-' && argv[argn][1] != '\0') {
+ +         if (pm_keymatch(argv[argn], "-gray", 1)) {
+ + 	    mono_only = 1;
+ +         } else if (pm_keymatch(argv[argn], "-verbose", 1)) {
+ + 	    verbose = 1;
+ +         } else if (pm_keymatch(argv[argn], "-rmap", 1)) {
+ + 	    if (rmap != NULL) {
+ +                 pm_error("already specified an input map");
+ + 	    }
+ + 	    argn++;
+ +             if (argn == argc || strcmp(argv[argn], "-") == 0) {
+ + 		pm_usage(usage);
+ + 	    }
+ + 	    rmap = pm_openr(argv[argn]);
+ +         } else if (pm_keymatch(argv[argn], "-wmap", 1)) {
+ + 	    if (wmap != NULL) {
+ +                 pm_error("already specified an output map");
+ + 	    }
+ + 	    argn++;
+ + 	    if (argn == argc) {
+ + 		pm_usage(usage);
+ + 	    }
+ + 	    wmap = pm_openw(argv[argn]);
+ + 	} else {
+ + 	    pm_usage(usage);
+ + 	}
+ + 	argn++;
+ +     }
+ + 
+ +     if (--argc > argn) {
+ + 	pm_usage(usage);
+ +     } else if (argc == argn) {
+ + 	ifp = pm_openr(argv[argn]);
+ +     } else {
+ + 	ifp = stdin;
+ +     }
+ + 
+ +     xels = pnm_readpnm(ifp, &hist_cols, &rows, &maxval, &format);
+ +     pm_close(ifp);
+ + 
+ +     /* Allocate histogram and luminosity map arrays.  If the
+ +        user has specified an input map file, read it in at
+ +        this point. */
+ + 
+ +     lumahist = (long *) pm_allocrow(maxval + 1, sizeof(long));
+ +     bzero((char *) lumahist, (maxval + 1) * sizeof(long));
+ + 
+ +     if (rmap == NULL) {
+ + 	lumamap = pgm_allocarray(maxval + 1, 1);
+ +     } else {
+ + 	int rmcols, rmrows; 
+ + 	gray rmmaxv;
+ + 
+ + 	lumamap = pgm_readpgm(rmap, &rmcols, &rmrows, &rmmaxv);
+ + 	if (rmmaxv != maxval) {
+ +             pm_error("maxval in map file (%d) different from input (%d)",
+ + 		rmmaxv, maxval);
+ + 	}
+ + 	if (rmrows != 1 || rmcols != rmmaxv) {
+ +             pm_error("map size (%d by %d) wrong; must be (%d by 1)",
+ + 		rmcols, rmrows, maxval);
+ + 	}
+ +     }
+ + 
+ +     /* Scan the image and build the luminosity histogram.  If
+ +        the input is a PPM, we calculate the luminosity of each
+ +        pixel from its RGB components. */
+ + 
+ +     lmin = maxval;
+ +     lmax = 0;
+ +     if (PNM_FORMAT_TYPE(format) == PGM_TYPE ||
+ + 	PNM_FORMAT_TYPE(format) == PBM_TYPE) {
+ + 
+ + 	/* Compute intensity histogram */
+ + 
+ + 	pixels = ((unsigned long) rows) * ((unsigned long) hist_cols);
+ + 	for (i = 0; i < rows; i++) {
+ + 	    xel *grayrow = xels[i];
+ + 	    for (j = 0; j < hist_cols; j++) {
+ + 		gray l = PNM_GET1(grayrow[j]);
+ + 		lmin = min(lmin, l);
+ + 		lmax = max(lmax, l);
+ + 		lumahist[l]++;
+ + 	    }
+ + 	}
+ +     } else if (PNM_FORMAT_TYPE(format) == PPM_TYPE) {
+ + 	for (i = 0; i < rows; i++) {
+ + 	    pixel *pixrow = (pixel *) xels[i];
+ + 
+ + 	    for (j = 0; j < hist_cols; j++) {
+ + 		if (!mono_only ||
+ + 		    ((PPM_GETR(pixrow[j]) == PPM_GETG(pixrow[j])) &&
+ + 		     (PPM_GETR(pixrow[j]) == PPM_GETB(pixrow[j])))) {
+ + 		    gray l = (gray) PPM_LUMIN(pixrow[j]);
+ + 		    lmin = min(lmin, l);
+ + 		    lmax = max(lmax, l);
+ + 		    lumahist[l]++;
+ + 		    pixels++;
+ + 		}
+ + 	    }
+ + 	}
+ +     } else {
+ +         pm_error("unknown input format");
+ +     }
+ + 
+ +     /* The PGM and PPM branches rejoin here to calculate the
+ +        luminosity mapping table which gives the histogram-equalised
+ +        luminosity for each original luminosity. */
+ + 
+ +     /* Calculate initial histogram equalisation curve. */
+ + 
+ +     for (i = 0; i <= (int) maxval; i++) {
+ + 
+ + 	/* Yick.  If PGM_BIGGRAYS is defined (I thought they were little
+ + 	   guys, about four foot, with funny eyes...) the following
+ + 	   calculation can overflow a 32 bit long.  So, we do it in
+ + 	   floating point.  Since this happens only maxval times, the
+ + 	   inefficiency is trivial compared to the every-pixel code above
+ + 	   and below. */
+ + 
+ + 	lumamap[0][i] = (gray) (((((double) pixsum * maxval)) / pixels) + 0.5);
+ + 	if (lumahist[i] > 0) {
+ + 	    maxluma = i;
+ + 	}
+ + 	pixsum += lumahist[i];
+ +     }
+ + 
+ +     /* Normalise so that the brightest pixels are set to
+ +        maxval. */
+ + 
+ +     lscale = ((double) maxval) / ((lumahist[maxluma] > 0) ?
+ + 	     ((double) lumamap[0][maxluma]) : ((double) maxval));
+ +     for (i = 0; i <= (int) maxval; i++) {
+ + 	lumamap[0][i] = (gray)
+ + 	    min(((long) maxval), ((long) (lumamap[0][i] * lscale + 0.5)));
+ +     }
+ + 
+ +     /* If requested, print the luminosity map and original histogram. */
+ + 
+ +     if (verbose) {
+ + 	fprintf(stderr,
+ +             "  Luminosity map    Number of\n Original    New     Pixels\n");
+ + 	for (i = 0; i <= (int) maxval; i++) {
+ + 	    if (lumahist[i] > 0) {
+ +                 fprintf(stderr,"%6d -> %6d  %8d\n", i,
+ + 			lumamap[0][i], lumahist[i]);
+ + 	    }
+ + 	}
+ +     }
+ + 
+ +     switch (PNM_FORMAT_TYPE(format)) {
+ + 	case PBM_TYPE:
+ + 	case PPM_TYPE:
+ + 	    for (i = 0; i < rows; i++) {
+ + 		pixrow = (pixel *) xels[i];
+ + 		for (j = 0; j < hist_cols; j++) {
+ + 		    if (!mono_only ||
+ + 			((PPM_GETR(pixrow[j]) == PPM_GETG(pixrow[j])) &&
+ + 			 (PPM_GETR(pixrow[j]) == PPM_GETB(pixrow[j])))) {
+ + 			double r, g, b, h, s, v;
+ + 			int iv;
+ + 
+ + 			r = (double) PPM_GETR(pixrow[j]) / ((double) maxval);
+ + 			g = (double) PPM_GETG(pixrow[j]) / ((double) maxval);
+ + 			b = (double) PPM_GETB(pixrow[j]) / ((double) maxval);
+ + 			rgb_hsv(r, g, b, &h, &s, &v);
+ + 			iv = (int) ((v * maxval) + 0.5);
+ + 
+ + 			if (iv > ((int) maxval)) {
+ + 			    iv = maxval;
+ + 			}
+ + 			v = ((double) lumamap[0][iv]) / ((double) maxval);
+ + 			if (v > 1.0) {
+ + 			    v = 1.0;
+ + 			}
+ + 			hsv_rgb(h, s, v, &r, &g, &b);
+ + 			PPM_ASSIGN(pixrow[j], (int) (r * maxval),
+ + 			    (int) (g * maxval), (int) (b * maxval));
+ + 		    }
+ + 		}
+ + 	    }
+ + 	    break;
+ + 
+ + 	case PGM_TYPE:
+ + 	    for (i = 0; i < rows; i++) {
+ + 		grayrow = xels[i];
+ + 		for (j = 0; j < hist_cols; j++) {
+ + 		    PNM_ASSIGN1(grayrow[j], lumamap[0][PNM_GET1(grayrow[j])]);
+ + 		}
+ + 	    }
+ + 	    break;
+ +     }
+ + 
+ +     pnm_writepnm(stdout, xels, hist_cols, rows, maxval, format, 0);
+ + 
+ +     /* If requested, save the map as a PGM file. */
+ + 
+ +     if (wmap != NULL) {
+ + 	pgm_writepgm(wmap, lumamap, maxval, 1, maxval, 0);
+ + 	fclose(wmap);
+ +     }
+ + 
+ +     return 0;
+ + }
diff -r -c -N /tmp/null/patches/patch-au ./patches/patch-au
*** /tmp/null/patches/patch-au	Wed Dec 31 18:00:00 1969
--- ./patches/patch-au	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,26 ----
+ *** /dev/null	Sat Jan  9 13:03:49 1999
+ --- ./pnm/pnmsmooth.README	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 0 ****
+ --- 1,21 ----
+ + README for pnmsmooth.c 2.0
+ + 
+ + This is a replacement for the pnmsmooth script that is distributed with
+ + pbmplus/netpbm.  This version of pnmsmooth is written as a C program rather
+ + than a shell script.  It accepts command line arguments to specify a size 
+ + other than 3x3 for the convolution matrix and an argument for dumping the 
+ + resultant convolution matrix as a PGM file.  By default it uses the same 3x3
+ + matrix size as the pnmsmooth script and can be used as a direct replacement.
+ + 
+ + Also included are an updated man page and a patch file to update the Imakefile
+ + in the pnm directory.  You may want to apply the patches by hand if you have
+ + already modified the Imakefile to add other new programs.   You will then
+ + have to remake the Makefiles and then type 'make all' in the pnm directory.
+ + 
+ + - Mike
+ + 
+ + ----------------------------------------------------------------------------
+ + Mike Burns                                              System Administrator
+ + burns@chem.psu.edu                                   Department of Chemistry
+ + (814) 863-2123                             The Pennsylvania State University
+ + 
diff -r -c -N /tmp/null/patches/patch-av ./patches/patch-av
*** /tmp/null/patches/patch-av	Wed Dec 31 18:00:00 1969
--- ./patches/patch-av	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,176 ----
+ *** /dev/null	Sat Jan  9 13:03:49 1999
+ --- ./pnm/pnmsmooth.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 0 ****
+ --- 1,171 ----
+ + /* pnmsmooth.c - smooth out an image by replacing each pixel with the 
+ + **               average of its width x height neighbors.
+ + **
+ + ** Version 2.0   December 5, 1994
+ + **
+ + ** Copyright (C) 1994 by Mike Burns (burns@chem.psu.edu)
+ + **
+ + ** 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.
+ + */
+ + 
+ + /* Version 2.0 - December 5, 1994
+ + ** ------------------------------
+ + ** Rewrote as a C program that accepts a few options instead of a shell 
+ + ** script with no options.
+ + **
+ + */
+ + 
+ + #include "pnm.h"
+ + #include <sys/wait.h>
+ + 
+ + #define TRUE    1
+ + #define FALSE   0
+ + 
+ + int
+ + main( argc, argv )
+ +     int argc;
+ +     char* argv[];
+ +     {
+ +     FILE *cofp;
+ +     char *tempfn;
+ +     char *pnmfn;
+ +     int argn;
+ +     int col, row;
+ +     int format, forceplain;
+ +     int cols, rows;
+ +     int newmaxval;		/* normally xelval, but want int here */
+ +     xelval g;
+ +     xel *outputrow;
+ +     int pid, status;
+ +     int DUMPFLAG = FALSE;
+ +     char *usage = "[-size width height] [-dump dumpfile] [pnmfile]";
+ + 
+ +     pnm_init( &argc, argv );
+ + 
+ +     /* set up defaults */
+ +     cols = 3;
+ +     rows = 3;
+ +     format = PGM_FORMAT;
+ +     forceplain = 1;
+ +     pnmfn = (char *) 0;		/* initialize to NULL just in case */
+ + 
+ +     argn = 1;
+ +     while ( argn < argc && argv[argn][0] == '-' && argv[argn][1] != '\0' )
+ + 	{
+ + 	if ( pm_keymatch( argv[argn], "-size", 2 ) )
+ + 	    {
+ + 	    ++argn;
+ + 	    if ( argn+1 >= argc )
+ + 		{
+ + 		pm_message( "incorrect number of arguments for -size option" );
+ + 		pm_usage( usage );
+ + 		}
+ + 	    else if ( argv[argn][0] == '-' || argv[argn+1][0] == '-' )
+ + 		{
+ + 		pm_message( "invalid arguments to -size option: %s %s", 
+ + 		    argv[argn], argv[argn+1] );
+ + 		pm_usage( usage );
+ + 		}
+ + 	    if ( (cols = atoi(argv[argn])) == 0 )
+ + 		pm_error( "invalid width size specification: %s", argv[argn] );
+ + 	    ++argn;
+ + 	    if ( (rows = atoi(argv[argn])) == 0 )
+ + 		pm_error( "invalid height size specification: %s",argv[argn] );
+ + 	    if ( cols % 2 != 1 || rows % 2 != 1 )
+ + 		pm_error( "the convolution matrix must have an odd number of rows and columns" );
+ + 	    }
+ + 	else if ( pm_keymatch( argv[argn], "-dump", 2 ) )
+ + 	    {
+ + 	    ++argn;
+ + 	    if ( argn >= argc )
+ + 		{
+ + 		pm_message( "missing argument to -dump option" );
+ + 		pm_usage( usage );
+ + 		}
+ + 	    else if ( argv[argn][0] == '-' )
+ + 		{
+ + 		pm_message( "invalid argument to -dump option: %s", 
+ + 		    argv[argn] );
+ + 		pm_usage( usage );
+ + 		}
+ + 	    cofp = pm_openw( argv[argn] );
+ + 	    DUMPFLAG = TRUE;
+ + 	    }
+ + 	else
+ + 	    pm_usage( usage );
+ + 	++argn;
+ + 	}
+ + 
+ +     /* Only get file name if given on command line to pass through to 
+ +     ** pnmconvol.  If filename is coming from stdin, pnmconvol will read it.
+ +     */
+ +     if ( argn < argc )
+ + 	{
+ + 	pnmfn = argv[argn];
+ + 	++argn;
+ + 	}
+ + 
+ +     if ( argn != argc )
+ + 	pm_usage( usage );
+ + 
+ + 
+ +     if ( !DUMPFLAG )
+ + 	{
+ + 	if ( (tempfn = tmpnam((char *) 0)) == NULL )
+ + 	    pm_error( "could not create temporary file name" );
+ + 	if ( (cofp = pm_openw(tempfn)) == NULL )
+ + 	    pm_error( "could not create temporary convolution file" );
+ + 	}
+ + 
+ +     /* Generate mean value for all pixels in convolution matrix. */
+ +     g = rows * cols + 1;
+ + 
+ +     /* Make sure newmaxval is not larger than PNM_MAXMAXVAL or else
+ +     ** newmaxval will overrun its defined data size and become garbage.
+ +     */
+ +     newmaxval = ( rows * cols ) * 2;
+ +     if ( newmaxval > PNM_MAXMAXVAL )
+ + 	pm_error( "generated maxval is too large: %d", newmaxval );
+ + 
+ +     pnm_writepnminit( cofp, cols, rows, newmaxval, format, forceplain );
+ +     outputrow = pnm_allocrow( cols );
+ + 
+ +     for ( row = 0; row < rows; ++ row )
+ + 	{
+ + 	for ( col = 0; col < cols; ++col )
+ + 	    PNM_ASSIGN1( outputrow[col], g );
+ + 	pnm_writepnmrow( cofp, outputrow, cols, newmaxval, format, forceplain );
+ + 	}
+ +     pm_close( cofp );
+ +     pnm_freerow( outputrow );
+ + 
+ +     /* If we're only going to dump the file, now is the time to stop. */
+ +     if ( DUMPFLAG )
+ + 	exit( 0 );
+ + 
+ +     /* fork a child process */
+ +     if ( (pid = fork()) < 0 )
+ + 	pm_error( "fork" );
+ + 
+ +     /* child process executes following code */
+ +     if ( pid == 0 )
+ + 	{
+ + 	/* If pnmfile name is not given on command line, then pnmfn will be
+ + 	** (char *) 0 and the arglist will terminate there.
+ + 	*/
+ + 	execlp( "pnmconvol", "pnmconvol", tempfn, pnmfn, (char *) 0 );
+ + 	pm_error( "error executing pnmconvol command" );
+ + 	}
+ + 
+ +     /* wait for child to finish */
+ +     while ( wait(&status) != pid )
+ + 	;
+ + 
+ +     unlink( tempfn );
+ +     exit( 0 );
+ +     }
diff -r -c -N /tmp/null/patches/patch-aw ./patches/patch-aw
*** /tmp/null/patches/patch-aw	Wed Dec 31 18:00:00 1969
--- ./patches/patch-aw	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,188 ----
+ *** ../../src/netpbm-1mar94/./ppm/Makefile	Mon Jan 31 10:44:34 1994
+ --- ./ppm/Makefile	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 9,31 ****
+   # documentation.  This software is provided "as is" without express or
+   # implied warranty.
+   
+   # Default values, usually overridden by top-level Makefile.
+ ! #CC =		cc
+ ! CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   #CFLAGS =	-O
+ ! CFLAGS =	-g
+   #CFLAGS =	-g -O
+ ! #LDFLAGS =	-s
+ ! LDFLAGS =	
+ ! INSTALLBINARIES =	/usr/new/pbm
+   INSTALLSCRIPTS =	$(INSTALLBINARIES)
+ ! INSTALLMANUALS1 =	/usr/man/mann
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	/usr/man/mann
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	/usr/man/mann
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			cp
+   
+   PGMDIR =	../pgm
+   INCLUDEPGM =	-I$(PGMDIR)
+ --- 9,34 ----
+   # documentation.  This software is provided "as is" without express or
+   # implied warranty.
+   
+ + PREFIX =	/usr/local
+   # Default values, usually overridden by top-level Makefile.
+ ! CC =		gcc
+ ! #CC =		gcc -ansi -pedantic -fcombine-regs -fpcc-struct-return
+   #CFLAGS =	-O
+ ! CFLAGS =	-O2
+   #CFLAGS =	-g -O
+ ! LDFLAGS =	-s
+ ! #LDFLAGS =	
+ ! INSTALLBINARIES =	$(PREFIX)/bin
+   INSTALLSCRIPTS =	$(INSTALLBINARIES)
+ ! INSTALLMANUALS1 =	$(PREFIX)/man/man1
+   SUFFIXMANUALS1 =	1
+ ! INSTALLMANUALS3 =	$(PREFIX)/man/man3
+   SUFFIXMANUALS3 =	3
+ ! INSTALLMANUALS5 =	$(PREFIX)/man/man5
+   SUFFIXMANUALS5 =	5
+ ! MANCP =			install -c -m 0644
+ ! INSTALLLIBS =		$(PREFIX)/lib
+ ! INSTALLDEFS =		$(PREFIX)/include
+   
+   PGMDIR =	../pgm
+   INCLUDEPGM =	-I$(PGMDIR)
+ ***************
+ *** 43,48 ****
+ --- 46,52 ----
+   INCLUDE =	-I.. $(INCLUDEPGM) $(INCLUDEPBM)
+   ALLCFLAGS =	$(CFLAGS) $(INCLUDE)
+   LIBPPM =	libppm.a
+ + DEFPPM =	ppm.h
+   
+   PORTBINARIES =	bmptoppm gouldtoppm hpcdtoppm ilbmtoppm imgtoppm \
+   		mtvtoppm pcxtoppm pgmtoppm pi1toppm picttoppm \
+ ***************
+ *** 85,105 ****
+   MANUALS5 =	ppm
+   
+   
+ ! #all:		binaries
+ ! all:		merge
+ ! #install:	install.bin
+ ! install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries $(SCRIPTS)
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	cp $(BINARIES) $(INSTALLBINARIES)
+   	cd $(INSTALLSCRIPTS) ; rm -f $(SCRIPTS)
+ ! 	cp $(SCRIPTS) $(INSTALLSCRIPTS)
+ ! 	cd $(INSTALLSCRIPTS) ; chmod +x $(SCRIPTS)
+ ! 
+   
+   merge:		ppmmerge
+   ppmmerge:	ppmmerge.c $(OBJECTS) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ --- 89,109 ----
+   MANUALS5 =	ppm
+   
+   
+ ! all:		binaries
+ ! #all:		merge
+ ! install:	install.bin
+ ! #install:	install.merge
+   
+   
+   binaries:	$(BINARIES)
+   
+   install.bin:	binaries $(SCRIPTS)
+   	cd $(INSTALLBINARIES) ; rm -f $(BINARIES)
+ ! 	install -c -s -m 0755 $(BINARIES) $(INSTALLBINARIES)
+   	cd $(INSTALLSCRIPTS) ; rm -f $(SCRIPTS)
+ ! 	install -c -m 0755 $(SCRIPTS) $(INSTALLSCRIPTS)
+ ! 	install -c -m 0644 $(LIBPPM) $(INSTALLLIBS)
+ ! 	install -c -m 0644 $(DEFPPM) $(INSTALLDEFS)
+   
+   merge:		ppmmerge
+   ppmmerge:	ppmmerge.c $(OBJECTS) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+ ***************
+ *** 132,146 ****
+   
+   
+   # Rule for plain programs.
+ ! $(PORTBINARIES):	ppm.h $(DEFPGM) $(DEFPBM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):	ppm.h $(DEFPGM) $(DEFPBM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	ppm.h $(DEFPGM) $(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And libraries.
+ --- 136,150 ----
+   
+   
+   # Rule for plain programs.
+ ! $(PORTBINARIES):	$(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   
+   # Rule for math-dependent programs.
+ ! $(MATHBINARIES):	$(DEFPPM) $(DEFPGM) $(DEFPBM) $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   	$(CC) $(ALLCFLAGS) $(LDFLAGS) -o $@ $@.c -lm $(LIBPPM) $(LIBPGM) $(LIBPBM)
+   
+   # Rule for objects.
+ ! $(OBJECTS):	$(DEFPPM) $(DEFPGM) $(DEFPBM)
+   	$(CC) $(ALLCFLAGS) "-Dmain=$*_main" -c $*.c
+   
+   # And libraries.
+ ***************
+ *** 155,170 ****
+   	libppm5.o bitio.o
+   	-ranlib $(LIBPPM)
+   
+ ! libppm1.o:	ppm.h $(DEFPGM) $(DEFPBM) libppm.h libppm1.c
+   	$(CC) $(ALLCFLAGS) -c libppm1.c
+ ! libppm2.o:	ppm.h $(DEFPGM) $(DEFPBM) libppm.h libppm2.c $(DEFLIBPGM) \
+   		$(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libppm2.c
+ ! libppm3.o:	ppm.h $(DEFPGM) $(DEFPBM) ppmcmap.h libppm.h libppm3.c
+   	$(CC) $(ALLCFLAGS) -c libppm3.c
+ ! libppm4.o:	ppm.h $(DEFPGM) $(DEFPBM) libppm4.c
+   	$(CC) $(ALLCFLAGS) -c libppm4.c
+ ! libppm5.o:	ppm.h $(DEFPGM) $(DEFPBM) ppmdraw.h libppm5.c
+   	$(CC) $(ALLCFLAGS) -c libppm5.c
+   bitio.o:	../pbmplus.h bitio.c
+   	$(CC) $(ALLCFLAGS) -c bitio.c
+ --- 159,174 ----
+   	libppm5.o bitio.o
+   	-ranlib $(LIBPPM)
+   
+ ! libppm1.o:	$(DEFPPM) $(DEFPGM) $(DEFPBM) libppm.h libppm1.c
+   	$(CC) $(ALLCFLAGS) -c libppm1.c
+ ! libppm2.o:	$(DEFPPM) $(DEFPGM) $(DEFPBM) libppm.h libppm2.c $(DEFLIBPGM) \
+   		$(DEFLIBPBM)
+   	$(CC) $(ALLCFLAGS) -c libppm2.c
+ ! libppm3.o:	$(DEFPPM) $(DEFPGM) $(DEFPBM) ppmcmap.h libppm.h libppm3.c
+   	$(CC) $(ALLCFLAGS) -c libppm3.c
+ ! libppm4.o:	$(DEFPPM) $(DEFPGM) $(DEFPBM) libppm4.c
+   	$(CC) $(ALLCFLAGS) -c libppm4.c
+ ! libppm5.o:	$(DEFPPM) $(DEFPGM) $(DEFPBM) ppmdraw.h libppm5.c
+   	$(CC) $(ALLCFLAGS) -c libppm5.c
+   bitio.o:	../pbmplus.h bitio.c
+   	$(CC) $(ALLCFLAGS) -c bitio.c
+ ***************
+ *** 235,238 ****
+   yuvsplittoppm yuvsplittoppm.o:	yuvsplittoppm.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core $(BINARIES) ppmmerge
+ --- 239,242 ----
+   yuvsplittoppm yuvsplittoppm.o:	yuvsplittoppm.c
+   
+   clean:
+ ! 	-rm -f *.o *.a *.cat *~ core *.core $(BINARIES) ppmmerge
diff -r -c -N /tmp/null/patches/patch-ax ./patches/patch-ax
*** /tmp/null/patches/patch-ax	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ax	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,19 ----
+ *** ../../src/netpbm-1mar94/./ppm/ppm.5	Mon Oct  4 04:12:19 1993
+ --- ./ppm/ppm.5	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 73,79 ****
+   it will automatically fall back on the slower but more general plain
+   format.
+   .SH "SEE ALSO"
+ ! giftoppm(1), gouldtoppm(1), ilbmtoppm(1), imgtoppm(1), mtvtoppm(1),
+   pcxtoppm(1), pgmtoppm(1), pi1toppm(1), picttoppm(1), pjtoppm(1), qrttoppm(1),
+   rawtoppm(1), rgb3toppm(1), sldtoppm(1), spctoppm(1), sputoppm(1), tgatoppm(1),
+   ximtoppm(1), xpmtoppm(1), yuvtoppm(1),
+ --- 73,79 ----
+   it will automatically fall back on the slower but more general plain
+   format.
+   .SH "SEE ALSO"
+ ! giftopnm(1), gouldtoppm(1), ilbmtoppm(1), imgtoppm(1), mtvtoppm(1),
+   pcxtoppm(1), pgmtoppm(1), pi1toppm(1), picttoppm(1), pjtoppm(1), qrttoppm(1),
+   rawtoppm(1), rgb3toppm(1), sldtoppm(1), spctoppm(1), sputoppm(1), tgatoppm(1),
+   ximtoppm(1), xpmtoppm(1), yuvtoppm(1),
diff -r -c -N /tmp/null/patches/patch-ay ./patches/patch-ay
*** /tmp/null/patches/patch-ay	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ay	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,15 ----
+ *** ../../src/netpbm-1mar94/./ppm/ppmmerge.c	Mon Jan 31 10:44:31 1994
+ --- ./ppm/ppmmerge.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 29,34 ****
+ --- 29,38 ----
+   	{
+   	++argv;
+   	--argc;
+ + 	if(!*argv)	{
+ + 		fprintf(stderr, "Usage: ppmmerge ppm_program_name [args ...]\n");
+ + 		exit(1);
+ + 		}
+   	goto again;
+   	}
+   
diff -r -c -N /tmp/null/patches/patch-az ./patches/patch-az
*** /tmp/null/patches/patch-az	Wed Dec 31 18:00:00 1969
--- ./patches/patch-az	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,19 ----
+ *** ../../src/netpbm-1mar94/./ppm/ppmtogif.1	Fri Nov 12 03:18:30 1993
+ --- ./ppm/ppmtogif.1	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 54,60 ****
+   .PP
+   All flags can be abbreviated to their shortest unique prefix.
+   .SH "SEE ALSO"
+ ! giftoppm(1), ppmquant(1), ppm(5)
+   .SH AUTHOR
+   Based on GIFENCOD by David Rowley <mgardi@watdcsu.waterloo.edu>.
+   Lempel-Ziv compression based on "compress".
+ --- 54,60 ----
+   .PP
+   All flags can be abbreviated to their shortest unique prefix.
+   .SH "SEE ALSO"
+ ! giftopnm(1), ppmquant(1), ppm(5)
+   .SH AUTHOR
+   Based on GIFENCOD by David Rowley <mgardi@watdcsu.waterloo.edu>.
+   Lempel-Ziv compression based on "compress".
diff -r -c -N /tmp/null/patches/patch-ba ./patches/patch-ba
*** /tmp/null/patches/patch-ba	Wed Dec 31 18:00:00 1969
--- ./patches/patch-ba	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,19 ----
+ *** ../../src/netpbm-1mar94/./ppm/ppmtoicr.1	Mon Oct  4 04:12:38 1993
+ --- ./ppm/ppmtoicr.1	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 83,89 ****
+   the displayed image by a factor of 2, and
+   run-length encode the data:
+   .nf
+ !     giftoppm giffile | ppmtoicr -w giffile -r -e 2
+   .fi
+   .SH BUGS
+   .PP
+ --- 83,89 ----
+   the displayed image by a factor of 2, and
+   run-length encode the data:
+   .nf
+ !     giftopnm giffile | ppmtoicr -w giffile -r -e 2
+   .fi
+   .SH BUGS
+   .PP
diff -r -c -N /tmp/null/patches/patch-bb ./patches/patch-bb
*** /tmp/null/patches/patch-bb	Wed Dec 31 18:00:00 1969
--- ./patches/patch-bb	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,45 ----
+ *** ../../src/netpbm-1mar94/./ppm/ppmtoxpm.1	Mon Jan 31 05:49:48 1994
+ --- ./ppm/ppmtoxpm.1	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 8,27 ****
+   Produces X11 pixmap  (version 3) as output which
+   can be loaded directly by the XPM library.
+   .PP
+ ! The \fB-name\fP option allows one to specify the prefix string which is printed
+   in the resulting XPM output.  If not specified, will default to the
+   filename (without extension) of the <ppmfile> argument.
+ ! If \fB-name\fP is not specified and <ppmfile>
+   is not specified (i.e. piped input), the prefix string will default to
+   the string "noname".
+   .PP
+ ! The \fB-rgb\fP option allows one to specify an X11 rgb text file for the
+   lookup of color name mnemonics.  This rgb text file is typically the
+   /usr/lib/X11/rgb.txt of the MIT X11 distribution, but any file using the
+   same format may be used.  When specified and
+   a RGB value from the ppm input matches a RGB value from the <rgb-textfile>,
+   then the corresponding color name mnemonic is printed in the XPM's colormap.
+ ! If \fB-rgb\fP is not specified, or if the RGB values don't match, then the color
+   will be printed with the #RGB, #RRGGBB, #RRRGGGBBB, or #RRRRGGGGBBBB
+   hexadecimal format.
+   .PP
+ --- 8,27 ----
+   Produces X11 pixmap  (version 3) as output which
+   can be loaded directly by the XPM library.
+   .PP
+ ! The \fB-name\f option allows one to specify the prefix string which is printed
+   in the resulting XPM output.  If not specified, will default to the
+   filename (without extension) of the <ppmfile> argument.
+ ! If \fB-name\f is not specified and <ppmfile>
+   is not specified (i.e. piped input), the prefix string will default to
+   the string "noname".
+   .PP
+ ! The \fB-rgb\f option allows one to specify an X11 rgb text file for the
+   lookup of color name mnemonics.  This rgb text file is typically the
+   /usr/lib/X11/rgb.txt of the MIT X11 distribution, but any file using the
+   same format may be used.  When specified and
+   a RGB value from the ppm input matches a RGB value from the <rgb-textfile>,
+   then the corresponding color name mnemonic is printed in the XPM's colormap.
+ ! If \fB-rgb\f is not specified, or if the RGB values don't match, then the color
+   will be printed with the #RGB, #RRGGBB, #RRRGGGBBB, or #RRRRGGGGBBBB
+   hexadecimal format.
+   .PP
diff -r -c -N /tmp/null/patches/patch-bc ./patches/patch-bc
*** /tmp/null/patches/patch-bc	Wed Dec 31 18:00:00 1969
--- ./patches/patch-bc	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,304 ----
+ *** ../../src/netpbm-1mar94/./ppm/ppmtoxpm.c	Mon Jan 31 01:44:41 1994
+ --- ./ppm/ppmtoxpm.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 27,37 ****
+ --- 27,51 ----
+   **    
+   **  - lowercase conversion of RGB names def'ed out,
+   **    considered harmful.
+ + **
+ + ** Michael Pall (pall@rz.uni-karlsruhe.de) - 29 Nov 93:
+ + **  - Use the algorithm from xpm-lib for pixel encoding
+ + **    (base 93 not base 28 -> saves a lot of space for colorful xpms)
+   */
+   
+ + #include <stdio.h>
+ + #include <ctype.h>
+   #include "ppm.h"
+   #include "ppmcmap.h"
+   
+ + #if defined(SYSV) || defined(SVR4)
+ + #include <string.h>
+ + #ifndef index
+ + #define index strchr
+ + #endif
+ + #else					/* SYSV */
+ + #include <strings.h>
+ + #endif					/* SYSV */
+   
+   /* Max number of colors allowed in ppm input. */
+   #define MAXCOLORS    256
+ ***************
+ *** 39,53 ****
+   /* Max number of rgb mnemonics allowed in rgb text file. */
+   #define MAX_RGBNAMES 1024
+   
+ ! /* Lower bound and upper bound of character-pixels printed in XPM output.
+ !    Be careful, don't want the character '"' in this range. */
+ ! /*#define LOW_CHAR  '#'  <-- minimum ascii character allowed */
+ ! /*#define HIGH_CHAR '~'  <-- maximum ascii character allowed */
+ ! #define LOW_CHAR  '`'
+ ! #define HIGH_CHAR 'z'
+   
+   #define max(a,b) ((a) > (b) ? (a) : (b))
+   
+   
+   typedef struct {			/* rgb values and ascii names (from
+   					 * rgb text file) */
+ --- 53,71 ----
+   /* Max number of rgb mnemonics allowed in rgb text file. */
+   #define MAX_RGBNAMES 1024
+   
+ ! #define MAXPRINTABLE 92			/* number of printable ascii chars
+ ! 					 * minus \ and " for string compat
+ ! 					 * and ? to avoid ANSI trigraphs. */
+ ! 
+ ! static char *printable =
+ ! " .XoO+@#$%&*=-;:>,<1234567890qwertyuipasdfghjklzxcvbnmMNBVCZ\
+ ! ASDFGHJKLPIUYTREWQ!~^/()_`'][{}|";
+ ! 
+   
+   #define max(a,b) ((a) > (b) ? (a) : (b))
+   
+ + void read_rgb_names();			/* forward reference */
+ + void gen_cmap();			/* forward reference */
+   
+   typedef struct {			/* rgb values and ascii names (from
+   					 * rgb text file) */
+ ***************
+ *** 62,78 ****
+   					 * mnemonic or #rgb value */
+   }      cixel_map;
+   
+ - 
+ - /* prototypes/forward reference */
+ - static void   read_rgb_names ARGS((char *, rgb_names *, int *));
+ - static char * gen_numstr ARGS((int, int, int));
+ - static void   gen_cmap ARGS((colorhist_vector, int, pixval, int, rgb_names *, int, cixel_map *, int *));
+ - 
+ - 
+   pixel **pixels;
+   
+ - 
+ - int
+   main(argc, argv)
+       int argc;
+       char *argv[];
+ --- 80,87 ----
+ ***************
+ *** 88,98 ****
+   
+       /* Used for rgb value -> rgb mnemonic mapping */
+       int map_rgb_names = 0;
+ !     rgb_names *rgbn;    /* rgb_names rgbn[MAX_RGBNAMES]; */
+       int rgbn_max;
+   
+       /* Used for rgb value -> character-pixel string mapping */
+ !     cixel_map *cmap;    /* cixel_map cmap[MAXCOLORS]; */
+       int charspp;			/* chars per pixel */
+   
+       char out_name[100], rgb_fname[100], *cp;
+ --- 97,107 ----
+   
+       /* Used for rgb value -> rgb mnemonic mapping */
+       int map_rgb_names = 0;
+ !     rgb_names rgbn[MAX_RGBNAMES];
+       int rgbn_max;
+   
+       /* Used for rgb value -> character-pixel string mapping */
+ !     cixel_map cmap[MAXCOLORS];
+       int charspp;			/* chars per pixel */
+   
+       char out_name[100], rgb_fname[100], *cp;
+ ***************
+ *** 188,204 ****
+        * If a rgb text file was specified, read in the rgb mnemonics. Does not
+        * return if fatal error occurs. 
+        */
+ -     rgbn = (rgb_names *) malloc(MAX_RGBNAMES * sizeof(rgb_names));
+ -     if (rgbn == (rgb_names *) NULL)
+ - 	pm_error("out of memory");
+ - 
+       if (map_rgb_names)
+   	read_rgb_names(rgb_fname, rgbn, &rgbn_max);
+   
+ -     cmap = (cixel_map *)malloc(ncolors * sizeof(cixel_map));
+ -     if (cmap == (cixel_map *) NULL)
+ - 	pm_error("out of memory");
+ -  
+       /* Now generate the character-pixel colormap table. */
+       gen_cmap(chv, ncolors, maxval, map_rgb_names, rgbn, rgbn_max,
+   	     cmap, &charspp);
+ --- 197,205 ----
+ ***************
+ *** 231,242 ****
+   /* This routine reads a rgb text file.  It stores the rgb values (0->65535)
+      and the rgb mnemonics (malloc'ed) into the "rgbn" array.  Returns the
+      number of entries stored in "rgbn_max". */
+ - static
+   void
+   read_rgb_names(rgb_fname, rgbn, rgbn_max)
+       char *rgb_fname;
+ !     rgb_names *rgbn;
+ !     int *rgbn_max;
+   {
+       FILE *rgbf;
+       int i, items, red, green, blue;
+ --- 232,243 ----
+   /* This routine reads a rgb text file.  It stores the rgb values (0->65535)
+      and the rgb mnemonics (malloc'ed) into the "rgbn" array.  Returns the
+      number of entries stored in "rgbn_max". */
+   void
+   read_rgb_names(rgb_fname, rgbn, rgbn_max)
+       char *rgb_fname;
+ !     rgb_names rgbn[MAX_RGBNAMES];
+ ! int *rgbn_max;
+ ! 
+   {
+       FILE *rgbf;
+       int i, items, red, green, blue;
+ ***************
+ *** 303,318 ****
+   }					/* read_rgb_names */
+   
+   /*---------------------------------------------------------------------------*/
+ ! /* Given a number and a base, (base == HIGH_CHAR-LOW_CHAR+1), this routine
+      prints the number into a malloc'ed string and returns it.  The length of
+      the string is specified by "digits".  The ascii characters of the printed
+ !    number range from LOW_CHAR to HIGH_CHAR.  The string is LOW_CHAR filled,
+ !    (e.g. if LOW_CHAR==0, HIGH_CHAR==1, digits==5, i=3, routine would return
+ !    the malloc'ed string "00011"). */
+ ! static
+   char *
+ ! gen_numstr(i, base, digits)
+ !     int i, base, digits;
+   {
+       char *str, *p;
+       int d;
+ --- 304,319 ----
+   }					/* read_rgb_names */
+   
+   /*---------------------------------------------------------------------------*/
+ ! /* Given a number and a base (MAXPRINTABLE), this routine
+      prints the number into a malloc'ed string and returns it.  The length of
+      the string is specified by "digits".  The ascii characters of the printed
+ !    number range from printable[0] to printable[MAXPRINTABLE].  The string is
+ !    printable[0] filled, (e.g. if printable[0]==0, printable[1]==1,
+ !    MAXPRINTABLE==2, digits==5, i=3, routine would return the malloc'ed
+ !    string "00011"). */
+   char *
+ ! gen_numstr(i, digits)
+ !     int i, digits;
+   {
+       char *str, *p;
+       int d;
+ ***************
+ *** 325,333 ****
+       p = str + digits;
+       *p-- = '\0';			/* nul terminate string */
+       while (p >= str) {
+ ! 	d = i % base;
+ ! 	i /= base;
+ ! 	*p-- = (char) ((int) LOW_CHAR + d);
+       }
+   
+       return str;
+ --- 326,334 ----
+       p = str + digits;
+       *p-- = '\0';			/* nul terminate string */
+       while (p >= str) {
+ ! 	d = i % MAXPRINTABLE;
+ ! 	i /= MAXPRINTABLE;
+ ! 	*p-- = printable[d];
+       }
+   
+       return str;
+ ***************
+ *** 336,342 ****
+   
+   /*---------------------------------------------------------------------------*/
+   /* This routine generates the character-pixel colormap table. */
+ - static
+   void
+   gen_cmap(chv, ncolors, maxval, map_rgb_names, rgbn, rgbn_max,
+   	 cmap, charspp)
+ --- 337,342 ----
+ ***************
+ *** 348,363 ****
+   					 * == unsigned short) */
+       int map_rgb_names;			/* == 1 if mapping rgb values to rgb
+   					 * mnemonics */
+ !     rgb_names *rgbn;                    /* rgb mnemonics from rgb text file */
+   int rgbn_max;				/* number of rgb mnemonics in table */
+   
+   /* output: */
+ ! cixel_map *cmap;                        /* pixel strings and ascii rgb
+   					 * colors */
+   int *charspp;				/* characters per pixel */
+   
+   {
+ !     int i, j, base, cpp, mval, red, green, blue, r, g, b, matched;
+       char *str;
+   
+       /*
+ --- 348,363 ----
+   					 * == unsigned short) */
+       int map_rgb_names;			/* == 1 if mapping rgb values to rgb
+   					 * mnemonics */
+ !     rgb_names rgbn[MAX_RGBNAMES];	/* rgb mnemonics from rgb text file */
+   int rgbn_max;				/* number of rgb mnemonics in table */
+   
+   /* output: */
+ ! cixel_map cmap[MAXCOLORS];		/* pixel strings and ascii rgb
+   					 * colors */
+   int *charspp;				/* characters per pixel */
+   
+   {
+ !     int i, j, cpp, mval, red, green, blue, r, g, b, matched;
+       char *str;
+   
+       /*
+ ***************
+ *** 365,373 ****
+        * to be forced to link with libm.a, so using a division loop rather
+        * than a log function. 
+        */
+ -     base = (int) HIGH_CHAR - (int) LOW_CHAR + 1;
+       for (cpp = 0, j = ncolors; j; cpp++)
+ ! 	j /= base;
+       *charspp = cpp;
+   
+       /*
+ --- 365,372 ----
+        * to be forced to link with libm.a, so using a division loop rather
+        * than a log function. 
+        */
+       for (cpp = 0, j = ncolors; j; cpp++)
+ ! 	j /= MAXPRINTABLE;
+       *charspp = cpp;
+   
+       /*
+ ***************
+ *** 392,401 ****
+   
+   	/*
+   	 * The character-pixel string is simply a printed number in base
+ ! 	 * "base" where the digits of the number range from LOW_CHAR to
+ ! 	 * HIGH_CHAR and the printed length of the number is "cpp". 
+   	 */
+ ! 	cmap[i].cixel = gen_numstr(i, base, cpp);
+   
+   	/* Fetch the rgb value of the current colormap entry. */
+   	red = PPM_GETR(chv[i].color);
+ --- 391,401 ----
+   
+   	/*
+   	 * The character-pixel string is simply a printed number in base
+ ! 	 * MAXPRINTABLE where the digits of the number range from
+ ! 	 * printable[0] .. printable[MAXPRINTABLE-1] and the printed length
+ ! 	 * of the number is "cpp". 
+   	 */
+ ! 	cmap[i].cixel = gen_numstr(i, cpp);
+   
+   	/* Fetch the rgb value of the current colormap entry. */
+   	red = PPM_GETR(chv[i].color);
diff -r -c -N /tmp/null/patches/patch-bd ./patches/patch-bd
*** /tmp/null/patches/patch-bd	Wed Dec 31 18:00:00 1969
--- ./patches/patch-bd	Sun Jan 10 00:51:53 1999
***************
*** 0 ****
--- 1,69 ----
+ *** ../../src/netpbm-1mar94/./ppm/xpmtoppm.c	Mon Jan 31 01:42:05 1994
+ --- ./ppm/xpmtoppm.c	Sun Jan 10 00:32:19 1999
+ ***************
+ *** 30,38 ****
+   
+   #include "ppm.h"
+   
+ ! static void ReadXPMFile ARGS((FILE *stream, int *widthP, int *heightP,
+ !     int *ncolorsP, int *chars_per_pixelP, pixel **colorsP, int **dataP));
+ ! static void getline ARGS((char *line, int size, FILE *stream));
+   
+   /* number of xpmColorKeys */
+   #define NKEYS 5
+ --- 30,37 ----
+   
+   #include "ppm.h"
+   
+ ! void ReadXPMFile();
+ ! static void getline();
+   
+   /* number of xpmColorKeys */
+   #define NKEYS 5
+ ***************
+ *** 46,52 ****
+    "c",					/* key #5: color visual */
+   };
+   
+ ! int
+   main(argc, argv)
+       int argc;
+       char *argv[];
+ --- 45,71 ----
+    "c",					/* key #5: color visual */
+   };
+   
+ ! #ifdef NEED_STRSTR
+ ! /* for systems which do not provide it */
+ ! static char *
+ ! strstr(s1, s2)
+ !     char *s1, *s2;
+ ! {
+ !     int ls2 = strlen(s2);
+ ! 
+ !     if (ls2 == 0)
+ ! 	return (s1);
+ !     while (strlen(s1) >= ls2) {
+ ! 	if (strncmp(s1, s2, ls2) == 0)
+ ! 	    return (s1);
+ ! 	s1++;
+ !     }
+ !     return (0);
+ ! }
+ ! 
+ ! #endif
+ ! 
+ ! void
+   main(argc, argv)
+       int argc;
+       char *argv[];
+ ***************
+ *** 89,95 ****
+   
+   #define MAX_LINE 2048
+   
+ - static
+   void
+   ReadXPMFile(stream, widthP, heightP, ncolorsP,
+   	    chars_per_pixelP, colorsP, dataP)
+ --- 108,113 ----
diff -r -c -N /tmp/null/patches/patch-bq ./patches/patch-bq
*** /tmp/null/patches/patch-bq	Wed Dec 31 18:00:00 1969
--- ./patches/patch-bq	Sun Jan 10 01:40:33 1999
***************
*** 0 ****
--- 1,25 ----
+ $NetBSD: patch-bq,v 1.2 1998/08/07 10:40:51 agc Exp $
+ 
+ --- /dev/null	Thu Oct 16 09:27:24 1997
+ +++ ./pnm/pnmsmooth.orig	Mon Oct  4 05:11:56 1993
+ @@ -0,0 +1,20 @@
+ +#!/bin/sh
+ +#
+ +# pnmsmooth - smooth out an image by replacing each xel with the
+ +#             average of its nine immediate neighbors
+ +
+ +tmp=/tmp/psm.$$
+ +rm -f $tmp
+ +
+ +cat > $tmp << MOO
+ +P2
+ +3 3
+ +18
+ +10 10 10
+ +10 10 10
+ +10 10 10
+ +MOO
+ +
+ +pnmconvol $tmp ${1+"$@"}
+ +
+ +rm -f $tmp
diff -r -c -N /tmp/null/pkg/COMMENT ./pkg/COMMENT
*** /tmp/null/pkg/COMMENT	Wed Dec 31 18:00:00 1969
--- ./pkg/COMMENT	Wed Oct 15 10:12:14 1997
***************
*** 0 ****
--- 1 ----
+ A toolkit for conversion of images between different formats
diff -r -c -N /tmp/null/pkg/DESCR ./pkg/DESCR
*** /tmp/null/pkg/DESCR	Wed Dec 31 18:00:00 1969
--- ./pkg/DESCR	Wed Oct 15 10:12:14 1997
***************
*** 0 ****
--- 1,183 ----
+ Netpbm is a toolkit for conversion of images between a variety of
+ different formats, as well as to allow a few basic image operations.
+ Netpbm is based on the widely spread Pbmplus package (release: 10 Dec
+ 91).  On top of that, a lot of improvements and additions have been
+ made. After the latest release of Pbmplus, a lot of additional filters
+ have been circulating on the net. The aim of Netpbm was, to collect
+ these and to turn them into a package. This work has been performed by
+ a group of programmers all over the world.
+ 
+ anytopnm - attempt to convert an unknown type of image file to a portable anymap
+ asciitopgm - convert ASCII graphics into a portable graymap
+ atktopbm - convert Andrew Toolkit raster object to portable bitmap
+ bioradtopgm - convert a Biorad confocal file into a portable graymap
+ bmptoppm - convert a BMP file into a portable pixmap
+ brushtopbm - convert a doodle brush file into a portable bitmap
+ cmuwmtopbm - convert a CMU window manager bitmap into a portable bitmap
+ fitstopnm - convert a FITS file into a portable anymap
+ fstopgm - convert a Usenix FaceSaver(tm) file into a portable graymap
+ g3topbm - convert a Group 3 fax file into a portable bitmap
+ gemtopbm - convert a GEM .img file into a portable bitmap
+ giftopnm - convert a GIF file into a portable anymap
+ gouldtoppm - convert Gould scanner file into a portable pixmap
+ hipstopgm - convert a HIPS file into a portable graymap
+ hpcdtoppm v0.3 - convert a Photo-CD file into a portable pixmap
+ icontopbm - convert a Sun icon into a portable bitmap
+ ilbmtoppm - convert an ILBM file into a portable pixmap
+ imgtoppm - convert an Img-whatnot file into a portable pixmap
+ lispmtopgm - convert a Lisp Machine bitmap file into pgm format
+ macptopbm - convert a MacPaint file into a portable bitmap
+ mgrtopbm - convert a MGR bitmap into a portable bitmap
+ mtvtoppm - convert output from the MTV or PRT ray tracers into a portable pixmap
+ pbmclean - flip isolated pixels in portable bitmap
+ pbmlife - apply Conway's rules of Life to a portable bitmap
+ pbmmake - create a blank bitmap of a specified size
+ pbmmask - create a mask bitmap from a regular bitmap
+ pbmpscale - enlarge a portable bitmap with edge smoothing
+ pbmreduce - read a portable bitmap and reduce it N times
+ pbmtext - render text into a bitmap
+ pbmto10x - convert a portable bitmap into Gemini 10X printer graphics
+ pbmto4425 - Display PBM images on an AT&T 4425 terminal
+ pbmtoascii - convert a portable bitmap into ASCII graphics
+ pbmtoatk - convert portable bitmap to Andrew Toolkit raster object
+ pbmtobg - convert a portable bitmap into BitGraph graphics
+ pbmtocmuwm - convert a portable bitmap into a CMU window manager bitmap
+ pbmtoepsi - convert a portable bitmap into an encapsulated PostScript
+ pbmtoepson - convert a portable bitmap into Epson printer graphics
+ pbmtog3 - convert a portable bitmap into a Group 3 fax file
+ pbmtogem - convert a portable bitmap into a GEM .img file
+ pbmtogo - convert a portable bitmap into compressed GraphOn graphics
+ pbmtoicon - convert a portable bitmap into a Sun icon
+ pbmtolj - convert a portable bitmap into HP LaserJet format
+ pbmtoln03 - convert protable bitmap to DEC LN03+ Sixel output
+ pbmtolps - convert portable bitmap to PostScript
+ pbmtomacp - convert a portable bitmap into a MacPaint file
+ pbmtomgr - convert a portable bitmap into a MGR bitmap
+ pbmtopgm - convert portable bitmap to portable graymap by averaging areas
+ pbmtopi3 - convert a portable bitmap into an Atari Degas .pi3 file 
+ pbmtopk - convert a portable bitmap into a packed (PK) format font
+ pbmtoplot - convert a portable bitmap into a Unix plot(5) file
+ pbmtoptx - convert a portable bitmap into Printronix printer graphics
+ pbmtox10bm - convert a portable bitmap into an X10 bitmap
+ pbmtoxbm - convert a portable bitmap into an X11 bitmap
+ pgmtoybm - convert a portable bitmap into a Bennet Yee "face" file
+ pbmtozinc - convert a portable bitmap into a Zinc bitmap
+ pbmupc - create a Universal Product Code bitmap
+ pcxtoppm - convert a PCX file into a portable pixmap
+ pgmbentley - Bentleyize a portable graymap
+ pgmcrater - create cratered terrain by fractal forgery
+ pgmedge - edge-detect a portable graymap
+ pgmenhance - edge-enhance a portable graymap
+ pgmhist - print a histogram of the values in a portable graymap
+ pgmkernel - generate a convolution kernel
+ pgmnoise - create a graymap made up of white noise
+ pgmnorm - normalize the contrast in a portable graymap
+ pgmoil - turn a portable graymap into an oil painting
+ pgmramp - generate a grayscale ramp
+ pgmtexture - calculate textural features on a portable graymap
+ pgmtofs - convert portable graymap to Usenix FaceSaver(tm) format
+ pgmtolispm - convert a portable graymap into Lisp Machine format
+ pgmtopbm - convert a portable graymap into a portable bitmap
+ pgmtoppm - colorize a portable graymap into a portable pixmap
+ pi1toppm - convert an Atari Degas .pi1 into a portable pixmap
+ pi3topbm - convert an Atari Degas .pi3 file into a portable bitmap
+ picttoppm - convert a Macintosh PICT file into a portable pixmap
+ pjtoppm - convert an HP PaintJet file to a portable pixmap
+ pktopbm - convert packed (PK) format font into portable bitmap(s)
+ pnmalias - antialias a portable anyumap.
+ pnmarith - perform arithmetic on two portable anymaps
+ pnmcat - concatenate portable anymaps
+ pnmcomp - composite two portable anymap files together
+ pnmconvol - general MxN convolution on a portable anymap
+ pnmcrop - crop a portable anymap
+ pnmcut - cut a rectangle out of a portable anymap
+ pnmdepth - change the maxval in a portable anymap
+ pnmenlarge - read a portable anymap and enlarge it N times
+ pnmfile - describe a portable anymap
+ pnmflip - perform one or more flip operations on a portable anymap
+ pnmgamma - perform gamma correction on a portable anymap
+ pnmhistmap - draw a histogram for a PGM or PPM file
+ pnmindex - build a visual index of a bunch of anymaps
+ pnminvert - invert a portable anymap
+ pnmmargin - add a border to a portable anymap
+ pnmnlfilt - non-linear filters: smooth, alpha trim mean, optimal
+ pnmnoraw - force a portable anymap into plain format
+ pnmpad - add borders to portable anymap
+ pnmpaste - paste a rectangle into a portable anymap
+ pnmrotate - rotate a portable anymap by some angle
+ pnmscale - scale a portable anymap
+ pnmshear - shear a portable anymap by some angle
+ pnmsmooth - smooth out an image
+ pnmtile - replicate a portable anymap into a specified size
+ pnmtoddif - Convert a portable anymap to DDIF format
+ pnmtofits - convert a portable anymap into FITS format
+ pnmtops - convert portable anymap to PostScript
+ pnmtorast - convert a portable pixmap into a Sun rasterfile
+ pnmtosgi - convert a portable anymap to a SGI image file
+ pnmtosir - convert a portable anymap into a Solitaire format
+ pnmtotiff - convert a a portable anymap into a TIFF file
+ pnmtoxwd - convert a portable anymap into an X11 window dump
+ ppm3d - convert two portable pixmap into a red/blue 3d glasses pixmap
+ ppmbrighten - change an images Saturation and Value from an HSV map
+ ppmchange - change all pixels of one color to another in a portable pixmap
+ ppmdim - dim a portable pixmap down to total blackness
+ ppmdist - simplistic grayscale assignment for machine generated, color images
+ ppmdither - ordered dither for color images
+ ppmflash - brighten a picture up to complete white-out
+ ppmforge - fractal forgeries of clouds, planets, and starry skies
+ ppmhist - print a histogram of a portable pixmap
+ ppmmake - create a pixmap of a specified size and color
+ ppmmix - blend together two portable pixmaps
+ ppmnorm - normalize the contrast in a portable pixmap
+ ppmntsc - make a portable pixmap look like taken from an American TV
+ ppmpat - make a pretty pixmap
+ ppmquant - quantize the colors in a portable pixmap down to a specified number
+ ppmquantall - run ppmquant on a bunch of files all at once, so they share a common colormap
+ ppmqvga - 8 plane quantization
+ ppmrelief - run a Laplacian relief filter on a portable pixmap
+ ppmshift - shift lines of a portable pixmap left or right by a random amount
+ ppmspread - displace a portable pixmap's pixels by a random amount
+ ppmtoacad - convert portable pixmap to AutoCAD database or slide
+ ppmtobmp - convert a portable pixmap into a BMP file
+ ppmtogif - convert a portable pixmap into a GIF file
+ ppmtoicr - convert a portable pixmap into NCSA ICR format 
+ ppmtoilbm - convert a portable pixmap into an ILBM file
+ ppmtomap - extract all colors from a portable pixmap
+ ppmtomitsu - convert a portable pixmap to a Mitsubishi S340-10 file
+ ppmtopcx - convert a portable pixmap into a PCX file
+ ppmtopgm - convert a portable pixmap into a portable graymap
+ ppmtopi1 - convert a portable pixmap into an Atari Degas .pi1 file
+ ppmtopict - convert a portable pixmap into a Macintosh PICT file
+ ppmtopj - convert a portable pixmap to an HP PaintJet file
+ ppmtopjxl - convert a portable pixmap into an HP PaintJet XL PCL file
+ ppmtopuzz - convert a portable pixmap into an X11 "puzzle" file
+ ppmtorgb3 - separate a portable pixmap into three portable graymaps
+ ppmtosixel - convert a portable pixmap into DEC sixel format
+ ppmtotga - convert portable pixmap into a TrueVision Targa file
+ ppmtouil - convert a portable pixmap into a Motif UIL icon file
+ ppmtoxpm - convert a portable pixmap into an X11 pixmap
+ ppmtoyuv - convert a portable pixmap into an Abekas YUV file
+ ppmtoyuvsplit - convert a portable pixmap into 3 subsampled raw YUV files
+ psidtopgm - convert PostScript "image" data into a portable graymap
+ qrttoppm - convert output from the QRT ray tracer into a portable pixmap
+ rasttopnm - convert a Sun rasterfile into a portable anymap
+ rawtopgm - convert raw grayscale bytes into a portable graymap
+ rawtoppm - convert raw RGB bytes into a portable pixmap
+ rgb3toppm - combine three portable graymaps into one portable pixmap
+ sgitopnm - convert a SGI image file to a portable anymap
+ sirtopnm - convert a Solitaire file into a portable anymap
+ sldtoppm - convert an AutoCAD slide file into a portable pixmap
+ spctoppm - convert an Atari compressed Spectrum file into a portable pixmap
+ spottopgm - convert SPOT satellite images to Portable Greymap format
+ sputoppm - convert an Atari uncompressed Spectrum file into a portable pixmap
+ tgatoppm - convert TrueVision Targa file into a portable pixmap
+ tifftopnm - convert a TIFF file into a portable anymap
+ xbmtopbm - convert an X11 or X10 bitmap into a portable bitmap
+ ximtoppm - convert an Xim file into a portable pixmap
+ xpmtoppm - convert an X11 pixmap into a portable pixmap
+ xvminitoppm - convert a XV "thumbnail" picture to PPM
+ xwdtopnm - convert a X11 or X10 window dump file into a portable anymap
+ ybmtopbm - convert a Bennet Yee "face" file into a portable bitmap
+ yuvplittoppm - convert a Y- an U- and a V-file into a portable pixmap.
+ yuvtoppm - convert Abekas YUV bytes into a portable pixmap
+ zeisstopnm - convert a Zeiss confocal file into a portable anymap
diff -r -c -N /tmp/null/pkg/PLIST ./pkg/PLIST
*** /tmp/null/pkg/PLIST	Wed Dec 31 18:00:00 1969
--- ./pkg/PLIST	Fri Nov 13 06:31:40 1998
***************
*** 0 ****
--- 1,377 ----
+ @comment $NetBSD: PLIST,v 1.5 1998/11/12 23:26:58 tron Exp $
+ bin/anytopnm
+ bin/asciitopgm
+ bin/atktopbm
+ bin/bioradtopgm
+ bin/bmptoppm
+ bin/brushtopbm
+ bin/cmuwmtopbm
+ bin/fitstopnm
+ bin/fstopgm
+ bin/g3topbm
+ bin/gemtopbm
+ bin/giftopnm
+ bin/gouldtoppm
+ bin/hipstopgm
+ bin/hpcdtoppm
+ bin/icontopbm
+ bin/ilbmtoppm
+ bin/imgtoppm
+ bin/lispmtopgm
+ bin/macptopbm
+ bin/mgrtopbm
+ bin/mtvtoppm
+ bin/pbmclean
+ bin/pbmlife
+ bin/pbmmake
+ bin/pbmmask
+ bin/pbmpscale
+ bin/pbmreduce
+ bin/pbmtext
+ bin/pbmto10x
+ bin/pbmto4425
+ bin/pbmtoascii
+ bin/pbmtoatk
+ bin/pbmtobbnbg
+ bin/pbmtocmuwm
+ bin/pbmtoepsi
+ bin/pbmtoepson
+ bin/pbmtog3
+ bin/pbmtogem
+ bin/pbmtogo
+ bin/pbmtoicon
+ bin/pbmtolj
+ bin/pbmtoln03
+ bin/pbmtolps
+ bin/pbmtomacp
+ bin/pbmtomgr
+ bin/pbmtopgm
+ bin/pbmtopi3
+ bin/pbmtopk
+ bin/pbmtoplot
+ bin/pbmtoptx
+ bin/pbmtox10bm
+ bin/pbmtoxbm
+ bin/pbmtoybm
+ bin/pbmtozinc
+ bin/pbmupc
+ bin/pcxtoppm
+ bin/pgmbentley
+ bin/pgmcrater
+ bin/pgmedge
+ bin/pgmenhance
+ bin/pgmhist
+ bin/pgmkernel
+ bin/pgmnoise
+ bin/pgmnorm
+ bin/pgmoil
+ bin/pgmramp
+ bin/pgmtexture
+ bin/pgmtofs
+ bin/pgmtolispm
+ bin/pgmtopbm
+ bin/pgmtoppm
+ bin/pi1toppm
+ bin/pi3topbm
+ bin/picttoppm
+ bin/pjtoppm
+ bin/pktopbm
+ bin/pngtopnm
+ bin/pnmalias
+ bin/pnmarith
+ bin/pnmcat
+ bin/pnmcomp
+ bin/pnmconvol
+ bin/pnmcrop
+ bin/pnmcut
+ bin/pnmdepth
+ bin/pnmenlarge
+ bin/pnmfile
+ bin/pnmflip
+ bin/pnmgamma
+ bin/pnmhisteq
+ bin/pnmhistmap
+ bin/pnmindex
+ bin/pnminvert
+ bin/pnmmargin
+ bin/pnmnlfilt
+ bin/pnmnoraw
+ bin/pnmpad
+ bin/pnmpaste
+ bin/pnmrotate
+ bin/pnmscale
+ bin/pnmshear
+ bin/pnmsmooth
+ bin/pnmtile
+ bin/pnmtoddif
+ bin/pnmtofits
+ bin/pnmtopng
+ bin/pnmtops
+ bin/pnmtorast
+ bin/pnmtorle
+ bin/pnmtosgi
+ bin/pnmtosir
+ bin/pnmtotiff
+ bin/pnmtoxwd
+ bin/ppm3d
+ bin/ppmbrighten
+ bin/ppmchange
+ bin/ppmdim
+ bin/ppmdist
+ bin/ppmdither
+ bin/ppmflash
+ bin/ppmforge
+ bin/ppmhist
+ bin/ppmmake
+ bin/ppmmix
+ bin/ppmnorm
+ bin/ppmntsc
+ bin/ppmpat
+ bin/ppmquant
+ bin/ppmquantall
+ bin/ppmqvga
+ bin/ppmrelief
+ bin/ppmshift
+ bin/ppmspread
+ bin/ppmtoacad
+ bin/ppmtobmp
+ bin/ppmtogif
+ bin/ppmtoicr
+ bin/ppmtoilbm
+ bin/ppmtomap
+ bin/ppmtomitsu
+ bin/ppmtopcx
+ bin/ppmtopgm
+ bin/ppmtopi1
+ bin/ppmtopict
+ bin/ppmtopj
+ bin/ppmtopjxl
+ bin/ppmtopuzz
+ bin/ppmtorgb3
+ bin/ppmtosixel
+ bin/ppmtotga
+ bin/ppmtouil
+ bin/ppmtoxpm
+ bin/ppmtoyuv
+ bin/ppmtoyuvsplit
+ bin/psidtopgm
+ bin/pstopnm
+ bin/qrttoppm
+ bin/rasttopnm
+ bin/rawtopgm
+ bin/rawtoppm
+ bin/rgb3toppm
+ bin/rletopnm
+ bin/sgitopnm
+ bin/sirtopnm
+ bin/sldtoppm
+ bin/spctoppm
+ bin/spottopgm
+ bin/sputoppm
+ bin/tgatoppm
+ bin/tifftopnm
+ bin/xbmtopbm
+ bin/ximtoppm
+ bin/xpmtoppm
+ bin/xvminitoppm
+ bin/xwdtopnm
+ bin/ybmtopbm
+ bin/yuvsplittoppm
+ bin/yuvtoppm
+ bin/zeisstopnm
+ include/pbm.h
+ include/pgm.h
+ include/pnm.h
+ include/ppm.h
+ lib/libpbm.a
+ lib/libpgm.a
+ lib/libpnm.a
+ lib/libppm.a
+ man/man1/anytopnm.1
+ man/man1/asciitopgm.1
+ man/man1/atktopbm.1
+ man/man1/bioradtopgm.1
+ man/man1/bmptoppm.1
+ man/man1/brushtopbm.1
+ man/man1/cmuwmtopbm.1
+ man/man1/fitstopnm.1
+ man/man1/fstopgm.1
+ man/man1/g3topbm.1
+ man/man1/gemtopbm.1
+ man/man1/giftopnm.1
+ man/man1/gouldtoppm.1
+ man/man1/hipstopgm.1
+ man/man1/hpcdtoppm.1
+ man/man1/icontopbm.1
+ man/man1/ilbmtoppm.1
+ man/man1/imgtoppm.1
+ man/man1/lispmtopgm.1
+ man/man1/macptopbm.1
+ man/man1/mgrtopbm.1
+ man/man1/mtvtoppm.1
+ man/man1/pbmclean.1
+ man/man1/pbmlife.1
+ man/man1/pbmmake.1
+ man/man1/pbmmask.1
+ man/man1/pbmpscale.1
+ man/man1/pbmreduce.1
+ man/man1/pbmtext.1
+ man/man1/pbmto10x.1
+ man/man1/pbmto4425.1
+ man/man1/pbmtoascii.1
+ man/man1/pbmtoatk.1
+ man/man1/pbmtobbnbg.1
+ man/man1/pbmtocmuwm.1
+ man/man1/pbmtoepsi.1
+ man/man1/pbmtoepson.1
+ man/man1/pbmtog3.1
+ man/man1/pbmtogem.1
+ man/man1/pbmtogo.1
+ man/man1/pbmtoicon.1
+ man/man1/pbmtolj.1
+ man/man1/pbmtoln03.1
+ man/man1/pbmtolps.1
+ man/man1/pbmtomacp.1
+ man/man1/pbmtomgr.1
+ man/man1/pbmtopgm.1
+ man/man1/pbmtopi3.1
+ man/man1/pbmtopk.1
+ man/man1/pbmtoplot.1
+ man/man1/pbmtoptx.1
+ man/man1/pbmtox10bm.1
+ man/man1/pbmtoxbm.1
+ man/man1/pbmtoybm.1
+ man/man1/pbmtozinc.1
+ man/man1/pbmupc.1
+ man/man1/pcxtoppm.1
+ man/man1/pgmbentley.1
+ man/man1/pgmcrater.1
+ man/man1/pgmedge.1
+ man/man1/pgmenhance.1
+ man/man1/pgmhist.1
+ man/man1/pgmkernel.1
+ man/man1/pgmnoise.1
+ man/man1/pgmnorm.1
+ man/man1/pgmoil.1
+ man/man1/pgmramp.1
+ man/man1/pgmtexture.1
+ man/man1/pgmtofs.1
+ man/man1/pgmtolispm.1
+ man/man1/pgmtopbm.1
+ man/man1/pgmtoppm.1
+ man/man1/pi1toppm.1
+ man/man1/pi3topbm.1
+ man/man1/picttoppm.1
+ man/man1/pjtoppm.1
+ man/man1/pktopbm.1
+ man/man1/pngtopnm.1
+ man/man1/pnmalias.1
+ man/man1/pnmarith.1
+ man/man1/pnmcat.1
+ man/man1/pnmcomp.1
+ man/man1/pnmconvol.1
+ man/man1/pnmcrop.1
+ man/man1/pnmcut.1
+ man/man1/pnmdepth.1
+ man/man1/pnmenlarge.1
+ man/man1/pnmfile.1
+ man/man1/pnmflip.1
+ man/man1/pnmgamma.1
+ man/man1/pnmhisteq.1
+ man/man1/pnmhistmap.1
+ man/man1/pnmindex.1
+ man/man1/pnminvert.1
+ man/man1/pnmmargin.1
+ man/man1/pnmnlfilt.1
+ man/man1/pnmnoraw.1
+ man/man1/pnmpad.1
+ man/man1/pnmpaste.1
+ man/man1/pnmrotate.1
+ man/man1/pnmscale.1
+ man/man1/pnmshear.1
+ man/man1/pnmsmooth.1
+ man/man1/pnmtile.1
+ man/man1/pnmtoddif.1
+ man/man1/pnmtofits.1
+ man/man1/pnmtopng.1
+ man/man1/pnmtops.1
+ man/man1/pnmtorast.1
+ man/man1/pnmtorle.1
+ man/man1/pnmtosgi.1
+ man/man1/pnmtosir.1
+ man/man1/pnmtotiff.1
+ man/man1/pnmtoxwd.1
+ man/man1/ppm3d.1
+ man/man1/ppmbrighten.1
+ man/man1/ppmchange.1
+ man/man1/ppmdim.1
+ man/man1/ppmdist.1
+ man/man1/ppmdither.1
+ man/man1/ppmflash.1
+ man/man1/ppmforge.1
+ man/man1/ppmhist.1
+ man/man1/ppmmake.1
+ man/man1/ppmmix.1
+ man/man1/ppmnorm.1
+ man/man1/ppmntsc.1
+ man/man1/ppmpat.1
+ man/man1/ppmquant.1
+ man/man1/ppmquantall.1
+ man/man1/ppmqvga.1
+ man/man1/ppmrelief.1
+ man/man1/ppmshift.1
+ man/man1/ppmspread.1
+ man/man1/ppmtoacad.1
+ man/man1/ppmtobmp.1
+ man/man1/ppmtogif.1
+ man/man1/ppmtoicr.1
+ man/man1/ppmtoilbm.1
+ man/man1/ppmtomap.1
+ man/man1/ppmtomitsu.1
+ man/man1/ppmtopcx.1
+ man/man1/ppmtopgm.1
+ man/man1/ppmtopi1.1
+ man/man1/ppmtopict.1
+ man/man1/ppmtopj.1
+ man/man1/ppmtopjxl.1
+ man/man1/ppmtopuzz.1
+ man/man1/ppmtorgb3.1
+ man/man1/ppmtosixel.1
+ man/man1/ppmtotga.1
+ man/man1/ppmtouil.1
+ man/man1/ppmtoxpm.1
+ man/man1/ppmtoyuv.1
+ man/man1/ppmtoyuvsplit.1
+ man/man1/psidtopgm.1
+ man/man1/pstopnm.1
+ man/man1/qrttoppm.1
+ man/man1/rasttopnm.1
+ man/man1/rawtopgm.1
+ man/man1/rawtoppm.1
+ man/man1/rgb3toppm.1
+ man/man1/rletopnm.1
+ man/man1/sgitopnm.1
+ man/man1/sirtopnm.1
+ man/man1/sldtoppm.1
+ man/man1/spctoppm.1
+ man/man1/spottopgm.1
+ man/man1/sputoppm.1
+ man/man1/tgatoppm.1
+ man/man1/tifftopnm.1
+ man/man1/xbmtopbm.1
+ man/man1/ximtoppm.1
+ man/man1/xpmtoppm.1
+ man/man1/xvminitoppm.1
+ man/man1/xwdtopnm.1
+ man/man1/ybmtopbm.1
+ man/man1/yuvsplittoppm.1
+ man/man1/yuvtoppm.1
+ man/man1/zeisstopnm.1
+ man/man3/libpbm.3
+ man/man3/libpgm.3
+ man/man3/libpnm.3
+ man/man3/libppm.3
+ man/man5/pbm.5
+ man/man5/pgm.5
+ man/man5/pnm.5
+ man/man5/ppm.5

>Audit-Trail:
>Unformatted: