--- ppm/ppmtobmp.c.orig	Mon Oct  4 18:12:36 1993
+++ ppm/ppmtobmp.c	Sat Oct 16 02:53:18 1999
@@ -75,7 +75,7 @@
     unsigned short cBitCount, pixel **pixels, colorhash_table cht));
 static int colorstobpp ARGS((int colors));
 static void BMPEncode ARGS((FILE *fp, int class, int x, int y, pixel **pixels,
-    int colors, colorhash_table cht, pixval *R, pixval *G, pixval *B));
+    int bpp, int colors, colorhash_table cht, pixval *R, pixval *G, pixval *B));
 static void
 PutByte(fp, v)
         FILE           *fp;
@@ -253,19 +253,23 @@
         int             i;
         long            ncolors;
 
-        for (i = 0; i < colors; i++)
-        {
-                nbyte += BMPwritergb(fp,class,R[i],G[i],B[i]);
-        }
-
-        ncolors = (1 << bpp);
+	if (bpp != 24)
+	{
 
-        for (; i < ncolors; i++)
-        {
-                nbyte += BMPwritergb(fp,class,0,0,0);
-        }
+		for (i = 0; i < colors; i++)
+		{
+			nbyte += BMPwritergb(fp,class,R[i],G[i],B[i]);
+		}
+
+		ncolors = (1 << bpp);
+
+		for (; i < ncolors; i++)
+		{
+			nbyte += BMPwritergb(fp,class,0,0,0);
+		}
+	}
 
-        return nbyte;
+	return nbyte;
 }
 
 /*
@@ -284,26 +288,38 @@
         int             rc;
         unsigned        x;
 
-        if ((b = pm_bitinit(fp, "w")) == (BITSTREAM) 0)
-        {
-                return -1;
-        }
-
-        for (x = 0; x < cx; x++, row++)
-        {
-                if ((rc = pm_bitwrite(b, bpp, ppm_lookupcolor(cht, row))) == -1)
-                {
-                        return -1;
-                }
-                nbyte += rc;
-        }
-
-        if ((rc = pm_bitfini(b)) == -1)
-        {
-                return -1;
-        }
-        nbyte += rc;
-
+	if (bpp != 24)
+	{
+		if ((b = pm_bitinit(fp, "w")) == (BITSTREAM) 0)
+		{
+			return -1;
+		}
+
+		for (x = 0; x < cx; x++, row++)
+		{
+			if ((rc = pm_bitwrite(b, bpp, ppm_lookupcolor(cht, row))) == -1)
+			{
+				return -1;
+			}
+			nbyte += rc;
+		}
+
+		if ((rc = pm_bitfini(b)) == -1)
+		{
+			return -1;
+		}
+		nbyte += rc;
+	}
+	else
+	{
+		for (x = 0; x < cx; x++, row++)
+		{
+			PutByte(fp, PPM_GETB(*row));
+			PutByte(fp, PPM_GETG(*row));
+			PutByte(fp, PPM_GETR(*row));
+			nbyte += 3;
+		}
+	}
         /*
          * Make sure we write a multiple of 4 bytes.
          */
@@ -394,48 +410,21 @@
  * arrays are undefined.
  */
 static void
-BMPEncode(fp, class, x, y, pixels, colors, cht, R, G, B)
+BMPEncode(fp, class, x, y, pixels, bpp, colors, cht, R, G, B)
         FILE           *fp;
         int             class;
         int             x;
         int             y;
         pixel         **pixels;
