home *** CD-ROM | disk | FTP | other *** search
/ Club Amiga de Montreal - CAM / CAM_CD_1.iso / files / 309.lha / PBM_PLUS / pbm / g3topbm.c < prev    next >
C/C++ Source or Header  |  1980-12-04  |  8KB  |  434 lines

  1. /* g3topbm.c - read a Group 3 FAX file and write a portable bitmap
  2. **
  3. ** Copyright (C) 1989 by Jef Poskanzer.
  4. **
  5. ** Permission to use, copy, modify, and distribute this software and its
  6. ** documentation for any purpose and without fee is hereby granted, provided
  7. ** that the above copyright notice appear in all copies and that both that
  8. ** copyright notice and this permission notice appear in supporting
  9. ** documentation.  This software is provided "as is" without express or
  10. ** implied warranty.
  11. */
  12.  
  13. #include <stdio.h>
  14. #include "pbm.h"
  15.  
  16. int eof;
  17.  
  18. main( argc, argv )
  19. int argc;
  20. char *argv[];
  21.     {
  22.     FILE *ifd;
  23.     /* register bit **bits, *bP; */
  24.     register bit *bitrow, *bP;
  25.     bit getbit();
  26.     int argn, rows, cols, row, col;
  27.  
  28.     pm_progname = argv[0];
  29.  
  30.     argn = 1;
  31.  
  32.     if ( argn < argc )
  33.     {
  34.     ifd = pm_openr( argv[argn] );
  35.     argn++;
  36.     }
  37.     else
  38.     ifd = stdin;
  39.  
  40.     if ( argn != argc )
  41.     pm_usage( "[g3file]" );
  42.  
  43.     getinit( ifd, &cols, &rows );
  44.  
  45.     /* bits = pbm_allocarray( cols, rows ); */
  46.     pbm_writepbminit( stdout, cols, rows );
  47.     bitrow = pbm_allocrow( cols );
  48.  
  49.     for ( row = 0; row < rows; row++ )
  50.     {
  51.     getlineinit( );
  52.         /* for ( col = 0, bP = bits[row]; col < cols; col++, bP++ ) */
  53.         for ( col = 0, bP = bitrow; col < cols; col++, bP++ )
  54.         *bP = getbit( ifd );
  55.     pbm_writepbmrow( stdout, bitrow, cols );
  56.     }
  57.  
  58.     pm_close( ifd );
  59.     
  60.     /* pbm_writepbm( stdout, bits, cols, rows ); */
  61.  
  62.     exit( 0 );
  63.     }
  64.  
  65.  
  66. bit data;
  67. int eol, eols, count, item, bitsinitem;
  68. int rawitem, rawbitsinitem, rawbitshift, rawzeros;
  69.  
  70. getinit( file, colsP, rowsP )
  71. FILE *file;
  72. int *colsP, *rowsP;
  73.     {
  74.     *colsP = 1728;
  75.     *rowsP = 2236;
  76.     eof = 0;
  77.     eols = 0;
  78.     }
  79.  
  80. getlineinit( )
  81.     {
  82.     rawbitsinitem = 8;
  83.     rawzeros = 0;
  84.     eol = 0;
  85.     data = 1;
  86.     count = 0;
  87.     }
  88.  
  89. bit
  90. getbit( file )
  91. FILE *file;
  92.     {
  93.     int i;
  94.     bit b, rawgetbit( );
  95.     struct tableentry {
  96.     int code;
  97.     int length;
  98.     int count;
  99.     };
  100.     static struct tableentry twtable[] = {
  101.     { 0x35, 8, 0 },
  102.     { 0x7, 6, 1 },
  103.     { 0x7, 4, 2 },
  104.     { 0x8, 4, 3 },
  105.     { 0xb, 4, 4 },
  106.     { 0xc, 4, 5 },
  107.     { 0xe, 4, 6 },
  108.     { 0xf, 4, 7 },
  109.     { 0x13, 5, 8 },
  110.     { 0x14, 5, 9 },
  111.     { 0x7, 5, 10 },
  112.     { 0x8, 5, 11 },
  113.     { 0x8, 6, 12 },
  114.     { 0x3, 6, 13 },
  115.     { 0x34, 6, 14 },
  116.     { 0x35, 6, 15 },
  117.     { 0x2a, 6, 16 },
  118.     { 0x2b, 6, 17 },
  119.     { 0x27, 7, 18 },
  120.     { 0xc, 7, 19 },
  121.     { 0x8, 7, 20 },
  122.     { 0x17, 7, 21 },
  123.     { 0x3, 7, 22 },
  124.     { 0x4, 7, 23 },
  125.     { 0x28, 7, 24 },
  126.     { 0x2b, 7, 25 },
  127.     { 0x13, 7, 26 },
  128.     { 0x24, 7, 27 },
  129.     { 0x18, 7, 28 },
  130.     { 0x2, 8, 29 },
  131.     { 0x3, 8, 30 },
  132.     { 0x1a, 8, 31 },
  133.     { 0x1b, 8, 32 },
  134.     { 0x12, 8, 33 },
  135.     { 0x13, 8, 34 },
  136.     { 0x14, 8, 35 },
  137.     { 0x15, 8, 36 },
  138.     { 0x16, 8, 37 },
  139.     { 0x17, 8, 38 },
  140.     { 0x28, 8, 39 },
  141.     { 0x29, 8, 40 },
  142.     { 0x2a, 8, 41 },
  143.     { 0x2b, 8, 42 },
  144.     { 0x2c, 8, 43 },
  145.     { 0x2d, 8, 44 },
  146.     { 0x4, 8, 45 },
  147.     { 0x5, 8, 46 },
  148.     { 0xa, 8, 47 },
  149.     { 0xb, 8, 48 },
  150.     { 0x52, 8, 49 },
  151.     { 0x53, 8, 50 },
  152.     { 0x54, 8, 51 },
  153.     { 0x55, 8, 52 },
  154.     { 0x24, 8, 53 },
  155.     { 0x25, 8, 54 },
  156.     { 0x58, 8, 55 },
  157.     { 0x59, 8, 56 },
  158.     { 0x5a, 8, 57 },
  159.     { 0x5b, 8, 58 },
  160.     { 0x4a, 8, 59 },
  161.     { 0x4b, 8, 60 },
  162.     { 0x32, 8, 61 },
  163.     { 0x33, 8, 62 },
  164.     { 0x34, 8, 63 },
  165.     };
  166.     static struct tableentry mwtable[] = {
  167.     { 0x1b, 5, 64 },
  168.     { 0x12, 5, 128 },
  169.     { 0x17, 6, 192 },
  170.     { 0x37, 7, 256 },
  171.     { 0x36, 8, 320 },
  172.     { 0x37, 8, 384 },
  173.     { 0x64, 8, 448 },
  174.     { 0x65, 8, 512 },
  175.     { 0x68, 8, 576 },
  176.     { 0x67, 8, 640 },
  177.     { 0xcc, 9, 704 },
  178.     { 0xcd, 9, 768 },
  179.     { 0xd2, 9, 832 },
  180.     { 0xd3, 9, 896 },
  181.     { 0xd4, 9, 960 },
  182.     { 0xd5, 9, 1024 },
  183.     { 0xd6, 9, 1088 },
  184.     { 0xd7, 9, 1152 },
  185.     { 0xd8, 9, 1216 },
  186.     { 0xd9, 9, 1280 },
  187.     { 0xda, 9, 1344 },
  188.     { 0xdb, 9, 1408 },
  189.     { 0x98, 9, 1472 },
  190.     { 0x99, 9, 1536 },
  191.     { 0x9a, 9, 1600 },
  192.     { 0x18, 6, 1664 },
  193.     { 0x9b, 9, 1728 },
  194.     };
  195.     static struct tableentry tbtable[] = {
  196.     { 0x37, 10, 0 },
  197.     { 0x2, 3, 1 },
  198.     { 0x3, 2, 2 },
  199.     { 0x2, 2, 3 },
  200.     { 0x3, 3, 4 },
  201.     { 0x3, 4, 5 },
  202.     { 0x2, 4, 6 },
  203.     { 0x3, 5, 7 },
  204.     { 0x5, 6, 8 },
  205.     { 0x4, 6, 9 },
  206.     { 0x4, 7, 10 },
  207.     { 0x5, 7, 11 },
  208.     { 0x7, 7, 12 },
  209.     { 0x4, 8, 13 },
  210.     { 0x7, 8, 14 },
  211.     { 0x18, 9, 15 },
  212.     { 0x17, 10, 16 },
  213.     { 0x18, 10, 17 },
  214.     { 0x8, 10, 18 },
  215.     { 0x67, 11, 19 },
  216.     { 0x68, 11, 20 },
  217.     { 0x6c, 11, 21 },
  218.     { 0x37, 11, 22 },
  219.     { 0x28, 11, 23 },
  220.     { 0x17, 11, 24 },
  221.     { 0x18, 11, 25 },
  222.     { 0xca, 12, 26 },
  223.     { 0xcb, 12, 27 },
  224.     { 0xcc, 12, 28 },
  225.     { 0xcd, 12, 29 },
  226.     { 0x68, 12, 30 },
  227.     { 0x69, 12, 31 },
  228.     { 0x6a, 12, 32 },
  229.     { 0x6b, 12, 33 },
  230.     { 0xd2, 12, 34 },
  231.     { 0xd3, 12, 35 },
  232.     { 0xd4, 12, 36 },
  233.     { 0xd5, 12, 37 },
  234.     { 0xd6, 12, 38 },
  235.     { 0xd7, 12, 39 },
  236.     { 0x6c, 12, 40 },
  237.     { 0x6d, 12, 41 },
  238.     { 0xda, 12, 42 },
  239.     { 0xdb, 12, 43 },
  240.     { 0x54, 12, 44 },
  241.     { 0x55, 12, 45 },
  242.     { 0x56, 12, 46 },
  243.     { 0x57, 12, 47 },
  244.     { 0x64, 12, 48 },
  245.     { 0x65, 12, 49 },
  246.     { 0x52, 12, 50 },
  247.     { 0x53, 12, 51 },
  248.     { 0x24, 12, 52 },
  249.     { 0x37, 12, 53 },
  250.     { 0x38, 12, 54 },
  251.     { 0x27, 12, 55 },
  252.     { 0x28, 12, 56 },
  253.     { 0x58, 12, 57 },
  254.     { 0x59, 12, 58 },
  255.     { 0x2b, 12, 59 },
  256.     { 0x2c, 12, 60 },
  257.     { 0x5a, 12, 61 },
  258.     { 0x66, 12, 62 },
  259.     { 0x67, 12, 63 },
  260.     };
  261.     static struct tableentry mbtable[] = {
  262.     { 0xf, 10, 64 },
  263.     { 0xc8, 12, 128 },
  264.     { 0xc9, 12, 192 },
  265.     { 0x5b, 12, 256 },
  266.     { 0x33, 12, 320 },
  267.     { 0x34, 12, 384 },
  268.     { 0x35, 12, 448 },
  269.     { 0x6c, 13, 512 },
  270.     { 0x6d, 13, 576 },
  271.     { 0x4a, 13, 640 },
  272.     { 0x4b, 13, 704 },
  273.     { 0x4c, 13, 768 },
  274.     { 0x4d, 13, 832 },
  275.     { 0x72, 13, 896 },
  276.     { 0x73, 13, 960 },
  277.     { 0x74, 13, 1024 },
  278.     { 0x75, 13, 1088 },
  279.     { 0x76, 13, 1152 },
  280.     { 0x77, 13, 1216 },
  281.     { 0x52, 13, 1280 },
  282.     { 0x53, 13, 1344 },
  283.     { 0x54, 13, 1408 },
  284.     { 0x55, 13, 1472 },
  285.     { 0x5a, 13, 1536 },
  286.     { 0x5b, 13, 1600 },
  287.     { 0x64, 13, 1664 },
  288.     { 0x65, 13, 1728 },
  289.     };
  290.     static struct tableentry embtable[] = {
  291.     { 0x8, 11, 1792 },
  292.     { 0xc, 11, 1856 },
  293.     { 0xd, 11, 1920 },
  294.     { 0x12, 12, 1984 },
  295.     { 0x13, 12, 2048 },
  296.     { 0x14, 12, 2112 },
  297.     { 0x15, 12, 2176 },
  298.     { 0x16, 12, 2240 },
  299.     { 0x17, 12, 2304 },
  300.     { 0x1c, 12, 2368 },
  301.     { 0x1d, 12, 2432 },
  302.     { 0x1e, 12, 2496 },
  303.     { 0x1f, 12, 2560 },
  304.     };
  305.  
  306.     while ( count == 0 && ! eol && ! eof )
  307.     {
  308.     data = 1 - data;
  309. makeup:
  310.     item = 0;
  311.     for ( bitsinitem = 1; bitsinitem <= ( data ? 13 : 9 ); bitsinitem++ )
  312.         {
  313.         /* Get bit and check for EOL. */
  314.         if ( rawzeros >= 11 && ( b = rawgetbit( file ) ) )
  315.         {
  316.         eol = 1;
  317.         eols++;
  318.         if ( eols >= 6 )
  319.             eof = 1;
  320.         goto continuewhile;
  321.         }
  322.         else
  323.         b = rawgetbit( file );
  324.         item = item * 2 + rawgetbit( file );
  325.         /* Check tables. */
  326.         if ( data )
  327.         { /* Black. */
  328.         for ( i = 0;
  329.               i < sizeof( tbtable ) / sizeof( struct tableentry );
  330.               i++ )
  331.             if ( bitsinitem == tbtable[i].length &&
  332.              item == tbtable[i].code )
  333.             {
  334.             count += tbtable[i].count;
  335.             eols = 0;
  336.             goto continuewhile;
  337.             }
  338.         for ( i = 0;
  339.               i < sizeof( mbtable ) / sizeof( struct tableentry );
  340.               i++ )
  341.             if ( bitsinitem == mbtable[i].length &&
  342.              item == mbtable[i].code )
  343.             {
  344.             count += mbtable[i].count;
  345.             eols = 0;
  346.             goto makeup;
  347.             }
  348.         for ( i = 0;
  349.               i < sizeof( embtable ) / sizeof( struct tableentry );
  350.               i++ )
  351.             if ( bitsinitem == embtable[i].length &&
  352.              item == embtable[i].code )
  353.             {
  354.             count += embtable[i].count;
  355.             eols = 0;
  356.             goto makeup;
  357.             }
  358.         }
  359.         else
  360.         { /* White. */
  361.         for ( i = 0;
  362.               i < sizeof( twtable ) / sizeof( struct tableentry );
  363.               i++ )
  364.             if ( bitsinitem == twtable[i].length &&
  365.              item == twtable[i].code )
  366.             {
  367.             count += twtable[i].count;
  368.             eols = 0;
  369.             goto continuewhile;
  370.             }
  371.         for ( i = 0;
  372.               i < sizeof( mwtable ) / sizeof( struct tableentry );
  373.               i++ )
  374.             if ( bitsinitem == mwtable[i].length &&
  375.              item == mwtable[i].code )
  376.             {
  377.             count += mwtable[i].count;
  378.             eols = 0;
  379.             goto makeup;
  380.             }
  381.         }
  382.         }
  383.     /* Unrecognized code.  Skip to EOL. */
  384.     fprintf( stderr, "g3topbm: unrecognized code - skipping to EOL\n" );
  385.     while ( rawzeros < 11 )
  386.         b = rawgetbit( file );
  387.     do
  388.         {
  389.         b = rawgetbit( file );
  390.         }
  391.     while ( ! b );
  392.     eol = 1;
  393.     eols++;
  394.     if ( eols >= 6 )
  395.         eof = 1;
  396.  
  397. continuewhile:
  398.     ;
  399.     }
  400.  
  401.     /* And return result. */
  402.     if ( eol || eof )
  403.     return 0;
  404.     else
  405.     {
  406.     count--;
  407.     return data;
  408.     }
  409.     }
  410.  
  411. bit
  412. rawgetbit( file )
  413. FILE *file;
  414.     {
  415.     bit b;
  416.  
  417.     if ( rawbitsinitem == 8 )
  418.     {
  419.     rawitem = getc( file );
  420.     if ( rawitem == EOF )
  421.         pm_error( "premature EOF", 0,0,0,0,0 );
  422.     rawbitsinitem = 0;
  423.     rawbitshift = 7;
  424.     }
  425.     rawbitsinitem++;
  426.     b = ( ( rawitem >> rawbitshift) & 1 ) ? PBM_BLACK : PBM_WHITE;
  427.     rawbitshift--;
  428.     if ( b )
  429.     rawzeros = 0;
  430.     else
  431.     rawzeros++;
  432.     return b;
  433.     }
  434.