diff options
author | Robin Watts <robin.watts@artifex.com> | 2017-02-24 18:21:12 +0000 |
---|---|---|
committer | Robin Watts <robin.watts@artifex.com> | 2017-02-27 15:34:10 +0000 |
commit | 009e40a0534e1d11ed5ee353477859b5cdd4faed (patch) | |
tree | 377e5e5c82cc2153475f24b109229aa80fee3c34 /base/gxiscale.c | |
parent | af3c1d10726b2d932d951bf021193cbd5bcc734d (diff) | |
download | ghostpdl-009e40a0534e1d11ed5ee353477859b5cdd4faed.tar.gz |
Bug 696921: Don't "early decode" when interpolating Lab images
Applying the decode array to Lab source values during the
conversion to fracs that takes place before non-icc based
interpolation causes an overflow.
We therefore leave the application of the decode array until
after the interpolation.
After the interpolation, we don't actually want to apply the
decode array though - in that we want the result in the usual
0...1 float form rather than the 0..100/-128..127/-128...127
ranges that the color would seem to require.
One option would be simply to not apply the decode array. This
will however go wrong when we meet an Lab file with a
non-standard Decode array. We therefore apply the given decode
array (which may well be the default), and 'undo' the default
one to get the values we actually want.
Diffstat (limited to 'base/gxiscale.c')
-rw-r--r-- | base/gxiscale.c | 68 |
1 files changed, 47 insertions, 21 deletions
diff --git a/base/gxiscale.c b/base/gxiscale.c index 456287195..115c889cf 100644 --- a/base/gxiscale.c +++ b/base/gxiscale.c @@ -789,24 +789,24 @@ initial_decode(gx_image_enum * penum, const byte * buffer, int data_x, int h, stream_r->ptr = (byte *) pdata - 1; } } else { - for (i = 0; i < pss->params.WidthIn; i++, - psrc += spp_decode) { - /* Lets get directly to a frac type loaded into psrc, - and do the interpolation in the source space. Then we - will do the appropriate remap function after - interpolation. */ - for (j = 0; j < dc; ++j) { - DECODE_FRAC_FRAC(((const frac *)pdata)[j], psrc[j], j); - } - pdata += dpd; + if (sizeof(frac) * dc == dpd) { + stream_r->ptr = (byte *) pdata - 1; + } else { + for (i = 0; i < pss->params.WidthIn; i++, + psrc += spp_decode) { + for (j = 0; j < dc; ++j) { + psrc[j] = ((const frac *)pdata)[j]; + } + pdata += dpd; #ifdef DEBUG - if (gs_debug_c('B')) { - int ci; + if (gs_debug_c('B')) { + int ci; - for (ci = 0; ci < spp_decode; ++ci) - dmprintf2(penum->memory, "%c%04x", (ci == 0 ? ' ' : ','), psrc[ci]); - } + for (ci = 0; ci < spp_decode; ++ci) + dmprintf2(penum->memory, "%c%04x", (ci == 0 ? ' ' : ','), psrc[ci]); + } #endif + } } } out += round_up(pss->params.WidthIn * spp_decode * sizeof(frac), @@ -901,13 +901,39 @@ static int handle_colors(gx_image_enum *penum, const frac *psrc, int spp_decode, int j; int num_components = gs_color_space_num_components(pactual_cs); - for (j = 0; j < num_components; ++j) { - /* If we were indexed, dont use the decode procedure for the index - values just get to float directly */ - if (is_index_space || islab) { - cc.paint.values[j] = frac2float(psrc[j]); + if (islab) { + /* LAB colors are normally decoded with a decode array + * of [0 100 -128 127 -128 127 ]. The color management + * however, expects this decode array NOT to have been + * applied. + * + * It would be possible for an LAB image to be given a + * non-standard decode array, in which case, we should + * take account of that. The easiest way is to apply the + * decode array as given, and then 'undo' the standard + * one. + */ + decode_sample_frac_to_float(penum, psrc[0], &cc, 0); + decode_sample_frac_to_float(penum, psrc[1], &cc, 1); + decode_sample_frac_to_float(penum, psrc[2], &cc, 2); + if (penum->bps <= 8) { + cc.paint.values[0] /= 100.0; + cc.paint.values[1] = (cc.paint.values[1] + 128) / 255.0; + cc.paint.values[2] = (cc.paint.values[2] + 128) / 255.0; } else { - decode_sample_frac_to_float(penum, psrc[j], &cc, j); + cc.paint.values[0] *= 0x7ff8 / 25500.0; + cc.paint.values[1] = (cc.paint.values[1] + 128) * 0x7ff8 / 65025.0; + cc.paint.values[2] = (cc.paint.values[2] + 128) * 0x7ff8 / 65025.0; + } + } else { + for (j = 0; j < num_components; ++j) { + /* If we were indexed, dont use the decode procedure for the index + values just get to float directly */ + if (is_index_space) { + cc.paint.values[j] = frac2float(psrc[j]); + } else { + decode_sample_frac_to_float(penum, psrc[j], &cc, j); + } } } /* If the source colors are LAB then use the mapping that does not |