+	int		bpp;	/* bits per pixel */
         int             colors; /* number of valid entries in R,G,B */
         colorhash_table cht;
         pixval         *R;
         pixval         *G;
         pixval         *B;
 {
-        int             bpp;    /* bits per pixel */
         unsigned long   nbyte = 0;
 
-        bpp = colorstobpp(colors);
-
-        /*
-         * I have found empirically at least one BMP-displaying program
-         * that can't deal with (for instance) using 3 bits per pixel.
-         * I have seen no programs that can deal with using 3 bits per
-         * pixel.  I have seen programs which can deal with 1, 4, and
-         * 8 bits per pixel.
-         *
-         * Based on this, I adjust actual the number of bits per pixel
-         * as follows.  If anyone knows better, PLEASE tell me!
-         */
-        switch(bpp)
-        {
-        case 2:
-        case 3:
-                bpp = 4;
-                break;
-        case 5:
-        case 6:
-        case 7:
-                bpp = 8;
-                break;
-        }
-
-        pm_message("Using %d bits per pixel", bpp);
-
         nbyte += BMPwritefileheader(fp, class, bpp, x, y);
         nbyte += BMPwriteinfoheader(fp, class, bpp, x, y);
         nbyte += BMPwritergbtable(fp, class, bpp, colors, R, G, B);
@@ -517,13 +506,15 @@
         char          **argv;
 {
         FILE           *ifp = stdin;
-        char           *usage = "[-windows] [-os2] [ppmfile]";
+        char           *usage = "[-windows] [-os2] [-1/4/8/24bits] [ppmfile]";
         int             class = C_OS2;
 
         int             argn;
         int             rows;
         int             cols;
         int             colors;
+	int		maxcolors = MAXCOLORS;
+        int		bpp = 0;
         int             i;
         pixval          maxval;
         colorhist_vector chv;
@@ -545,6 +536,14 @@
                         class = C_WIN;
                 else if (pm_keymatch(argv[argn], "-os2", 2))
                         class = C_OS2;
+                else if (pm_keymatch(argv[argn], "-24bits", 3))
+                        bpp = 24, maxcolors = 256;
+                else if (pm_keymatch(argv[argn], "-8bits", 2))
+                        bpp = 8, maxcolors = 256;
+                else if (pm_keymatch(argv[argn], "-4bits", 2))
+                        bpp = 4, maxcolors = 16;
+                else if (pm_keymatch(argv[argn], "-1bit", 2))
+                        bpp = 1, maxcolors = 2;
                 else
                         pm_usage(usage);
                 ++argn;
@@ -585,44 +584,90 @@
 #endif
 
         /* Figure out the colormap. */
-        pm_message("computing colormap...");
-        chv = ppm_computecolorhist(pixels, cols, rows, MAXCOLORS, &colors);
+	chv = (colorhist_vector) 0;
+        if(bpp != 24)
+	{
+		pm_message("computing colormap...");
+		chv = ppm_computecolorhist(pixels, cols, rows, maxcolors, &colors);
+	}
         if (chv == (colorhist_vector) 0)
-                pm_error("too many colors - try doing a 'ppmquant %d'"
-                        , MAXCOLORS);
-        pm_message("%d colors found", colors);
-
-        /*
-         * Now turn the ppm colormap into the appropriate GIF
-         * colormap.
-         */
-        if (maxval > 255)
-        {
-                pm_message("maxval is not 255 - automatically rescaling colors");
-        }
-        for (i = 0; i < colors; ++i)
-        {
-                if (maxval == 255)
-                {
-                        Red[i] = PPM_GETR(chv[i].color);
-                        Green[i] = PPM_GETG(chv[i].color);
-                        Blue[i] = PPM_GETB(chv[i].color);
-                }
-                else
-                {
-                        Red[i] = (pixval) PPM_GETR(chv[i].color) * 255 / maxval;
-                        Green[i] = (pixval) PPM_GETG(chv[i].color) * 255 / maxval;
-                        Blue[i] = (pixval) PPM_GETB(chv[i].color) * 255 / maxval;
-                }
-        }
+	{
+		if (bpp == 0)
+		{
+			pm_message("over 256 colors found");
+			bpp = 24;
+		}
+		else if (bpp != 24)
+			pm_error("too many colors - try doing a 'ppmquant %d'"
+				, maxcolors);
+	}
+	else
+	{
+		pm_message("%d colors found", colors);
+
+		/*
+		 * I have found empirically at least one BMP-displaying program
+		 * that can't deal with (for instance) using 3 bits per pixel.
+		 * I have seen no programs that can deal with using 3 bits per
+		 * pixel.  I have seen programs which can deal with 1, 4, and
+		 * 8 bits per pixel.
+		 *
+		 * Based on this, I adjust actual the number of bits per pixel
+		 * as follows.  If anyone knows better, PLEASE tell me!
+		 */
+
+		if (!bpp)
+		{
+			bpp = colorstobpp(colors);
+
+			switch(bpp)
+			{
+			case 2:
+			case 3:
+				bpp = 4;
+				break;
+			case 5:
+			case 6:
+			case 7:
+				bpp = 8;
+				break;
+			}
+		}
+
+		/*
+		 * Now turn the ppm colormap into the appropriate GIF
+		 * colormap.
+		 */
+		if (maxval > 255)
+		{
+			pm_message("maxval is not 255 - automatically rescaling colors");
+		}
+		for (i = 0; i < colors; ++i)
+		{
+			if (maxval == 255)
+			{
+				Red[i] = PPM_GETR(chv[i].color);
+				Green[i] = PPM_GETG(chv[i].color);
+				Blue[i] = PPM_GETB(chv[i].color);
+			}
+			else
+			{
+				Red[i] = (pixval) PPM_GETR(chv[i].color) * 255 / maxval;
+				Green[i] = (pixval) PPM_GETG(chv[i].color) * 255 / maxval;
+				Blue[i] = (pixval) PPM_GETB(chv[i].color) * 255 / maxval;
+			}
+		}
+
+		/* And make a hash table for fast lookup. */
+		cht = ppm_colorhisttocolorhash(chv, colors);
+		ppm_freecolorhist(chv);
+	}
 
-        /* And make a hash table for fast lookup. */
-        cht = ppm_colorhisttocolorhash(chv, colors);
-        ppm_freecolorhist(chv);
+	pm_message("Using %d bits per pixel", bpp);
 
         /* All set, let's do it. */
         BMPEncode(stdout, class
-                , cols, rows, pixels, colors, cht
+                , cols, rows, pixels, bpp, colors, cht
                 ,Red, Green, Blue);
 
         pm_close(stdout);
