home *** CD-ROM | disk | FTP | other *** search
/ Source Code 1994 March / Source_Code_CD-ROM_Walnut_Creek_March_1994.iso / compsrcs / misc / volume34 / jpeg / part11 < prev    next >
Encoding:
Text File  |  1992-12-16  |  58.0 KB  |  1,869 lines

  1. Newsgroups: comp.sources.misc
  2. From: jpeg-info@uunet.uu.net (Independent JPEG Group)
  3. Subject:  v34i065:  jpeg - JPEG image compression, Part11/18
  4. Message-ID: <1992Dec17.164717.6009@sparky.imd.sterling.com>
  5. X-Md4-Signature: 50408c53090c67035085854eaabb06f3
  6. Date: Thu, 17 Dec 1992 16:47:17 GMT
  7. Approved: kent@sparky.imd.sterling.com
  8.  
  9. Submitted-by: jpeg-info@uunet.uu.net (Independent JPEG Group)
  10. Posting-number: Volume 34, Issue 65
  11. Archive-name: jpeg/part11
  12. Environment: UNIX, VMS, MS-DOS, Mac, Amiga, Atari, Cray
  13. Supersedes: jpeg: Volume 29, Issue 1-18
  14.  
  15. #! /bin/sh
  16. # This is a shell archive.  Remove anything before this line, then feed it
  17. # into a shell via "sh file" or similar.  To overwrite existing files,
  18. # type "sh file -c".
  19. # Contents:  jcmain.c jdmain.c jrdgif.c
  20. # Wrapped by kent@sparky on Wed Dec 16 20:52:29 1992
  21. PATH=/bin:/usr/bin:/usr/ucb:/usr/local/bin:/usr/lbin ; export PATH
  22. echo If this archive is complete, you will see the following message:
  23. echo '          "shar: End of archive 11 (of 18)."'
  24. if test -f 'jcmain.c' -a "${1}" != "-c" ; then 
  25.   echo shar: Will not clobber existing file \"'jcmain.c'\"
  26. else
  27.   echo shar: Extracting \"'jcmain.c'\" \(20781 characters\)
  28.   sed "s/^X//" >'jcmain.c' <<'END_OF_FILE'
  29. X/*
  30. X * jcmain.c
  31. X *
  32. X * Copyright (C) 1991, 1992, Thomas G. Lane.
  33. X * This file is part of the Independent JPEG Group's software.
  34. X * For conditions of distribution and use, see the accompanying README file.
  35. X *
  36. X * This file contains a command-line user interface for the JPEG compressor.
  37. X * It should work on any system with Unix- or MS-DOS-style command lines.
  38. X *
  39. X * Two different command line styles are permitted, depending on the
  40. X * compile-time switch TWO_FILE_COMMANDLINE:
  41. X *    cjpeg [options]  inputfile outputfile
  42. X *    cjpeg [options]  [inputfile]
  43. X * In the second style, output is always to standard output, which you'd
  44. X * normally redirect to a file or pipe to some other program.  Input is
  45. X * either from a named file or from standard input (typically redirected).
  46. X * The second style is convenient on Unix but is unhelpful on systems that
  47. X * don't support pipes.  Also, you MUST use the first style if your system
  48. X * doesn't do binary I/O to stdin/stdout.
  49. X */
  50. X
  51. X#include "jinclude.h"
  52. X#ifdef INCLUDES_ARE_ANSI
  53. X#include <stdlib.h>        /* to declare exit() */
  54. X#endif
  55. X#include <ctype.h>        /* to declare isupper(), tolower() */
  56. X#ifdef NEED_SIGNAL_CATCHER
  57. X#include <signal.h>        /* to declare signal() */
  58. X#endif
  59. X#ifdef USE_SETMODE
  60. X#include <fcntl.h>        /* to declare setmode() */
  61. X#endif
  62. X
  63. X#ifdef THINK_C
  64. X#include <console.h>        /* command-line reader for Macintosh */
  65. X#endif
  66. X
  67. X#ifdef DONT_USE_B_MODE        /* define mode parameters for fopen() */
  68. X#define READ_BINARY    "r"
  69. X#define WRITE_BINARY    "w"
  70. X#else
  71. X#define READ_BINARY    "rb"
  72. X#define WRITE_BINARY    "wb"
  73. X#endif
  74. X
  75. X#ifndef EXIT_FAILURE        /* define exit() codes if not provided */
  76. X#define EXIT_FAILURE  1
  77. X#endif
  78. X#ifndef EXIT_SUCCESS
  79. X#ifdef VMS
  80. X#define EXIT_SUCCESS  1        /* VMS is very nonstandard */
  81. X#else
  82. X#define EXIT_SUCCESS  0
  83. X#endif
  84. X#endif
  85. X
  86. X
  87. X#include "jversion.h"        /* for version message */
  88. X
  89. X
  90. X/*
  91. X * This routine determines what format the input file is,
  92. X * and selects the appropriate input-reading module.
  93. X *
  94. X * To determine which family of input formats the file belongs to,
  95. X * we may look only at the first byte of the file, since C does not
  96. X * guarantee that more than one character can be pushed back with ungetc.
  97. X * Looking at additional bytes would require one of these approaches:
  98. X *     1) assume we can fseek() the input file (fails for piped input);
  99. X *     2) assume we can push back more than one character (works in
  100. X *        some C implementations, but unportable);
  101. X *     3) provide our own buffering as is done in djpeg (breaks input readers
  102. X *        that want to use stdio directly, such as the RLE library);
  103. X * or  4) don't put back the data, and modify the input_init methods to assume
  104. X *        they start reading after the start of file (also breaks RLE library).
  105. X * #1 is attractive for MS-DOS but is untenable on Unix.
  106. X *
  107. X * The most portable solution for file types that can't be identified by their
  108. X * first byte is to make the user tell us what they are.  This is also the
  109. X * only approach for "raw" file types that contain only arbitrary values.
  110. X * We presently apply this method for Targa files.  Most of the time Targa
  111. X * files start with 0x00, so we recognize that case.  Potentially, however,
  112. X * a Targa file could start with any byte value (byte 0 is the length of the
  113. X * seldom-used ID field), so we provide a switch to force Targa input mode.
  114. X */
  115. X
  116. Xstatic boolean is_targa;    /* records user -targa switch */
  117. X
  118. X
  119. XLOCAL void
  120. Xselect_file_type (compress_info_ptr cinfo)
  121. X{
  122. X  int c;
  123. X
  124. X  if (is_targa) {
  125. X#ifdef TARGA_SUPPORTED
  126. X    jselrtarga(cinfo);
  127. X#else
  128. X    ERREXIT(cinfo->emethods, "Targa support was not compiled");
  129. X#endif
  130. X    return;
  131. X  }
  132. X
  133. X  if ((c = getc(cinfo->input_file)) == EOF)
  134. X    ERREXIT(cinfo->emethods, "Empty input file");
  135. X
  136. X  switch (c) {
  137. X#ifdef GIF_SUPPORTED
  138. X  case 'G':
  139. X    jselrgif(cinfo);
  140. X    break;
  141. X#endif
  142. X#ifdef PPM_SUPPORTED
  143. X  case 'P':
  144. X    jselrppm(cinfo);
  145. X    break;
  146. X#endif
  147. X#ifdef RLE_SUPPORTED
  148. X  case 'R':
  149. X    jselrrle(cinfo);
  150. X    break;
  151. X#endif
  152. X#ifdef TARGA_SUPPORTED
  153. X  case 0x00:
  154. X    jselrtarga(cinfo);
  155. X    break;
  156. X#endif
  157. X  default:
  158. X#ifdef TARGA_SUPPORTED
  159. X    ERREXIT(cinfo->emethods, "Unrecognized input file format --- perhaps you need -targa");
  160. X#else
  161. X    ERREXIT(cinfo->emethods, "Unrecognized input file format");
  162. X#endif
  163. X    break;
  164. X  }
  165. X
  166. X  if (ungetc(c, cinfo->input_file) == EOF)
  167. X    ERREXIT(cinfo->emethods, "ungetc failed");
  168. X}
  169. X
  170. X
  171. X/*
  172. X * This routine gets control after the input file header has been read.
  173. X * It must determine what output JPEG file format is to be written,
  174. X * and make any other compression parameter changes that are desirable.
  175. X */
  176. X
  177. XMETHODDEF void
  178. Xc_ui_method_selection (compress_info_ptr cinfo)
  179. X{
  180. X  /* If the input is gray scale, generate a monochrome JPEG file. */
  181. X  if (cinfo->in_color_space == CS_GRAYSCALE)
  182. X    j_monochrome_default(cinfo);
  183. X  /* For now, always select JFIF output format. */
  184. X#ifdef JFIF_SUPPORTED
  185. X  jselwjfif(cinfo);
  186. X#else
  187. X  You shoulda defined JFIF_SUPPORTED.   /* deliberate syntax error */
  188. X#endif
  189. X}
  190. X
  191. X
  192. X/*
  193. X * Signal catcher to ensure that temporary files are removed before aborting.
  194. X * NB: for Amiga Manx C this is actually a global routine named _abort();
  195. X * see -Dsignal_catcher=_abort in CFLAGS.  Talk about bogus...
  196. X */
  197. X
  198. X#ifdef NEED_SIGNAL_CATCHER
  199. X
  200. Xstatic external_methods_ptr emethods; /* for access to free_all */
  201. X
  202. XGLOBAL void
  203. Xsignal_catcher (int signum)
  204. X{
  205. X  if (emethods != NULL) {
  206. X    emethods->trace_level = 0;    /* turn off trace output */
  207. X    (*emethods->free_all) ();    /* clean up memory allocation & temp files */
  208. X  }
  209. X  exit(EXIT_FAILURE);
  210. X}
  211. X
  212. X#endif
  213. X
  214. X
  215. X/*
  216. X * Optional routine to display a percent-done figure on stderr.
  217. X * See jcdeflts.c for explanation of the information used.
  218. X */
  219. X
  220. X#ifdef PROGRESS_REPORT
  221. X
  222. XMETHODDEF void
  223. Xprogress_monitor (compress_info_ptr cinfo, long loopcounter, long looplimit)
  224. X{
  225. X  if (cinfo->total_passes > 1) {
  226. X    fprintf(stderr, "\rPass %d/%d: %3d%% ",
  227. X        cinfo->completed_passes+1, cinfo->total_passes,
  228. X        (int) (loopcounter*100L/looplimit));
  229. X  } else {
  230. X    fprintf(stderr, "\r %3d%% ",
  231. X        (int) (loopcounter*100L/looplimit));
  232. X  }
  233. X  fflush(stderr);
  234. X}
  235. X
  236. X#endif
  237. X
  238. X
  239. X/*
  240. X * Argument-parsing code.
  241. X * The switch parser is designed to be useful with DOS-style command line
  242. X * syntax, ie, intermixed switches and file names, where only the switches
  243. X * to the left of a given file name affect processing of that file.
  244. X * The main program in this file doesn't actually use this capability...
  245. X */
  246. X
  247. X
  248. Xstatic char * progname;        /* program name for error messages */
  249. X
  250. X
  251. XLOCAL void
  252. Xusage (void)
  253. X/* complain about bad command line */
  254. X{
  255. X  fprintf(stderr, "usage: %s [switches] ", progname);
  256. X#ifdef TWO_FILE_COMMANDLINE
  257. X  fprintf(stderr, "inputfile outputfile\n");
  258. X#else
  259. X  fprintf(stderr, "[inputfile]\n");
  260. X#endif
  261. X
  262. X  fprintf(stderr, "Switches (names may be abbreviated):\n");
  263. X  fprintf(stderr, "  -quality N     Compression quality (0..100; 5-95 is useful range)\n");
  264. X  fprintf(stderr, "  -grayscale     Create monochrome JPEG file\n");
  265. X#ifdef ENTROPY_OPT_SUPPORTED
  266. X  fprintf(stderr, "  -optimize      Optimize Huffman table (smaller file, but slow compression)\n");
  267. X#endif
  268. X#ifdef TARGA_SUPPORTED
  269. X  fprintf(stderr, "  -targa         Input file is Targa format (usually not needed)\n");
  270. X#endif
  271. X  fprintf(stderr, "Switches for advanced users:\n");
  272. X  fprintf(stderr, "  -restart N     Set restart interval in rows, or in blocks with B\n");
  273. X#ifdef INPUT_SMOOTHING_SUPPORTED
  274. X  fprintf(stderr, "  -smooth N      Smooth dithered input (N=1..100 is strength)\n");
  275. X#endif
  276. X  fprintf(stderr, "  -maxmemory N   Maximum memory to use (in kbytes)\n");
  277. X  fprintf(stderr, "  -verbose  or  -debug   Emit debug output\n");
  278. X  fprintf(stderr, "Switches for wizards:\n");
  279. X#ifdef C_ARITH_CODING_SUPPORTED
  280. X  fprintf(stderr, "  -arithmetic    Use arithmetic coding\n");
  281. X#endif
  282. X#ifdef C_MULTISCAN_FILES_SUPPORTED
  283. X  fprintf(stderr, "  -nointerleave  Create noninterleaved JPEG file\n");
  284. X#endif
  285. X  fprintf(stderr, "  -qtables file  Use quantization tables given in file\n");
  286. X  fprintf(stderr, "  -sample HxV[,...]  Set JPEG sampling factors\n");
  287. X  exit(EXIT_FAILURE);
  288. X}
  289. X
  290. X
  291. XLOCAL boolean
  292. Xkeymatch (char * arg, const char * keyword, int minchars)
  293. X/* Case-insensitive matching of (possibly abbreviated) keyword switches. */
  294. X/* keyword is the constant keyword (must be lower case already), */
  295. X/* minchars is length of minimum legal abbreviation. */
  296. X{
  297. X  register int ca, ck;
  298. X  register int nmatched = 0;
  299. X
  300. X  while ((ca = *arg++) != '\0') {
  301. X    if ((ck = *keyword++) == '\0')
  302. X      return FALSE;        /* arg longer than keyword, no good */
  303. X    if (isupper(ca))        /* force arg to lcase (assume ck is already) */
  304. X      ca = tolower(ca);
  305. X    if (ca != ck)
  306. X      return FALSE;        /* no good */
  307. X    nmatched++;            /* count matched characters */
  308. X  }
  309. X  /* reached end of argument; fail if it's too short for unique abbrev */
  310. X  if (nmatched < minchars)
  311. X    return FALSE;
  312. X  return TRUE;            /* A-OK */
  313. X}
  314. X
  315. X
  316. XLOCAL int
  317. Xqt_getc (FILE * file)
  318. X/* Read next char, skipping over any comments (# to end of line) */
  319. X/* A comment/newline sequence is returned as a newline */
  320. X{
  321. X  register int ch;
  322. X  
  323. X  ch = getc(file);
  324. X  if (ch == '#') {
  325. X    do {
  326. X      ch = getc(file);
  327. X    } while (ch != '\n' && ch != EOF);
  328. X  }
  329. X  return ch;
  330. X}
  331. X
  332. X
  333. XLOCAL long
  334. Xread_qt_integer (FILE * file)
  335. X/* Read an unsigned decimal integer from a quantization-table file */
  336. X/* Swallows one trailing character after the integer */
  337. X{
  338. X  register int ch;
  339. X  register long val;
  340. X  
  341. X  /* Skip any leading whitespace, detect EOF */
  342. X  do {
  343. X    ch = qt_getc(file);
  344. X    if (ch == EOF)
  345. X      return EOF;
  346. X  } while (isspace(ch));
  347. X  
  348. X  if (! isdigit(ch)) {
  349. X    fprintf(stderr, "%s: bogus data in quantization file\n", progname);
  350. X    exit(EXIT_FAILURE);
  351. X  }
  352. X
  353. X  val = ch - '0';
  354. X  while (ch = qt_getc(file), isdigit(ch)) {
  355. X    val *= 10;
  356. X    val += ch - '0';
  357. X  }
  358. X  return val;
  359. X}
  360. X
  361. X
  362. XLOCAL void
  363. Xread_quant_tables (compress_info_ptr cinfo, char * filename, int scale_factor)
  364. X/* Read a set of quantization tables from the specified file.
  365. X * The file is plain ASCII text: decimal numbers with whitespace between.
  366. X * Comments preceded by '#' may be included in the file.
  367. X * There may be one to NUM_QUANT_TBLS tables in the file, each of 64 values.
  368. X * The tables are implicitly numbered 0,1,etc.
  369. X */
  370. X{
  371. X  /* ZIG[i] is the zigzag-order position of the i'th element of a DCT block */
  372. X  /* read in natural order (left to right, top to bottom). */
  373. X  static const short ZIG[DCTSIZE2] = {
  374. X     0,  1,  5,  6, 14, 15, 27, 28,
  375. X     2,  4,  7, 13, 16, 26, 29, 42,
  376. X     3,  8, 12, 17, 25, 30, 41, 43,
  377. X     9, 11, 18, 24, 31, 40, 44, 53,
  378. X    10, 19, 23, 32, 39, 45, 52, 54,
  379. X    20, 22, 33, 38, 46, 51, 55, 60,
  380. X    21, 34, 37, 47, 50, 56, 59, 61,
  381. X    35, 36, 48, 49, 57, 58, 62, 63
  382. X    };
  383. X  FILE * fp;
  384. X  int tblno, i;
  385. X  long val;
  386. X  QUANT_TBL table;
  387. X
  388. X  if ((fp = fopen(filename, "r")) == NULL) {
  389. X    fprintf(stderr, "%s: can't open %s\n", progname, filename);
  390. X    exit(EXIT_FAILURE);
  391. X  }
  392. X  tblno = 0;
  393. X
  394. X  while ((val = read_qt_integer(fp)) != EOF) { /* read 1st element of table */
  395. X    if (tblno >= NUM_QUANT_TBLS) {
  396. X      fprintf(stderr, "%s: too many tables in file %s\n", progname, filename);
  397. X      exit(EXIT_FAILURE);
  398. X    }
  399. X    table[0] = (QUANT_VAL) val;
  400. X    for (i = 1; i < DCTSIZE2; i++) {
  401. X      if ((val = read_qt_integer(fp)) == EOF) {
  402. X    fprintf(stderr, "%s: incomplete table in file %s\n", progname, filename);
  403. X    exit(EXIT_FAILURE);
  404. X      }
  405. X      table[ZIG[i]] = (QUANT_VAL) val;
  406. X    }
  407. X    j_add_quant_table(cinfo, tblno, table, scale_factor, FALSE);
  408. X    tblno++;
  409. X  }
  410. X
  411. X  fclose(fp);
  412. X}
  413. X
  414. X
  415. XLOCAL void
  416. Xset_sample_factors (compress_info_ptr cinfo, char *arg)
  417. X/* Process a sample-factors parameter string, of the form */
  418. X/*     HxV[,HxV,...]    */
  419. X{
  420. X#define MAX_COMPONENTS 4    /* # of comp_info slots made by jcdeflts.c */
  421. X  int ci, val1, val2;
  422. X  char ch1, ch2;
  423. X
  424. X  for (ci = 0; ci < MAX_COMPONENTS; ci++) {
  425. X    if (*arg) {
  426. X      ch2 = ',';        /* if not set by sscanf, will be ',' */
  427. X      if (sscanf(arg, "%d%c%d%c", &val1, &ch1, &val2, &ch2) < 3)
  428. X    usage();
  429. X      if ((ch1 != 'x' && ch1 != 'X') || ch2 != ',')
  430. X    usage();        /* syntax check */
  431. X      if (val1 <= 0 || val1 > 4 || val2 <= 0 || val2 > 4) {
  432. X    fprintf(stderr, "JPEG sampling factors must be 1..4\n");
  433. X    exit(EXIT_FAILURE);
  434. X      }
  435. X      cinfo->comp_info[ci].h_samp_factor = val1;
  436. X      cinfo->comp_info[ci].v_samp_factor = val2;
  437. X      while (*arg && *arg++ != ',') /* advance to next segment of arg string */
  438. X    ;
  439. X    } else {
  440. X      /* reached end of parameter, set remaining components to 1x1 sampling */
  441. X      cinfo->comp_info[ci].h_samp_factor = 1;
  442. X      cinfo->comp_info[ci].v_samp_factor = 1;
  443. X    }
  444. X  }
  445. X}
  446. X
  447. X
  448. XLOCAL int
  449. Xparse_switches (compress_info_ptr cinfo, int last_file_arg_seen,
  450. X        int argc, char **argv)
  451. X/* Initialize cinfo with default switch settings, then parse option switches.
  452. X * Returns argv[] index of first file-name argument (== argc if none).
  453. X * Any file names with indexes <= last_file_arg_seen are ignored;
  454. X * they have presumably been processed in a previous iteration.
  455. X * (Pass 0 for last_file_arg_seen on the first or only iteration.)
  456. X */
  457. X{
  458. X  int argn;
  459. X  char * arg;
  460. X  char * qtablefile = NULL;    /* saves -qtables filename if any */
  461. X  int q_scale_factor = 100;    /* default to no scaling for -qtables */
  462. X
  463. X  /* (Re-)initialize the system-dependent error and memory managers. */
  464. X  jselerror(cinfo->emethods);    /* error/trace message routines */
  465. X  jselmemmgr(cinfo->emethods);    /* memory allocation routines */
  466. X  cinfo->methods->c_ui_method_selection = c_ui_method_selection;
  467. X
  468. X  /* Now OK to enable signal catcher. */
  469. X#ifdef NEED_SIGNAL_CATCHER
  470. X  emethods = cinfo->emethods;
  471. X#endif
  472. X
  473. X  /* Set up default JPEG parameters. */
  474. X  /* Note that default -quality level here need not, and does not,
  475. X   * match the default scaling for an explicit -qtables argument.
  476. X   */
  477. X  j_c_defaults(cinfo, 75, FALSE); /* default quality level = 75 */
  478. X  is_targa = FALSE;
  479. X
  480. X  /* Scan command line options, adjust parameters */
  481. X
  482. X  for (argn = 1; argn < argc; argn++) {
  483. X    arg = argv[argn];
  484. X    if (*arg != '-') {
  485. X      /* Not a switch, must be a file name argument */
  486. X      if (argn <= last_file_arg_seen)
  487. X    continue;        /* ignore it if previously processed */
  488. X      break;            /* else done parsing switches */
  489. X    }
  490. X    arg++;            /* advance past switch marker character */
  491. X
  492. X    if (keymatch(arg, "arithmetic", 1)) {
  493. X      /* Use arithmetic coding. */
  494. X#ifdef C_ARITH_CODING_SUPPORTED
  495. X      cinfo->arith_code = TRUE;
  496. X#else
  497. X      fprintf(stderr, "%s: sorry, arithmetic coding not supported\n",
  498. X          progname);
  499. X      exit(EXIT_FAILURE);
  500. X#endif
  501. X
  502. X    } else if (keymatch(arg, "debug", 1) || keymatch(arg, "verbose", 1)) {
  503. X      /* Enable debug printouts. */
  504. X      /* On first -d, print version identification */
  505. X      if (last_file_arg_seen == 0 && cinfo->emethods->trace_level == 0)
  506. X    fprintf(stderr, "Independent JPEG Group's CJPEG, version %s\n%s\n",
  507. X        JVERSION, JCOPYRIGHT);
  508. X      cinfo->emethods->trace_level++;
  509. X
  510. X    } else if (keymatch(arg, "grayscale", 2) || keymatch(arg, "greyscale",2)) {
  511. X      /* Force a monochrome JPEG file to be generated. */
  512. X      j_monochrome_default(cinfo);
  513. X
  514. X    } else if (keymatch(arg, "maxmemory", 1)) {
  515. X      /* Maximum memory in Kb (or Mb with 'm'). */
  516. X      long lval;
  517. X      char ch = 'x';
  518. X
  519. X      if (++argn >= argc)    /* advance to next argument */
  520. X    usage();
  521. X      if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
  522. X    usage();
  523. X      if (ch == 'm' || ch == 'M')
  524. X    lval *= 1000L;
  525. X      cinfo->emethods->max_memory_to_use = lval * 1000L;
  526. X
  527. X    } else if (keymatch(arg, "nointerleave", 3)) {
  528. X      /* Create noninterleaved file. */
  529. X#ifdef C_MULTISCAN_FILES_SUPPORTED
  530. X      cinfo->interleave = FALSE;
  531. X#else
  532. X      fprintf(stderr, "%s: sorry, multiple-scan support was not compiled\n",
  533. X          progname);
  534. X      exit(EXIT_FAILURE);
  535. X#endif
  536. X
  537. X    } else if (keymatch(arg, "optimize", 1) || keymatch(arg, "optimise", 1)) {
  538. X      /* Enable entropy parm optimization. */
  539. X#ifdef ENTROPY_OPT_SUPPORTED
  540. X      cinfo->optimize_coding = TRUE;
  541. X#else
  542. X      fprintf(stderr, "%s: sorry, entropy optimization was not compiled\n",
  543. X          progname);
  544. X      exit(EXIT_FAILURE);
  545. X#endif
  546. X
  547. X    } else if (keymatch(arg, "quality", 1)) {
  548. X      /* Quality factor (quantization table scaling factor). */
  549. X      int val;
  550. X
  551. X      if (++argn >= argc)    /* advance to next argument */
  552. X    usage();
  553. X      if (sscanf(argv[argn], "%d", &val) != 1)
  554. X    usage();
  555. X      /* Set quantization tables (will be overridden if -qtables also given).
  556. X       * Note: we make force_baseline FALSE.
  557. X       * This means non-baseline JPEG files can be created with low Q values.
  558. X       * To ensure only baseline files are generated, pass TRUE instead.
  559. X       */
  560. X      j_set_quality(cinfo, val, FALSE);
  561. X      /* Change scale factor in case -qtables is present. */
  562. X      q_scale_factor = j_quality_scaling(val);
  563. X
  564. X    } else if (keymatch(arg, "qtables", 2)) {
  565. X      /* Quantization tables fetched from file. */
  566. X      if (++argn >= argc)    /* advance to next argument */
  567. X    usage();
  568. X      qtablefile = argv[argn];
  569. X      /* we postpone actually reading the file in case -quality comes later */
  570. X
  571. X    } else if (keymatch(arg, "restart", 1)) {
  572. X      /* Restart interval in MCU rows (or in MCUs with 'b'). */
  573. X      long lval;
  574. X      char ch = 'x';
  575. X
  576. X      if (++argn >= argc)    /* advance to next argument */
  577. X    usage();
  578. X      if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
  579. X    usage();
  580. X      if (lval < 0 || lval > 65535L)
  581. X    usage();
  582. X      if (ch == 'b' || ch == 'B')
  583. X    cinfo->restart_interval = (UINT16) lval;
  584. X      else
  585. X    cinfo->restart_in_rows = (int) lval;
  586. X
  587. X    } else if (keymatch(arg, "sample", 2)) {
  588. X      /* Set sampling factors. */
  589. X      if (++argn >= argc)    /* advance to next argument */
  590. X    usage();
  591. X      set_sample_factors(cinfo, argv[argn]);
  592. X
  593. X    } else if (keymatch(arg, "smooth", 2)) {
  594. X      /* Set input smoothing factor. */
  595. X      int val;
  596. X
  597. X      if (++argn >= argc)    /* advance to next argument */
  598. X    usage();
  599. X      if (sscanf(argv[argn], "%d", &val) != 1)
  600. X    usage();
  601. X      if (val < 0 || val > 100)
  602. X    usage();
  603. X      cinfo->smoothing_factor = val;
  604. X
  605. X    } else if (keymatch(arg, "targa", 1)) {
  606. X      /* Input file is Targa format. */
  607. X      is_targa = TRUE;
  608. X
  609. X    } else {
  610. X      usage();            /* bogus switch */
  611. X    }
  612. X  }
  613. X
  614. X  /* Post-switch-scanning cleanup */
  615. X
  616. X  if (qtablefile != NULL)    /* process -qtables if it was present */
  617. X    read_quant_tables(cinfo, qtablefile, q_scale_factor);
  618. X
  619. X  return argn;            /* return index of next arg (file name) */
  620. X}
  621. X
  622. X
  623. X/*
  624. X * The main program.
  625. X */
  626. X
  627. XGLOBAL int
  628. Xmain (int argc, char **argv)
  629. X{
  630. X  struct Compress_info_struct cinfo;
  631. X  struct Compress_methods_struct c_methods;
  632. X  struct External_methods_struct e_methods;
  633. X  int file_index;
  634. X
  635. X  /* On Mac, fetch a command line. */
  636. X#ifdef THINK_C
  637. X  argc = ccommand(&argv);
  638. X#endif
  639. X
  640. X  progname = argv[0];
  641. X
  642. X  /* Set up links to method structures. */
  643. X  cinfo.methods = &c_methods;
  644. X  cinfo.emethods = &e_methods;
  645. X
  646. X  /* Install, but don't yet enable signal catcher. */
  647. X#ifdef NEED_SIGNAL_CATCHER
  648. X  emethods = NULL;
  649. X  signal(SIGINT, signal_catcher);
  650. X#ifdef SIGTERM            /* not all systems have SIGTERM */
  651. X  signal(SIGTERM, signal_catcher);
  652. X#endif
  653. X#endif
  654. X
  655. X  /* Scan command line: set up compression parameters, input & output files. */
  656. X
  657. X  file_index = parse_switches(&cinfo, 0, argc, argv);
  658. X
  659. X#ifdef TWO_FILE_COMMANDLINE
  660. X
  661. X  if (file_index != argc-2) {
  662. X    fprintf(stderr, "%s: must name one input and one output file\n", progname);
  663. X    usage();
  664. X  }
  665. X  if ((cinfo.input_file = fopen(argv[file_index], READ_BINARY)) == NULL) {
  666. X    fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index]);
  667. X    exit(EXIT_FAILURE);
  668. X  }
  669. X  if ((cinfo.output_file = fopen(argv[file_index+1], WRITE_BINARY)) == NULL) {
  670. X    fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index+1]);
  671. X    exit(EXIT_FAILURE);
  672. X  }
  673. X
  674. X#else /* not TWO_FILE_COMMANDLINE -- use Unix style */
  675. X
  676. X  cinfo.input_file = stdin;    /* default input file */
  677. X  cinfo.output_file = stdout;    /* always the output file */
  678. X
  679. X#ifdef USE_SETMODE        /* need to hack file mode? */
  680. X  setmode(fileno(stdin), O_BINARY);
  681. X  setmode(fileno(stdout), O_BINARY);
  682. X#endif
  683. X
  684. X  if (file_index < argc-1) {
  685. X    fprintf(stderr, "%s: only one input file\n", progname);
  686. X    usage();
  687. X  }
  688. X  if (file_index < argc) {
  689. X    if ((cinfo.input_file = fopen(argv[file_index], READ_BINARY)) == NULL) {
  690. X      fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index]);
  691. X      exit(EXIT_FAILURE);
  692. X    }
  693. X  }
  694. X
  695. X#endif /* TWO_FILE_COMMANDLINE */
  696. X
  697. X  /* Figure out the input file format, and set up to read it. */
  698. X  select_file_type(&cinfo);
  699. X
  700. X#ifdef PROGRESS_REPORT
  701. X  /* Start up progress display, unless trace output is on */
  702. X  if (e_methods.trace_level == 0)
  703. X    c_methods.progress_monitor = progress_monitor;
  704. X#endif
  705. X
  706. X  /* Do it to it! */
  707. X  jpeg_compress(&cinfo);
  708. X
  709. X#ifdef PROGRESS_REPORT
  710. X  /* Clear away progress display */
  711. X  if (e_methods.trace_level == 0) {
  712. X    fprintf(stderr, "\r                \r");
  713. X    fflush(stderr);
  714. X  }
  715. X#endif
  716. X
  717. X  /* All done. */
  718. X  exit(EXIT_SUCCESS);
  719. X  return 0;            /* suppress no-return-value warnings */
  720. X}
  721. END_OF_FILE
  722.   if test 20781 -ne `wc -c <'jcmain.c'`; then
  723.     echo shar: \"'jcmain.c'\" unpacked with wrong size!
  724.   fi
  725.   # end of 'jcmain.c'
  726. fi
  727. if test -f 'jdmain.c' -a "${1}" != "-c" ; then 
  728.   echo shar: Will not clobber existing file \"'jdmain.c'\"
  729. else
  730.   echo shar: Extracting \"'jdmain.c'\" \(13745 characters\)
  731.   sed "s/^X//" >'jdmain.c' <<'END_OF_FILE'
  732. X/*
  733. X * jdmain.c
  734. X *
  735. X * Copyright (C) 1991, 1992, Thomas G. Lane.
  736. X * This file is part of the Independent JPEG Group's software.
  737. X * For conditions of distribution and use, see the accompanying README file.
  738. X *
  739. X * This file contains a command-line user interface for the JPEG decompressor.
  740. X * It should work on any system with Unix- or MS-DOS-style command lines.
  741. X *
  742. X * Two different command line styles are permitted, depending on the
  743. X * compile-time switch TWO_FILE_COMMANDLINE:
  744. X *    djpeg [options]  inputfile outputfile
  745. X *    djpeg [options]  [inputfile]
  746. X * In the second style, output is always to standard output, which you'd
  747. X * normally redirect to a file or pipe to some other program.  Input is
  748. X * either from a named file or from standard input (typically redirected).
  749. X * The second style is convenient on Unix but is unhelpful on systems that
  750. X * don't support pipes.  Also, you MUST use the first style if your system
  751. X * doesn't do binary I/O to stdin/stdout.
  752. X */
  753. X
  754. X#include "jinclude.h"
  755. X#ifdef INCLUDES_ARE_ANSI
  756. X#include <stdlib.h>        /* to declare exit() */
  757. X#endif
  758. X#include <ctype.h>        /* to declare isupper(), tolower() */
  759. X#ifdef NEED_SIGNAL_CATCHER
  760. X#include <signal.h>        /* to declare signal() */
  761. X#endif
  762. X#ifdef USE_SETMODE
  763. X#include <fcntl.h>        /* to declare setmode() */
  764. X#endif
  765. X
  766. X#ifdef THINK_C
  767. X#include <console.h>        /* command-line reader for Macintosh */
  768. X#endif
  769. X
  770. X#ifdef DONT_USE_B_MODE        /* define mode parameters for fopen() */
  771. X#define READ_BINARY    "r"
  772. X#define WRITE_BINARY    "w"
  773. X#else
  774. X#define READ_BINARY    "rb"
  775. X#define WRITE_BINARY    "wb"
  776. X#endif
  777. X
  778. X#ifndef EXIT_FAILURE        /* define exit() codes if not provided */
  779. X#define EXIT_FAILURE  1
  780. X#endif
  781. X#ifndef EXIT_SUCCESS
  782. X#ifdef VMS
  783. X#define EXIT_SUCCESS  1        /* VMS is very nonstandard */
  784. X#else
  785. X#define EXIT_SUCCESS  0
  786. X#endif
  787. X#endif
  788. X
  789. X
  790. X#include "jversion.h"        /* for version message */
  791. X
  792. X
  793. X/*
  794. X * This list defines the known output image formats
  795. X * (not all of which need be supported by a given version).
  796. X * You can change the default output format by defining DEFAULT_FMT;
  797. X * indeed, you had better do so if you undefine PPM_SUPPORTED.
  798. X */
  799. X
  800. Xtypedef enum {
  801. X    FMT_GIF,        /* GIF format */
  802. X    FMT_PPM,        /* PPM/PGM (PBMPLUS formats) */
  803. X    FMT_RLE,        /* RLE format */
  804. X    FMT_TARGA,        /* Targa format */
  805. X    FMT_TIFF        /* TIFF format */
  806. X} IMAGE_FORMATS;
  807. X
  808. X#ifndef DEFAULT_FMT        /* so can override from CFLAGS in Makefile */
  809. X#define DEFAULT_FMT    FMT_PPM
  810. X#endif
  811. X
  812. Xstatic IMAGE_FORMATS requested_fmt;
  813. X
  814. X
  815. X/*
  816. X * This routine gets control after the input file header has been read.
  817. X * It must determine what output file format is to be written,
  818. X * and make any other decompression parameter changes that are desirable.
  819. X */
  820. X
  821. XMETHODDEF void
  822. Xd_ui_method_selection (decompress_info_ptr cinfo)
  823. X{
  824. X  /* if grayscale or CMYK input, force similar output; */
  825. X  /* else leave the output colorspace as set by options. */
  826. X  if (cinfo->jpeg_color_space == CS_GRAYSCALE)
  827. X    cinfo->out_color_space = CS_GRAYSCALE;
  828. X  else if (cinfo->jpeg_color_space == CS_CMYK)
  829. X    cinfo->out_color_space = CS_CMYK;
  830. X
  831. X  /* select output file format */
  832. X  /* Note: jselwxxx routine may make additional parameter changes,
  833. X   * such as forcing color quantization if it's a colormapped format.
  834. X   */
  835. X  switch (requested_fmt) {
  836. X#ifdef GIF_SUPPORTED
  837. X  case FMT_GIF:
  838. X    jselwgif(cinfo);
  839. X    break;
  840. X#endif
  841. X#ifdef PPM_SUPPORTED
  842. X  case FMT_PPM:
  843. X    jselwppm(cinfo);
  844. X    break;
  845. X#endif
  846. X#ifdef RLE_SUPPORTED
  847. X  case FMT_RLE:
  848. X    jselwrle(cinfo);
  849. X    break;
  850. X#endif
  851. X#ifdef TARGA_SUPPORTED
  852. X  case FMT_TARGA:
  853. X    jselwtarga(cinfo);
  854. X    break;
  855. X#endif
  856. X  default:
  857. X    ERREXIT(cinfo->emethods, "Unsupported output file format");
  858. X    break;
  859. X  }
  860. X}
  861. X
  862. X
  863. X/*
  864. X * Signal catcher to ensure that temporary files are removed before aborting.
  865. X * NB: for Amiga Manx C this is actually a global routine named _abort();
  866. X * see -Dsignal_catcher=_abort in CFLAGS.  Talk about bogus...
  867. X */
  868. X
  869. X#ifdef NEED_SIGNAL_CATCHER
  870. X
  871. Xstatic external_methods_ptr emethods; /* for access to free_all */
  872. X
  873. XGLOBAL void
  874. Xsignal_catcher (int signum)
  875. X{
  876. X  if (emethods != NULL) {
  877. X    emethods->trace_level = 0;    /* turn off trace output */
  878. X    (*emethods->free_all) ();    /* clean up memory allocation & temp files */
  879. X  }
  880. X  exit(EXIT_FAILURE);
  881. X}
  882. X
  883. X#endif
  884. X
  885. X
  886. X/*
  887. X * Optional routine to display a percent-done figure on stderr.
  888. X * See jddeflts.c for explanation of the information used.
  889. X */
  890. X
  891. X#ifdef PROGRESS_REPORT
  892. X
  893. XMETHODDEF void
  894. Xprogress_monitor (decompress_info_ptr cinfo, long loopcounter, long looplimit)
  895. X{
  896. X  if (cinfo->total_passes > 1) {
  897. X    fprintf(stderr, "\rPass %d/%d: %3d%% ",
  898. X        cinfo->completed_passes+1, cinfo->total_passes,
  899. X        (int) (loopcounter*100L/looplimit));
  900. X  } else {
  901. X    fprintf(stderr, "\r %3d%% ",
  902. X        (int) (loopcounter*100L/looplimit));
  903. X  }
  904. X  fflush(stderr);
  905. X}
  906. X
  907. X#endif
  908. X
  909. X
  910. X/*
  911. X * Argument-parsing code.
  912. X * The switch parser is designed to be useful with DOS-style command line
  913. X * syntax, ie, intermixed switches and file names, where only the switches
  914. X * to the left of a given file name affect processing of that file.
  915. X * The main program in this file doesn't actually use this capability...
  916. X */
  917. X
  918. X
  919. Xstatic char * progname;        /* program name for error messages */
  920. X
  921. X
  922. XLOCAL void
  923. Xusage (void)
  924. X/* complain about bad command line */
  925. X{
  926. X  fprintf(stderr, "usage: %s [switches] ", progname);
  927. X#ifdef TWO_FILE_COMMANDLINE
  928. X  fprintf(stderr, "inputfile outputfile\n");
  929. X#else
  930. X  fprintf(stderr, "[inputfile]\n");
  931. X#endif
  932. X
  933. X  fprintf(stderr, "Switches (names may be abbreviated):\n");
  934. X  fprintf(stderr, "  -colors N      Reduce image to no more than N colors\n");
  935. X#ifdef GIF_SUPPORTED
  936. X  fprintf(stderr, "  -gif           Select GIF output format\n");
  937. X#endif
  938. X#ifdef PPM_SUPPORTED
  939. X  fprintf(stderr, "  -pnm           Select PBMPLUS (PPM/PGM) output format (default)\n");
  940. X#endif
  941. X  fprintf(stderr, "  -quantize N    Same as -colors N\n");
  942. X#ifdef RLE_SUPPORTED
  943. X  fprintf(stderr, "  -rle           Select Utah RLE output format\n");
  944. X#endif
  945. X#ifdef TARGA_SUPPORTED
  946. X  fprintf(stderr, "  -targa         Select Targa output format\n");
  947. X#endif
  948. X  fprintf(stderr, "Switches for advanced users:\n");
  949. X#ifdef BLOCK_SMOOTHING_SUPPORTED
  950. X  fprintf(stderr, "  -blocksmooth   Apply cross-block smoothing\n");
  951. X#endif
  952. X  fprintf(stderr, "  -grayscale     Force grayscale output\n");
  953. X  fprintf(stderr, "  -nodither      Don't use dithering in quantization\n");
  954. X#ifdef QUANT_1PASS_SUPPORTED
  955. X  fprintf(stderr, "  -onepass       Use 1-pass quantization (fast, low quality)\n");
  956. X#endif
  957. X  fprintf(stderr, "  -maxmemory N   Maximum memory to use (in kbytes)\n");
  958. X  fprintf(stderr, "  -verbose  or  -debug   Emit debug output\n");
  959. X  exit(EXIT_FAILURE);
  960. X}
  961. X
  962. X
  963. XLOCAL boolean
  964. Xkeymatch (char * arg, const char * keyword, int minchars)
  965. X/* Case-insensitive matching of (possibly abbreviated) keyword switches. */
  966. X/* keyword is the constant keyword (must be lower case already), */
  967. X/* minchars is length of minimum legal abbreviation. */
  968. X{
  969. X  register int ca, ck;
  970. X  register int nmatched = 0;
  971. X
  972. X  while ((ca = *arg++) != '\0') {
  973. X    if ((ck = *keyword++) == '\0')
  974. X      return FALSE;        /* arg longer than keyword, no good */
  975. X    if (isupper(ca))        /* force arg to lcase (assume ck is already) */
  976. X      ca = tolower(ca);
  977. X    if (ca != ck)
  978. X      return FALSE;        /* no good */
  979. X    nmatched++;            /* count matched characters */
  980. X  }
  981. X  /* reached end of argument; fail if it's too short for unique abbrev */
  982. X  if (nmatched < minchars)
  983. X    return FALSE;
  984. X  return TRUE;            /* A-OK */
  985. X}
  986. X
  987. X
  988. XLOCAL int
  989. Xparse_switches (decompress_info_ptr cinfo, int last_file_arg_seen,
  990. X        int argc, char **argv)
  991. X/* Initialize cinfo with default switch settings, then parse option switches.
  992. X * Returns argv[] index of first file-name argument (== argc if none).
  993. X * Any file names with indexes <= last_file_arg_seen are ignored;
  994. X * they have presumably been processed in a previous iteration.
  995. X * (Pass 0 for last_file_arg_seen on the first or only iteration.)
  996. X */
  997. X{
  998. X  int argn;
  999. X  char * arg;
  1000. X
  1001. X  /* (Re-)initialize the system-dependent error and memory managers. */
  1002. X  jselerror(cinfo->emethods);    /* error/trace message routines */
  1003. X  jselmemmgr(cinfo->emethods);    /* memory allocation routines */
  1004. X  cinfo->methods->d_ui_method_selection = d_ui_method_selection;
  1005. X
  1006. X  /* Now OK to enable signal catcher. */
  1007. X#ifdef NEED_SIGNAL_CATCHER
  1008. X  emethods = cinfo->emethods;
  1009. X#endif
  1010. X
  1011. X  /* Set up default JPEG parameters. */
  1012. X  j_d_defaults(cinfo, TRUE);
  1013. X  requested_fmt = DEFAULT_FMT;    /* set default output file format */
  1014. X
  1015. X  /* Scan command line options, adjust parameters */
  1016. X
  1017. X  for (argn = 1; argn < argc; argn++) {
  1018. X    arg = argv[argn];
  1019. X    if (*arg != '-') {
  1020. X      /* Not a switch, must be a file name argument */
  1021. X      if (argn <= last_file_arg_seen)
  1022. X    continue;        /* ignore it if previously processed */
  1023. X      break;            /* else done parsing switches */
  1024. X    }
  1025. X    arg++;            /* advance past switch marker character */
  1026. X
  1027. X    if (keymatch(arg, "blocksmooth", 1)) {
  1028. X      /* Enable cross-block smoothing. */
  1029. X      cinfo->do_block_smoothing = TRUE;
  1030. X
  1031. X    } else if (keymatch(arg, "colors", 1) || keymatch(arg, "colours", 1) ||
  1032. X           keymatch(arg, "quantize", 1) || keymatch(arg, "quantise", 1)) {
  1033. X      /* Do color quantization. */
  1034. X      int val;
  1035. X
  1036. X      if (++argn >= argc)    /* advance to next argument */
  1037. X    usage();
  1038. X      if (sscanf(argv[argn], "%d", &val) != 1)
  1039. X    usage();
  1040. X      cinfo->desired_number_of_colors = val;
  1041. X      cinfo->quantize_colors = TRUE;
  1042. X
  1043. X    } else if (keymatch(arg, "debug", 1) || keymatch(arg, "verbose", 1)) {
  1044. X      /* Enable debug printouts. */
  1045. X      /* On first -d, print version identification */
  1046. X      if (last_file_arg_seen == 0 && cinfo->emethods->trace_level == 0)
  1047. X    fprintf(stderr, "Independent JPEG Group's DJPEG, version %s\n%s\n",
  1048. X        JVERSION, JCOPYRIGHT);
  1049. X      cinfo->emethods->trace_level++;
  1050. X
  1051. X    } else if (keymatch(arg, "gif", 1)) {
  1052. X      /* GIF output format. */
  1053. X      requested_fmt = FMT_GIF;
  1054. X
  1055. X    } else if (keymatch(arg, "grayscale", 2) || keymatch(arg, "greyscale",2)) {
  1056. X      /* Force monochrome output. */
  1057. X      cinfo->out_color_space = CS_GRAYSCALE;
  1058. X
  1059. X    } else if (keymatch(arg, "maxmemory", 1)) {
  1060. X      /* Maximum memory in Kb (or Mb with 'm'). */
  1061. X      long lval;
  1062. X      char ch = 'x';
  1063. X
  1064. X      if (++argn >= argc)    /* advance to next argument */
  1065. X    usage();
  1066. X      if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
  1067. X    usage();
  1068. X      if (ch == 'm' || ch == 'M')
  1069. X    lval *= 1000L;
  1070. X      cinfo->emethods->max_memory_to_use = lval * 1000L;
  1071. X
  1072. X    } else if (keymatch(arg, "nodither", 3)) {
  1073. X      /* Suppress dithering in color quantization. */
  1074. X      cinfo->use_dithering = FALSE;
  1075. X
  1076. X    } else if (keymatch(arg, "onepass", 1)) {
  1077. X      /* Use fast one-pass quantization. */
  1078. X      cinfo->two_pass_quantize = FALSE;
  1079. X
  1080. X    } else if (keymatch(arg, "pnm", 1)) {
  1081. X      /* PPM/PGM output format. */
  1082. X      requested_fmt = FMT_PPM;
  1083. X
  1084. X    } else if (keymatch(arg, "rle", 1)) {
  1085. X      /* RLE output format. */
  1086. X      requested_fmt = FMT_RLE;
  1087. X
  1088. X    } else if (keymatch(arg, "targa", 1)) {
  1089. X      /* Targa output format. */
  1090. X      requested_fmt = FMT_TARGA;
  1091. X
  1092. X    } else {
  1093. X      usage();            /* bogus switch */
  1094. X    }
  1095. X  }
  1096. X
  1097. X  return argn;            /* return index of next arg (file name) */
  1098. X}
  1099. X
  1100. X
  1101. X/*
  1102. X * The main program.
  1103. X */
  1104. X
  1105. XGLOBAL int
  1106. Xmain (int argc, char **argv)
  1107. X{
  1108. X  struct Decompress_info_struct cinfo;
  1109. X  struct Decompress_methods_struct dc_methods;
  1110. X  struct External_methods_struct e_methods;
  1111. X  int file_index;
  1112. X
  1113. X  /* On Mac, fetch a command line. */
  1114. X#ifdef THINK_C
  1115. X  argc = ccommand(&argv);
  1116. X#endif
  1117. X
  1118. X  progname = argv[0];
  1119. X
  1120. X  /* Set up links to method structures. */
  1121. X  cinfo.methods = &dc_methods;
  1122. X  cinfo.emethods = &e_methods;
  1123. X
  1124. X  /* Install, but don't yet enable signal catcher. */
  1125. X#ifdef NEED_SIGNAL_CATCHER
  1126. X  emethods = NULL;
  1127. X  signal(SIGINT, signal_catcher);
  1128. X#ifdef SIGTERM            /* not all systems have SIGTERM */
  1129. X  signal(SIGTERM, signal_catcher);
  1130. X#endif
  1131. X#endif
  1132. X
  1133. X  /* Scan command line: set up compression parameters, input & output files. */
  1134. X
  1135. X  file_index = parse_switches(&cinfo, 0, argc, argv);
  1136. X
  1137. X#ifdef TWO_FILE_COMMANDLINE
  1138. X
  1139. X  if (file_index != argc-2) {
  1140. X    fprintf(stderr, "%s: must name one input and one output file\n", progname);
  1141. X    usage();
  1142. X  }
  1143. X  if ((cinfo.input_file = fopen(argv[file_index], READ_BINARY)) == NULL) {
  1144. X    fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index]);
  1145. X    exit(EXIT_FAILURE);
  1146. X  }
  1147. X  if ((cinfo.output_file = fopen(argv[file_index+1], WRITE_BINARY)) == NULL) {
  1148. X    fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index+1]);
  1149. X    exit(EXIT_FAILURE);
  1150. X  }
  1151. X
  1152. X#else /* not TWO_FILE_COMMANDLINE -- use Unix style */
  1153. X
  1154. X  cinfo.input_file = stdin;    /* default input file */
  1155. X  cinfo.output_file = stdout;    /* always the output file */
  1156. X
  1157. X#ifdef USE_SETMODE        /* need to hack file mode? */
  1158. X  setmode(fileno(stdin), O_BINARY);
  1159. X  setmode(fileno(stdout), O_BINARY);
  1160. X#endif
  1161. X
  1162. X  if (file_index < argc-1) {
  1163. X    fprintf(stderr, "%s: only one input file\n", progname);
  1164. X    usage();
  1165. X  }
  1166. X  if (file_index < argc) {
  1167. X    if ((cinfo.input_file = fopen(argv[file_index], READ_BINARY)) == NULL) {
  1168. X      fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index]);
  1169. X      exit(EXIT_FAILURE);
  1170. X    }
  1171. X  }
  1172. X
  1173. X#endif /* TWO_FILE_COMMANDLINE */
  1174. X  
  1175. X  /* Set up to read a JFIF or baseline-JPEG file. */
  1176. X  /* A smarter UI would inspect the first few bytes of the input file */
  1177. X  /* to determine its type. */
  1178. X#ifdef JFIF_SUPPORTED
  1179. X  jselrjfif(&cinfo);
  1180. X#else
  1181. X  You shoulda defined JFIF_SUPPORTED.   /* deliberate syntax error */
  1182. X#endif
  1183. X
  1184. X#ifdef PROGRESS_REPORT
  1185. X  /* Start up progress display, unless trace output is on */
  1186. X  if (e_methods.trace_level == 0)
  1187. X    dc_methods.progress_monitor = progress_monitor;
  1188. X#endif
  1189. X
  1190. X  /* Do it to it! */
  1191. X  jpeg_decompress(&cinfo);
  1192. X
  1193. X#ifdef PROGRESS_REPORT
  1194. X  /* Clear away progress display */
  1195. X  if (e_methods.trace_level == 0) {
  1196. X    fprintf(stderr, "\r                \r");
  1197. X    fflush(stderr);
  1198. X  }
  1199. X#endif
  1200. X
  1201. X  /* All done. */
  1202. X  exit(EXIT_SUCCESS);
  1203. X  return 0;            /* suppress no-return-value warnings */
  1204. X}
  1205. END_OF_FILE
  1206.   if test 13745 -ne `wc -c <'jdmain.c'`; then
  1207.     echo shar: \"'jdmain.c'\" unpacked with wrong size!
  1208.   fi
  1209.   # end of 'jdmain.c'
  1210. fi
  1211. if test -f 'jrdgif.c' -a "${1}" != "-c" ; then 
  1212.   echo shar: Will not clobber existing file \"'jrdgif.c'\"
  1213. else
  1214.   echo shar: Extracting \"'jrdgif.c'\" \(20480 characters\)
  1215.   sed "s/^X//" >'jrdgif.c' <<'END_OF_FILE'
  1216. X/*
  1217. X * jrdgif.c
  1218. X *
  1219. X * Copyright (C) 1991, 1992, Thomas G. Lane.
  1220. X * This file is part of the Independent JPEG Group's software.
  1221. X * For conditions of distribution and use, see the accompanying README file.
  1222. X *
  1223. X * This file contains routines to read input images in GIF format.
  1224. X *
  1225. X * These routines may need modification for non-Unix environments or
  1226. X * specialized applications.  As they stand, they assume input from
  1227. X * an ordinary stdio stream.  They further assume that reading begins
  1228. X * at the start of the file; input_init may need work if the
  1229. X * user interface has already read some data (e.g., to determine that
  1230. X * the file is indeed GIF format).
  1231. X *
  1232. X * These routines are invoked via the methods get_input_row
  1233. X * and input_init/term.
  1234. X */
  1235. X
  1236. X/*
  1237. X * This code is loosely based on giftoppm from the PBMPLUS distribution
  1238. X * of Feb. 1991.  That file contains the following copyright notice:
  1239. X * +-------------------------------------------------------------------+
  1240. X * | Copyright 1990, David Koblas.                                     |
  1241. X * |   Permission to use, copy, modify, and distribute this software   |
  1242. X * |   and its documentation for any purpose and without fee is hereby |
  1243. X * |   granted, provided that the above copyright notice appear in all |
  1244. X * |   copies and that both that copyright notice and this permission  |
  1245. X * |   notice appear in supporting documentation.  This software is    |
  1246. X * |   provided "as is" without express or implied warranty.           |
  1247. X * +-------------------------------------------------------------------+
  1248. X *
  1249. X * We are also required to state that
  1250. X *    "The Graphics Interchange Format(c) is the Copyright property of
  1251. X *    CompuServe Incorporated. GIF(sm) is a Service Mark property of
  1252. X *    CompuServe Incorporated."
  1253. X */
  1254. X
  1255. X#include "jinclude.h"
  1256. X
  1257. X#ifdef GIF_SUPPORTED
  1258. X
  1259. X
  1260. X#define    MAXCOLORMAPSIZE    256    /* max # of colors in a GIF colormap */
  1261. X#define NUMCOLORS    3    /* # of colors */
  1262. X#define CM_RED        0    /* color component numbers */
  1263. X#define CM_GREEN    1
  1264. X#define CM_BLUE        2
  1265. X
  1266. Xstatic JSAMPARRAY colormap;    /* the colormap to use */
  1267. X/* colormap[i][j] = value of i'th color component for pixel value j */
  1268. X
  1269. X#define    MAX_LZW_BITS    12    /* maximum LZW code size */
  1270. X#define LZW_TABLE_SIZE    (1<<MAX_LZW_BITS) /* # of possible LZW symbols */
  1271. X
  1272. X/* Macros for extracting header data --- note we assume chars may be signed */
  1273. X
  1274. X#define LM_to_uint(a,b)        ((((b)&0xFF) << 8) | ((a)&0xFF))
  1275. X
  1276. X#define BitSet(byte, bit)    ((byte) & (bit))
  1277. X#define INTERLACE    0x40    /* mask for bit signifying interlaced image */
  1278. X#define COLORMAPFLAG    0x80    /* mask for bit signifying colormap presence */
  1279. X
  1280. X#define    ReadOK(file,buffer,len)    (JFREAD(file,buffer,len) == ((size_t) (len)))
  1281. X
  1282. X/* Static vars for GetCode and LZWReadByte */
  1283. X
  1284. Xstatic char code_buf[256+4];    /* current input data block */
  1285. Xstatic int last_byte;        /* # of bytes in code_buf */
  1286. Xstatic int last_bit;        /* # of bits in code_buf */
  1287. Xstatic int cur_bit;        /* next bit index to read */
  1288. Xstatic boolean out_of_blocks;    /* TRUE if hit terminator data block */
  1289. X
  1290. Xstatic int input_code_size;    /* codesize given in GIF file */
  1291. Xstatic int clear_code,end_code; /* values for Clear and End codes */
  1292. X
  1293. Xstatic int code_size;        /* current actual code size */
  1294. Xstatic int limit_code;        /* 2^code_size */
  1295. Xstatic int max_code;        /* first unused code value */
  1296. Xstatic boolean first_time;    /* flags first call to LZWReadByte */
  1297. X
  1298. X/* LZW decompression tables:
  1299. X *   symbol_head[K] = prefix symbol of any LZW symbol K (0..LZW_TABLE_SIZE-1)
  1300. X *   symbol_tail[K] = suffix byte   of any LZW symbol K (0..LZW_TABLE_SIZE-1)
  1301. X * Note that entries 0..end_code of the above tables are not used,
  1302. X * since those symbols represent raw bytes or special codes.
  1303. X *
  1304. X * The stack represents the not-yet-used expansion of the last LZW symbol.
  1305. X * In the worst case, a symbol could expand to as many bytes as there are
  1306. X * LZW symbols, so we allocate LZW_TABLE_SIZE bytes for the stack.
  1307. X * (This is conservative since that number includes the raw-byte symbols.)
  1308. X *
  1309. X * The tables are allocated from FAR heap space since they would use up
  1310. X * rather a lot of the near data space in a PC.
  1311. X */
  1312. X
  1313. Xstatic UINT16 FAR *symbol_head; /* => table of prefix symbols */
  1314. Xstatic UINT8  FAR *symbol_tail; /* => table of suffix bytes */
  1315. Xstatic UINT8  FAR *symbol_stack; /* stack for symbol expansions */
  1316. Xstatic UINT8  FAR *sp;        /* stack pointer */
  1317. X
  1318. X/* Static state for interlaced image processing */
  1319. X
  1320. Xstatic boolean is_interlaced;    /* TRUE if have interlaced image */
  1321. Xstatic big_sarray_ptr interlaced_image;    /* full image in interlaced order */
  1322. Xstatic long cur_row_number;    /* need to know actual row number */
  1323. Xstatic long pass2_offset;    /* # of pixel rows in pass 1 */
  1324. Xstatic long pass3_offset;    /* # of pixel rows in passes 1&2 */
  1325. Xstatic long pass4_offset;    /* # of pixel rows in passes 1,2,3 */
  1326. X
  1327. X
  1328. X/* Forward declarations */
  1329. XMETHODDEF void load_interlaced_image PP((compress_info_ptr cinfo, JSAMPARRAY pixel_row));
  1330. XMETHODDEF void get_interlaced_row PP((compress_info_ptr cinfo, JSAMPARRAY pixel_row));
  1331. X
  1332. X
  1333. X
  1334. XLOCAL int
  1335. XReadByte (compress_info_ptr cinfo)
  1336. X/* Read next byte from GIF file */
  1337. X{
  1338. X  register FILE * infile = cinfo->input_file;
  1339. X  int c;
  1340. X
  1341. X  if ((c = getc(infile)) == EOF)
  1342. X    ERREXIT(cinfo->emethods, "Premature EOF in GIF file");
  1343. X  return c;
  1344. X}
  1345. X
  1346. X
  1347. XLOCAL int
  1348. XGetDataBlock (compress_info_ptr cinfo, char *buf)
  1349. X/* Read a GIF data block, which has a leading count byte */
  1350. X/* A zero-length block marks the end of a data block sequence */
  1351. X{
  1352. X  int count;
  1353. X
  1354. X  count = ReadByte(cinfo);
  1355. X  if (count > 0) {
  1356. X    if (! ReadOK(cinfo->input_file, buf, count))
  1357. X      ERREXIT(cinfo->emethods, "Premature EOF in GIF file");
  1358. X  }
  1359. X  return count;
  1360. X}
  1361. X
  1362. X
  1363. XLOCAL void
  1364. XSkipDataBlocks (compress_info_ptr cinfo)
  1365. X/* Skip a series of data blocks, until a block terminator is found */
  1366. X{
  1367. X  char buf[256];
  1368. X
  1369. X  while (GetDataBlock(cinfo, buf) > 0)
  1370. X    /* skip */;
  1371. X}
  1372. X
  1373. X
  1374. XLOCAL void
  1375. XReInitLZW (void)
  1376. X/* (Re)initialize LZW state; shared code for startup and Clear processing */
  1377. X{
  1378. X  code_size = input_code_size+1;
  1379. X  limit_code = clear_code << 1;    /* 2^code_size */
  1380. X  max_code = clear_code + 2;    /* first unused code value */
  1381. X  sp = symbol_stack;        /* init stack to empty */
  1382. X}
  1383. X
  1384. X
  1385. XLOCAL void
  1386. XInitLZWCode (void)
  1387. X/* Initialize for a series of LZWReadByte (and hence GetCode) calls */
  1388. X{
  1389. X  /* GetCode initialization */
  1390. X  last_byte = 2;        /* make safe to "recopy last two bytes" */
  1391. X  last_bit = 0;            /* nothing in the buffer */
  1392. X  cur_bit = 0;            /* force buffer load on first call */
  1393. X  out_of_blocks = FALSE;
  1394. X
  1395. X  /* LZWReadByte initialization */
  1396. X  clear_code = 1 << input_code_size; /* compute special code values */
  1397. X  end_code = clear_code + 1;    /* note that these do not change */
  1398. X  first_time = TRUE;
  1399. X  ReInitLZW();
  1400. X}
  1401. X
  1402. X
  1403. XLOCAL int
  1404. XGetCode (compress_info_ptr cinfo)
  1405. X/* Fetch the next code_size bits from the GIF data */
  1406. X/* We assume code_size is less than 16 */
  1407. X{
  1408. X  register INT32 accum;
  1409. X  int offs, ret, count;
  1410. X
  1411. X  if ( (cur_bit+code_size) > last_bit) {
  1412. X    /* Time to reload the buffer */
  1413. X    if (out_of_blocks) {
  1414. X      WARNMS(cinfo->emethods, "Ran out of GIF bits");
  1415. X      return end_code;        /* fake something useful */
  1416. X    }
  1417. X    /* preserve last two bytes of what we have -- assume code_size <= 16 */
  1418. X    code_buf[0] = code_buf[last_byte-2];
  1419. X    code_buf[1] = code_buf[last_byte-1];
  1420. X    /* Load more bytes; set flag if we reach the terminator block */
  1421. X    if ((count = GetDataBlock(cinfo, &code_buf[2])) == 0) {
  1422. X      out_of_blocks = TRUE;
  1423. X      WARNMS(cinfo->emethods, "Ran out of GIF bits");
  1424. X      return end_code;        /* fake something useful */
  1425. X    }
  1426. X    /* Reset counters */
  1427. X    cur_bit = (cur_bit - last_bit) + 16;
  1428. X    last_byte = 2 + count;
  1429. X    last_bit = last_byte * 8;
  1430. X  }
  1431. X
  1432. X  /* Form up next 24 bits in accum */
  1433. X  offs = cur_bit >> 3;        /* byte containing cur_bit */
  1434. X#ifdef CHAR_IS_UNSIGNED
  1435. X  accum = code_buf[offs+2];
  1436. X  accum <<= 8;
  1437. X  accum |= code_buf[offs+1];
  1438. X  accum <<= 8;
  1439. X  accum |= code_buf[offs];
  1440. X#else
  1441. X  accum = code_buf[offs+2] & 0xFF;
  1442. X  accum <<= 8;
  1443. X  accum |= code_buf[offs+1] & 0xFF;
  1444. X  accum <<= 8;
  1445. X  accum |= code_buf[offs] & 0xFF;
  1446. X#endif
  1447. X
  1448. X  /* Right-align cur_bit in accum, then mask off desired number of bits */
  1449. X  accum >>= (cur_bit & 7);
  1450. X  ret = ((int) accum) & ((1 << code_size) - 1);
  1451. X  
  1452. X  cur_bit += code_size;
  1453. X  return ret;
  1454. X}
  1455. X
  1456. X
  1457. XLOCAL int
  1458. XLZWReadByte (compress_info_ptr cinfo)
  1459. X/* Read an LZW-compressed byte */
  1460. X{
  1461. X  static int oldcode;        /* previous LZW symbol */
  1462. X  static int firstcode;        /* first byte of oldcode's expansion */
  1463. X  register int code;        /* current working code */
  1464. X  int incode;            /* saves actual input code */
  1465. X
  1466. X  /* First time, just eat the expected Clear code(s) and return next code, */
  1467. X  /* which is expected to be a raw byte. */
  1468. X  if (first_time) {
  1469. X    first_time = FALSE;
  1470. X    code = clear_code;        /* enables sharing code with Clear case */
  1471. X  } else {
  1472. X
  1473. X    /* If any codes are stacked from a previously read symbol, return them */
  1474. X    if (sp > symbol_stack)
  1475. X      return (int) *(--sp);
  1476. X
  1477. X    /* Time to read a new symbol */
  1478. X    code = GetCode(cinfo);
  1479. X
  1480. X  }
  1481. X
  1482. X  if (code == clear_code) {
  1483. X    /* Reinit static state, swallow any extra Clear codes, and */
  1484. X    /* return next code, which is expected to be a raw byte. */
  1485. X    ReInitLZW();
  1486. X    do {
  1487. X      code = GetCode(cinfo);
  1488. X    } while (code == clear_code);
  1489. X    if (code > clear_code) {    /* make sure it is a raw byte */
  1490. X      WARNMS(cinfo->emethods, "Corrupt data in GIF file");
  1491. X      code = 0;            /* use something valid */
  1492. X    }
  1493. X    firstcode = oldcode = code;    /* make firstcode, oldcode valid! */
  1494. X    return code;
  1495. X  }
  1496. X
  1497. X  if (code == end_code) {
  1498. X    /* Skip the rest of the image, unless GetCode already read terminator */
  1499. X    if (! out_of_blocks) {
  1500. X      SkipDataBlocks(cinfo);
  1501. X      out_of_blocks = TRUE;
  1502. X    }
  1503. X    /* Complain that there's not enough data */
  1504. X    WARNMS(cinfo->emethods, "Premature end of GIF image");
  1505. X    /* Pad data with 0's */
  1506. X    return 0;            /* fake something usable */
  1507. X  }
  1508. X
  1509. X  /* Got normal raw byte or LZW symbol */
  1510. X  incode = code;        /* save for a moment */
  1511. X  
  1512. X  if (code >= max_code) {    /* special case for not-yet-defined symbol */
  1513. X    /* code == max_code is OK; anything bigger is bad data */
  1514. X    if (code > max_code) {
  1515. X      WARNMS(cinfo->emethods, "Corrupt data in GIF file");
  1516. X      incode = 0;        /* prevent creation of loops in symbol table */
  1517. X    }
  1518. X    *sp++ = (UINT8) firstcode;    /* it will be defined as oldcode/firstcode */
  1519. X    code = oldcode;
  1520. X  }
  1521. X
  1522. X  /* If it's a symbol, expand it into the stack */
  1523. X  while (code >= clear_code) {
  1524. X    *sp++ = symbol_tail[code];    /* tail of symbol: a simple byte value */
  1525. X    code = symbol_head[code];    /* head of symbol: another LZW symbol */
  1526. X  }
  1527. X  /* At this point code just represents a raw byte */
  1528. X  firstcode = code;        /* save for possible future use */
  1529. X
  1530. X  /* If there's room in table, */
  1531. X  if ((code = max_code) < LZW_TABLE_SIZE) {
  1532. X    /* Define a new symbol = prev sym + head of this sym's expansion */
  1533. X    symbol_head[code] = oldcode;
  1534. X    symbol_tail[code] = (UINT8) firstcode;
  1535. X    max_code++;
  1536. X    /* Is it time to increase code_size? */
  1537. X    if ((max_code >= limit_code) && (code_size < MAX_LZW_BITS)) {
  1538. X      code_size++;
  1539. X      limit_code <<= 1;        /* keep equal to 2^code_size */
  1540. X    }
  1541. X  }
  1542. X  
  1543. X  oldcode = incode;        /* save last input symbol for future use */
  1544. X  return firstcode;        /* return first byte of symbol's expansion */
  1545. X}
  1546. X
  1547. X
  1548. XLOCAL void
  1549. XReadColorMap (compress_info_ptr cinfo, int cmaplen, JSAMPARRAY cmap)
  1550. X/* Read a GIF colormap */
  1551. X{
  1552. X  int i;
  1553. X
  1554. X  for (i = 0; i < cmaplen; i++) {
  1555. X    cmap[CM_RED][i]   = (JSAMPLE) ReadByte(cinfo);
  1556. X    cmap[CM_GREEN][i] = (JSAMPLE) ReadByte(cinfo);
  1557. X    cmap[CM_BLUE][i]  = (JSAMPLE) ReadByte(cinfo);
  1558. X  }
  1559. X}
  1560. X
  1561. X
  1562. XLOCAL void
  1563. XDoExtension (compress_info_ptr cinfo)
  1564. X/* Process an extension block */
  1565. X/* Currently we ignore 'em all */
  1566. X{
  1567. X  int extlabel;
  1568. X
  1569. X  /* Read extension label byte */
  1570. X  extlabel = ReadByte(cinfo);
  1571. X  TRACEMS1(cinfo->emethods, 1, "Ignoring GIF extension block of type 0x%02x",
  1572. X       extlabel);
  1573. X  /* Skip the data block(s) associated with the extension */
  1574. X  SkipDataBlocks(cinfo);
  1575. X}
  1576. X
  1577. X
  1578. X/*
  1579. X * Read the file header; return image size and component count.
  1580. X */
  1581. X
  1582. XMETHODDEF void
  1583. Xinput_init (compress_info_ptr cinfo)
  1584. X{
  1585. X  char hdrbuf[10];        /* workspace for reading control blocks */
  1586. X  UINT16 width, height;        /* image dimensions */
  1587. X  int colormaplen, aspectRatio;
  1588. X  int c;
  1589. X
  1590. X  /* Allocate space to store the colormap */
  1591. X  colormap = (*cinfo->emethods->alloc_small_sarray)
  1592. X        ((long) MAXCOLORMAPSIZE, (long) NUMCOLORS);
  1593. X
  1594. X  /* Read and verify GIF Header */
  1595. X  if (! ReadOK(cinfo->input_file, hdrbuf, 6))
  1596. X    ERREXIT(cinfo->emethods, "Not a GIF file");
  1597. X  if (hdrbuf[0] != 'G' || hdrbuf[1] != 'I' || hdrbuf[2] != 'F')
  1598. X    ERREXIT(cinfo->emethods, "Not a GIF file");
  1599. X  /* Check for expected version numbers.
  1600. X   * If unknown version, give warning and try to process anyway;
  1601. X   * this is per recommendation in GIF89a standard.
  1602. X   */
  1603. X  if ((hdrbuf[3] != '8' || hdrbuf[4] != '7' || hdrbuf[5] != 'a') &&
  1604. X      (hdrbuf[3] != '8' || hdrbuf[4] != '9' || hdrbuf[5] != 'a'))
  1605. X    TRACEMS3(cinfo->emethods, 1,
  1606. X         "Warning: unexpected GIF version number '%c%c%c'",
  1607. X         hdrbuf[3], hdrbuf[4], hdrbuf[5]);
  1608. X
  1609. X  /* Read and decipher Logical Screen Descriptor */
  1610. X  if (! ReadOK(cinfo->input_file, hdrbuf, 7))
  1611. X    ERREXIT(cinfo->emethods, "Premature EOF in GIF file");
  1612. X  width = LM_to_uint(hdrbuf[0],hdrbuf[1]);
  1613. X  height = LM_to_uint(hdrbuf[2],hdrbuf[3]);
  1614. X  colormaplen = 2 << (hdrbuf[4] & 0x07);
  1615. X  /* we ignore the color resolution, sort flag, and background color index */
  1616. X  aspectRatio = hdrbuf[6] & 0xFF;
  1617. X  if (aspectRatio != 0 && aspectRatio != 49)
  1618. X    TRACEMS(cinfo->emethods, 1, "Warning: nonsquare pixels in input");
  1619. X
  1620. X  /* Read global colormap if header indicates it is present */
  1621. X  if (BitSet(hdrbuf[4], COLORMAPFLAG))
  1622. X    ReadColorMap(cinfo, colormaplen, colormap);
  1623. X
  1624. X  /* Scan until we reach start of desired image.
  1625. X   * We don't currently support skipping images, but could add it easily.
  1626. X   */
  1627. X  for (;;) {
  1628. X    c = ReadByte(cinfo);
  1629. X
  1630. X    if (c == ';')        /* GIF terminator?? */
  1631. X      ERREXIT(cinfo->emethods, "Too few images in GIF file");
  1632. X
  1633. X    if (c == '!') {        /* Extension */
  1634. X      DoExtension(cinfo);
  1635. X      continue;
  1636. X    }
  1637. X    
  1638. X    if (c != ',') {        /* Not an image separator? */
  1639. X      TRACEMS1(cinfo->emethods, 1, "Bogus input char 0x%02x, ignoring", c);
  1640. X      continue;
  1641. X    }
  1642. X
  1643. X    /* Read and decipher Local Image Descriptor */
  1644. X    if (! ReadOK(cinfo->input_file, hdrbuf, 9))
  1645. X      ERREXIT(cinfo->emethods, "Premature EOF in GIF file");
  1646. X    /* we ignore top/left position info, also sort flag */
  1647. X    width = LM_to_uint(hdrbuf[4],hdrbuf[5]);
  1648. X    height = LM_to_uint(hdrbuf[6],hdrbuf[7]);
  1649. X    is_interlaced = BitSet(hdrbuf[8], INTERLACE);
  1650. X
  1651. X    /* Read local colormap if header indicates it is present */
  1652. X    /* Note: if we wanted to support skipping images, */
  1653. X    /* we'd need to skip rather than read colormap for ignored images */
  1654. X    if (BitSet(hdrbuf[8], COLORMAPFLAG)) {
  1655. X      colormaplen = 2 << (hdrbuf[8] & 0x07);
  1656. X      ReadColorMap(cinfo, colormaplen, colormap);
  1657. X    }
  1658. X
  1659. X    input_code_size = ReadByte(cinfo); /* get minimum-code-size byte */
  1660. X    if (input_code_size < 2 || input_code_size >= MAX_LZW_BITS)
  1661. X      ERREXIT1(cinfo->emethods, "Bogus codesize %d", input_code_size);
  1662. X
  1663. X    /* Reached desired image, so break out of loop */
  1664. X    /* If we wanted to skip this image, */
  1665. X    /* we'd call SkipDataBlocks and then continue the loop */
  1666. X    break;
  1667. X  }
  1668. X
  1669. X  /* Prepare to read selected image: first initialize LZW decompressor */
  1670. X  symbol_head = (UINT16 FAR *) (*cinfo->emethods->alloc_medium)
  1671. X                (LZW_TABLE_SIZE * SIZEOF(UINT16));
  1672. X  symbol_tail = (UINT8 FAR *) (*cinfo->emethods->alloc_medium)
  1673. X                (LZW_TABLE_SIZE * SIZEOF(UINT8));
  1674. X  symbol_stack = (UINT8 FAR *) (*cinfo->emethods->alloc_medium)
  1675. X                (LZW_TABLE_SIZE * SIZEOF(UINT8));
  1676. X  InitLZWCode();
  1677. X
  1678. X  /*
  1679. X   * If image is interlaced, we read it into a full-size sample array,
  1680. X   * decompressing as we go; then get_input_row selects rows from the
  1681. X   * sample array in the proper order.
  1682. X   */
  1683. X  if (is_interlaced) {
  1684. X    /* We request the big array now, but can't access it until the pipeline
  1685. X     * controller causes all the big arrays to be allocated.  Hence, the
  1686. X     * actual work of reading the image is postponed until the first call
  1687. X     * of get_input_row.
  1688. X     */
  1689. X    interlaced_image = (*cinfo->emethods->request_big_sarray)
  1690. X        ((long) width, (long) height, 1L);
  1691. X    cinfo->methods->get_input_row = load_interlaced_image;
  1692. X    cinfo->total_passes++;    /* count file reading as separate pass */
  1693. X  }
  1694. X
  1695. X  /* Return info about the image. */
  1696. X  cinfo->input_components = NUMCOLORS;
  1697. X  cinfo->in_color_space = CS_RGB;
  1698. X  cinfo->image_width = width;
  1699. X  cinfo->image_height = height;
  1700. X  cinfo->data_precision = 8;    /* always, even if 12-bit JSAMPLEs */
  1701. X
  1702. X  TRACEMS3(cinfo->emethods, 1, "%ux%ux%d GIF image",
  1703. X       (unsigned int) width, (unsigned int) height, colormaplen);
  1704. X}
  1705. X
  1706. X
  1707. X/*
  1708. X * Read one row of pixels.
  1709. X * This version is used for noninterlaced GIF images:
  1710. X * we read directly from the GIF file.
  1711. X */
  1712. X
  1713. XMETHODDEF void
  1714. Xget_input_row (compress_info_ptr cinfo, JSAMPARRAY pixel_row)
  1715. X{
  1716. X  register JSAMPROW ptr0, ptr1, ptr2;
  1717. X  register long col;
  1718. X  register int c;
  1719. X  
  1720. X  ptr0 = pixel_row[0];
  1721. X  ptr1 = pixel_row[1];
  1722. X  ptr2 = pixel_row[2];
  1723. X  for (col = cinfo->image_width; col > 0; col--) {
  1724. X    c = LZWReadByte(cinfo);
  1725. X    *ptr0++ = colormap[CM_RED][c];
  1726. X    *ptr1++ = colormap[CM_GREEN][c];
  1727. X    *ptr2++ = colormap[CM_BLUE][c];
  1728. X  }
  1729. X}
  1730. X
  1731. X
  1732. X/*
  1733. X * Read one row of pixels.
  1734. X * This version is used for the first call on get_input_row when
  1735. X * reading an interlaced GIF file: we read the whole image into memory.
  1736. X */
  1737. X
  1738. XMETHODDEF void
  1739. Xload_interlaced_image (compress_info_ptr cinfo, JSAMPARRAY pixel_row)
  1740. X{
  1741. X  JSAMPARRAY image_ptr;
  1742. X  register JSAMPROW sptr;
  1743. X  register long col;
  1744. X  long row;
  1745. X
  1746. X  /* Read the interlaced image into the big array we've created. */
  1747. X  for (row = 0; row < cinfo->image_height; row++) {
  1748. X    (*cinfo->methods->progress_monitor) (cinfo, row, cinfo->image_height);
  1749. X    image_ptr = (*cinfo->emethods->access_big_sarray)
  1750. X            (interlaced_image, row, TRUE);
  1751. X    sptr = image_ptr[0];
  1752. X    for (col = cinfo->image_width; col > 0; col--) {
  1753. X      *sptr++ = (JSAMPLE) LZWReadByte(cinfo);
  1754. X    }
  1755. X  }
  1756. X  cinfo->completed_passes++;
  1757. X
  1758. X  /* Replace method pointer so subsequent calls don't come here. */
  1759. X  cinfo->methods->get_input_row = get_interlaced_row;
  1760. X  /* Initialize for get_interlaced_row, and perform first call on it. */
  1761. X  cur_row_number = 0;
  1762. X  pass2_offset = (cinfo->image_height + 7L) / 8L;
  1763. X  pass3_offset = pass2_offset + (cinfo->image_height + 3L) / 8L;
  1764. X  pass4_offset = pass3_offset + (cinfo->image_height + 1L) / 4L;
  1765. X
  1766. X  get_interlaced_row(cinfo, pixel_row);
  1767. X}
  1768. X
  1769. X
  1770. X/*
  1771. X * Read one row of pixels.
  1772. X * This version is used for interlaced GIF images:
  1773. X * we read from the big in-memory image.
  1774. X */
  1775. X
  1776. XMETHODDEF void
  1777. Xget_interlaced_row (compress_info_ptr cinfo, JSAMPARRAY pixel_row)
  1778. X{
  1779. X  JSAMPARRAY image_ptr;
  1780. X  register JSAMPROW sptr, ptr0, ptr1, ptr2;
  1781. X  register long col;
  1782. X  register int c;
  1783. X  long irow;
  1784. X
  1785. X  /* Figure out which row of interlaced image is needed, and access it. */
  1786. X  switch ((int) (cur_row_number & 7L)) {
  1787. X  case 0:            /* first-pass row */
  1788. X    irow = cur_row_number >> 3;
  1789. X    break;
  1790. X  case 4:            /* second-pass row */
  1791. X    irow = (cur_row_number >> 3) + pass2_offset;
  1792. X    break;
  1793. X  case 2:            /* third-pass row */
  1794. X  case 6:
  1795. X    irow = (cur_row_number >> 2) + pass3_offset;
  1796. X    break;
  1797. X  default:            /* fourth-pass row */
  1798. X    irow = (cur_row_number >> 1) + pass4_offset;
  1799. X    break;
  1800. X  }
  1801. X  image_ptr = (*cinfo->emethods->access_big_sarray)
  1802. X            (interlaced_image, irow, FALSE);
  1803. X  /* Scan the row, expand colormap, and output */
  1804. X  sptr = image_ptr[0];
  1805. X  ptr0 = pixel_row[0];
  1806. X  ptr1 = pixel_row[1];
  1807. X  ptr2 = pixel_row[2];
  1808. X  for (col = cinfo->image_width; col > 0; col--) {
  1809. X    c = GETJSAMPLE(*sptr++);
  1810. X    *ptr0++ = colormap[CM_RED][c];
  1811. X    *ptr1++ = colormap[CM_GREEN][c];
  1812. X    *ptr2++ = colormap[CM_BLUE][c];
  1813. X  }
  1814. X  cur_row_number++;        /* for next time */
  1815. X}
  1816. X
  1817. X
  1818. X/*
  1819. X * Finish up at the end of the file.
  1820. X */
  1821. X
  1822. XMETHODDEF void
  1823. Xinput_term (compress_info_ptr cinfo)
  1824. X{
  1825. X  /* no work (we let free_all release the workspace) */
  1826. X}
  1827. X
  1828. X
  1829. X/*
  1830. X * The method selection routine for GIF format input.
  1831. X * Note that this must be called by the user interface before calling
  1832. X * jpeg_compress.  If multiple input formats are supported, the
  1833. X * user interface is responsible for discovering the file format and
  1834. X * calling the appropriate method selection routine.
  1835. X */
  1836. X
  1837. XGLOBAL void
  1838. Xjselrgif (compress_info_ptr cinfo)
  1839. X{
  1840. X  cinfo->methods->input_init = input_init;
  1841. X  cinfo->methods->get_input_row = get_input_row; /* assume uninterlaced */
  1842. X  cinfo->methods->input_term = input_term;
  1843. X}
  1844. X
  1845. X#endif /* GIF_SUPPORTED */
  1846. END_OF_FILE
  1847.   if test 20480 -ne `wc -c <'jrdgif.c'`; then
  1848.     echo shar: \"'jrdgif.c'\" unpacked with wrong size!
  1849.   fi
  1850.   # end of 'jrdgif.c'
  1851. fi
  1852. echo shar: End of archive 11 \(of 18\).
  1853. cp /dev/null ark11isdone
  1854. MISSING=""
  1855. for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 ; do
  1856.     if test ! -f ark${I}isdone ; then
  1857.     MISSING="${MISSING} ${I}"
  1858.     fi
  1859. done
  1860. if test "${MISSING}" = "" ; then
  1861.     echo You have unpacked all 18 archives.
  1862.     rm -f ark[1-9]isdone ark[1-9][0-9]isdone
  1863. else
  1864.     echo You still must unpack the following archives:
  1865.     echo "        " ${MISSING}
  1866. fi
  1867. exit 0
  1868. exit 0 # Just in case...
  1869.