blob: 12804f316aa91365840edf45200235c59c359cf0 [file] [log] [blame]
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +00001/*
2 * jccolor.c
3 *
Thomas G. Lane489583f1996-02-07 00:00:00 +00004 * Copyright (C) 1991-1996, Thomas G. Lane.
Pierre Ossman59a39382009-03-09 13:15:56 +00005 * Copyright 2009 Pierre Ossman <ossman@cendio.se> for Cendio AB
DRCb4570bb2011-09-07 06:31:00 +00006 * Copyright (C) 2009-2011, D. R. Commander.
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +00007 * This file is part of the Independent JPEG Group's software.
8 * For conditions of distribution and use, see the accompanying README file.
9 *
10 * This file contains input colorspace conversion routines.
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +000011 */
12
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +000013#define JPEG_INTERNALS
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +000014#include "jinclude.h"
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +000015#include "jpeglib.h"
Pierre Ossman59a39382009-03-09 13:15:56 +000016#include "jsimd.h"
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +000017
18
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +000019/* Private subobject */
20
21typedef struct {
22 struct jpeg_color_converter pub; /* public fields */
23
24 /* Private state for RGB->YCC conversion */
25 INT32 * rgb_ycc_tab; /* => table for RGB to YCbCr conversion */
26} my_color_converter;
27
28typedef my_color_converter * my_cconvert_ptr;
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +000029
30
Thomas G. Lane88aeed41992-12-10 00:00:00 +000031/**************** RGB -> YCbCr conversion: most common case **************/
32
33/*
34 * YCbCr is defined per CCIR 601-1, except that Cb and Cr are
35 * normalized to the range 0..MAXJSAMPLE rather than -0.5 .. 0.5.
36 * The conversion equations to be implemented are therefore
37 * Y = 0.29900 * R + 0.58700 * G + 0.11400 * B
Thomas G. Lane9ba2f5e1994-12-07 00:00:00 +000038 * Cb = -0.16874 * R - 0.33126 * G + 0.50000 * B + CENTERJSAMPLE
39 * Cr = 0.50000 * R - 0.41869 * G - 0.08131 * B + CENTERJSAMPLE
Thomas G. Lane88aeed41992-12-10 00:00:00 +000040 * (These numbers are derived from TIFF 6.0 section 21, dated 3-June-92.)
Thomas G. Lane9ba2f5e1994-12-07 00:00:00 +000041 * Note: older versions of the IJG code used a zero offset of MAXJSAMPLE/2,
42 * rather than CENTERJSAMPLE, for Cb and Cr. This gave equal positive and
43 * negative swings for Cb/Cr, but meant that grayscale values (Cb=Cr=0)
44 * were not represented exactly. Now we sacrifice exact representation of
45 * maximum red and maximum blue in order to get exact grayscales.
Thomas G. Lane88aeed41992-12-10 00:00:00 +000046 *
47 * To avoid floating-point arithmetic, we represent the fractional constants
48 * as integers scaled up by 2^16 (about 4 digits precision); we have to divide
49 * the products by 2^16, with appropriate rounding, to get the correct answer.
50 *
51 * For even more speed, we avoid doing any multiplications in the inner loop
52 * by precalculating the constants times R,G,B for all possible values.
53 * For 8-bit JSAMPLEs this is very reasonable (only 256 entries per table);
54 * for 12-bit samples it is still acceptable. It's not very reasonable for
55 * 16-bit samples, but if you want lossless storage you shouldn't be changing
56 * colorspace anyway.
Thomas G. Lane9ba2f5e1994-12-07 00:00:00 +000057 * The CENTERJSAMPLE offsets and the rounding fudge-factor of 0.5 are included
Thomas G. Lane88aeed41992-12-10 00:00:00 +000058 * in the tables to save adding them separately in the inner loop.
59 */
60
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +000061#define SCALEBITS 16 /* speediest right-shift on some machines */
Thomas G. Lane9ba2f5e1994-12-07 00:00:00 +000062#define CBCR_OFFSET ((INT32) CENTERJSAMPLE << SCALEBITS)
Thomas G. Lane88aeed41992-12-10 00:00:00 +000063#define ONE_HALF ((INT32) 1 << (SCALEBITS-1))
64#define FIX(x) ((INT32) ((x) * (1L<<SCALEBITS) + 0.5))
65
66/* We allocate one big table and divide it up into eight parts, instead of
67 * doing eight alloc_small requests. This lets us use a single table base
68 * address, which can be held in a register in the inner loops on many
69 * machines (more than can hold all eight addresses, anyway).
70 */
71
Thomas G. Lane88aeed41992-12-10 00:00:00 +000072#define R_Y_OFF 0 /* offset to R => Y section */
73#define G_Y_OFF (1*(MAXJSAMPLE+1)) /* offset to G => Y section */
74#define B_Y_OFF (2*(MAXJSAMPLE+1)) /* etc. */
75#define R_CB_OFF (3*(MAXJSAMPLE+1))
76#define G_CB_OFF (4*(MAXJSAMPLE+1))
77#define B_CB_OFF (5*(MAXJSAMPLE+1))
78#define R_CR_OFF B_CB_OFF /* B=>Cb, R=>Cr are the same */
79#define G_CR_OFF (6*(MAXJSAMPLE+1))
80#define B_CR_OFF (7*(MAXJSAMPLE+1))
81#define TABLE_SIZE (8*(MAXJSAMPLE+1))
82
83
DRCb4570bb2011-09-07 06:31:00 +000084/* Include inline routines for colorspace extensions */
85
86#include "jccolext.c"
87#undef RGB_RED
88#undef RGB_GREEN
89#undef RGB_BLUE
90#undef RGB_PIXELSIZE
91
92#define RGB_RED EXT_RGB_RED
93#define RGB_GREEN EXT_RGB_GREEN
94#define RGB_BLUE EXT_RGB_BLUE
95#define RGB_PIXELSIZE EXT_RGB_PIXELSIZE
96#define rgb_ycc_convert_internal extrgb_ycc_convert_internal
97#define rgb_gray_convert_internal extrgb_gray_convert_internal
98#include "jccolext.c"
99#undef RGB_RED
100#undef RGB_GREEN
101#undef RGB_BLUE
102#undef RGB_PIXELSIZE
103#undef rgb_ycc_convert_internal
104#undef rgb_gray_convert_internal
105
106#define RGB_RED EXT_RGBX_RED
107#define RGB_GREEN EXT_RGBX_GREEN
108#define RGB_BLUE EXT_RGBX_BLUE
109#define RGB_PIXELSIZE EXT_RGBX_PIXELSIZE
110#define rgb_ycc_convert_internal extrgbx_ycc_convert_internal
111#define rgb_gray_convert_internal extrgbx_gray_convert_internal
112#include "jccolext.c"
113#undef RGB_RED
114#undef RGB_GREEN
115#undef RGB_BLUE
116#undef RGB_PIXELSIZE
117#undef rgb_ycc_convert_internal
118#undef rgb_gray_convert_internal
119
120#define RGB_RED EXT_BGR_RED
121#define RGB_GREEN EXT_BGR_GREEN
122#define RGB_BLUE EXT_BGR_BLUE
123#define RGB_PIXELSIZE EXT_BGR_PIXELSIZE
124#define rgb_ycc_convert_internal extbgr_ycc_convert_internal
125#define rgb_gray_convert_internal extbgr_gray_convert_internal
126#include "jccolext.c"
127#undef RGB_RED
128#undef RGB_GREEN
129#undef RGB_BLUE
130#undef RGB_PIXELSIZE
131#undef rgb_ycc_convert_internal
132#undef rgb_gray_convert_internal
133
134#define RGB_RED EXT_BGRX_RED
135#define RGB_GREEN EXT_BGRX_GREEN
136#define RGB_BLUE EXT_BGRX_BLUE
137#define RGB_PIXELSIZE EXT_BGRX_PIXELSIZE
138#define rgb_ycc_convert_internal extbgrx_ycc_convert_internal
139#define rgb_gray_convert_internal extbgrx_gray_convert_internal
140#include "jccolext.c"
141#undef RGB_RED
142#undef RGB_GREEN
143#undef RGB_BLUE
144#undef RGB_PIXELSIZE
145#undef rgb_ycc_convert_internal
146#undef rgb_gray_convert_internal
147
148#define RGB_RED EXT_XBGR_RED
149#define RGB_GREEN EXT_XBGR_GREEN
150#define RGB_BLUE EXT_XBGR_BLUE
151#define RGB_PIXELSIZE EXT_XBGR_PIXELSIZE
152#define rgb_ycc_convert_internal extxbgr_ycc_convert_internal
153#define rgb_gray_convert_internal extxbgr_gray_convert_internal
154#include "jccolext.c"
155#undef RGB_RED
156#undef RGB_GREEN
157#undef RGB_BLUE
158#undef RGB_PIXELSIZE
159#undef rgb_ycc_convert_internal
160#undef rgb_gray_convert_internal
161
162#define RGB_RED EXT_XRGB_RED
163#define RGB_GREEN EXT_XRGB_GREEN
164#define RGB_BLUE EXT_XRGB_BLUE
165#define RGB_PIXELSIZE EXT_XRGB_PIXELSIZE
166#define rgb_ycc_convert_internal extxrgb_ycc_convert_internal
167#define rgb_gray_convert_internal extxrgb_gray_convert_internal
168#include "jccolext.c"
169#undef RGB_RED
170#undef RGB_GREEN
171#undef RGB_BLUE
172#undef RGB_PIXELSIZE
173#undef rgb_ycc_convert_internal
174#undef rgb_gray_convert_internal
175
176
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000177/*
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000178 * Initialize for RGB->YCC colorspace conversion.
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000179 */
180
Thomas G. Lane489583f1996-02-07 00:00:00 +0000181METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000182rgb_ycc_start (j_compress_ptr cinfo)
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000183{
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000184 my_cconvert_ptr cconvert = (my_cconvert_ptr) cinfo->cconvert;
185 INT32 * rgb_ycc_tab;
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000186 INT32 i;
187
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000188 /* Allocate and fill in the conversion tables. */
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000189 cconvert->rgb_ycc_tab = rgb_ycc_tab = (INT32 *)
190 (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE,
191 (TABLE_SIZE * SIZEOF(INT32)));
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000192
193 for (i = 0; i <= MAXJSAMPLE; i++) {
194 rgb_ycc_tab[i+R_Y_OFF] = FIX(0.29900) * i;
195 rgb_ycc_tab[i+G_Y_OFF] = FIX(0.58700) * i;
196 rgb_ycc_tab[i+B_Y_OFF] = FIX(0.11400) * i + ONE_HALF;
197 rgb_ycc_tab[i+R_CB_OFF] = (-FIX(0.16874)) * i;
198 rgb_ycc_tab[i+G_CB_OFF] = (-FIX(0.33126)) * i;
Thomas G. Lane9ba2f5e1994-12-07 00:00:00 +0000199 /* We use a rounding fudge-factor of 0.5-epsilon for Cb and Cr.
200 * This ensures that the maximum output will round to MAXJSAMPLE
201 * not MAXJSAMPLE+1, and thus that we don't have to range-limit.
202 */
203 rgb_ycc_tab[i+B_CB_OFF] = FIX(0.50000) * i + CBCR_OFFSET + ONE_HALF-1;
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000204/* B=>Cb and R=>Cr tables are the same
Thomas G. Lane9ba2f5e1994-12-07 00:00:00 +0000205 rgb_ycc_tab[i+R_CR_OFF] = FIX(0.50000) * i + CBCR_OFFSET + ONE_HALF-1;
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000206*/
207 rgb_ycc_tab[i+G_CR_OFF] = (-FIX(0.41869)) * i;
208 rgb_ycc_tab[i+B_CR_OFF] = (-FIX(0.08131)) * i;
209 }
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000210}
211
212
213/*
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000214 * Convert some rows of samples to the JPEG colorspace.
Thomas G. Lane4a6b7301992-03-17 00:00:00 +0000215 */
216
Thomas G. Lane489583f1996-02-07 00:00:00 +0000217METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000218rgb_ycc_convert (j_compress_ptr cinfo,
219 JSAMPARRAY input_buf, JSAMPIMAGE output_buf,
220 JDIMENSION output_row, int num_rows)
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000221{
DRCb4570bb2011-09-07 06:31:00 +0000222 switch (cinfo->in_color_space) {
223 case JCS_EXT_RGB:
224 extrgb_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
225 num_rows);
226 break;
227 case JCS_EXT_RGBX:
228 extrgbx_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
229 num_rows);
230 break;
231 case JCS_EXT_BGR:
232 extbgr_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
233 num_rows);
234 break;
235 case JCS_EXT_BGRX:
236 extbgrx_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
237 num_rows);
238 break;
239 case JCS_EXT_XBGR:
240 extxbgr_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
241 num_rows);
242 break;
243 case JCS_EXT_XRGB:
244 extxrgb_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
245 num_rows);
246 break;
247 default:
248 rgb_ycc_convert_internal(cinfo, input_buf, output_buf, output_row,
249 num_rows);
250 break;
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000251 }
252}
253
254
255/**************** Cases other than RGB -> YCbCr **************/
256
257
258/*
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000259 * Convert some rows of samples to the JPEG colorspace.
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000260 */
261
Thomas G. Lane489583f1996-02-07 00:00:00 +0000262METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000263rgb_gray_convert (j_compress_ptr cinfo,
264 JSAMPARRAY input_buf, JSAMPIMAGE output_buf,
265 JDIMENSION output_row, int num_rows)
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000266{
DRCb4570bb2011-09-07 06:31:00 +0000267 switch (cinfo->in_color_space) {
268 case JCS_EXT_RGB:
269 extrgb_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
270 num_rows);
271 break;
272 case JCS_EXT_RGBX:
273 extrgbx_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
274 num_rows);
275 break;
276 case JCS_EXT_BGR:
277 extbgr_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
278 num_rows);
279 break;
280 case JCS_EXT_BGRX:
281 extbgrx_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
282 num_rows);
283 break;
284 case JCS_EXT_XBGR:
285 extxbgr_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
286 num_rows);
287 break;
288 case JCS_EXT_XRGB:
289 extxrgb_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
290 num_rows);
291 break;
292 default:
293 rgb_gray_convert_internal(cinfo, input_buf, output_buf, output_row,
294 num_rows);
295 break;
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000296 }
297}
298
299
300/*
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000301 * Convert some rows of samples to the JPEG colorspace.
302 * This version handles Adobe-style CMYK->YCCK conversion,
303 * where we convert R=1-C, G=1-M, and B=1-Y to YCbCr using the same
304 * conversion as above, while passing K (black) unchanged.
305 * We assume rgb_ycc_start has been called.
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000306 */
307
Thomas G. Lane489583f1996-02-07 00:00:00 +0000308METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000309cmyk_ycck_convert (j_compress_ptr cinfo,
310 JSAMPARRAY input_buf, JSAMPIMAGE output_buf,
311 JDIMENSION output_row, int num_rows)
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000312{
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000313 my_cconvert_ptr cconvert = (my_cconvert_ptr) cinfo->cconvert;
314 register int r, g, b;
315 register INT32 * ctab = cconvert->rgb_ycc_tab;
316 register JSAMPROW inptr;
317 register JSAMPROW outptr0, outptr1, outptr2, outptr3;
318 register JDIMENSION col;
319 JDIMENSION num_cols = cinfo->image_width;
Thomas G. Lane88aeed41992-12-10 00:00:00 +0000320
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000321 while (--num_rows >= 0) {
322 inptr = *input_buf++;
323 outptr0 = output_buf[0][output_row];
324 outptr1 = output_buf[1][output_row];
325 outptr2 = output_buf[2][output_row];
326 outptr3 = output_buf[3][output_row];
327 output_row++;
328 for (col = 0; col < num_cols; col++) {
329 r = MAXJSAMPLE - GETJSAMPLE(inptr[0]);
330 g = MAXJSAMPLE - GETJSAMPLE(inptr[1]);
331 b = MAXJSAMPLE - GETJSAMPLE(inptr[2]);
332 /* K passes through as-is */
333 outptr3[col] = inptr[3]; /* don't need GETJSAMPLE here */
334 inptr += 4;
335 /* If the inputs are 0..MAXJSAMPLE, the outputs of these equations
336 * must be too; we do not need an explicit range-limiting operation.
337 * Hence the value being shifted is never negative, and we don't
338 * need the general RIGHT_SHIFT macro.
339 */
340 /* Y */
341 outptr0[col] = (JSAMPLE)
342 ((ctab[r+R_Y_OFF] + ctab[g+G_Y_OFF] + ctab[b+B_Y_OFF])
343 >> SCALEBITS);
344 /* Cb */
345 outptr1[col] = (JSAMPLE)
346 ((ctab[r+R_CB_OFF] + ctab[g+G_CB_OFF] + ctab[b+B_CB_OFF])
347 >> SCALEBITS);
348 /* Cr */
349 outptr2[col] = (JSAMPLE)
350 ((ctab[r+R_CR_OFF] + ctab[g+G_CR_OFF] + ctab[b+B_CR_OFF])
351 >> SCALEBITS);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000352 }
353 }
354}
355
356
357/*
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000358 * Convert some rows of samples to the JPEG colorspace.
359 * This version handles grayscale output with no conversion.
360 * The source can be either plain grayscale or YCbCr (since Y == gray).
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000361 */
362
Thomas G. Lane489583f1996-02-07 00:00:00 +0000363METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000364grayscale_convert (j_compress_ptr cinfo,
365 JSAMPARRAY input_buf, JSAMPIMAGE output_buf,
366 JDIMENSION output_row, int num_rows)
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000367{
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000368 register JSAMPROW inptr;
369 register JSAMPROW outptr;
370 register JDIMENSION col;
371 JDIMENSION num_cols = cinfo->image_width;
372 int instride = cinfo->input_components;
373
374 while (--num_rows >= 0) {
375 inptr = *input_buf++;
376 outptr = output_buf[0][output_row];
377 output_row++;
378 for (col = 0; col < num_cols; col++) {
379 outptr[col] = inptr[0]; /* don't need GETJSAMPLE() here */
380 inptr += instride;
381 }
382 }
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000383}
384
385
386/*
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000387 * Convert some rows of samples to the JPEG colorspace.
388 * This version handles multi-component colorspaces without conversion.
389 * We assume input_components == num_components.
390 */
391
Thomas G. Lane489583f1996-02-07 00:00:00 +0000392METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000393null_convert (j_compress_ptr cinfo,
394 JSAMPARRAY input_buf, JSAMPIMAGE output_buf,
395 JDIMENSION output_row, int num_rows)
396{
397 register JSAMPROW inptr;
398 register JSAMPROW outptr;
399 register JDIMENSION col;
400 register int ci;
401 int nc = cinfo->num_components;
402 JDIMENSION num_cols = cinfo->image_width;
403
404 while (--num_rows >= 0) {
405 /* It seems fastest to make a separate pass for each component. */
406 for (ci = 0; ci < nc; ci++) {
407 inptr = *input_buf;
408 outptr = output_buf[ci][output_row];
409 for (col = 0; col < num_cols; col++) {
410 outptr[col] = inptr[ci]; /* don't need GETJSAMPLE() here */
411 inptr += nc;
412 }
413 }
414 input_buf++;
415 output_row++;
416 }
417}
418
419
420/*
421 * Empty method for start_pass.
422 */
423
Thomas G. Lane489583f1996-02-07 00:00:00 +0000424METHODDEF(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000425null_method (j_compress_ptr cinfo)
426{
427 /* no work needed */
428}
429
430
431/*
432 * Module initialization routine for input colorspace conversion.
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000433 */
434
Thomas G. Lane489583f1996-02-07 00:00:00 +0000435GLOBAL(void)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000436jinit_color_converter (j_compress_ptr cinfo)
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000437{
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000438 my_cconvert_ptr cconvert;
439
440 cconvert = (my_cconvert_ptr)
441 (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE,
442 SIZEOF(my_color_converter));
443 cinfo->cconvert = (struct jpeg_color_converter *) cconvert;
444 /* set start_pass to null method until we find out differently */
445 cconvert->pub.start_pass = null_method;
446
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000447 /* Make sure input_components agrees with in_color_space */
448 switch (cinfo->in_color_space) {
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000449 case JCS_GRAYSCALE:
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000450 if (cinfo->input_components != 1)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000451 ERREXIT(cinfo, JERR_BAD_IN_COLORSPACE);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000452 break;
453
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000454 case JCS_RGB:
DRCf25c0712009-04-03 12:00:51 +0000455 case JCS_EXT_RGB:
456 case JCS_EXT_RGBX:
457 case JCS_EXT_BGR:
458 case JCS_EXT_BGRX:
459 case JCS_EXT_XBGR:
460 case JCS_EXT_XRGB:
461 if (cinfo->input_components != rgb_pixelsize[cinfo->in_color_space])
462 ERREXIT(cinfo, JERR_BAD_IN_COLORSPACE);
463 break;
464
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000465 case JCS_YCbCr:
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000466 if (cinfo->input_components != 3)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000467 ERREXIT(cinfo, JERR_BAD_IN_COLORSPACE);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000468 break;
469
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000470 case JCS_CMYK:
471 case JCS_YCCK:
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000472 if (cinfo->input_components != 4)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000473 ERREXIT(cinfo, JERR_BAD_IN_COLORSPACE);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000474 break;
475
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000476 default: /* JCS_UNKNOWN can be anything */
477 if (cinfo->input_components < 1)
478 ERREXIT(cinfo, JERR_BAD_IN_COLORSPACE);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000479 break;
480 }
481
482 /* Check num_components, set conversion method based on requested space */
483 switch (cinfo->jpeg_color_space) {
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000484 case JCS_GRAYSCALE:
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000485 if (cinfo->num_components != 1)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000486 ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
487 if (cinfo->in_color_space == JCS_GRAYSCALE)
488 cconvert->pub.color_convert = grayscale_convert;
DRCf25c0712009-04-03 12:00:51 +0000489 else if (cinfo->in_color_space == JCS_RGB ||
490 cinfo->in_color_space == JCS_EXT_RGB ||
491 cinfo->in_color_space == JCS_EXT_RGBX ||
492 cinfo->in_color_space == JCS_EXT_BGR ||
493 cinfo->in_color_space == JCS_EXT_BGRX ||
494 cinfo->in_color_space == JCS_EXT_XBGR ||
495 cinfo->in_color_space == JCS_EXT_XRGB) {
DRCc8666332011-02-18 11:23:45 +0000496 if (jsimd_can_rgb_gray())
497 cconvert->pub.color_convert = jsimd_rgb_gray_convert;
498 else {
499 cconvert->pub.start_pass = rgb_ycc_start;
500 cconvert->pub.color_convert = rgb_gray_convert;
501 }
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000502 } else if (cinfo->in_color_space == JCS_YCbCr)
503 cconvert->pub.color_convert = grayscale_convert;
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000504 else
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000505 ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000506 break;
507
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000508 case JCS_RGB:
DRCf25c0712009-04-03 12:00:51 +0000509 case JCS_EXT_RGB:
510 case JCS_EXT_RGBX:
511 case JCS_EXT_BGR:
512 case JCS_EXT_BGRX:
513 case JCS_EXT_XBGR:
514 case JCS_EXT_XRGB:
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000515 if (cinfo->num_components != 3)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000516 ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
DRCf25c0712009-04-03 12:00:51 +0000517 if (cinfo->in_color_space == cinfo->jpeg_color_space &&
518 rgb_pixelsize[cinfo->in_color_space] == 3)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000519 cconvert->pub.color_convert = null_convert;
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000520 else
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000521 ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000522 break;
523
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000524 case JCS_YCbCr:
525 if (cinfo->num_components != 3)
526 ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
DRCf25c0712009-04-03 12:00:51 +0000527 if (cinfo->in_color_space == JCS_RGB ||
528 cinfo->in_color_space == JCS_EXT_RGB ||
529 cinfo->in_color_space == JCS_EXT_RGBX ||
530 cinfo->in_color_space == JCS_EXT_BGR ||
531 cinfo->in_color_space == JCS_EXT_BGRX ||
532 cinfo->in_color_space == JCS_EXT_XBGR ||
533 cinfo->in_color_space == JCS_EXT_XRGB) {
Pierre Ossman59a39382009-03-09 13:15:56 +0000534 if (jsimd_can_rgb_ycc())
535 cconvert->pub.color_convert = jsimd_rgb_ycc_convert;
536 else {
537 cconvert->pub.start_pass = rgb_ycc_start;
538 cconvert->pub.color_convert = rgb_ycc_convert;
539 }
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000540 } else if (cinfo->in_color_space == JCS_YCbCr)
541 cconvert->pub.color_convert = null_convert;
542 else
543 ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
544 break;
545
546 case JCS_CMYK:
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000547 if (cinfo->num_components != 4)
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000548 ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
549 if (cinfo->in_color_space == JCS_CMYK)
550 cconvert->pub.color_convert = null_convert;
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000551 else
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000552 ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000553 break;
554
Thomas G. Lane36a4ccc1994-09-24 00:00:00 +0000555 case JCS_YCCK:
556 if (cinfo->num_components != 4)
557 ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
558 if (cinfo->in_color_space == JCS_CMYK) {
559 cconvert->pub.start_pass = rgb_ycc_start;
560 cconvert->pub.color_convert = cmyk_ycck_convert;
561 } else if (cinfo->in_color_space == JCS_YCCK)
562 cconvert->pub.color_convert = null_convert;
563 else
564 ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
565 break;
566
567 default: /* allow null conversion of JCS_UNKNOWN */
568 if (cinfo->jpeg_color_space != cinfo->in_color_space ||
569 cinfo->num_components != cinfo->input_components)
570 ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
571 cconvert->pub.color_convert = null_convert;
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000572 break;
573 }
Thomas G. Lane2cbeb8a1991-10-07 00:00:00 +0000574}