home *** CD-ROM | disk | FTP | other *** search
Text File | 1993-07-13 | 50.3 KB | 1,473 lines |
- Newsgroups: comp.sources.x
- From: cristy@eplrx7.es.duPont.com (Cristy)
- Subject: v20i061: imagemagic - X11 image processing and display, Part05/38
- Message-ID: <1993Jul14.175334.852@sparky.sterling.com>
- X-Md4-Signature: e6eb6c345341cf17e3845291820e9536
- Sender: chris@sparky.sterling.com (Chris Olson)
- Organization: Sterling Software
- Date: Wed, 14 Jul 1993 17:53:34 GMT
- Approved: chris@sterling.com
-
- Submitted-by: cristy@eplrx7.es.duPont.com (Cristy)
- Posting-number: Volume 20, Issue 61
- Archive-name: imagemagic/part05
- Environment: X11
- Supersedes: imagemagic: Volume 13, Issue 17-37
-
- #!/bin/sh
- # this is magick.05 (part 5 of ImageMagick)
- # do not concatenate these parts, unpack them in order with /bin/sh
- # file ImageMagick/utilities/segment.c continued
- #
- if test ! -r _shar_seq_.tmp; then
- echo 'Please unpack part 1 first!'
- exit 1
- fi
- (read Scheck
- if test "$Scheck" != 5; then
- echo Please unpack part "$Scheck" next!
- exit 1
- else
- exit 0
- fi
- ) < _shar_seq_.tmp || exit 1
- if test ! -f _shar_wnt_.tmp; then
- echo 'x - still skipping ImageMagick/utilities/segment.c'
- else
- echo 'x - continuing file ImageMagick/utilities/segment.c'
- sed 's/^X//' << 'SHAR_EOF' >> 'ImageMagick/utilities/segment.c' &&
- X Error("unrecognized option",option);
- X break;
- X }
- X case 'f':
- X {
- X font=(char *) NULL;
- X if (*option == '-')
- X {
- X i++;
- X if (i == argc)
- X Error("missing font name on -font",(char *) NULL);
- X font=argv[i];
- X }
- X break;
- X }
- X case 'g':
- X {
- X image_geometry=(char *) NULL;
- X if (*option == '-')
- X {
- X i++;
- X if (i == argc)
- X Error("missing geometry on -geometry",(char *) NULL);
- X image_geometry=argv[i];
- X }
- X break;
- X }
- X case 'h':
- X {
- X Usage();
- X break;
- X }
- X case 'i':
- X {
- X if (strncmp("interlace",option+1,3) == 0)
- X {
- X interlace=NoneInterlace;
- X if (*option == '-')
- X {
- X i++;
- X if (i == argc)
- X Error("missing type on -interlace",(char *) NULL);
- X option=argv[i];
- X interlace=UndefinedInterlace;
- X if (Latin1Compare("none",option) == 0)
- X interlace=NoneInterlace;
- X if (Latin1Compare("line",option) == 0)
- X interlace=LineInterlace;
- X if (Latin1Compare("plane",option) == 0)
- X interlace=PlaneInterlace;
- X if (interlace == UndefinedInterlace)
- X Error("invalid interlace type on -interlace",option);
- X }
- X break;
- X }
- X Error("unrecognized option",option);
- X }
- X case 'p':
- X {
- X if (strncmp("page",option+1,2) == 0)
- X {
- X page_geometry=(char *) NULL;
- X if (*option == '-')
- X {
- X i++;
- X if (i == argc)
- X Error("missing page geometry on -page",(char *) NULL);
- X page_geometry=argv[i];
- X }
- X break;
- X }
- X Error("unrecognized option",option);
- X break;
- X }
- X case 'q':
- X {
- X i++;
- X if ((i == argc) || !sscanf(argv[i],"%d",&x))
- X Error("missing quality on -quality",(char *) NULL);
- X quality=atoi(argv[i]);
- X break;
- X }
- X case 's':
- X {
- X scene=0;
- X if (*option == '-')
- X {
- X i++;
- X if ((i == argc) || !sscanf(argv[i],"%d",&x))
- X Error("missing scene number on -scene",(char *) NULL);
- X scene=atoi(argv[i]);
- X }
- X break;
- X }
- X case 'v':
- X {
- X verbose=(*option == '-');
- X break;
- X }
- X default:
- X {
- X Error("unrecognized option",option);
- X break;
- X }
- X }
- X }
- X if (image == (Image *) NULL)
- X Error("missing an image file name",(char *) NULL);
- X /*
- X Write images.
- X */
- X do
- X {
- X total_colors=0;
- X if (alpha != NotInitialized)
- X image->alpha=alpha;
- X if (compression != UndefinedCompression)
- X image->compression=compression;
- X if (scene != 0)
- X image->scene=scene;
- X (void) strcpy(image->filename,argv[i]);
- X if (image->previous != (Image *) NULL)
- X (void) sprintf(image->filename,"%s.%u",argv[i],image->scene);
- X if (colorspace == GRAYColorspace)
- X QuantizeImage(image,256,8,False,GRAYColorspace,True);
- X /*
- X Reduce the number of colors in the image.
- X */
- X SegmentImage(image,colorspace,verbose);
- X if (verbose)
- X {
- X /*
- X Measure quantization error.
- X */
- X QuantizationError(image,&mean_error_per_pixel,&normalized_mean_error,
- X &normalized_maximum_error);
- X total_colors=NumberColors(image,(FILE *) NULL);
- X }
- X SyncImage(image);
- X status=WriteImage(&image_info,image);
- X if (verbose)
- X {
- X /*
- X Display detailed info about the image.
- X */
- X (void) fprintf(stderr,"[%u] %s=>%s %ux%u",image->scene,filename,
- X image->filename,image->columns,image->rows);
- X if (image->class == DirectClass)
- X (void) fprintf(stderr," DirectClass");
- X else
- X if (total_colors == 0)
- X (void) fprintf(stderr," PseudoClass %uc",image->colors);
- X else
- X {
- X (void) fprintf(stderr," PseudoClass %lu=>%uc",total_colors,
- X image->colors);
- X (void) fprintf(stderr," %u/%.6f/%.6fe",mean_error_per_pixel,
- X normalized_mean_error,normalized_maximum_error);
- X }
- X (void) fprintf(stderr," %s %lds\n",image->magick,
- X time((time_t *) NULL)-start_time+1);
- X }
- X next_image=image->next;
- X DestroyImage(image);
- X image=next_image;
- X } while (image != (Image *) NULL);
- X return(!status);
- }
- SHAR_EOF
- echo 'File ImageMagick/utilities/segment.c is complete' &&
- chmod 0644 ImageMagick/utilities/segment.c ||
- echo 'restore of ImageMagick/utilities/segment.c failed'
- Wc_c="`wc -c < 'ImageMagick/utilities/segment.c'`"
- test 59822 -eq "$Wc_c" ||
- echo 'ImageMagick/utilities/segment.c: original size 59822, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/utilities/segment.man ==============
- if test -f 'ImageMagick/utilities/segment.man' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/utilities/segment.man (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/utilities/segment.man (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/utilities/segment.man' &&
- .ad l
- .nh
- .TH segment 1 "10 April 1993" "ImageMagick"
- .SH NAME
- segment - segments an image with thresholding and the fuzzy c-Means
- technique.
- .SH SYNOPSIS
- .B "segment"
- [ \fIoptions\fP ... ] \fIinput_file\fP \fIoutput_file\fP
- .SH DESCRIPTION
- \fBsegment\fP segments an image by analyzing the histograms of the color
- components and identifying units that are homogeneous with the fuzzy c-means
- technique. The scale-space filter analyzes the histograms of the three
- color components of the image and identifies a set of classes. The
- extents of each class is used to coarsely segment the image with
- thresholding. The color associated with each class is determined by
- the mean color of all pixels within the extents of a particular class.
- Finally, any unclassified pixels are assigned to the closest class with
- the fuzzy c-means technique.
- .PP
- The fuzzy c-Means algorithm can be summarized as follows:
- .RS
- .LP
- o Build a histogram, one for each color component of the image.
- .LP
- o For each histogram, successively apply the scale-space filter and
- build an interval tree of zero crossings in the second derivative at
- each scale. Analyze this scale-space ``fingerprint'' to determine
- which peaks or valleys in the histogram are most predominant.
- .LP
- o The fingerprint defines intervals on the axis of the histogram. Each
- interval contains either a minima or a maxima in the original signal.
- If each color component lies within the maxima interval, that pixel is
- considered ``classified'' and is assigned an unique class number.
- .LP
- o Any pixel that fails to be classified in the above thresholding pass is
- classified using the fuzzy c-Means technique. It is assigned to one
- of the classes discovered in the histogram analysis phase.
- .RE
- .PP
- The fuzzy c-Means technique attempts to cluster a pixel by finding the local
- minima of the generalized within group sum of squared error objective
- function. A pixel is assigned to the closest class of which the fuzzy
- membership has a maximum value.
- X
- For additional information see
- .IP
- Young Won Lim, Sang Uk Lee, "On The Color Image Segmentation Algorithm Based
- on the Thresholding and the Fuzzy c-Means Techniques", Pattern Recognition,
- Volume 23, Number 9, pages 935-952, 1990.
- .SH EXAMPLES
- .PP
- To segment an image of a cockatoo, use:
- .PP
- .B
- X segment cockatoo.miff cockatoo.segmented
- .PP
- To segment a raw grayscale image, use:
- .PP
- .B
- X segment -geometry 768x512 gray:raw image.miff
- .SH OPTIONS
- .TP 5
- .B "-alpha"
- store alpha channel if the image has one.
- .TP 5
- .B "-colorspace \fIvalue\fP"
- the type of colorspace: \fBGRAY\fP, \fBRGB\fP, \fBXYZ\fP, \fBYCbCr\fP,
- \fBYIQ\fP, or \fBYUV\fP.
- X
- Color reduction, by default, takes place in the RGB color space.
- Empirical evidence suggests that distances in color spaces such as YUV
- or YIQ correspond to perceptual color differences more closely
- than do distances in RGB space. These color spaces may give better
- results when color reducing an image. Refer to \fBquantize(9)\fP for
- more details.
- X
- The \fB-colors\fP or \fB-monochrome\fP option is required for this option
- to take effect.
- .TP 5
- .B "-compress \fItype\fP"
- the type of image compression: \fIQEncoded\fP or \fIRunlengthEncoded\fP.
- X
- Specify \fB\+compress\fP to store the binary image in an uncompressed format.
- The default is the compression type of the specified image file.
- .TP 5
- .B "-density \fI<width>x<height>
- vertical and horizonal density of the image.
- X
- This option specifies an image density whose interpretation changes
- with the type of image. The default is 72 dots per inch in the
- horizonal and vertical direction for Postscript. Text files default to
- 80 characters in width and 60 lines in height. Use this option to
- alter the default density.
- .TP 5
- .B "-display \fIhost:display[.screen]\fP"
- specifies the X server to contact; see \fBX(1)\fP.
- .TP 5
- .B "-font \fIname\fP"
- This option specifies the font to be used for displaying normal text.
- The default is \fBfixed\fP.
- .TP 5
- .B "-geometry \fI<width>x<height>\fP"
- the width and height of the image.
- X
- Use this option to specified the width and height of raw images whose
- dimensions are unknown such as \fBGRAY\fP, \fBRGB\fP, and \fBCMYK\fP.
- This option can also change the default 8.5 by 11 width and height of
- the Postscript canvas.
- .TP 5
- .B "-interlace \fItype\fP"
- the type of interlacing scheme: \fBNONE\fP, \fBLINE\fP, or \fBPLANE\fP.
- X
- This option is used to specify the type of interlacing scheme for raw
- image formats such as \fBRGB\fP or \fBYUV\fP. \fBNONE\fP means do not
- interlace (RGBRGBRGBRGBRGBRGB...), \fBLINE\fP uses scanline
- interlacing (RRR...GGG...BBB...RRR...GGG...BBB...), and \fBPLANE\fP uses
- plane interlacing (RRRRRR...GGGGGG...BBBBBB...).
- .TP 5
- .B "-page \fI<width>x<height>{\+-}<x offset>{\+-}<y offset>\fP"
- preferred size and location of the Postscript page.
- X
- Use this option to specify the dimensions of the Postscript page in picas. The
- default is to center the image on a letter page, 612 by 792 picas.
- Other common sizes are:
- X
- X 540x720 Note
- X 612x1008 Legal
- X 842x1190 A3
- X 595x842 A4
- X 421x595 A5
- X 297x421 A6
- X 709x1002 B4
- X 612x936 U.S. Foolscap
- X 612x936 European Foolscap
- X 396x612 Half Letter
- X 792x1224 11x17
- X 1224x792 Ledger
- X
- The page geometry is relative to the vertical and horizonal density of the
- Postscript page. See \fB-density\fP for details.
- .TP 5
- .B "-quality \fIvalue\fP"
- JPEG quality setting.
- X
- Quality is 0 (worst) to 100 (best). The default is 75.
- .TP 5
- .B "-scene \fIvalue\fP"
- image scene number.
- .TP 5
- .B -verbose
- print detailed information about the image.
- X
- This information is printed: image scene number; image name; converted
- image name; image size; the image class (\fIDirectClass\fP or
- \fIPseudoClass\fP); the total number of unique colors; and the number
- of seconds to read and convert the image.
- .PP
- Change '-' to '+' in any option above to reverse its effect. For
- example, specify +alpha to store the image without its alpha channel.
- .PP
- By default, the image format is determined by its magic number. To
- specify a particular image format, precede the filename with an image
- format name and a colon (i.e. ps:image) or specify the image type as
- the filename suffix (i.e. image.ps). See \fBconvert(1)\fP for a list
- of valid image formats.
- .PP
- When you specify \fBX\fP as your image type, the filename has special
- meaning. It specifies an X window by id, name, or \fBroot\fP. If no
- filename is specified, the window is selected by clicking the mouse in
- the desired window.
- .PP
- Specify \fIinput_file\fP as \fI-\fP for standard input,
- \fIoutput_file\fP as \fI-\fP for standard output. If \fIinput_file\fP
- has the extension \fB.Z\fP or \fB.gz\fP, the file is uncompressed with
- \fBuncompress\fP or \fBgunzip\fP respectively. If \fIoutput_file\fP
- has the extension \fB.Z\fP or \fB.gz\fP, the file size is compressed
- using with \fBcompress\fP or \fBgzip\fP respectively. If
- \fIoutput_file\fP already exists, you will be prompted as to whether it
- should be overwritten.
- .SH ENVIRONMENT
- .PP
- .TP 5
- .B display
- To get the default host, display number, and screen.
- .SH SEE ALSO
- .B
- display(1), animate(1), mogrify(1), quantize(9), X(1), miff(5)
- .SH COPYRIGHT
- Copyright 1993 E. I. du Pont de Nemours & Company
- .PP
- Permission to use, copy, modify, distribute, and sell this software and
- its documentation for any purpose is hereby granted without fee,
- provided that the above copyright notice appear in all copies and that
- both that copyright notice and this permission notice appear in
- supporting documentation, and that the name of E. I. du Pont de Nemours
- & Company not be used in advertising or publicity pertaining to
- distribution of the software without specific, written prior
- permission. E. I. du Pont de Nemours & Company makes no representations
- about the suitability of this software for any purpose. It is provided
- "as is" without express or implied warranty.
- .PP
- E. I. du Pont de Nemours & Company disclaims all warranties with regard
- to this software, including all implied warranties of merchantability
- and fitness, in no event shall E. I. du Pont de Nemours & Company be
- liable for any special, indirect or consequential damages or any
- damages whatsoever resulting from loss of use, data or profits, whether
- in an action of contract, negligence or other tortious action, arising
- out of or in connection with the use or performance of this software.
- .SH ACKNOWLEDGEMENTS
- Andy Gallo, University of Delaware. This software is strongly based on
- software Andy wrote.
- .SH AUTHORS
- John Cristy, E.I. du Pont De Nemours & Company Incorporated
- SHAR_EOF
- chmod 0644 ImageMagick/utilities/segment.man ||
- echo 'restore of ImageMagick/utilities/segment.man failed'
- Wc_c="`wc -c < 'ImageMagick/utilities/segment.man'`"
- test 8572 -eq "$Wc_c" ||
- echo 'ImageMagick/utilities/segment.man: original size 8572, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/xtp/Imakefile ==============
- if test ! -d 'ImageMagick/xtp'; then
- echo 'x - creating directory ImageMagick/xtp'
- mkdir 'ImageMagick/xtp'
- fi
- if test -f 'ImageMagick/xtp/Imakefile' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/xtp/Imakefile (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/xtp/Imakefile (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/xtp/Imakefile' &&
- #
- # Imakefile for xtp.
- #
- # Copyright 1992 E. I. du Pont de Nemours & Company
- #
- # Permission to use, copy, modify, distribute, and sell this software and
- # its documentation for any purpose is hereby granted without fee,
- # provided that the above Copyright notice appear in all copies and that
- # both that Copyright notice and this permission notice appear in
- # supporting documentation, and that the name of E. I. du Pont de Nemours
- # & Company not be used in advertising or publicity pertaining to
- # distribution of the software without specific, written prior
- # permission. E. I. du Pont de Nemours & Company makes no representations
- # about the suitability of this software for any purpose. It is provided
- # "as is" without express or implied warranty.
- #
- # E. I. du Pont de Nemours & Company disclaims all warranties with regard
- # to this software, including all implied warranties of merchantability
- # and fitness, in no event shall E. I. du Pont de Nemours & Company be
- # liable for any special, indirect or consequential damages or any
- # damages whatsoever resulting from loss of use, data or profits, whether
- # in an action of contract, negligence or other tortious action, arising
- # out of or in connection with the use or performance of this software.
- #
- X
- #include "../Magick.tmpl"
- X
- XXTPObjects= xtp.o network.o regular.o
- X
- PROGRAMS= xtp
- X
- AllTarget($(PROGRAMS))
- X
- NormalProgramTarget(xtp,$(XTPObjects), , , )
- InstallProgram(xtp,$(LOCALDIR))
- InstallManPage(xtp,$(MANDIR))
- DependTarget()
- SHAR_EOF
- chmod 0644 ImageMagick/xtp/Imakefile ||
- echo 'restore of ImageMagick/xtp/Imakefile failed'
- Wc_c="`wc -c < 'ImageMagick/xtp/Imakefile'`"
- test 1512 -eq "$Wc_c" ||
- echo 'ImageMagick/xtp/Imakefile: original size 1512, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/xtp/Makefile ==============
- if test -f 'ImageMagick/xtp/Makefile' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/xtp/Makefile (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/xtp/Makefile (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/xtp/Makefile' &&
- #
- # Generic makefile for xtp for computers that do not have xmkmf.
- #
- # Copyright 1992 E. I. du Pont de Nemours & Company
- #
- # Permission to use, copy, modify, distribute, and sell this software and
- # its documentation for any purpose is hereby granted without fee,
- # provided that the above Copyright notice appear in all copies and that
- # both that Copyright notice and this permission notice appear in
- # supporting documentation, and that the name of E. I. du Pont de Nemours
- # & Company not be used in advertising or publicity pertaining to
- # distribution of the software without specific, written prior
- # permission. E. I. du Pont de Nemours & Company makes no representations
- # about the suitability of this software for any purpose. It is provided
- # "as is" without express or implied warranty.
- #
- # E. I. du Pont de Nemours & Company disclaims all warranties with regard
- # to this software, including all implied warranties of merchantability
- # and fitness, in no event shall E. I. du Pont de Nemours & Company be
- # liable for any special, indirect or consequential damages or any
- # damages whatsoever resulting from loss of use, data or profits, whether
- # in an action of contract, negligence or other tortious action, arising
- # out of or in connection with the use or performance of this software.
- #
- X
- CC= cc -O
- DESTDIR= /usr/local/bin
- INSTALL = install -c
- RM= /bin/rm -f
- #SYS_LIBRARIES= -lnsl
- X
- XXTPObjects= xtp.o network.o regular.o
- X
- PROGRAMS= xtp
- X
- all: $(PROGRAMS)
- X
- xtp: $(XTPObjects)
- X $(RM) $@
- X $(CC) -o $@ $(XTPObjects) $(SYS_LIBRARIES)
- X
- clean::
- X $(RM) xtp
- X
- install:: xtp
- X $(INSTALL) xtp $(DESTDIR)
- X
- clean::
- X $(RM) *.ln *.bak *.o core errs ,* *~ *.a .emacs_* make.log MakeOut
- X
- SHAR_EOF
- chmod 0644 ImageMagick/xtp/Makefile ||
- echo 'restore of ImageMagick/xtp/Makefile failed'
- Wc_c="`wc -c < 'ImageMagick/xtp/Makefile'`"
- test 1709 -eq "$Wc_c" ||
- echo 'ImageMagick/xtp/Makefile: original size 1709, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/xtp/README ==============
- if test -f 'ImageMagick/xtp/README' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/xtp/README (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/xtp/README (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/xtp/README' &&
- XXtp is a utility for retrieving, listing, or printing files from a
- remote network site. Xtp performs most of the same functions as the
- ftp program, but does not require any interactive commands. You simply
- specify the file transfer task on the command line and xtp performs the
- transfer automatically.
- X
- To retrieve file contrib/ImageMagick.tar.Z from host export.lcs.mit.edu,
- use:
- X
- X xtp -binary -retrieve ImageMagick.tar.Z export.lcs.mit.edu contrib
- X
- XXtp requires 4.3 BSD compatibilities. I have successfully executed it on
- a SUN, DEC Ultrix, MIPS, IBM RS/6000, and Ardent Titan.
- X
- The author is cristy@dupont.com. Comments, suggestions, etc, are
- welcome, but be kind.
- X
- ---
- X
- Copyright 1990 E. I. Dupont de Nemours & Company
- X
- Permission to use, copy, modify, distribute, and sell this software and
- its documentation for any purpose is hereby granted without fee,
- provided that the above copyright notice appear in all copies and that
- both that copyright notice and this permission notice appear in
- supporting documentation, and that the name of E. I. Dupont de Nemours
- & Company not be used in advertising or publicity pertaining to
- distribution of the software without specific, written prior
- permission. E. I. Dupont de Nemours & Company makes no representations
- about the suitability of this software for any purpose. It is provided
- "as is" without express or implied warranty.
- X
- E. I. Dupont de Nemours & Company disclaims all warranties with regard
- to this software, including all implied warranties of merchantability
- and fitness, in no event shall E. I. Dupont de Nemours & Company be
- liable for any special, indirect or consequential damages or any
- damages whatsoever resulting from loss of use, data or profits, whether
- in an action of contract, negligence or other tortious action, arising
- out of or in connection with the use or performance of this software.
- X
- SHAR_EOF
- chmod 0644 ImageMagick/xtp/README ||
- echo 'restore of ImageMagick/xtp/README failed'
- Wc_c="`wc -c < 'ImageMagick/xtp/README'`"
- test 1876 -eq "$Wc_c" ||
- echo 'ImageMagick/xtp/README: original size 1876, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/xtp/get ==============
- if test -f 'ImageMagick/xtp/get' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/xtp/get (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/xtp/get (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/xtp/get' &&
- #!/usr/bin/perl
- #
- # Retrieve files from remote host using standard 'host: filename' string:
- #
- # get export.lcs.mit.edu: contrib/ImageMagick.tar.Z
- #
- $host=shift || die "Usage: get host/ip-address file\n";
- $file=shift || die "Usage: get host/ip-address file\n";
- $host=~s/:$//;
- $directory=`dirname $file`;
- chop($directory);
- $file=`basename $file`;
- chop($file);
- printf("Getting %s in directory %s from host %s...\n",$file,$directory,$host);
- $pid=fork;
- if ($pid == 0)
- X {
- X exec("xtp -r $file -b $host $directory");
- X exit(0);
- X }
- exit(0);
- SHAR_EOF
- chmod 0644 ImageMagick/xtp/get ||
- echo 'restore of ImageMagick/xtp/get failed'
- Wc_c="`wc -c < 'ImageMagick/xtp/get'`"
- test 541 -eq "$Wc_c" ||
- echo 'ImageMagick/xtp/get: original size 541, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/xtp/network.c ==============
- if test -f 'ImageMagick/xtp/network.c' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/xtp/network.c (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/xtp/network.c (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/xtp/network.c' &&
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % N N EEEEE TTTTT W W OOO RRRR K K %
- % NN N E T W W O O R R K K %
- % N N N EEE T W W W O O RRRR KKK %
- % N NN E T WW WW O O R R K K %
- % N N EEEEE T W W OOO R R K K %
- % %
- % %
- % Network Routines. %
- % %
- % %
- % Software Design %
- % John Cristy %
- % October 1992 %
- % %
- % %
- % Copyright 1993 E. I. Dupont de Nemours & Company %
- % %
- % Permission to use, copy, modify, distribute, and sell this software and %
- % its documentation for any purpose is hereby granted without fee, %
- % provided that the above Copyright notice appear in all copies and that %
- % both that Copyright notice and this permission notice appear in %
- % supporting documentation, and that the name of E. I. Dupont de Nemours %
- % & Company not be used in advertising or publicity pertaining to %
- % distribution of the software without specific, written prior %
- % permission. E. I. Dupont de Nemours & Company makes no representations %
- % about the suitability of this software for any purpose. It is provided %
- % "as is" without express or implied warranty. %
- % %
- % E. I. Dupont de Nemours & Company disclaims all warranties with regard %
- % to this software, including all implied warranties of merchantability %
- % and fitness, in no event shall E. I. Dupont de Nemours & Company be %
- % liable for any special, indirect or consequential damages or any %
- % damages whatsoever resulting from loss of use, data or profits, whether %
- % in an action of contract, negligence or other tortious action, arising %
- % out of or in connection with the use or performance of this software. %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- %
- */
- X
- #include "xtp.h"
- #include "regular.h"
- #include <unistd.h>
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <netdb.h>
- #include <arpa/inet.h>
- X
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % G e t H o s t I n f o %
- % %
- % %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- % Function GetHostInfo accepts a host name or address, verifies it is valid,
- % and returns both the host name and address from the network host entry.
- %
- % The format of the GetHostInfo routine is:
- %
- % info=GetHostInfo(name)
- %
- % A description of each parameter follows:
- %
- % o info: Function GetHostInfo returns a pointer to the host name and
- % IP address. A null pointer is returned if there the host cannot be
- % located.
- %
- % o name: Specifies a pointer to a character array that contains either
- % a name of a host or an IP address.
- %
- %
- */
- char *GetHostInfo(name)
- char
- X *name;
- {
- X char
- X info[2048],
- X *p;
- X
- X struct in_addr
- X in;
- X
- X struct hostent
- X *hp;
- X
- X /*
- X Get host name and address.
- X */
- X if (isascii(*name) && isdigit(*name))
- X in.s_addr=inet_addr(name);
- X else
- X {
- X in.s_addr=(unsigned long) -1;
- X hp=gethostbyname(name);
- X if (hp != (struct hostent *) NULL)
- X in.s_addr=(*(int *) hp->h_addr);
- X }
- X hp=gethostbyaddr((char *) &in,sizeof(struct in_addr),AF_INET);
- X if (hp == (struct hostent *) NULL)
- X {
- X hp=gethostbyname(name);
- X if (hp == (struct hostent *) NULL)
- X return((char *) NULL);
- X }
- X /*
- X Convert hostname to lower-case characters.
- X */
- X p=hp->h_name;
- X while (*p)
- X {
- X if (isupper(*p))
- X *p=tolower(*p);
- X p++;
- X }
- X (void) sprintf(info,"%s [%s]: ",hp->h_name,inet_ntoa(in));
- X return(info);
- }
- SHAR_EOF
- chmod 0644 ImageMagick/xtp/network.c ||
- echo 'restore of ImageMagick/xtp/network.c failed'
- Wc_c="`wc -c < 'ImageMagick/xtp/network.c'`"
- test 5583 -eq "$Wc_c" ||
- echo 'ImageMagick/xtp/network.c: original size 5583, current size' "$Wc_c"
- rm -f _shar_wnt_.tmp
- fi
- # ============= ImageMagick/xtp/regular.c ==============
- if test -f 'ImageMagick/xtp/regular.c' -a X"$1" != X"-c"; then
- echo 'x - skipping ImageMagick/xtp/regular.c (File already exists)'
- rm -f _shar_wnt_.tmp
- else
- > _shar_wnt_.tmp
- echo 'x - extracting ImageMagick/xtp/regular.c (Text)'
- sed 's/^X//' << 'SHAR_EOF' > 'ImageMagick/xtp/regular.c' &&
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % RRRR EEEEE GGGG U U L AAA RRRR %
- % R R E G U U L A A R R %
- % RRRR EEE G GG U U L AAAAA RRRR %
- % R R E G G U U L A A R R %
- % R R EEEEE GGGG UUU LLLLL A A R R %
- % %
- % %
- % Regular Expression Interpreter. %
- % %
- % %
- % %
- % Software Design %
- % John Cristy %
- % July 1992 %
- % %
- % %
- % Copyright 1993 E. I. Dupont de Nemours & Company %
- % %
- % Permission to use, copy, modify, distribute, and sell this software and %
- % its documentation for any purpose is hereby granted without fee, %
- % provided that the above Copyright notice appear in all copies and that %
- % both that Copyright notice and this permission notice appear in %
- % supporting documentation, and that the name of E. I. Dupont de Nemours %
- % & Company not be used in advertising or publicity pertaining to %
- % distribution of the software without specific, written prior %
- % permission. E. I. Dupont de Nemours & Company makes no representations %
- % about the suitability of this software for any purpose. It is provided %
- % "as is" without express or implied warranty. %
- % %
- % E. I. Dupont de Nemours & Company disclaims all warranties with regard %
- % to this software, including all implied warranties of merchantability %
- % and fitness, in no event shall E. I. Dupont de Nemours & Company be %
- % liable for any special, indirect or consequential damages or any %
- % damages whatsoever resulting from loss of use, data or profits, whether %
- % in an action of contract, negligence or other tortious action, arising %
- % out of or in connection with the use or performance of this software. %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- % CompileRegularExpression returns NULL for a failure, where failures are
- % syntax errors, exceeding implementation limits, or applying `+' or `*'
- % to a possibly-null operand.
- %
- % This is essentially the same routine written and copywrited by Henry
- % Spencer, University of Toronto. I made minor programming changes but
- % major variable name changes to improve readability.
- %
- % A regular expression is zero or more branches, separated by `|'. It
- % matches anything that matches one of the branches.
- %
- % A branch is zero or more pieces, concatenated. It matches a match for
- % the first, followed by a match for the second, etc.
- %
- % A piece is an atom possibly followed by `*', `+', or `?'. An atom
- % followed by `*' matches a sequence of 0 or more matches of the atom. An
- % atom followed by `+' matches a sequence of 1 or more matches of the
- % atom. An atom followed by `?' matches a match of the atom, or the null
- % pattern.
- %
- % An atom is a regular expression in parentheses (matching a match for
- % the regular expression), a range (see below), `.' (matching any single
- % character), `^' (matching the null pattern at the beginning of the input
- % pattern), `$' (matching the null pattern at the end of the input pattern),
- % a `\' followed by a single character (matching that character), or a
- % single character with no other significance (matching that character).
- %
- % A range is a sequence of characters enclosed in `[]'. It normally
- % matches any single character from the sequence. If the sequence begins
- % with `^', it matches any single character not from the rest of the
- % sequence. If two characters in the sequence are separated by `-', this
- % is shorthand for the full list of ASCII characters between them (e.g.
- % `[0-9]' matches any decimal digit). To include a literal `]' in the
- % sequence, make it the first character (following a possible `^'). To
- % include a literal `-', make it the first or last character.
- %
- % If a regular expression could match two different parts of the input
- % pattern, it will match the one which begins earliest. If both begin in
- % the same place but match different lengths, or match the same length
- % in different ways, life gets messier, as follows.
- %
- % In general, the possibilities in a list of branches are considered in
- % left-to-right order, the possibilities for `*', `+', and `?' are
- % considered longest-first, nested constructs are considered from the
- % outermost in, and concatenated constructs are considered
- % leftmost-first. The match that will be chosen is the one that uses the
- % earliest possibility in the first choice that has to be made. If there
- % is more than one choice, the next will be made in the same manner
- % (earliest possibility) subject to the decision on the first choice.
- % And so forth.
- %
- % For example, `(ab|a)b*c' could match `abc' in one of two ways. The
- % first choice is between `ab' and `a'; since `ab' is earlier, and does
- % lead to a successful overall match, it is chosen. Since the `b' is
- % already spoken for, the `b*' must match its last possibility-the empty
- % pattern-since it must respect the earlier choice.
- %
- % In the particular case where no `|'s are present and there is only one
- % `*', `+', or `?', the net effect is that the longest possible match
- % will be chosen. So `ab*', presented with `xabbbby', will match `abbbb'.
- % Note that if `ab*' is tried against `xabyabbbz', it will match `ab'
- % just after `x', due to the begins-earliest rule. (In effect, the deci-
- % sion on where to start the match is the first choice to be made, hence
- % subsequent choices must respect it even if this leads them to
- % less-preferred alternatives.)
- %
- %
- */
- X
- #include "xtp.h"
- #include "regular.h"
- X
- /*
- X Variable declarations.
- */
- char
- X *code,
- X **subpattern_end,
- X *p,
- X start_code,
- X *start_pattern,
- X **subpattern;
- X
- static char
- X *token;
- X
- static int
- X number_parenthesis;
- X
- static long
- X code_size;
- X
- /*
- X Forward declarations.
- */
- static char
- X *NextToken _Declare((register char *)),
- X *Node _Declare((int)),
- X *Piece _Declare((int *)),
- X *Regular _Declare((int,int *));
- X
- static int
- X Repeat _Declare((char *));
- X
- static void
- X EmitCode _Declare((int)),
- X Tail _Declare((char *,char *));
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % A t o m %
- % %
- % %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- %
- */
- static char *Atom(flagp)
- int
- X *flagp;
- {
- X int
- X flags;
- X
- X register char
- X *status;
- X
- X *flagp=WorstCase;
- X switch(*token++)
- X {
- X case '^':
- X {
- X status=Node(MatchBeginningOfLine);
- X break;
- X }
- X case '$':
- X {
- X status=Node(MatchEndOfProgramOfLine);
- X break;
- X }
- X case '.':
- X {
- X status=Node(MatchAnyCharacter);
- X *flagp|=NonNull | Simple;
- X break;
- X }
- X case '[':
- X {
- X register int
- X class,
- X class_end;
- X
- X if (*token != '^')
- X status=Node(MatchAnyCharacterOf);
- X else
- X {
- X /*
- X Complement of range.
- X */
- X status=Node(MatchAnyCharacterBut);
- X token++;
- X }
- X if ((*token == ']') || (*token == '-'))
- X EmitCode(*token++);
- X while ((*token != '\0') && (*token != ']'))
- X {
- X if (*token != '-')
- X EmitCode(*token++);
- X else
- X {
- X token++;
- X if ((*token == ']') || (*token == '\0'))
- X EmitCode('-');
- X else
- X {
- X class=((int)*(unsigned char *)(token-2))+1;
- X class_end=((int)*(unsigned char *)(token));
- X if (class > class_end+1)
- X Fail("invalid [] range");
- X for(; class <= class_end; class++)
- X EmitCode((char) class);
- X token++;
- X }
- X }
- X }
- X EmitCode('\0');
- X if (*token != ']')
- X Fail("unmatched []");
- X token++;
- X *flagp|=NonNull | Simple;
- X break;
- X }
- X case '(':
- X {
- X status=Regular(1,&flags);
- X if (status == NULL)
- X return(NULL);
- X *flagp|=flags & (NonNull | SpecialStart);
- X break;
- X }
- X case '\0':
- X case '|':
- X case ')':
- X {
- X Fail("internal urp");
- X break;
- X }
- X case '?':
- X case '+':
- X case '*':
- X {
- X Fail("?+* follows nothing");
- X break;
- X }
- X case '\\':
- X {
- X if (*token == '\0')
- X Fail("trailing \\");
- X status=Node(MatchExactly);
- X EmitCode(*token++);
- X EmitCode('\0');
- X *flagp|=NonNull | Simple;
- X break;
- X }
- X default:
- X {
- X register char
- X ender;
- X
- X register int
- X length;
- X
- X token--;
- X length=strcspn(token,Meta);
- X if (length <= 0)
- X Fail("internal disaster");
- X ender=(*(token+length));
- X if (length > 1 && MultipleMatches(ender))
- X length--;
- X *flagp|=NonNull;
- X if (length == 1)
- X *flagp|=Simple;
- X status=Node(MatchExactly);
- X while (length > 0)
- X {
- X EmitCode(*token++);
- X length--;
- X }
- X EmitCode('\0');
- X break;
- X }
- X }
- X return(status);
- }
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % B r a n c h %
- % %
- % %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- % Function Branch Implements the | operator.
- %
- %
- */
- static char *Branch(flagp)
- int
- X *flagp;
- {
- X int
- X flags;
- X
- X register char
- X *chain,
- X *latest,
- X *status;
- X
- X *flagp=WorstCase;
- X status=Node(MatchThisOrNext);
- X chain=NULL;
- X while ((*token != '\0') && (*token != '|') && (*token != ')'))
- X {
- X latest=Piece(&flags);
- X if (latest == NULL)
- X return(NULL);
- X *flagp|=flags & NonNull;
- X if (chain == NULL)
- X *flagp|=flags & SpecialStart;
- X else
- X Tail(chain,latest);
- X chain=latest;
- X }
- X if (chain == NULL)
- X (void) Node(MatchEmptyString);
- X return(status);
- }
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % E m i t C o d e %
- % %
- % %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- %
- */
- static void EmitCode(opcode)
- int
- X opcode;
- {
- X if (code != &start_code)
- X *code++=(char) opcode;
- X else
- X code_size++;
- }
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % I n s e r t %
- % %
- % %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- % Function Insert inserts an operator in front of an already-emitted operand.
- %
- */
- static void Insert(opcode,operand)
- char
- X opcode,
- X *operand;
- {
- X register char
- X *p,
- X *place,
- X *q;
- X
- X if (code == &start_code)
- X {
- X code_size+=3;
- X return;
- X }
- X p=code;
- X code+=3;
- X q=code;
- X while (p > operand)
- X *--q=(*--p);
- X place=operand;
- X *place++=opcode;
- X *place++='\0';
- X *place++='\0';
- }
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % M a t c h %
- % %
- % %
- % %
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- %
- %
- */
- static int Match(regular_expression)
- char
- X *regular_expression;
- {
- X char
- X *next_token;
- X
- X register char
- X *scan;
- X
- X scan=regular_expression;
- X while (scan != NULL)
- X {
- X next_token=NextToken(scan);
- X switch(OpCode(scan))
- X {
- X case MatchBeginningOfLine:
- X {
- X if (p != start_pattern)
- X return(0);
- X break;
- X }
- X case MatchEndOfProgramOfLine:
- X {
- X if (*p != '\0')
- X return(0);
- X break;
- X }
- X case MatchAnyCharacter:
- X {
- X if (*p == '\0')
- X return(0);
- X p++;
- X break;
- X }
- X case MatchExactly:
- X {
- X register char
- X *operand;
- X
- X register int
- X length;
- X
- X operand=Operand(scan);
- X /*
- X Inline the first character for speed.
- X */
- X if (*operand != *p)
- X return(0);
- X length=strlen(operand);
- X if ((length > 1) && (strncmp(operand,p,length) != 0))
- X return(0);
- X p+=length;
- X break;
- X }
- X case MatchAnyCharacterOf:
- X {
- X if ((*p == '\0' || strchr(Operand(scan),*p) == NULL))
- X return(0);
- X p++;
- X break;
- X }
- X case MatchAnyCharacterBut:
- X {
- X if ((*p == '\0') || (strchr(Operand(scan),*p) != NULL))
- X return(0);
- X p++;
- X break;
- X }
- X case MatchEmptyString:
- X break;
- X case Back:
- X break;
- X case Open+1:
- X case Open+2:
- X case Open+3:
- X case Open+4:
- X case Open+5:
- X case Open+6:
- X case Open+7:
- X case Open+8:
- X case Open+9:
- X {
- X register char
- X *save;
- X
- X register int
- X no;
- X
- X no=OpCode(scan)-Open;
- X save=p;
- X if (!Match(next_token))
- X return(0);
- X else
- X {
- X /*
- X Don't set subpattern if some later invocation of the same
- X parentheses already has.
- X */
- X if (subpattern[no] == NULL)
- X subpattern[no]=save;
- X return(1);
- X }
- X break;
- X }
- X case Close+1:
- X case Close+2:
- X case Close+3:
- X case Close+4:
- X case Close+5:
- X case Close+6:
- X case Close+7:
- X case Close+8:
- X case Close+9:
- X {
- X register char
- X *save;
- X
- X register int
- X no;
- X
- X no=OpCode(scan)-Close;
- X save=p;
- X if (!Match(next_token))
- X return(0);
- X else
- X {
- X /*
- X Don't set subpattern_end if some later invocation of the same
- X parentheses already has.
- X */
- X if (subpattern_end[no] == NULL)
- X subpattern_end[no]=save;
- X return(1);
- X }
- X break;
- X }
- X case MatchThisOrNext:
- X {
- X register char
- X *save;
- X
- X if (OpCode(next_token) != MatchThisOrNext)
- X next_token=Operand(scan);
- X else
- X {
- X do
- X {
- X save=p;
- X if (Match(Operand(scan)))
- X return(1);
- X p=save;
- X scan=NextToken(scan);
- X } while ((scan != NULL) && (OpCode(scan) == MatchThisOrNext));
- X return(0);
- X }
- X break;
- X }
- X case MatchZeroOrMore:
- X case MatchOneOrMore:
- X {
- X register char
- X next_tokench,
- X *save;
- X
- X register int
- X min,
- X no;
- X
- X /*
- X Lookahead to avoid useless match attempts when we know what
- X character comes next_token.
- X */
- X next_tokench='\0';
- X if (OpCode(next_token) == MatchExactly)
- X next_tokench=(*Operand(next_token));
- X min=(OpCode(scan) == MatchZeroOrMore) ? 0 : 1;
- X save=p;
- X no=Repeat(Operand(scan));
- X while (no >= min)
- X {
- X /*
- X If it could work, try it.
- X */
- X if ((next_tokench == '\0') || (*p == next_tokench))
- X if (Match(next_token))
- X return(1);
- X /*
- X Couldn't or didn't -- back up.
- X */
- X no--;
- X p=save+no;
- X }
- X return(0);
- X break;
- X }
- X case EndOfProgram:
- X return(1);
- X break;
- X default:
- X (void) fprintf(stderr,"Regular(3): %s","memory corruption");
- X return(0);
- X break;
- X }
- X scan=next_token;
- X }
- X (void) fprintf(stderr,"Regular(3): %s","corrupted pointers");
- X return(0);
- }
- X
- /*
- %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
- % %
- % %
- % %
- % N e x t T o k e n %
- % %
- SHAR_EOF
- true || echo 'restore of ImageMagick/xtp/regular.c failed'
- fi
- echo 'End of ImageMagick part 5'
- echo 'File ImageMagick/xtp/regular.c is continued in part 6'
- echo 6 > _shar_seq_.tmp
- exit 0
-
- exit 0 # Just in case...
- --
- // chris@Sterling.COM | Send comp.sources.x submissions to:
- \X/ Amiga - The only way to fly! | sources-x@sterling.com
- "It's intuitively obvious to the |
- most casual observer..." | GCS d+/-- p+ c++ l+ m+ s++/+ g+ w+ t+ r+ x+
-