xref: /plan9/sys/src/cmd/gs/jpeg/jcparam.c (revision 593dc095aefb2a85c828727bbfa9da139a49bdf4)
17dd7cddfSDavid du Colombier /*
27dd7cddfSDavid du Colombier  * jcparam.c
37dd7cddfSDavid du Colombier  *
4*593dc095SDavid du Colombier  * Copyright (C) 1991-1998, Thomas G. Lane.
57dd7cddfSDavid du Colombier  * This file is part of the Independent JPEG Group's software.
67dd7cddfSDavid du Colombier  * For conditions of distribution and use, see the accompanying README file.
77dd7cddfSDavid du Colombier  *
87dd7cddfSDavid du Colombier  * This file contains optional default-setting code for the JPEG compressor.
97dd7cddfSDavid du Colombier  * Applications do not have to use this file, but those that don't use it
107dd7cddfSDavid du Colombier  * must know a lot more about the innards of the JPEG code.
117dd7cddfSDavid du Colombier  */
127dd7cddfSDavid du Colombier 
137dd7cddfSDavid du Colombier #define JPEG_INTERNALS
147dd7cddfSDavid du Colombier #include "jinclude.h"
157dd7cddfSDavid du Colombier #include "jpeglib.h"
167dd7cddfSDavid du Colombier 
177dd7cddfSDavid du Colombier 
187dd7cddfSDavid du Colombier /*
197dd7cddfSDavid du Colombier  * Quantization table setup routines
207dd7cddfSDavid du Colombier  */
217dd7cddfSDavid du Colombier 
227dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_add_quant_table(j_compress_ptr cinfo,int which_tbl,const unsigned int * basic_table,int scale_factor,boolean force_baseline)237dd7cddfSDavid du Colombier jpeg_add_quant_table (j_compress_ptr cinfo, int which_tbl,
247dd7cddfSDavid du Colombier 		      const unsigned int *basic_table,
257dd7cddfSDavid du Colombier 		      int scale_factor, boolean force_baseline)
267dd7cddfSDavid du Colombier /* Define a quantization table equal to the basic_table times
277dd7cddfSDavid du Colombier  * a scale factor (given as a percentage).
287dd7cddfSDavid du Colombier  * If force_baseline is TRUE, the computed quantization table entries
297dd7cddfSDavid du Colombier  * are limited to 1..255 for JPEG baseline compatibility.
307dd7cddfSDavid du Colombier  */
317dd7cddfSDavid du Colombier {
32*593dc095SDavid du Colombier   JQUANT_TBL ** qtblptr;
337dd7cddfSDavid du Colombier   int i;
347dd7cddfSDavid du Colombier   long temp;
357dd7cddfSDavid du Colombier 
367dd7cddfSDavid du Colombier   /* Safety check to ensure start_compress not called yet. */
377dd7cddfSDavid du Colombier   if (cinfo->global_state != CSTATE_START)
387dd7cddfSDavid du Colombier     ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state);
397dd7cddfSDavid du Colombier 
40*593dc095SDavid du Colombier   if (which_tbl < 0 || which_tbl >= NUM_QUANT_TBLS)
41*593dc095SDavid du Colombier     ERREXIT1(cinfo, JERR_DQT_INDEX, which_tbl);
42*593dc095SDavid du Colombier 
43*593dc095SDavid du Colombier   qtblptr = & cinfo->quant_tbl_ptrs[which_tbl];
44*593dc095SDavid du Colombier 
457dd7cddfSDavid du Colombier   if (*qtblptr == NULL)
467dd7cddfSDavid du Colombier     *qtblptr = jpeg_alloc_quant_table((j_common_ptr) cinfo);
477dd7cddfSDavid du Colombier 
487dd7cddfSDavid du Colombier   for (i = 0; i < DCTSIZE2; i++) {
497dd7cddfSDavid du Colombier     temp = ((long) basic_table[i] * scale_factor + 50L) / 100L;
507dd7cddfSDavid du Colombier     /* limit the values to the valid range */
517dd7cddfSDavid du Colombier     if (temp <= 0L) temp = 1L;
527dd7cddfSDavid du Colombier     if (temp > 32767L) temp = 32767L; /* max quantizer needed for 12 bits */
537dd7cddfSDavid du Colombier     if (force_baseline && temp > 255L)
547dd7cddfSDavid du Colombier       temp = 255L;		/* limit to baseline range if requested */
557dd7cddfSDavid du Colombier     (*qtblptr)->quantval[i] = (UINT16) temp;
567dd7cddfSDavid du Colombier   }
577dd7cddfSDavid du Colombier 
587dd7cddfSDavid du Colombier   /* Initialize sent_table FALSE so table will be written to JPEG file. */
597dd7cddfSDavid du Colombier   (*qtblptr)->sent_table = FALSE;
607dd7cddfSDavid du Colombier }
617dd7cddfSDavid du Colombier 
627dd7cddfSDavid du Colombier 
637dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_set_linear_quality(j_compress_ptr cinfo,int scale_factor,boolean force_baseline)647dd7cddfSDavid du Colombier jpeg_set_linear_quality (j_compress_ptr cinfo, int scale_factor,
657dd7cddfSDavid du Colombier 			 boolean force_baseline)
667dd7cddfSDavid du Colombier /* Set or change the 'quality' (quantization) setting, using default tables
677dd7cddfSDavid du Colombier  * and a straight percentage-scaling quality scale.  In most cases it's better
687dd7cddfSDavid du Colombier  * to use jpeg_set_quality (below); this entry point is provided for
697dd7cddfSDavid du Colombier  * applications that insist on a linear percentage scaling.
707dd7cddfSDavid du Colombier  */
717dd7cddfSDavid du Colombier {
727dd7cddfSDavid du Colombier   /* These are the sample quantization tables given in JPEG spec section K.1.
737dd7cddfSDavid du Colombier    * The spec says that the values given produce "good" quality, and
747dd7cddfSDavid du Colombier    * when divided by 2, "very good" quality.
757dd7cddfSDavid du Colombier    */
767dd7cddfSDavid du Colombier   static const unsigned int std_luminance_quant_tbl[DCTSIZE2] = {
777dd7cddfSDavid du Colombier     16,  11,  10,  16,  24,  40,  51,  61,
787dd7cddfSDavid du Colombier     12,  12,  14,  19,  26,  58,  60,  55,
797dd7cddfSDavid du Colombier     14,  13,  16,  24,  40,  57,  69,  56,
807dd7cddfSDavid du Colombier     14,  17,  22,  29,  51,  87,  80,  62,
817dd7cddfSDavid du Colombier     18,  22,  37,  56,  68, 109, 103,  77,
827dd7cddfSDavid du Colombier     24,  35,  55,  64,  81, 104, 113,  92,
837dd7cddfSDavid du Colombier     49,  64,  78,  87, 103, 121, 120, 101,
847dd7cddfSDavid du Colombier     72,  92,  95,  98, 112, 100, 103,  99
857dd7cddfSDavid du Colombier   };
867dd7cddfSDavid du Colombier   static const unsigned int std_chrominance_quant_tbl[DCTSIZE2] = {
877dd7cddfSDavid du Colombier     17,  18,  24,  47,  99,  99,  99,  99,
887dd7cddfSDavid du Colombier     18,  21,  26,  66,  99,  99,  99,  99,
897dd7cddfSDavid du Colombier     24,  26,  56,  99,  99,  99,  99,  99,
907dd7cddfSDavid du Colombier     47,  66,  99,  99,  99,  99,  99,  99,
917dd7cddfSDavid du Colombier     99,  99,  99,  99,  99,  99,  99,  99,
927dd7cddfSDavid du Colombier     99,  99,  99,  99,  99,  99,  99,  99,
937dd7cddfSDavid du Colombier     99,  99,  99,  99,  99,  99,  99,  99,
947dd7cddfSDavid du Colombier     99,  99,  99,  99,  99,  99,  99,  99
957dd7cddfSDavid du Colombier   };
967dd7cddfSDavid du Colombier 
977dd7cddfSDavid du Colombier   /* Set up two quantization tables using the specified scaling */
987dd7cddfSDavid du Colombier   jpeg_add_quant_table(cinfo, 0, std_luminance_quant_tbl,
997dd7cddfSDavid du Colombier 		       scale_factor, force_baseline);
1007dd7cddfSDavid du Colombier   jpeg_add_quant_table(cinfo, 1, std_chrominance_quant_tbl,
1017dd7cddfSDavid du Colombier 		       scale_factor, force_baseline);
1027dd7cddfSDavid du Colombier }
1037dd7cddfSDavid du Colombier 
1047dd7cddfSDavid du Colombier 
1057dd7cddfSDavid du Colombier GLOBAL(int)
jpeg_quality_scaling(int quality)1067dd7cddfSDavid du Colombier jpeg_quality_scaling (int quality)
1077dd7cddfSDavid du Colombier /* Convert a user-specified quality rating to a percentage scaling factor
1087dd7cddfSDavid du Colombier  * for an underlying quantization table, using our recommended scaling curve.
1097dd7cddfSDavid du Colombier  * The input 'quality' factor should be 0 (terrible) to 100 (very good).
1107dd7cddfSDavid du Colombier  */
1117dd7cddfSDavid du Colombier {
1127dd7cddfSDavid du Colombier   /* Safety limit on quality factor.  Convert 0 to 1 to avoid zero divide. */
1137dd7cddfSDavid du Colombier   if (quality <= 0) quality = 1;
1147dd7cddfSDavid du Colombier   if (quality > 100) quality = 100;
1157dd7cddfSDavid du Colombier 
1167dd7cddfSDavid du Colombier   /* The basic table is used as-is (scaling 100) for a quality of 50.
1177dd7cddfSDavid du Colombier    * Qualities 50..100 are converted to scaling percentage 200 - 2*Q;
1187dd7cddfSDavid du Colombier    * note that at Q=100 the scaling is 0, which will cause jpeg_add_quant_table
1197dd7cddfSDavid du Colombier    * to make all the table entries 1 (hence, minimum quantization loss).
1207dd7cddfSDavid du Colombier    * Qualities 1..50 are converted to scaling percentage 5000/Q.
1217dd7cddfSDavid du Colombier    */
1227dd7cddfSDavid du Colombier   if (quality < 50)
1237dd7cddfSDavid du Colombier     quality = 5000 / quality;
1247dd7cddfSDavid du Colombier   else
1257dd7cddfSDavid du Colombier     quality = 200 - quality*2;
1267dd7cddfSDavid du Colombier 
1277dd7cddfSDavid du Colombier   return quality;
1287dd7cddfSDavid du Colombier }
1297dd7cddfSDavid du Colombier 
1307dd7cddfSDavid du Colombier 
1317dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_set_quality(j_compress_ptr cinfo,int quality,boolean force_baseline)1327dd7cddfSDavid du Colombier jpeg_set_quality (j_compress_ptr cinfo, int quality, boolean force_baseline)
1337dd7cddfSDavid du Colombier /* Set or change the 'quality' (quantization) setting, using default tables.
1347dd7cddfSDavid du Colombier  * This is the standard quality-adjusting entry point for typical user
1357dd7cddfSDavid du Colombier  * interfaces; only those who want detailed control over quantization tables
1367dd7cddfSDavid du Colombier  * would use the preceding three routines directly.
1377dd7cddfSDavid du Colombier  */
1387dd7cddfSDavid du Colombier {
1397dd7cddfSDavid du Colombier   /* Convert user 0-100 rating to percentage scaling */
1407dd7cddfSDavid du Colombier   quality = jpeg_quality_scaling(quality);
1417dd7cddfSDavid du Colombier 
1427dd7cddfSDavid du Colombier   /* Set up standard quality tables */
1437dd7cddfSDavid du Colombier   jpeg_set_linear_quality(cinfo, quality, force_baseline);
1447dd7cddfSDavid du Colombier }
1457dd7cddfSDavid du Colombier 
1467dd7cddfSDavid du Colombier 
1477dd7cddfSDavid du Colombier /*
1487dd7cddfSDavid du Colombier  * Huffman table setup routines
1497dd7cddfSDavid du Colombier  */
1507dd7cddfSDavid du Colombier 
1517dd7cddfSDavid du Colombier LOCAL(void)
add_huff_table(j_compress_ptr cinfo,JHUFF_TBL ** htblptr,const UINT8 * bits,const UINT8 * val)1527dd7cddfSDavid du Colombier add_huff_table (j_compress_ptr cinfo,
1537dd7cddfSDavid du Colombier 		JHUFF_TBL **htblptr, const UINT8 *bits, const UINT8 *val)
1547dd7cddfSDavid du Colombier /* Define a Huffman table */
1557dd7cddfSDavid du Colombier {
156*593dc095SDavid du Colombier   int nsymbols, len;
157*593dc095SDavid du Colombier 
1587dd7cddfSDavid du Colombier   if (*htblptr == NULL)
1597dd7cddfSDavid du Colombier     *htblptr = jpeg_alloc_huff_table((j_common_ptr) cinfo);
1607dd7cddfSDavid du Colombier 
161*593dc095SDavid du Colombier   /* Copy the number-of-symbols-of-each-code-length counts */
1627dd7cddfSDavid du Colombier   MEMCOPY((*htblptr)->bits, bits, SIZEOF((*htblptr)->bits));
163*593dc095SDavid du Colombier 
164*593dc095SDavid du Colombier   /* Validate the counts.  We do this here mainly so we can copy the right
165*593dc095SDavid du Colombier    * number of symbols from the val[] array, without risking marching off
166*593dc095SDavid du Colombier    * the end of memory.  jchuff.c will do a more thorough test later.
167*593dc095SDavid du Colombier    */
168*593dc095SDavid du Colombier   nsymbols = 0;
169*593dc095SDavid du Colombier   for (len = 1; len <= 16; len++)
170*593dc095SDavid du Colombier     nsymbols += bits[len];
171*593dc095SDavid du Colombier   if (nsymbols < 1 || nsymbols > 256)
172*593dc095SDavid du Colombier     ERREXIT(cinfo, JERR_BAD_HUFF_TABLE);
173*593dc095SDavid du Colombier 
174*593dc095SDavid du Colombier   MEMCOPY((*htblptr)->huffval, val, nsymbols * SIZEOF(UINT8));
1757dd7cddfSDavid du Colombier 
1767dd7cddfSDavid du Colombier   /* Initialize sent_table FALSE so table will be written to JPEG file. */
1777dd7cddfSDavid du Colombier   (*htblptr)->sent_table = FALSE;
1787dd7cddfSDavid du Colombier }
1797dd7cddfSDavid du Colombier 
1807dd7cddfSDavid du Colombier 
1817dd7cddfSDavid du Colombier LOCAL(void)
std_huff_tables(j_compress_ptr cinfo)1827dd7cddfSDavid du Colombier std_huff_tables (j_compress_ptr cinfo)
1837dd7cddfSDavid du Colombier /* Set up the standard Huffman tables (cf. JPEG standard section K.3) */
1847dd7cddfSDavid du Colombier /* IMPORTANT: these are only valid for 8-bit data precision! */
1857dd7cddfSDavid du Colombier {
1867dd7cddfSDavid du Colombier   static const UINT8 bits_dc_luminance[17] =
1877dd7cddfSDavid du Colombier     { /* 0-base */ 0, 0, 1, 5, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0 };
1887dd7cddfSDavid du Colombier   static const UINT8 val_dc_luminance[] =
1897dd7cddfSDavid du Colombier     { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
1907dd7cddfSDavid du Colombier 
1917dd7cddfSDavid du Colombier   static const UINT8 bits_dc_chrominance[17] =
1927dd7cddfSDavid du Colombier     { /* 0-base */ 0, 0, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0 };
1937dd7cddfSDavid du Colombier   static const UINT8 val_dc_chrominance[] =
1947dd7cddfSDavid du Colombier     { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
1957dd7cddfSDavid du Colombier 
1967dd7cddfSDavid du Colombier   static const UINT8 bits_ac_luminance[17] =
1977dd7cddfSDavid du Colombier     { /* 0-base */ 0, 0, 2, 1, 3, 3, 2, 4, 3, 5, 5, 4, 4, 0, 0, 1, 0x7d };
1987dd7cddfSDavid du Colombier   static const UINT8 val_ac_luminance[] =
1997dd7cddfSDavid du Colombier     { 0x01, 0x02, 0x03, 0x00, 0x04, 0x11, 0x05, 0x12,
2007dd7cddfSDavid du Colombier       0x21, 0x31, 0x41, 0x06, 0x13, 0x51, 0x61, 0x07,
2017dd7cddfSDavid du Colombier       0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xa1, 0x08,
2027dd7cddfSDavid du Colombier       0x23, 0x42, 0xb1, 0xc1, 0x15, 0x52, 0xd1, 0xf0,
2037dd7cddfSDavid du Colombier       0x24, 0x33, 0x62, 0x72, 0x82, 0x09, 0x0a, 0x16,
2047dd7cddfSDavid du Colombier       0x17, 0x18, 0x19, 0x1a, 0x25, 0x26, 0x27, 0x28,
2057dd7cddfSDavid du Colombier       0x29, 0x2a, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39,
2067dd7cddfSDavid du Colombier       0x3a, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49,
2077dd7cddfSDavid du Colombier       0x4a, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59,
2087dd7cddfSDavid du Colombier       0x5a, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69,
2097dd7cddfSDavid du Colombier       0x6a, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79,
2107dd7cddfSDavid du Colombier       0x7a, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89,
2117dd7cddfSDavid du Colombier       0x8a, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98,
2127dd7cddfSDavid du Colombier       0x99, 0x9a, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
2137dd7cddfSDavid du Colombier       0xa8, 0xa9, 0xaa, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6,
2147dd7cddfSDavid du Colombier       0xb7, 0xb8, 0xb9, 0xba, 0xc2, 0xc3, 0xc4, 0xc5,
2157dd7cddfSDavid du Colombier       0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xd2, 0xd3, 0xd4,
2167dd7cddfSDavid du Colombier       0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xe1, 0xe2,
2177dd7cddfSDavid du Colombier       0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9, 0xea,
2187dd7cddfSDavid du Colombier       0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8,
2197dd7cddfSDavid du Colombier       0xf9, 0xfa };
2207dd7cddfSDavid du Colombier 
2217dd7cddfSDavid du Colombier   static const UINT8 bits_ac_chrominance[17] =
2227dd7cddfSDavid du Colombier     { /* 0-base */ 0, 0, 2, 1, 2, 4, 4, 3, 4, 7, 5, 4, 4, 0, 1, 2, 0x77 };
2237dd7cddfSDavid du Colombier   static const UINT8 val_ac_chrominance[] =
2247dd7cddfSDavid du Colombier     { 0x00, 0x01, 0x02, 0x03, 0x11, 0x04, 0x05, 0x21,
2257dd7cddfSDavid du Colombier       0x31, 0x06, 0x12, 0x41, 0x51, 0x07, 0x61, 0x71,
2267dd7cddfSDavid du Colombier       0x13, 0x22, 0x32, 0x81, 0x08, 0x14, 0x42, 0x91,
2277dd7cddfSDavid du Colombier       0xa1, 0xb1, 0xc1, 0x09, 0x23, 0x33, 0x52, 0xf0,
2287dd7cddfSDavid du Colombier       0x15, 0x62, 0x72, 0xd1, 0x0a, 0x16, 0x24, 0x34,
2297dd7cddfSDavid du Colombier       0xe1, 0x25, 0xf1, 0x17, 0x18, 0x19, 0x1a, 0x26,
2307dd7cddfSDavid du Colombier       0x27, 0x28, 0x29, 0x2a, 0x35, 0x36, 0x37, 0x38,
2317dd7cddfSDavid du Colombier       0x39, 0x3a, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48,
2327dd7cddfSDavid du Colombier       0x49, 0x4a, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58,
2337dd7cddfSDavid du Colombier       0x59, 0x5a, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68,
2347dd7cddfSDavid du Colombier       0x69, 0x6a, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78,
2357dd7cddfSDavid du Colombier       0x79, 0x7a, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
2367dd7cddfSDavid du Colombier       0x88, 0x89, 0x8a, 0x92, 0x93, 0x94, 0x95, 0x96,
2377dd7cddfSDavid du Colombier       0x97, 0x98, 0x99, 0x9a, 0xa2, 0xa3, 0xa4, 0xa5,
2387dd7cddfSDavid du Colombier       0xa6, 0xa7, 0xa8, 0xa9, 0xaa, 0xb2, 0xb3, 0xb4,
2397dd7cddfSDavid du Colombier       0xb5, 0xb6, 0xb7, 0xb8, 0xb9, 0xba, 0xc2, 0xc3,
2407dd7cddfSDavid du Colombier       0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xd2,
2417dd7cddfSDavid du Colombier       0xd3, 0xd4, 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda,
2427dd7cddfSDavid du Colombier       0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9,
2437dd7cddfSDavid du Colombier       0xea, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8,
2447dd7cddfSDavid du Colombier       0xf9, 0xfa };
2457dd7cddfSDavid du Colombier 
2467dd7cddfSDavid du Colombier   add_huff_table(cinfo, &cinfo->dc_huff_tbl_ptrs[0],
2477dd7cddfSDavid du Colombier 		 bits_dc_luminance, val_dc_luminance);
2487dd7cddfSDavid du Colombier   add_huff_table(cinfo, &cinfo->ac_huff_tbl_ptrs[0],
2497dd7cddfSDavid du Colombier 		 bits_ac_luminance, val_ac_luminance);
2507dd7cddfSDavid du Colombier   add_huff_table(cinfo, &cinfo->dc_huff_tbl_ptrs[1],
2517dd7cddfSDavid du Colombier 		 bits_dc_chrominance, val_dc_chrominance);
2527dd7cddfSDavid du Colombier   add_huff_table(cinfo, &cinfo->ac_huff_tbl_ptrs[1],
2537dd7cddfSDavid du Colombier 		 bits_ac_chrominance, val_ac_chrominance);
2547dd7cddfSDavid du Colombier }
2557dd7cddfSDavid du Colombier 
2567dd7cddfSDavid du Colombier 
2577dd7cddfSDavid du Colombier /*
2587dd7cddfSDavid du Colombier  * Default parameter setup for compression.
2597dd7cddfSDavid du Colombier  *
2607dd7cddfSDavid du Colombier  * Applications that don't choose to use this routine must do their
2617dd7cddfSDavid du Colombier  * own setup of all these parameters.  Alternately, you can call this
2627dd7cddfSDavid du Colombier  * to establish defaults and then alter parameters selectively.  This
2637dd7cddfSDavid du Colombier  * is the recommended approach since, if we add any new parameters,
2647dd7cddfSDavid du Colombier  * your code will still work (they'll be set to reasonable defaults).
2657dd7cddfSDavid du Colombier  */
2667dd7cddfSDavid du Colombier 
2677dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_set_defaults(j_compress_ptr cinfo)2687dd7cddfSDavid du Colombier jpeg_set_defaults (j_compress_ptr cinfo)
2697dd7cddfSDavid du Colombier {
2707dd7cddfSDavid du Colombier   int i;
2717dd7cddfSDavid du Colombier 
2727dd7cddfSDavid du Colombier   /* Safety check to ensure start_compress not called yet. */
2737dd7cddfSDavid du Colombier   if (cinfo->global_state != CSTATE_START)
2747dd7cddfSDavid du Colombier     ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state);
2757dd7cddfSDavid du Colombier 
2767dd7cddfSDavid du Colombier   /* Allocate comp_info array large enough for maximum component count.
2777dd7cddfSDavid du Colombier    * Array is made permanent in case application wants to compress
2787dd7cddfSDavid du Colombier    * multiple images at same param settings.
2797dd7cddfSDavid du Colombier    */
2807dd7cddfSDavid du Colombier   if (cinfo->comp_info == NULL)
2817dd7cddfSDavid du Colombier     cinfo->comp_info = (jpeg_component_info *)
2827dd7cddfSDavid du Colombier       (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_PERMANENT,
2837dd7cddfSDavid du Colombier 				  MAX_COMPONENTS * SIZEOF(jpeg_component_info));
2847dd7cddfSDavid du Colombier 
2857dd7cddfSDavid du Colombier   /* Initialize everything not dependent on the color space */
2867dd7cddfSDavid du Colombier 
2877dd7cddfSDavid du Colombier   cinfo->data_precision = BITS_IN_JSAMPLE;
2887dd7cddfSDavid du Colombier   /* Set up two quantization tables using default quality of 75 */
2897dd7cddfSDavid du Colombier   jpeg_set_quality(cinfo, 75, TRUE);
2907dd7cddfSDavid du Colombier   /* Set up two Huffman tables */
2917dd7cddfSDavid du Colombier   std_huff_tables(cinfo);
2927dd7cddfSDavid du Colombier 
2937dd7cddfSDavid du Colombier   /* Initialize default arithmetic coding conditioning */
2947dd7cddfSDavid du Colombier   for (i = 0; i < NUM_ARITH_TBLS; i++) {
2957dd7cddfSDavid du Colombier     cinfo->arith_dc_L[i] = 0;
2967dd7cddfSDavid du Colombier     cinfo->arith_dc_U[i] = 1;
2977dd7cddfSDavid du Colombier     cinfo->arith_ac_K[i] = 5;
2987dd7cddfSDavid du Colombier   }
2997dd7cddfSDavid du Colombier 
3007dd7cddfSDavid du Colombier   /* Default is no multiple-scan output */
3017dd7cddfSDavid du Colombier   cinfo->scan_info = NULL;
3027dd7cddfSDavid du Colombier   cinfo->num_scans = 0;
3037dd7cddfSDavid du Colombier 
3047dd7cddfSDavid du Colombier   /* Expect normal source image, not raw downsampled data */
3057dd7cddfSDavid du Colombier   cinfo->raw_data_in = FALSE;
3067dd7cddfSDavid du Colombier 
3077dd7cddfSDavid du Colombier   /* Use Huffman coding, not arithmetic coding, by default */
3087dd7cddfSDavid du Colombier   cinfo->arith_code = FALSE;
3097dd7cddfSDavid du Colombier 
3107dd7cddfSDavid du Colombier   /* By default, don't do extra passes to optimize entropy coding */
3117dd7cddfSDavid du Colombier   cinfo->optimize_coding = FALSE;
3127dd7cddfSDavid du Colombier   /* The standard Huffman tables are only valid for 8-bit data precision.
3137dd7cddfSDavid du Colombier    * If the precision is higher, force optimization on so that usable
3147dd7cddfSDavid du Colombier    * tables will be computed.  This test can be removed if default tables
3157dd7cddfSDavid du Colombier    * are supplied that are valid for the desired precision.
3167dd7cddfSDavid du Colombier    */
3177dd7cddfSDavid du Colombier   if (cinfo->data_precision > 8)
3187dd7cddfSDavid du Colombier     cinfo->optimize_coding = TRUE;
3197dd7cddfSDavid du Colombier 
3207dd7cddfSDavid du Colombier   /* By default, use the simpler non-cosited sampling alignment */
3217dd7cddfSDavid du Colombier   cinfo->CCIR601_sampling = FALSE;
3227dd7cddfSDavid du Colombier 
3237dd7cddfSDavid du Colombier   /* No input smoothing */
3247dd7cddfSDavid du Colombier   cinfo->smoothing_factor = 0;
3257dd7cddfSDavid du Colombier 
3267dd7cddfSDavid du Colombier   /* DCT algorithm preference */
3277dd7cddfSDavid du Colombier   cinfo->dct_method = JDCT_DEFAULT;
3287dd7cddfSDavid du Colombier 
3297dd7cddfSDavid du Colombier   /* No restart markers */
3307dd7cddfSDavid du Colombier   cinfo->restart_interval = 0;
3317dd7cddfSDavid du Colombier   cinfo->restart_in_rows = 0;
3327dd7cddfSDavid du Colombier 
3337dd7cddfSDavid du Colombier   /* Fill in default JFIF marker parameters.  Note that whether the marker
3347dd7cddfSDavid du Colombier    * will actually be written is determined by jpeg_set_colorspace.
335*593dc095SDavid du Colombier    *
336*593dc095SDavid du Colombier    * By default, the library emits JFIF version code 1.01.
337*593dc095SDavid du Colombier    * An application that wants to emit JFIF 1.02 extension markers should set
338*593dc095SDavid du Colombier    * JFIF_minor_version to 2.  We could probably get away with just defaulting
339*593dc095SDavid du Colombier    * to 1.02, but there may still be some decoders in use that will complain
340*593dc095SDavid du Colombier    * about that; saying 1.01 should minimize compatibility problems.
3417dd7cddfSDavid du Colombier    */
342*593dc095SDavid du Colombier   cinfo->JFIF_major_version = 1; /* Default JFIF version = 1.01 */
343*593dc095SDavid du Colombier   cinfo->JFIF_minor_version = 1;
3447dd7cddfSDavid du Colombier   cinfo->density_unit = 0;	/* Pixel size is unknown by default */
3457dd7cddfSDavid du Colombier   cinfo->X_density = 1;		/* Pixel aspect ratio is square by default */
3467dd7cddfSDavid du Colombier   cinfo->Y_density = 1;
3477dd7cddfSDavid du Colombier 
3487dd7cddfSDavid du Colombier   /* Choose JPEG colorspace based on input space, set defaults accordingly */
3497dd7cddfSDavid du Colombier 
3507dd7cddfSDavid du Colombier   jpeg_default_colorspace(cinfo);
3517dd7cddfSDavid du Colombier }
3527dd7cddfSDavid du Colombier 
3537dd7cddfSDavid du Colombier 
3547dd7cddfSDavid du Colombier /*
3557dd7cddfSDavid du Colombier  * Select an appropriate JPEG colorspace for in_color_space.
3567dd7cddfSDavid du Colombier  */
3577dd7cddfSDavid du Colombier 
3587dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_default_colorspace(j_compress_ptr cinfo)3597dd7cddfSDavid du Colombier jpeg_default_colorspace (j_compress_ptr cinfo)
3607dd7cddfSDavid du Colombier {
3617dd7cddfSDavid du Colombier   switch (cinfo->in_color_space) {
3627dd7cddfSDavid du Colombier   case JCS_GRAYSCALE:
3637dd7cddfSDavid du Colombier     jpeg_set_colorspace(cinfo, JCS_GRAYSCALE);
3647dd7cddfSDavid du Colombier     break;
3657dd7cddfSDavid du Colombier   case JCS_RGB:
3667dd7cddfSDavid du Colombier     jpeg_set_colorspace(cinfo, JCS_YCbCr);
3677dd7cddfSDavid du Colombier     break;
3687dd7cddfSDavid du Colombier   case JCS_YCbCr:
3697dd7cddfSDavid du Colombier     jpeg_set_colorspace(cinfo, JCS_YCbCr);
3707dd7cddfSDavid du Colombier     break;
3717dd7cddfSDavid du Colombier   case JCS_CMYK:
3727dd7cddfSDavid du Colombier     jpeg_set_colorspace(cinfo, JCS_CMYK); /* By default, no translation */
3737dd7cddfSDavid du Colombier     break;
3747dd7cddfSDavid du Colombier   case JCS_YCCK:
3757dd7cddfSDavid du Colombier     jpeg_set_colorspace(cinfo, JCS_YCCK);
3767dd7cddfSDavid du Colombier     break;
3777dd7cddfSDavid du Colombier   case JCS_UNKNOWN:
3787dd7cddfSDavid du Colombier     jpeg_set_colorspace(cinfo, JCS_UNKNOWN);
3797dd7cddfSDavid du Colombier     break;
3807dd7cddfSDavid du Colombier   default:
3817dd7cddfSDavid du Colombier     ERREXIT(cinfo, JERR_BAD_IN_COLORSPACE);
3827dd7cddfSDavid du Colombier   }
3837dd7cddfSDavid du Colombier }
3847dd7cddfSDavid du Colombier 
3857dd7cddfSDavid du Colombier 
3867dd7cddfSDavid du Colombier /*
3877dd7cddfSDavid du Colombier  * Set the JPEG colorspace, and choose colorspace-dependent default values.
3887dd7cddfSDavid du Colombier  */
3897dd7cddfSDavid du Colombier 
3907dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_set_colorspace(j_compress_ptr cinfo,J_COLOR_SPACE colorspace)3917dd7cddfSDavid du Colombier jpeg_set_colorspace (j_compress_ptr cinfo, J_COLOR_SPACE colorspace)
3927dd7cddfSDavid du Colombier {
3937dd7cddfSDavid du Colombier   jpeg_component_info * compptr;
3947dd7cddfSDavid du Colombier   int ci;
3957dd7cddfSDavid du Colombier 
3967dd7cddfSDavid du Colombier #define SET_COMP(index,id,hsamp,vsamp,quant,dctbl,actbl)  \
3977dd7cddfSDavid du Colombier   (compptr = &cinfo->comp_info[index], \
3987dd7cddfSDavid du Colombier    compptr->component_id = (id), \
3997dd7cddfSDavid du Colombier    compptr->h_samp_factor = (hsamp), \
4007dd7cddfSDavid du Colombier    compptr->v_samp_factor = (vsamp), \
4017dd7cddfSDavid du Colombier    compptr->quant_tbl_no = (quant), \
4027dd7cddfSDavid du Colombier    compptr->dc_tbl_no = (dctbl), \
4037dd7cddfSDavid du Colombier    compptr->ac_tbl_no = (actbl) )
4047dd7cddfSDavid du Colombier 
4057dd7cddfSDavid du Colombier   /* Safety check to ensure start_compress not called yet. */
4067dd7cddfSDavid du Colombier   if (cinfo->global_state != CSTATE_START)
4077dd7cddfSDavid du Colombier     ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state);
4087dd7cddfSDavid du Colombier 
4097dd7cddfSDavid du Colombier   /* For all colorspaces, we use Q and Huff tables 0 for luminance components,
4107dd7cddfSDavid du Colombier    * tables 1 for chrominance components.
4117dd7cddfSDavid du Colombier    */
4127dd7cddfSDavid du Colombier 
4137dd7cddfSDavid du Colombier   cinfo->jpeg_color_space = colorspace;
4147dd7cddfSDavid du Colombier 
4157dd7cddfSDavid du Colombier   cinfo->write_JFIF_header = FALSE; /* No marker for non-JFIF colorspaces */
4167dd7cddfSDavid du Colombier   cinfo->write_Adobe_marker = FALSE; /* write no Adobe marker by default */
4177dd7cddfSDavid du Colombier 
4187dd7cddfSDavid du Colombier   switch (colorspace) {
4197dd7cddfSDavid du Colombier   case JCS_GRAYSCALE:
4207dd7cddfSDavid du Colombier     cinfo->write_JFIF_header = TRUE; /* Write a JFIF marker */
4217dd7cddfSDavid du Colombier     cinfo->num_components = 1;
4227dd7cddfSDavid du Colombier     /* JFIF specifies component ID 1 */
4237dd7cddfSDavid du Colombier     SET_COMP(0, 1, 1,1, 0, 0,0);
4247dd7cddfSDavid du Colombier     break;
4257dd7cddfSDavid du Colombier   case JCS_RGB:
4267dd7cddfSDavid du Colombier     cinfo->write_Adobe_marker = TRUE; /* write Adobe marker to flag RGB */
4277dd7cddfSDavid du Colombier     cinfo->num_components = 3;
4287dd7cddfSDavid du Colombier     SET_COMP(0, 0x52 /* 'R' */, 1,1, 0, 0,0);
4297dd7cddfSDavid du Colombier     SET_COMP(1, 0x47 /* 'G' */, 1,1, 0, 0,0);
4307dd7cddfSDavid du Colombier     SET_COMP(2, 0x42 /* 'B' */, 1,1, 0, 0,0);
4317dd7cddfSDavid du Colombier     break;
4327dd7cddfSDavid du Colombier   case JCS_YCbCr:
4337dd7cddfSDavid du Colombier     cinfo->write_JFIF_header = TRUE; /* Write a JFIF marker */
4347dd7cddfSDavid du Colombier     cinfo->num_components = 3;
4357dd7cddfSDavid du Colombier     /* JFIF specifies component IDs 1,2,3 */
4367dd7cddfSDavid du Colombier     /* We default to 2x2 subsamples of chrominance */
4377dd7cddfSDavid du Colombier     SET_COMP(0, 1, 2,2, 0, 0,0);
4387dd7cddfSDavid du Colombier     SET_COMP(1, 2, 1,1, 1, 1,1);
4397dd7cddfSDavid du Colombier     SET_COMP(2, 3, 1,1, 1, 1,1);
4407dd7cddfSDavid du Colombier     break;
4417dd7cddfSDavid du Colombier   case JCS_CMYK:
4427dd7cddfSDavid du Colombier     cinfo->write_Adobe_marker = TRUE; /* write Adobe marker to flag CMYK */
4437dd7cddfSDavid du Colombier     cinfo->num_components = 4;
4447dd7cddfSDavid du Colombier     SET_COMP(0, 0x43 /* 'C' */, 1,1, 0, 0,0);
4457dd7cddfSDavid du Colombier     SET_COMP(1, 0x4D /* 'M' */, 1,1, 0, 0,0);
4467dd7cddfSDavid du Colombier     SET_COMP(2, 0x59 /* 'Y' */, 1,1, 0, 0,0);
4477dd7cddfSDavid du Colombier     SET_COMP(3, 0x4B /* 'K' */, 1,1, 0, 0,0);
4487dd7cddfSDavid du Colombier     break;
4497dd7cddfSDavid du Colombier   case JCS_YCCK:
4507dd7cddfSDavid du Colombier     cinfo->write_Adobe_marker = TRUE; /* write Adobe marker to flag YCCK */
4517dd7cddfSDavid du Colombier     cinfo->num_components = 4;
4527dd7cddfSDavid du Colombier     SET_COMP(0, 1, 2,2, 0, 0,0);
4537dd7cddfSDavid du Colombier     SET_COMP(1, 2, 1,1, 1, 1,1);
4547dd7cddfSDavid du Colombier     SET_COMP(2, 3, 1,1, 1, 1,1);
4557dd7cddfSDavid du Colombier     SET_COMP(3, 4, 2,2, 0, 0,0);
4567dd7cddfSDavid du Colombier     break;
4577dd7cddfSDavid du Colombier   case JCS_UNKNOWN:
4587dd7cddfSDavid du Colombier     cinfo->num_components = cinfo->input_components;
4597dd7cddfSDavid du Colombier     if (cinfo->num_components < 1 || cinfo->num_components > MAX_COMPONENTS)
4607dd7cddfSDavid du Colombier       ERREXIT2(cinfo, JERR_COMPONENT_COUNT, cinfo->num_components,
4617dd7cddfSDavid du Colombier 	       MAX_COMPONENTS);
4627dd7cddfSDavid du Colombier     for (ci = 0; ci < cinfo->num_components; ci++) {
4637dd7cddfSDavid du Colombier       SET_COMP(ci, ci, 1,1, 0, 0,0);
4647dd7cddfSDavid du Colombier     }
4657dd7cddfSDavid du Colombier     break;
4667dd7cddfSDavid du Colombier   default:
4677dd7cddfSDavid du Colombier     ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
4687dd7cddfSDavid du Colombier   }
4697dd7cddfSDavid du Colombier }
4707dd7cddfSDavid du Colombier 
4717dd7cddfSDavid du Colombier 
4727dd7cddfSDavid du Colombier #ifdef C_PROGRESSIVE_SUPPORTED
4737dd7cddfSDavid du Colombier 
4747dd7cddfSDavid du Colombier LOCAL(jpeg_scan_info *)
fill_a_scan(jpeg_scan_info * scanptr,int ci,int Ss,int Se,int Ah,int Al)4757dd7cddfSDavid du Colombier fill_a_scan (jpeg_scan_info * scanptr, int ci,
4767dd7cddfSDavid du Colombier 	     int Ss, int Se, int Ah, int Al)
4777dd7cddfSDavid du Colombier /* Support routine: generate one scan for specified component */
4787dd7cddfSDavid du Colombier {
4797dd7cddfSDavid du Colombier   scanptr->comps_in_scan = 1;
4807dd7cddfSDavid du Colombier   scanptr->component_index[0] = ci;
4817dd7cddfSDavid du Colombier   scanptr->Ss = Ss;
4827dd7cddfSDavid du Colombier   scanptr->Se = Se;
4837dd7cddfSDavid du Colombier   scanptr->Ah = Ah;
4847dd7cddfSDavid du Colombier   scanptr->Al = Al;
4857dd7cddfSDavid du Colombier   scanptr++;
4867dd7cddfSDavid du Colombier   return scanptr;
4877dd7cddfSDavid du Colombier }
4887dd7cddfSDavid du Colombier 
4897dd7cddfSDavid du Colombier LOCAL(jpeg_scan_info *)
fill_scans(jpeg_scan_info * scanptr,int ncomps,int Ss,int Se,int Ah,int Al)4907dd7cddfSDavid du Colombier fill_scans (jpeg_scan_info * scanptr, int ncomps,
4917dd7cddfSDavid du Colombier 	    int Ss, int Se, int Ah, int Al)
4927dd7cddfSDavid du Colombier /* Support routine: generate one scan for each component */
4937dd7cddfSDavid du Colombier {
4947dd7cddfSDavid du Colombier   int ci;
4957dd7cddfSDavid du Colombier 
4967dd7cddfSDavid du Colombier   for (ci = 0; ci < ncomps; ci++) {
4977dd7cddfSDavid du Colombier     scanptr->comps_in_scan = 1;
4987dd7cddfSDavid du Colombier     scanptr->component_index[0] = ci;
4997dd7cddfSDavid du Colombier     scanptr->Ss = Ss;
5007dd7cddfSDavid du Colombier     scanptr->Se = Se;
5017dd7cddfSDavid du Colombier     scanptr->Ah = Ah;
5027dd7cddfSDavid du Colombier     scanptr->Al = Al;
5037dd7cddfSDavid du Colombier     scanptr++;
5047dd7cddfSDavid du Colombier   }
5057dd7cddfSDavid du Colombier   return scanptr;
5067dd7cddfSDavid du Colombier }
5077dd7cddfSDavid du Colombier 
5087dd7cddfSDavid du Colombier LOCAL(jpeg_scan_info *)
fill_dc_scans(jpeg_scan_info * scanptr,int ncomps,int Ah,int Al)5097dd7cddfSDavid du Colombier fill_dc_scans (jpeg_scan_info * scanptr, int ncomps, int Ah, int Al)
5107dd7cddfSDavid du Colombier /* Support routine: generate interleaved DC scan if possible, else N scans */
5117dd7cddfSDavid du Colombier {
5127dd7cddfSDavid du Colombier   int ci;
5137dd7cddfSDavid du Colombier 
5147dd7cddfSDavid du Colombier   if (ncomps <= MAX_COMPS_IN_SCAN) {
5157dd7cddfSDavid du Colombier     /* Single interleaved DC scan */
5167dd7cddfSDavid du Colombier     scanptr->comps_in_scan = ncomps;
5177dd7cddfSDavid du Colombier     for (ci = 0; ci < ncomps; ci++)
5187dd7cddfSDavid du Colombier       scanptr->component_index[ci] = ci;
5197dd7cddfSDavid du Colombier     scanptr->Ss = scanptr->Se = 0;
5207dd7cddfSDavid du Colombier     scanptr->Ah = Ah;
5217dd7cddfSDavid du Colombier     scanptr->Al = Al;
5227dd7cddfSDavid du Colombier     scanptr++;
5237dd7cddfSDavid du Colombier   } else {
5247dd7cddfSDavid du Colombier     /* Noninterleaved DC scan for each component */
5257dd7cddfSDavid du Colombier     scanptr = fill_scans(scanptr, ncomps, 0, 0, Ah, Al);
5267dd7cddfSDavid du Colombier   }
5277dd7cddfSDavid du Colombier   return scanptr;
5287dd7cddfSDavid du Colombier }
5297dd7cddfSDavid du Colombier 
5307dd7cddfSDavid du Colombier 
5317dd7cddfSDavid du Colombier /*
5327dd7cddfSDavid du Colombier  * Create a recommended progressive-JPEG script.
5337dd7cddfSDavid du Colombier  * cinfo->num_components and cinfo->jpeg_color_space must be correct.
5347dd7cddfSDavid du Colombier  */
5357dd7cddfSDavid du Colombier 
5367dd7cddfSDavid du Colombier GLOBAL(void)
jpeg_simple_progression(j_compress_ptr cinfo)5377dd7cddfSDavid du Colombier jpeg_simple_progression (j_compress_ptr cinfo)
5387dd7cddfSDavid du Colombier {
5397dd7cddfSDavid du Colombier   int ncomps = cinfo->num_components;
5407dd7cddfSDavid du Colombier   int nscans;
5417dd7cddfSDavid du Colombier   jpeg_scan_info * scanptr;
5427dd7cddfSDavid du Colombier 
5437dd7cddfSDavid du Colombier   /* Safety check to ensure start_compress not called yet. */
5447dd7cddfSDavid du Colombier   if (cinfo->global_state != CSTATE_START)
5457dd7cddfSDavid du Colombier     ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state);
5467dd7cddfSDavid du Colombier 
5477dd7cddfSDavid du Colombier   /* Figure space needed for script.  Calculation must match code below! */
5487dd7cddfSDavid du Colombier   if (ncomps == 3 && cinfo->jpeg_color_space == JCS_YCbCr) {
5497dd7cddfSDavid du Colombier     /* Custom script for YCbCr color images. */
5507dd7cddfSDavid du Colombier     nscans = 10;
5517dd7cddfSDavid du Colombier   } else {
5527dd7cddfSDavid du Colombier     /* All-purpose script for other color spaces. */
5537dd7cddfSDavid du Colombier     if (ncomps > MAX_COMPS_IN_SCAN)
5547dd7cddfSDavid du Colombier       nscans = 6 * ncomps;	/* 2 DC + 4 AC scans per component */
5557dd7cddfSDavid du Colombier     else
5567dd7cddfSDavid du Colombier       nscans = 2 + 4 * ncomps;	/* 2 DC scans; 4 AC scans per component */
5577dd7cddfSDavid du Colombier   }
5587dd7cddfSDavid du Colombier 
559*593dc095SDavid du Colombier   /* Allocate space for script.
560*593dc095SDavid du Colombier    * We need to put it in the permanent pool in case the application performs
561*593dc095SDavid du Colombier    * multiple compressions without changing the settings.  To avoid a memory
562*593dc095SDavid du Colombier    * leak if jpeg_simple_progression is called repeatedly for the same JPEG
563*593dc095SDavid du Colombier    * object, we try to re-use previously allocated space, and we allocate
564*593dc095SDavid du Colombier    * enough space to handle YCbCr even if initially asked for grayscale.
565*593dc095SDavid du Colombier    */
566*593dc095SDavid du Colombier   if (cinfo->script_space == NULL || cinfo->script_space_size < nscans) {
567*593dc095SDavid du Colombier     cinfo->script_space_size = MAX(nscans, 10);
568*593dc095SDavid du Colombier     cinfo->script_space = (jpeg_scan_info *)
5697dd7cddfSDavid du Colombier       (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_PERMANENT,
570*593dc095SDavid du Colombier 			cinfo->script_space_size * SIZEOF(jpeg_scan_info));
571*593dc095SDavid du Colombier   }
572*593dc095SDavid du Colombier   scanptr = cinfo->script_space;
5737dd7cddfSDavid du Colombier   cinfo->scan_info = scanptr;
5747dd7cddfSDavid du Colombier   cinfo->num_scans = nscans;
5757dd7cddfSDavid du Colombier 
5767dd7cddfSDavid du Colombier   if (ncomps == 3 && cinfo->jpeg_color_space == JCS_YCbCr) {
5777dd7cddfSDavid du Colombier     /* Custom script for YCbCr color images. */
5787dd7cddfSDavid du Colombier     /* Initial DC scan */
5797dd7cddfSDavid du Colombier     scanptr = fill_dc_scans(scanptr, ncomps, 0, 1);
5807dd7cddfSDavid du Colombier     /* Initial AC scan: get some luma data out in a hurry */
5817dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 0, 1, 5, 0, 2);
5827dd7cddfSDavid du Colombier     /* Chroma data is too small to be worth expending many scans on */
5837dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 2, 1, 63, 0, 1);
5847dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 1, 1, 63, 0, 1);
5857dd7cddfSDavid du Colombier     /* Complete spectral selection for luma AC */
5867dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 0, 6, 63, 0, 2);
5877dd7cddfSDavid du Colombier     /* Refine next bit of luma AC */
5887dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 0, 1, 63, 2, 1);
5897dd7cddfSDavid du Colombier     /* Finish DC successive approximation */
5907dd7cddfSDavid du Colombier     scanptr = fill_dc_scans(scanptr, ncomps, 1, 0);
5917dd7cddfSDavid du Colombier     /* Finish AC successive approximation */
5927dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 2, 1, 63, 1, 0);
5937dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 1, 1, 63, 1, 0);
5947dd7cddfSDavid du Colombier     /* Luma bottom bit comes last since it's usually largest scan */
5957dd7cddfSDavid du Colombier     scanptr = fill_a_scan(scanptr, 0, 1, 63, 1, 0);
5967dd7cddfSDavid du Colombier   } else {
5977dd7cddfSDavid du Colombier     /* All-purpose script for other color spaces. */
5987dd7cddfSDavid du Colombier     /* Successive approximation first pass */
5997dd7cddfSDavid du Colombier     scanptr = fill_dc_scans(scanptr, ncomps, 0, 1);
6007dd7cddfSDavid du Colombier     scanptr = fill_scans(scanptr, ncomps, 1, 5, 0, 2);
6017dd7cddfSDavid du Colombier     scanptr = fill_scans(scanptr, ncomps, 6, 63, 0, 2);
6027dd7cddfSDavid du Colombier     /* Successive approximation second pass */
6037dd7cddfSDavid du Colombier     scanptr = fill_scans(scanptr, ncomps, 1, 63, 2, 1);
6047dd7cddfSDavid du Colombier     /* Successive approximation final pass */
6057dd7cddfSDavid du Colombier     scanptr = fill_dc_scans(scanptr, ncomps, 1, 0);
6067dd7cddfSDavid du Colombier     scanptr = fill_scans(scanptr, ncomps, 1, 63, 1, 0);
6077dd7cddfSDavid du Colombier   }
6087dd7cddfSDavid du Colombier }
6097dd7cddfSDavid du Colombier 
6107dd7cddfSDavid du Colombier #endif /* C_PROGRESSIVE_SUPPORTED */
611