Coverage Report

Created: 2025-06-10 06:49

/src/ghostpdl/base/gxcht.c
Line
Count
Source (jump to first uncovered line)
1
/* Copyright (C) 2001-2023 Artifex Software, Inc.
2
   All Rights Reserved.
3
4
   This software is provided AS-IS with no warranty, either express or
5
   implied.
6
7
   This software is distributed under license and may not be copied,
8
   modified or distributed except as expressly authorized under the terms
9
   of the license contained in the file LICENSE in this distribution.
10
11
   Refer to licensing information at http://www.artifex.com or contact
12
   Artifex Software, Inc.,  39 Mesa Street, Suite 108A, San Francisco,
13
   CA 94129, USA, for further information.
14
*/
15
16
17
/* Color halftone rendering for Ghostscript imaging library */
18
#include "memory_.h"
19
#include "gx.h"
20
#include "gserrors.h"
21
#include "gsutil.h"   /* for id generation */
22
#include "gxarith.h"
23
#include "gxfixed.h"
24
#include "gxmatrix.h"
25
#include "gxdevice.h"
26
#include "gxcmap.h"
27
#include "gxdcolor.h"
28
#include "gxgstate.h"
29
#include "gzht.h"
30
#include "gsserial.h"
31
#include "gxdevsop.h"
32
33
/* Define whether to force use of the slow code, for testing. */
34
#define USE_SLOW_CODE 0
35
36
/* Define the size of the tile buffer allocated on the stack. */
37
42.4k
#define tile_longs_LARGE 256
38
#define tile_longs_SMALL 64
39
#if ARCH_SMALL_MEMORY
40
#  define tile_longs_allocated tile_longs_SMALL
41
#  define tile_longs tile_longs_SMALL
42
#else
43
#  define tile_longs_allocated tile_longs_LARGE
44
#  ifdef DEBUG
45
#    define tile_longs\
46
       (gs_debug_c('.') ? tile_longs_SMALL : tile_longs_LARGE)
47
#  else
48
42.4k
#    define tile_longs tile_longs_LARGE
49
#  endif
50
#endif
51
52
/* Define the colored halftone device color type. */
53
gs_private_st_ptrs1(st_dc_ht_colored, gx_device_color, "dc_ht_colored",
54
    dc_ht_colored_enum_ptrs, dc_ht_colored_reloc_ptrs, colors.colored.c_ht);
55
static dev_color_proc_save_dc(gx_dc_ht_colored_save_dc);
56
static dev_color_proc_get_dev_halftone(gx_dc_ht_colored_get_dev_halftone);
57
static dev_color_proc_load(gx_dc_ht_colored_load);
58
static dev_color_proc_fill_rectangle(gx_dc_ht_colored_fill_rectangle);
59
static dev_color_proc_equal(gx_dc_ht_colored_equal);
60
static dev_color_proc_write(gx_dc_ht_colored_write);
61
static dev_color_proc_read(gx_dc_ht_colored_read);
62
const gx_device_color_type_t gx_dc_type_data_ht_colored = {
63
    &st_dc_ht_colored,
64
    gx_dc_ht_colored_save_dc, gx_dc_ht_colored_get_dev_halftone,
65
    gx_dc_ht_get_phase,
66
    gx_dc_ht_colored_load, gx_dc_ht_colored_fill_rectangle,
67
    gx_dc_default_fill_masked, gx_dc_ht_colored_equal,
68
    gx_dc_ht_colored_write, gx_dc_ht_colored_read,
69
    gx_dc_ht_colored_get_nonzero_comps
70
};
71
#undef gx_dc_type_ht_colored
72
const gx_device_color_type_t *const gx_dc_type_ht_colored =
73
    &gx_dc_type_data_ht_colored;
74
154
#define gx_dc_type_ht_colored (&gx_dc_type_data_ht_colored)
75
76
/* save information about the operand device color */
77
static void
78
gx_dc_ht_colored_save_dc(const gx_device_color * pdevc,
79
                         gx_device_color_saved * psdc)
80
77
{
81
77
    psdc->type = pdevc->type;
82
77
    memcpy( psdc->colors.colored.c_base,
83
77
            pdevc->colors.colored.c_base,
84
77
            sizeof(psdc->colors.colored.c_base) );
85
77
    memcpy( psdc->colors.colored.c_level,
86
77
            pdevc->colors.colored.c_level,
87
77
            sizeof(psdc->colors.colored.c_base) );
88
77
    psdc->phase = pdevc->phase;
89
77
}
90
91
/* get the halftone used for the operand device color */
92
static const gx_device_halftone *
93
gx_dc_ht_colored_get_dev_halftone(const gx_device_color * pdevc)
94
2.28k
{
95
2.28k
    return pdevc->colors.colored.c_ht;
96
2.28k
}
97
98
/* Compare two colored halftones for equality. */
99
static bool
100
gx_dc_ht_colored_equal(const gx_device_color * pdevc1,
101
                       const gx_device_color * pdevc2)
102
9
{
103
9
    uint num_comp = pdevc1->colors.colored.num_components;
104
105
9
    if (pdevc2->type != pdevc1->type ||
106
9
        pdevc1->colors.colored.c_ht != pdevc2->colors.colored.c_ht ||
107
9
        pdevc1->phase.x != pdevc2->phase.x ||
108
9
        pdevc1->phase.y != pdevc2->phase.y ||
109
9
        num_comp != pdevc2->colors.colored.num_components
110
9
        )
111
4
        return false;
112
5
    return
113
5
        !memcmp(pdevc1->colors.colored.c_base,
114
5
                pdevc2->colors.colored.c_base,
115
5
                num_comp * sizeof(pdevc1->colors.colored.c_base[0])) &&
116
5
        !memcmp(pdevc1->colors.colored.c_level,
117
4
                pdevc2->colors.colored.c_level,
118
4
                num_comp * sizeof(pdevc1->colors.colored.c_level[0]));
119
9
}
120
121
/*
122
 * Flags to indicate the pieces of a colored halftone that are included
123
 * in its string representation. The first byte of the string holds this
124
 * set of flags.
125
 *
126
 * The case alpha = gx_max_color_value is by far the most common, so
127
 * special treatment is provided for this case.
128
 *
129
 * The halftone is never transmitted as part of a device color, so there
130
 * is no flag for it.
131
 */
132
enum {
133
   dc_ht_colored_has_base = 0x01,
134
   dc_ht_colored_has_level = 0x02,
135
   dc_ht_colored_has_phase_x = 0x04,
136
   dc_ht_colored_has_phase_y = 0x08,
137
};
138
139
/*
140
 * Serialize a device color that uses a traditional colored halftone.
141
 *
142
 * The number of components of a device color must match that of the
143
 * process color model, so it is not transmitted.
144
 *
145
 * The most common situation in which this routine is used is for 1-bit
146
 * per component devices. In that case, base[i] will always be 0 or 1,
147
 * and thus may be fit in a single bit.
148
 *
149
 * In many situations, one or more of the color component intensity
150
 * levels will be 0. The plane_mask field identifies those components
151
 * where this is not the case. By tansmitting the plane_mask, only those
152
 * components with non-zero levels need be transmitted.
153
 *
154
 * The case alpha = gx_max_color_value is by far the most common, so
155
 * special treatment is provided for this case.
156
 *
157
 *
158
 * Operands:
159
 *
160
 *  pdevc       pointer to device color to be serialized
161
 *
162
 *  psdc        pointer ot saved version of last serialized color (for
163
 *              this band)
164
 *
165
 *  dev         pointer to the current device, used to retrieve process
166
 *              color model information
167
 *
168
 *  pdata       pointer to buffer in which to write the data
169
 *
170
 *  psize       pointer to a location that, on entry, contains the size of
171
 *              the buffer pointed to by pdata; on return, the size of
172
 *              the data required or actually used will be written here.
173
 *
174
 * Returns:
175
 *  1, with *psize set to 0, if *psdc and *pdevc represent the same color
176
 *
177
 *  0, with *psize set to the amount of data written, if everything OK
178
 *
179
 *  gs_error_rangecheck, with *psize set to the size of buffer required,
180
 *  if *psize was not large enough
181
 *
182
 *  < 0, != gs_error_rangecheck, in the event of some other error
183
 *  (currently none); in this case *psize is not changed.
184
 */
185
static int
186
gx_dc_ht_colored_write(
187
    const gx_device_color *         pdevc,
188
    const gx_device_color_saved *   psdc0,
189
    const gx_device *               dev,
190
    int64_t         offset,
191
    byte *                          pdata,
192
    uint *                          psize )
193
2.36k
{
194
2.36k
    int                             req_size = 1;
195
2.36k
    int                             flag_bits = 0;
196
2.36k
    int                             num_comps = dev->color_info.num_components;
197
2.36k
    int                             depth = dev->color_info.depth;
198
2.36k
    gx_color_index                  plane_mask = pdevc->colors.colored.plane_mask;
199
2.36k
    const gx_device_color_saved *   psdc = psdc0;
200
2.36k
    byte *                          pdata0 = pdata;
201
202
2.36k
    if (offset != 0)
203
0
        return_error(gs_error_unregistered); /* Not implemented yet. */
204
205
    /* sanity check */
206
2.36k
    if (pdevc->colors.colored.num_components != num_comps)
207
0
        return_error(gs_error_unregistered); /* Must not happen. */
208
209
    /* check if saved color is of the same type */
210
2.36k
    if (psdc != 0 && psdc->type != pdevc->type)
211
148
        psdc = 0;
212
213
    /* calculate the size required */
214
2.36k
    if ( psdc == 0                                                         ||
215
2.36k
         memcmp( pdevc->colors.colored.c_base,
216
2.21k
                 psdc->colors.colored.c_base,
217
2.21k
                 num_comps * sizeof(pdevc->colors.colored.c_base[0]) ) != 0  ) {
218
150
        flag_bits |= dc_ht_colored_has_base;
219
150
        if (num_comps == depth)     /* 1 bit / component */
220
106
            req_size += (num_comps + 7) >> 3;
221
44
        else
222
44
            req_size += num_comps * sizeof(pdevc->colors.colored.c_base[0]);
223
150
    }
224
225
2.36k
    plane_mask = pdevc->colors.colored.plane_mask;
226
2.36k
    if ( psdc == NULL                                                       ||
227
2.36k
         memcmp( pdevc->colors.colored.c_level,
228
2.21k
                 psdc->colors.colored.c_level,
229
2.21k
                 num_comps * sizeof(pdevc->colors.colored.c_level[0]) ) != 0  ) {
230
154
        gx_color_index  comp_bit;
231
154
        int             i;
232
154
        uint            tmp_mask;
233
234
154
        flag_bits |= dc_ht_colored_has_level;
235
154
        if (num_comps > 8 * sizeof(uint)) {
236
0
            tmp_mask = (uint)plane_mask;
237
0
            req_size += enc_u_sizew(tmp_mask);
238
0
            tmp_mask = (uint)((plane_mask >> (8*sizeof(uint)-1)) >> 1);
239
0
            req_size += enc_u_sizew(tmp_mask);
240
154
        } else {
241
154
            tmp_mask = (uint)plane_mask;
242
154
            req_size += enc_u_sizew(tmp_mask);
243
154
        }
244
722
        for (i = 0, comp_bit = 0x1; i < num_comps; i++, comp_bit <<= 1) {
245
568
            if ((plane_mask & comp_bit) != 0)
246
394
                req_size += enc_u_sizew(pdevc->colors.colored.c_level[i]);
247
568
        }
248
154
    }
249
250
2.36k
    if (psdc == NULL || psdc->phase.x != pdevc->phase.x)
251
148
        flag_bits |= dc_ht_colored_has_phase_x, req_size += enc_u_sizew(pdevc->phase.x);
252
2.36k
    if (psdc == NULL || psdc->phase.y != pdevc->phase.y)
253
148
        flag_bits |= dc_ht_colored_has_phase_y, req_size += enc_u_sizew(pdevc->phase.y);
254
255
    /* see if there is anything to do */
256
2.36k
    if (flag_bits == 0) {
257
2.21k
        *psize = 0;
258
2.21k
        return 1;
259
2.21k
    }
260
261
    /* see if enough space is available */
262
154
    if (req_size > *psize) {
263
77
        *psize = req_size;
264
77
        return_error(gs_error_rangecheck);
265
77
    }
266
267
    /* write out the flag byte */
268
77
    *pdata++ = (byte)flag_bits;
269
270
    /* write out such other parts of the device color as required */
271
77
    if ((flag_bits & dc_ht_colored_has_base) != 0) {
272
75
        if (num_comps == depth) {
273
53
            gx_color_index  base_mask = 0;
274
53
            int             num_bytes = (num_comps + 7) >> 3;
275
53
            int             i;
276
277
265
            for (i = 0; i < num_comps; i++) {
278
212
                if (pdevc->colors.colored.c_base[i] != 0)
279
0
                    base_mask |= (gx_color_index)1 << i;
280
212
            }
281
106
            for (i = 0; i < num_bytes; i++, base_mask >>= 8)
282
53
                *pdata++ = (byte)base_mask;
283
53
        } else {
284
22
            memcpy( pdata,
285
22
                    pdevc->colors.colored.c_base,
286
22
                    num_comps * sizeof(pdevc->colors.colored.c_base[0]) );
287
22
            pdata += num_comps * sizeof(pdevc->colors.colored.c_base[0]);
288
22
        }
289
75
    }
290
291
77
    if ((flag_bits & dc_ht_colored_has_level) != 0) {
292
77
        gx_color_index  code_bit;
293
77
        int             i;
294
77
        uint            tmp_mask;
295
296
77
        if (num_comps > 8 * sizeof(uint)) {
297
0
            tmp_mask = (uint)plane_mask;
298
0
            enc_u_putw(tmp_mask, pdata);
299
0
            tmp_mask = (uint)((plane_mask >> (8*sizeof(uint)-1))>>1);
300
0
            enc_u_putw(tmp_mask, pdata);
301
77
        } else {
302
77
            tmp_mask = (uint)plane_mask;
303
77
            enc_u_putw(tmp_mask, pdata);
304
77
        }
305
361
        for (i = 0, code_bit = 0x1; i < num_comps; i++, code_bit <<= 1) {
306
284
            if ((plane_mask & code_bit) != 0)
307
284
                enc_u_putw(pdevc->colors.colored.c_level[i], pdata);
308
284
        }
309
77
    }
310
311
77
    if ((flag_bits & dc_ht_colored_has_phase_x) != 0) {
312
74
        enc_u_putw(pdevc->phase.x, pdata);
313
74
    }
314
77
    if ((flag_bits & dc_ht_colored_has_phase_x) != 0) {
315
74
        enc_u_putw(pdevc->phase.y, pdata);
316
74
    }
317
318
77
    *psize = pdata - pdata0;
319
77
    return 0;
320
154
}
321
322
/*
323
 * Reconstruct a device color from its serial representation.
324
 *
325
 * Operands:
326
 *
327
 *  pdevc       pointer to the location in which to write the
328
 *              reconstructed device color
329
 *
330
 *  pgs         pointer to the current gs_gstate (to access the
331
 *              current halftone)
332
 *
333
 *  prior_devc  pointer to the current device color (this is provided
334
 *              separately because the device color is not part of the
335
 *              gs_gstate)
336
 *
337
 *  dev         pointer to the current device, used to retrieve process
338
 *              color model information
339
 *
340
 *  pdata       pointer to the buffer to be read
341
 *
342
 *  size        size of the buffer to be read; this should be large
343
 *              enough to hold the entire color description
344
 *
345
 *  mem         pointer to the memory to be used for allocations
346
 *              (ignored here)
347
 *
348
 * Returns:
349
 *
350
 *  # of bytes read if everthing OK, < 0 in the event of an error
351
 */
352
static int
353
gx_dc_ht_colored_read(
354
    gx_device_color *       pdevc,
355
    const gs_gstate *       pgs,
356
    const gx_device_color * prior_devc,
357
    const gx_device *       dev,
358
    int64_t                 offset,
359
    const byte *            pdata,
360
    uint                    size,
361
    gs_memory_t *           mem,        /* ignored */
362
    int                     x0,
363
    int                     y0)
364
77
{
365
77
    gx_device_color         devc;
366
77
    int                     num_comps = dev->color_info.num_components;
367
77
    int                     depth = dev->color_info.depth;
368
77
    const byte *            pdata0 = pdata;
369
77
    int                     flag_bits;
370
371
77
    if (offset != 0)
372
0
        return_error(gs_error_unregistered); /* Not implemented yet. */
373
374
    /* if prior information is available, use it */
375
77
    if (prior_devc != 0 && prior_devc->type == gx_dc_type_ht_colored)
376
6
        devc = *prior_devc;
377
71
    else
378
71
        memset(&devc, 0, sizeof(devc));   /* clear pointers */
379
77
    devc.type = gx_dc_type_ht_colored;
380
381
    /* the number of components is determined by the color model */
382
77
    devc.colors.colored.num_components = num_comps;
383
77
    devc.colors.colored.c_ht = pgs->dev_ht[HT_OBJTYPE_DEFAULT];
384
385
    /*
386
     * Verify that we have at least the flag bits. For performance
387
     * reasons, the routines that convert serialized representations
388
     * of integers do not check buffer size. Hence, in many cases below,
389
     * only a very rough check is made to verify that we have not
390
     * exhausted the buffer. This should not cause a problem in
391
     * practice.
392
     */
393
77
    if (size == 0)
394
0
        return_error(gs_error_rangecheck);
395
77
    size--;
396
77
    flag_bits = *pdata++;
397
398
    /* read the other components provided */
399
77
    if ((flag_bits & dc_ht_colored_has_base) != 0) {
400
75
        if (depth == num_comps) {
401
53
            gx_color_index  base_mask = 0;
402
53
            int             num_bytes = (num_comps + 7) >> 3;
403
53
            int             i, shift = 0;
404
405
53
            if (size < num_bytes)
406
0
                return_error(gs_error_rangecheck);
407
53
            size -= num_bytes;
408
106
            for (i = 0; i < num_bytes; i++, shift += 8)
409
53
                base_mask |= (gx_color_index)(*pdata++) << shift;
410
265
            for (i = 0; i < num_comps; i++, base_mask >>= 1)
411
212
                devc.colors.colored.c_base[i] = base_mask & 0x1;
412
53
        } else {
413
22
            if (size < num_comps)
414
0
                return_error(gs_error_rangecheck);
415
22
            size -= num_comps;
416
22
            memcpy(devc.colors.colored.c_base, pdata, num_comps);
417
22
            pdata += num_comps;
418
22
        }
419
75
    }
420
421
77
    if ((flag_bits & dc_ht_colored_has_level) != 0) {
422
77
        const byte *    pdata_start = pdata;
423
77
        gx_color_index  plane_mask;
424
77
        uint            tmp_mask;
425
77
        int             i;
426
427
77
        if (size < 1)
428
0
            return_error(gs_error_rangecheck);
429
430
77
        if (num_comps > 8 * sizeof(uint)) {
431
0
            enc_u_getw(tmp_mask, pdata);
432
0
            plane_mask = (gx_color_index)tmp_mask;
433
0
            enc_u_getw(tmp_mask, pdata);
434
0
            plane_mask = (((gx_color_index)tmp_mask)<<(8 * sizeof(uint)-1))<<1;
435
77
        } else {
436
77
            enc_u_getw(tmp_mask, pdata);
437
77
            plane_mask = (gx_color_index)tmp_mask;
438
77
        }
439
77
        devc.colors.colored.plane_mask = plane_mask;
440
361
        for (i = 0; i < num_comps; i++, plane_mask >>= 1) {
441
284
            if ((plane_mask & 0x1) != 0) {
442
197
                if (size - (pdata - pdata_start) < 1)
443
0
                    return_error(gs_error_rangecheck);
444
197
                enc_u_getw(devc.colors.colored.c_level[i], pdata);
445
197
            } else
446
87
                devc.colors.colored.c_level[i] = 0;
447
284
        }
448
77
        size -= pdata - pdata_start;
449
77
    }
450
451
77
    if ((flag_bits & dc_ht_colored_has_phase_x) != 0) {
452
74
        enc_u_getw(devc.phase.x, pdata);
453
74
        devc.phase.x += x0;
454
74
    }
455
77
    if ((flag_bits & dc_ht_colored_has_phase_y) != 0) {
456
74
        enc_u_getw(devc.phase.y, pdata);
457
74
        devc.phase.y += y0;
458
74
    }
459
460
    /* everything looks OK */
461
77
    *pdevc = devc;
462
77
    return pdata - pdata0;
463
77
}
464
465
/*
466
 * Get the nonzero components of a coloredhalftone. This is used to
467
 * distinguish components that are given zero intensity due to halftoning
468
 * from those for which the original color intensity was in fact zero.
469
 *
470
 * An original component intensity of zero will yield a c_base value of
471
 * 0 and a c_level of 0. The plane_mask field already contains the latter
472
 * information, so we need only add those components for which c_base is
473
 * non-zero.
474
 */
475
int
476
gx_dc_ht_colored_get_nonzero_comps(
477
    const gx_device_color * pdevc,
478
    const gx_device *       dev_ignored,
479
    gx_color_index *        pcomp_bits )
480
0
{
481
0
    int                     i, ncomps =  pdevc->colors.colored.num_components;
482
0
    gx_color_index          comp_bits = pdevc->colors.colored.plane_mask;
483
484
0
    for (i = 0; i < ncomps; i++) {
485
0
        if (pdevc->colors.colored.c_base[i] != 0)
486
0
            comp_bits |= ((gx_color_index)1) << i;
487
0
    }
488
0
    *pcomp_bits = comp_bits;
489
490
0
    return 0;
491
0
}
492
493
/*
494
 * Define an abbreviation for a heavily used value: the maximum number of
495
 * of device colorants (device colors).
496
 */
497
#define MAX_DCC GX_DEVICE_COLOR_MAX_COMPONENTS
498
/*
499
 * Define a size for the "colors" array.  For less than 5 colors, there are
500
 * 2**n values stored (for a maximum of 16 values).  For 5 or more colors, we
501
 * only store 2 values per color so the array size can be 2 * MAX_DCC.  Use which
502
 * ever is larger for the array size.
503
 */
504
#define MAX_DCC_16 (2 * MAX_DCC < 16 ? 16 : 2 * MAX_DCC)
505
506
/* Forward references. */
507
/* Use a typedef to attempt to work around overly picky compilers. */
508
typedef gx_color_value gx_color_value_array[MAX_DCC];
509
typedef struct color_values_pair_s {
510
    gx_color_value_array values[2];
511
} color_values_pair_t;
512
#define SET_HT_COLORS_PROC(proc)\
513
42.4k
  int proc(\
514
42.4k
              color_values_pair_t *pvp,\
515
42.4k
              gx_color_index colors[MAX_DCC_16],\
516
42.4k
              const gx_const_strip_bitmap *sbits[MAX_DCC],\
517
42.4k
              const gx_device_color *pdevc,\
518
42.4k
              gx_device *dev,\
519
42.4k
              gx_ht_cache *caches[MAX_DCC],\
520
42.4k
              int nplanes\
521
42.4k
              )
522
523
static SET_HT_COLORS_PROC(set_ht_colors_le_4);
524
static SET_HT_COLORS_PROC(set_cmyk_1bit_colors);
525
static SET_HT_COLORS_PROC(set_ht_colors_gt_4);
526
527
#define SET_COLOR_HT_PROC(proc)\
528
42.4k
  void proc(\
529
42.4k
                byte *dest_data, /* the output tile */\
530
42.4k
                uint dest_raster, /* ibid. */\
531
42.4k
                int px, /* the initial phase of the output tile */\
532
42.4k
                int py,\
533
42.4k
                int w,  /* how much of the tile to set */\
534
42.4k
                int h,\
535
42.4k
                int depth,  /* depth of tile (4, 8, 16, 24, 32) */\
536
42.4k
                int special,  /* >0 means special 1-bit CMYK */\
537
42.4k
                int nplanes,\
538
42.4k
                gx_color_index plane_mask,  /* which planes are halftoned */\
539
42.4k
                gx_device *dev,   /* in case we are mapping lazily */\
540
42.4k
                const color_values_pair_t *pvp, /* color values ditto */\
541
42.4k
                gx_color_index colors[MAX_DCC_16],  /* the actual colors for the tile, */\
542
42.4k
                                /* actually [nplanes] */\
543
42.4k
                const gx_const_strip_bitmap * sbits[MAX_DCC_16] /* the bitmaps for the planes, */\
544
42.4k
                                /* actually [nplanes] */\
545
42.4k
                )
546
547
static SET_COLOR_HT_PROC(set_color_ht_le_4);
548
static SET_COLOR_HT_PROC(set_color_ht_gt_4);
549
550
/* Prepare to use a colored halftone, by loading the default cache. */
551
static int
552
gx_dc_ht_colored_load(gx_device_color * pdevc, const gs_gstate * pgs,
553
                      gx_device * ignore_dev, gs_color_select_t select)
554
4.16k
{
555
    /* TO_DO_DEVICEN */
556
557
4.16k
    return 0;
558
4.16k
}
559
560
/* Fill a rectangle with a colored halftone. */
561
/* Note that we treat this as "texture" for RasterOp. */
562
static int
563
gx_dc_ht_colored_fill_rectangle(const gx_device_color * pdevc,
564
                                int x, int y, int w, int h,
565
                                gx_device * dev, gs_logical_operation_t lop,
566
                                const gx_rop_source_t * source)
567
42.4k
{
568
42.4k
#if defined(PACIFY_VALGRIND) || defined(MEMENTO)
569
42.4k
    ulong tbits[tile_longs_allocated] = { 0 };
570
#else
571
    ulong tbits[tile_longs_allocated];
572
#endif
573
42.4k
    const uint tile_bytes = tile_longs * size_of(long);
574
42.4k
    gx_strip_bitmap tiles;
575
42.4k
    gx_rop_source_t no_source;
576
42.4k
    const gx_device_halftone *pdht = pdevc->colors.colored.c_ht;
577
42.4k
    int depth = dev->color_info.depth;
578
42.4k
    int nplanes = dev->color_info.num_components;
579
580
42.4k
    SET_HT_COLORS_PROC((*set_ht_colors)) =
581
42.4k
        (
582
#if USE_SLOW_CODE
583
         set_ht_colors_gt_4
584
#else
585
42.4k
         (dev_proc(dev, dev_spec_op)(dev, gxdso_is_std_cmyk_1bit, NULL, 0) > 0) ?
586
0
            set_cmyk_1bit_colors :
587
42.4k
            nplanes <= 4 ? set_ht_colors_le_4 :
588
42.4k
                          set_ht_colors_gt_4
589
42.4k
#endif
590
42.4k
         );
591
42.4k
    SET_COLOR_HT_PROC((*set_color_ht)) =
592
42.4k
        (
593
42.4k
#if !USE_SLOW_CODE
594
42.4k
         !(pdevc->colors.colored.plane_mask & ~(gx_color_index)15) &&
595
42.4k
          set_ht_colors != set_ht_colors_gt_4 ?
596
42.4k
           set_color_ht_le_4 :
597
42.4k
#endif
598
42.4k
         set_color_ht_gt_4);
599
42.4k
    color_values_pair_t vp;
600
42.4k
    gx_color_index colors[MAX_DCC_16];
601
42.4k
    const gx_const_strip_bitmap *sbits[MAX_DCC];
602
42.4k
    gx_ht_cache *caches[MAX_DCC];
603
42.4k
    int special;
604
42.4k
    int code = 0;
605
42.4k
    int raster;
606
42.4k
    uint size_x;
607
42.4k
    int dw, dh;
608
42.4k
    int lw = pdht->lcm_width, lh = pdht->lcm_height;
609
42.4k
    bool no_rop;
610
42.4k
    int i;
611
42.4k
    int origx, origy;
612
613
    /* This routine cannot build 3bit chunky halftones, as 3 bit
614
     * things don't pack nicely into bytes or words. Accordingly
615
     * treat 3 bit things as 4 bit things. This is appropriate when
616
     * generating halftones for planar. */
617
42.4k
    if (depth == 3)
618
0
        depth = 4;
619
620
42.4k
    if (w <= 0 || h <= 0)
621
0
        return 0;
622
42.4k
    origx = x;
623
42.4k
    origy = y;
624
42.4k
    if ((w | h) >= 16) {
625
        /* It's worth taking the trouble to check the clipping box. */
626
378
        gs_fixed_rect cbox;
627
378
        int t;
628
629
378
        dev_proc(dev, get_clipping_box)(dev, &cbox);
630
378
        if ((t = fixed2int(cbox.p.x)) > x) {
631
0
            if ((w += x - t) <= 0)
632
0
                return 0;
633
0
            x = t;
634
0
        }
635
378
        if ((t = fixed2int(cbox.p.y)) > y) {
636
2
            if ((h += y - t) <= 0)
637
2
                return 0;
638
0
            y = t;
639
0
        }
640
376
        if ((t = fixed2int(cbox.q.x)) < x + w)
641
0
            if ((w = t - x) <= 0)
642
0
                return 0;
643
376
        if ((t = fixed2int(cbox.q.y)) < y + h)
644
1
            if ((h = t - y) <= 0)
645
1
                return 0;
646
376
    }
647
    /* Colored halftone patterns are unconditionally opaque. */
648
42.4k
    lop &= ~lop_T_transparent;
649
42.4k
    if (pdht->components == 0) {
650
0
        caches[0] = caches[1] = caches[2] = caches[3] = pdht->order.cache;
651
0
        for (i = 4; i < nplanes; ++i)
652
0
            caches[i] = pdht->order.cache;
653
42.4k
    } else {
654
42.4k
        gx_ht_order_component *pocs = pdht->components;
655
656
209k
        for (i = 0; i < nplanes; ++i)
657
167k
            caches[i] = pocs[i].corder.cache;
658
42.4k
    }
659
42.4k
    special = set_ht_colors(&vp, colors, sbits, pdevc, dev, caches, nplanes);
660
42.4k
    no_rop = source == NULL && lop_no_S_is_T(lop);
661
42.4k
    if ((!no_rop) && (source == NULL))
662
0
        set_rop_no_source(source, no_source, dev);
663
664
    /*
665
     * If the LCM of the plane cell sizes is smaller than the rectangle
666
     * being filled, compute a single tile and let strip_tile_rectangle
667
     * do the replication.
668
     */
669
42.4k
    if ((w > lw || h > lh) &&
670
42.4k
        (raster = bitmap_raster(lw * depth)) <= tile_bytes / lh
671
42.4k
        ) {
672
        /*
673
         * The only reason we need to do fit_fill here is that if the
674
         * device is a clipper, the caller might be counting on it to do
675
         * all necessary clipping.  Actually, we should clip against the
676
         * device's clipping box, not the default....
677
         */
678
0
        fit_fill(dev, x, y, w, h);
679
        /* Check to make sure we still have a big rectangle. */
680
0
        if (w > lw || h > lh) {
681
0
            tiles.data = (byte *)tbits;
682
0
            tiles.raster = raster;
683
0
            tiles.rep_width = tiles.size.x = lw;
684
0
            tiles.rep_height = tiles.size.y = lh;
685
0
            tiles.id = gs_next_ids(pdht->rc.memory, 1);
686
0
            tiles.rep_shift = tiles.shift = 0;
687
0
            tiles.num_planes = 1;
688
0
            set_color_ht((byte *)tbits, raster, 0, 0, lw, lh, depth,
689
0
                         special, nplanes, pdevc->colors.colored.plane_mask,
690
0
                         dev, &vp, colors, sbits);
691
0
            if (no_rop)
692
0
                return (*dev_proc(dev, strip_tile_rectangle)) (dev, &tiles,
693
0
                                                               x, y, w, h,
694
0
                                                               gx_no_color_index,
695
0
                                                               gx_no_color_index,
696
0
                                                               pdevc->phase.x,
697
0
                                                               pdevc->phase.y);
698
0
            return (*dev_proc(dev, strip_copy_rop2))
699
0
                               (dev,
700
0
                                source->sdata + (y - origy) * source->sraster,
701
0
                                source->sourcex + (x - origx),
702
0
                                source->sraster, source->id,
703
0
                                (source->use_scolors ? source->scolors : NULL),
704
0
                                &tiles, NULL,
705
0
                                x, y, w, h,
706
0
                                pdevc->phase.x, pdevc->phase.y, lop,
707
0
                                source->planar_height);
708
0
        }
709
0
    }
710
42.4k
    size_x = w * depth;
711
42.4k
    raster = bitmap_raster(size_x);
712
42.4k
    if (raster > tile_bytes) {
713
        /*
714
         * We can't even do an entire line at once.  See above for
715
         * why we do the X equivalent of fit_fill here.
716
         */
717
0
        if (x < 0)
718
0
            w += x, x = 0;
719
0
        if (x > dev->width - w)
720
0
            w = dev->width - x;
721
0
        if (w <= 0)
722
0
            return 0;
723
0
        size_x = w * depth;
724
0
        raster = bitmap_raster(size_x);
725
0
        if (raster > tile_bytes) {
726
            /* We'll have to do a partial line. */
727
0
            dw = tile_bytes * 8 / depth;
728
0
            size_x = dw * depth;
729
0
            raster = bitmap_raster(size_x);
730
0
            dh = 1;
731
0
            goto fit;
732
0
        }
733
0
    }
734
    /* Do as many lines as will fit. */
735
42.4k
    dw = w;
736
42.4k
    dh = tile_bytes / raster;
737
42.4k
    if (dh > h)
738
42.3k
        dh = h;
739
42.4k
fit:        /* Now the tile will definitely fit. */
740
42.4k
    if (!no_rop) {
741
0
        tiles.data = (byte *)tbits;
742
0
        tiles.id = gx_no_bitmap_id;
743
0
        tiles.raster = raster;
744
0
        tiles.rep_width = tiles.size.x = size_x / depth;
745
0
        tiles.rep_shift = tiles.shift = 0;
746
0
        tiles.num_planes = 1;
747
0
    }
748
42.4k
    while (w) {
749
42.4k
        int cy = y, ch = dh, left = h;
750
751
50.4k
        for (;;) {
752
50.4k
            set_color_ht((byte *)tbits, raster,
753
50.4k
                         x + pdevc->phase.x, cy + pdevc->phase.y,
754
50.4k
                         dw, ch, depth, special, nplanes,
755
50.4k
                         pdevc->colors.colored.plane_mask,
756
50.4k
                         dev, &vp, colors, sbits);
757
50.4k
            if (no_rop) {
758
50.4k
                code = (*dev_proc(dev, copy_color))
759
50.4k
                    (dev, (byte *)tbits, 0, raster, gx_no_bitmap_id,
760
50.4k
                     x, cy, dw, ch);
761
50.4k
            } else {
762
0
                tiles.rep_height = tiles.size.y = ch;
763
0
                code = (*dev_proc(dev, strip_copy_rop2))
764
0
                          (dev, source->sdata + source->sraster * (cy-origy),
765
0
                           source->sourcex + (x - origx),
766
0
                           source->sraster,
767
0
                           source->id,
768
0
                           (source->use_scolors ? source->scolors : NULL),
769
0
                           &tiles, NULL, x, cy, dw, ch, 0, 0, lop,
770
0
                           source->planar_height);
771
0
            }
772
50.4k
            if (code < 0)
773
0
                return code;
774
50.4k
            if (!(left -= ch))
775
42.4k
                break;
776
7.98k
            cy += ch;
777
7.98k
            if (ch > left)
778
9
                ch = left;
779
7.98k
        }
780
42.4k
        if (!(w -= dw))
781
42.4k
            break;
782
0
        x += dw;
783
0
        if (dw > w)
784
0
            dw = w;
785
0
    }
786
42.4k
    return code;
787
42.4k
}
788
789
/* ---------------- Color table setup ---------------- */
790
791
/*
792
 * We could cache this if we had a place to store it.  Even a 1-element
793
 * cache would help performance substantially.
794
 *   Key: device + c_base/c_level of device color
795
 *   Value: colors table
796
 */
797
798
/*
799
 * We construct color halftone tiles out of multiple "planes".
800
 * Each plane specifies halftoning for one component (R/G/B, C/M/Y/K,
801
 * or DeviceN components).
802
 */
803
804
static const struct {
805
    ulong pad;      /* to get bytes aligned properly */
806
    byte bytes[sizeof(ulong) * 8];  /* 8 is arbitrary */
807
} ht_no_bitmap_data = { 0 };
808
static const gx_const_strip_bitmap ht_no_bitmap = {
809
    &ht_no_bitmap_data.bytes[0], sizeof(ulong),
810
    {sizeof(ulong) * 8, sizeof(ht_no_bitmap_data.bytes) / sizeof(ulong)},
811
    gx_no_bitmap_id, 1, 1, 0, 0
812
};
813
814
/* Set the color value(s) and halftone mask for one plane. */
815
static inline void set_plane_color(int i, color_values_pair_t *pvp, const gx_device_color * pdc,
816
    const gx_const_strip_bitmap * sbits[MAX_DCC], gx_ht_cache * caches[MAX_DCC],
817
    gx_color_value max_color, bool invert)
818
167k
{
819
167k
    uint q = pdc->colors.colored.c_base[i];
820
167k
    uint r = pdc->colors.colored.c_level[i];
821
822
167k
    pvp->values[0][i] = fractional_color(q, max_color);
823
167k
    if (r == 0)
824
358
        pvp->values[1][i] = pvp->values[0][i], sbits[i] = &ht_no_bitmap;
825
166k
    else if (!invert) {
826
7.14k
        pvp->values[1][i] = fractional_color(q + 1, max_color);
827
7.14k
        sbits[i] = (const gx_const_strip_bitmap *) &gx_render_ht(caches[i], r)->tiles;
828
159k
    } else {
829
159k
        const gx_device_halftone *pdht = pdc->colors.colored.c_ht;
830
159k
        int nlevels =
831
159k
            (pdht->components ? pdht->components[i].corder.num_levels : pdht->order.num_levels);
832
159k
        pvp->values[1][i] = pvp->values[0][i];
833
159k
        pvp->values[0][i] = fractional_color(q + 1, max_color);
834
159k
        sbits[i] = (const gx_const_strip_bitmap *) &gx_render_ht(caches[i], nlevels - r)->tiles;
835
159k
    }
836
167k
}
837
838
/* Set up the colors and the individual plane halftone bitmaps. */
839
static int
840
set_ht_colors_le_4(color_values_pair_t *pvp /* only used internally */,
841
                   gx_color_index colors[MAX_DCC_16] /* 16 used */,
842
                   const gx_const_strip_bitmap * sbits[MAX_DCC],
843
                   const gx_device_color * pdc, gx_device * dev,
844
                   gx_ht_cache * caches[MAX_DCC], int nplanes)
845
42.4k
{
846
42.4k
    gx_color_value max_color = dev->color_info.dither_colors - 1;
847
42.4k
    gx_color_value cvalues[4];
848
    /*
849
     * NB: the halftone orders are all set up for an additive color space.
850
     *     To make these work with a subtractive device space such as CMYK,
851
     *     it is necessary to invert both the color level and the color
852
     *     pair. Note that if the original color was provided an additive
853
     *     space, this will reverse (in an approximate sense) the color
854
     *     conversion performed to express the color in the device space.
855
     */
856
42.4k
    bool invert = dev->color_info.polarity == GX_CINFO_POLARITY_SUBTRACTIVE;
857
858
42.4k
    set_plane_color(0, pvp, pdc, sbits, caches, max_color, invert);
859
42.4k
    if (nplanes >= 2) {
860
42.4k
        set_plane_color(1, pvp, pdc, sbits, caches, max_color, invert);
861
42.4k
    }
862
42.4k
    if (nplanes >= 3) {
863
42.4k
        set_plane_color(2, pvp, pdc, sbits, caches, max_color, invert);
864
42.4k
    }
865
42.4k
    if (nplanes == 3) {
866
2.45k
#define M(i)\
867
19.6k
  cvalues[0] = pvp->values[(i) & 1][0];\
868
19.6k
  cvalues[1] = pvp->values[((i) & 2) >> 1][1];\
869
19.6k
  cvalues[2] = pvp->values[(i) >> 2][2];\
870
19.6k
  colors[i] = dev_proc(dev, encode_color)(dev, cvalues);
871
872
2.45k
            M(0); M(1); M(2); M(3); M(4); M(5); M(6); M(7);
873
2.45k
#undef M
874
39.9k
    } else if (nplanes > 3){
875
39.9k
        set_plane_color(3, pvp, pdc, sbits, caches, max_color, invert);
876
39.9k
        if (nplanes > 4) {
877
            /*
878
             * Set colors for any planes beyond the 4th.  Since this code
879
             * only handles the case of at most 4 active planes, we know
880
             * that any further planes are constant.
881
             */
882
            /****** DOESN'T MAP COLORS RIGHT, DOESN'T HANDLE ALPHA ******/
883
0
            int pi;
884
885
0
            for (pi = 4; pi < nplanes; ++pi) {
886
0
                pvp->values[1][pi] = pvp->values[0][pi] =
887
0
                    fractional_color(pdc->colors.colored.c_base[pi], max_color);
888
0
                sbits[pi] = &ht_no_bitmap;
889
0
            }
890
0
        }
891
        /*
892
         * For CMYK output, especially if the input was RGB, it's
893
         * common for one or more of the components to be zero.
894
         * Each zero component can cut the cost of color mapping in
895
         * half, so it's worth doing a little checking here.
896
         */
897
39.9k
#define M(i)\
898
638k
    cvalues[0] = pvp->values[(i) & 1][0];\
899
638k
    cvalues[1] = pvp->values[((i) & 2) >> 1][1];\
900
638k
    cvalues[2] = pvp->values[((i) & 4) >> 2][2];\
901
638k
    cvalues[3] = pvp->values[(i) >> 3][3];\
902
638k
    colors[i] = dev_proc(dev, encode_color)(dev, cvalues)
903
904
      /* We know that plane_mask <= 15. */
905
39.9k
        switch ((int)pdc->colors.colored.plane_mask) {
906
39.8k
            case 15:
907
39.8k
                M(15); M(14); M(13); M(12);
908
39.8k
                M(11); M(10); M(9); M(8);
909
39.8k
            case 7:
910
39.8k
                M(7); M(6); M(5); M(4);
911
39.8k
c3:     case 3:
912
39.8k
                M(3); M(2);
913
39.8k
c1:     case 1:
914
39.8k
                M(1);
915
39.8k
                break;
916
40
            case 14:
917
40
                M(14); M(12); M(10); M(8);
918
76
            case 6:
919
76
                M(6); M(4);
920
76
c2:     case 2:
921
76
                M(2);
922
76
                break;
923
19
            case 13:
924
19
                M(13); M(12); M(9); M(8);
925
19
            case 5:
926
19
                M(5); M(4);
927
19
                goto c1;
928
0
            case 12:
929
0
                M(12); M(8);
930
0
            case 4:
931
0
                M(4);
932
0
                break;
933
0
            case 11:
934
0
                M(11); M(10); M(9); M(8);
935
0
                goto c3;
936
0
            case 10:
937
0
                M(10); M(8);
938
0
                goto c2;
939
0
            case 9:
940
0
                M(9); M(8);
941
0
                goto c1;
942
0
            case 8:
943
0
                M(8);
944
0
                break;
945
0
            case 0:;
946
39.9k
        }
947
39.9k
        M(0);
948
949
39.9k
#undef M
950
39.9k
    }
951
42.4k
    return 0;
952
42.4k
}
953
954
/* Set up colors using the standard 1-bit CMYK mapping. */
955
static int
956
set_cmyk_1bit_colors(color_values_pair_t *ignore_pvp,
957
                     gx_color_index colors[MAX_DCC_16] /*2 used*/,
958
                     const gx_const_strip_bitmap * sbits[MAX_DCC /*4 used*/],
959
                     const gx_device_color * pdc, gx_device * dev,
960
                     gx_ht_cache * caches[MAX_DCC /*4 used*/],
961
                     int nplanes /*4*/)
962
0
{
963
0
    const gx_device_halftone *pdht = pdc->colors.colored.c_ht;
964
    /*
965
     * By reversing the order of the planes, we make the pixel values
966
     * line up with the color indices.  Then instead of a lookup, we
967
     * can compute the pixels directly using a Boolean function.
968
     *
969
     * We compute each output bit
970
     *   out[i] = (in[i] & mask1) | (~in[i] & mask0)
971
     * We store the two masks in colors[0] and colors[1], since the
972
     * colors array is otherwise unused in this case.  We duplicate
973
     * the values in all the nibbles so we can do several pixels at a time.
974
     */
975
0
    bits32 mask0 = 0, mask1 = 0;
976
0
#define SET_PLANE_COLOR_CMYK(i, mask)\
977
0
  BEGIN\
978
0
    uint r = pdc->colors.colored.c_level[i];\
979
0
\
980
0
    if (r == 0) {\
981
0
        if (pdc->colors.colored.c_base[i])\
982
0
            mask0 |= mask, mask1 |= mask;\
983
0
        sbits[3 - i] = &ht_no_bitmap;\
984
0
    } else {\
985
0
        int nlevels =\
986
0
            (pdht->components ?\
987
0
             pdht->components[i].corder.num_levels :\
988
0
             pdht->order.num_levels);\
989
0
\
990
0
        mask0 |= mask;\
991
0
        sbits[3 - i] = (const gx_const_strip_bitmap *)\
992
0
            &gx_render_ht(caches[i], nlevels - r)->tiles;\
993
0
    }\
994
0
  END
995
         /* Suppress a compiler warning about signed/unsigned constants. */
996
0
    SET_PLANE_COLOR_CMYK(0, /*0x88888888*/ (bits32)~0x77777777);
997
0
    SET_PLANE_COLOR_CMYK(1, 0x44444444);
998
0
    SET_PLANE_COLOR_CMYK(2, 0x22222222);
999
0
    SET_PLANE_COLOR_CMYK(3, 0x11111111);
1000
1001
0
#undef SET_PLANE_COLOR_CMYK
1002
0
    {
1003
0
        gx_ht_cache *ctemp;
1004
1005
0
        ctemp = caches[0], caches[0] = caches[3], caches[3] = ctemp;
1006
0
        ctemp = caches[1], caches[1] = caches[2], caches[2] = ctemp;
1007
0
    }
1008
0
    colors[0] = mask0;
1009
0
    colors[1] = mask1;
1010
0
    return 1;
1011
0
}
1012
1013
/*
1014
 * Set up colors for >4 planes.  In this case, we assume that the color
1015
 * component values are "separable".  (That we can form a gx_color_index value
1016
 * for a color by a bit wise or of the gx_color_index values of the individual
1017
 * components.)
1018
 */
1019
static int
1020
set_ht_colors_gt_4(color_values_pair_t *pvp,
1021
                   gx_color_index colors[MAX_DCC_16 /* 2 * nplanes */],
1022
                   const gx_const_strip_bitmap * sbits[MAX_DCC],
1023
                   const gx_device_color * pdc, gx_device * dev,
1024
                   gx_ht_cache * caches[MAX_DCC], int nplanes)
1025
0
{
1026
0
    gx_color_value max_color = dev->color_info.dither_colors - 1;
1027
0
    bool invert = dev->color_info.polarity == GX_CINFO_POLARITY_SUBTRACTIVE;
1028
0
    gx_color_index plane_mask = pdc->colors.colored.plane_mask;
1029
0
    int i;
1030
0
    gx_color_value cv[MAX_DCC] = {0};
1031
1032
    /* Set the color values and halftone caches. */
1033
0
    for (i = 0; i < nplanes; ++i) {
1034
0
        if ((plane_mask >> i) & 1)
1035
0
            set_plane_color(i, pvp, pdc, sbits, caches, max_color, invert);
1036
0
        else {
1037
0
            pvp->values[1][i] = pvp->values[0][i] =
1038
0
                fractional_color(pdc->colors.colored.c_base[i], max_color);
1039
0
            sbits[i] = &ht_no_bitmap;
1040
0
        }
1041
0
    }
1042
    /*
1043
     * Determine a gs_color_index value for each pair of component values.
1044
     * We assume that an overall index value can be formed from the
1045
     * bitwise or of each component.  We calculate a value for both
1046
     * the high and low value of each component.  These are stored
1047
     * in adjacent locations in 'colors'.
1048
     */
1049
0
    for (i = 0; i < nplanes; i++ ) {
1050
0
        cv[i] = pvp->values[0][i];
1051
0
        colors[2 * i] = dev_proc(dev, encode_color)(dev, cv);
1052
        /* We only need both values for components being halftoned */
1053
0
        if ((plane_mask >> i) & 1) {
1054
0
            cv[i] = pvp->values[1][i];
1055
0
            colors[2 * i + 1] = dev_proc(dev, encode_color)(dev, cv);
1056
0
        }
1057
0
        cv[i] = 0;
1058
0
    }
1059
1060
0
    return 0;
1061
0
}
1062
1063
/* ---------------- Color rendering ---------------- */
1064
1065
/* Define the bookkeeping structure for each plane of halftone rendering. */
1066
typedef struct tile_cursor_s {
1067
    int tile_shift;   /* X shift per copy of tile */
1068
    int xoffset;
1069
    int xshift;
1070
    uint xbytes;
1071
    int xbits;
1072
    const byte *row;
1073
    const byte *tdata;
1074
    uint raster;
1075
    const byte *data;
1076
    int bit_shift;
1077
} tile_cursor_t;
1078
1079
/*
1080
 * Initialize one plane cursor, including setting up for the first row
1081
 * (data and bit_shift).
1082
 */
1083
static void
1084
init_tile_cursor(int i, tile_cursor_t *ptc, const gx_const_strip_bitmap *btile,
1085
                 int endx, int lasty)
1086
182k
{
1087
182k
    int tw = btile->size.x;
1088
182k
    int bx = ((ptc->tile_shift = btile->shift) == 0 ? endx :
1089
182k
              endx + lasty / btile->size.y * ptc->tile_shift) % tw;
1090
182k
    int by = lasty % btile->size.y;
1091
1092
182k
    ptc->xoffset = bx >> 3;
1093
182k
    ptc->xshift = 8 - (bx & 7);
1094
182k
    ptc->xbytes = (tw - 1) >> 3;
1095
182k
    ptc->xbits = ((tw - 1) & 7) + 1;
1096
182k
    ptc->tdata = btile->data;
1097
182k
    ptc->raster = btile->raster;
1098
182k
    ptc->row = ptc->tdata + by * (int)ptc->raster;
1099
182k
    ptc->data = ptc->row + ptc->xoffset;
1100
182k
    ptc->bit_shift = ptc->xshift;
1101
182k
    if_debug6('h', "[h]plane %d: size=%d,%d shift=%d bx=%d by=%d\n",
1102
182k
              i, tw, btile->size.y, btile->shift, bx, by);
1103
182k
}
1104
1105
/* Step a cursor to the next row. */
1106
static void
1107
wrap_shifted_cursor(tile_cursor_t *ptc, const gx_const_strip_bitmap *psbit)
1108
2.82k
{
1109
2.82k
    ptc->row += ptc->raster * (psbit->size.y - 1);
1110
2.82k
    if (ptc->tile_shift) {
1111
0
        if ((ptc->xshift += ptc->tile_shift) >= 8) {
1112
0
            if ((ptc->xoffset -= ptc->xshift >> 3) < 0) {
1113
                /* wrap around in X */
1114
0
                int bx = (ptc->xoffset << 3) + 8 - (ptc->xshift & 7) +
1115
0
                    psbit->size.x;
1116
1117
0
                ptc->xoffset = bx >> 3;
1118
0
                ptc->xshift = 8 - (bx & 7);
1119
0
            } else
1120
0
                ptc->xshift &= 7;
1121
0
        }
1122
0
    }
1123
2.82k
}
1124
#define STEP_ROW(c, i)\
1125
61.2k
  BEGIN\
1126
61.2k
    if (c.row > c.tdata)\
1127
61.2k
      c.row -= c.raster;\
1128
61.2k
    else { /* wrap around to end of tile */\
1129
2.82k
        wrap_shifted_cursor(&c, sbits[i]);\
1130
2.82k
    }\
1131
61.2k
    c.data = c.row + c.xoffset;\
1132
61.2k
    c.bit_shift = c.xshift;\
1133
61.2k
  END
1134
1135
/* Define a table for expanding 8x1 bits to 8x4. */
1136
static const bits32 expand_8x1_to_8x4[256] = {
1137
#define X16(c)\
1138
  c+0, c+1, c+0x10, c+0x11, c+0x100, c+0x101, c+0x110, c+0x111,\
1139
  c+0x1000, c+0x1001, c+0x1010, c+0x1011, c+0x1100, c+0x1101, c+0x1110, c+0x1111
1140
    X16(0x00000000), X16(0x00010000), X16(0x00100000), X16(0x00110000),
1141
    X16(0x01000000), X16(0x01010000), X16(0x01100000), X16(0x01110000),
1142
    X16(0x10000000), X16(0x10010000), X16(0x10100000), X16(0x10110000),
1143
    X16(0x11000000), X16(0x11010000), X16(0x11100000), X16(0x11110000)
1144
#undef X16
1145
};
1146
1147
/*
1148
 * Render the combined halftone for nplanes <= 4.
1149
 */
1150
static void
1151
set_color_ht_le_4(byte *dest_data, uint dest_raster, int px, int py,
1152
                  int w, int h, int depth, int special, int nplanes,
1153
                  gx_color_index plane_mask, gx_device *ignore_dev,
1154
                  const color_values_pair_t *ignore_pvp,
1155
                  gx_color_index colors[MAX_DCC_16],
1156
                  const gx_const_strip_bitmap * sbits[MAX_DCC_16])
1157
50.4k
{
1158
    /*
1159
     * Note that the planes are specified in the order RGB or CMYK, but
1160
     * the indices used for the internal colors array are BGR or KYMC,
1161
     * except for the special 1-bit CMYK case.
1162
     */
1163
50.4k
    int x, y;
1164
50.4k
    tile_cursor_t cursor[MAX_DCC];
1165
50.4k
    int dbytes = depth >> 3;
1166
50.4k
    byte *dest_row =
1167
50.4k
        dest_data + dest_raster * (h - 1) + (w * depth) / 8;
1168
1169
50.4k
    if (special > 0) {
1170
        /* Planes are in reverse order. */
1171
0
        plane_mask =
1172
0
            "\000\010\004\014\002\012\006\016\001\011\005\015\003\013\007\017"[plane_mask];
1173
0
    }
1174
50.4k
    if_debug6('h',
1175
50.4k
              "[h]color_ht_le_4: x=%d y=%d w=%d h=%d plane_mask=0x%lu depth=%d\n",
1176
50.4k
              px, py, w, h, (ulong)plane_mask, depth);
1177
1178
    /* Do one-time cursor initialization. */
1179
50.4k
    {
1180
50.4k
        int endx = w + px;
1181
50.4k
        int lasty = h - 1 + py;
1182
1183
50.4k
        if (plane_mask & 1)
1184
43.5k
            init_tile_cursor(0, &cursor[0], sbits[0], endx, lasty);
1185
50.4k
        if (plane_mask & 2)
1186
50.1k
            init_tile_cursor(1, &cursor[1], sbits[1], endx, lasty);
1187
50.4k
        if (plane_mask & 4)
1188
49.2k
            init_tile_cursor(2, &cursor[2], sbits[2], endx, lasty);
1189
50.4k
        if (plane_mask & 8)
1190
39.9k
            init_tile_cursor(3, &cursor[3], sbits[3], endx, lasty);
1191
50.4k
    }
1192
1193
    /* Now compute the actual tile. */
1194
63.2k
    for (y = h; ; dest_row -= dest_raster) {
1195
63.2k
        byte *dest = dest_row;
1196
1197
63.2k
        --y;
1198
3.35M
        for (x = w; x > 0;) {
1199
3.28M
            bits32 indices;
1200
3.28M
            int nx, i;
1201
3.28M
            register uint bits;
1202
1203
/* Get the next byte's worth of bits.  Note that there may be */
1204
/* excess bits set beyond the 8th. */
1205
3.28M
#define NEXT_BITS(c)\
1206
6.70M
  BEGIN\
1207
6.70M
    if (c.data > c.row) {\
1208
6.66M
      bits = ((c.data[-1] << 8) | *c.data) >> c.bit_shift;\
1209
6.66M
      c.data--;\
1210
6.66M
    } else {\
1211
36.3k
      bits = *c.data >> c.bit_shift;\
1212
36.3k
      c.data += c.xbytes;\
1213
36.3k
      if ((c.bit_shift -= c.xbits) < 0) {\
1214
35.4k
        bits |= *c.data << -c.bit_shift;\
1215
35.4k
        c.bit_shift += 8;\
1216
35.4k
      } else {\
1217
838
        bits |= ((c.data[-1] << 8) | *c.data) >> c.bit_shift;\
1218
838
        c.data--;\
1219
838
      }\
1220
36.3k
    }\
1221
6.70M
  END
1222
3.28M
            if (plane_mask & 1) {
1223
539k
                NEXT_BITS(cursor[0]);
1224
539k
                indices = expand_8x1_to_8x4[bits & 0xff];
1225
539k
            } else
1226
2.75M
                indices = 0;
1227
3.28M
            if (plane_mask & 2) {
1228
3.28M
                NEXT_BITS(cursor[1]);
1229
3.28M
                indices |= expand_8x1_to_8x4[bits & 0xff] << 1;
1230
3.28M
            }
1231
3.28M
            if (plane_mask & 4) {
1232
2.82M
                NEXT_BITS(cursor[2]);
1233
2.82M
                indices |= expand_8x1_to_8x4[bits & 0xff] << 2;
1234
2.82M
            }
1235
3.28M
            if (plane_mask & 8) {
1236
53.4k
                NEXT_BITS(cursor[3]);
1237
53.4k
                indices |= expand_8x1_to_8x4[bits & 0xff] << 3;
1238
53.4k
            }
1239
3.28M
#undef NEXT_BITS
1240
3.28M
            nx = min(x, 8); /* 1 <= nx <= 8 */
1241
3.28M
            x -= nx;
1242
3.28M
            switch (dbytes) {
1243
3.28M
                case 0: /* 4 */
1244
3.28M
                    if (special > 0) {
1245
                        /* Special 1-bit CMYK. */
1246
                        /* Compute all the pixels at once! */
1247
0
                        indices =
1248
0
                            (indices & colors[1]) | (~indices & colors[0]);
1249
0
                        i = nx;
1250
0
                        if ((x + nx) & 1) {
1251
                            /* First pixel is even nibble. */
1252
0
                            *dest = (*dest & 0xf) +
1253
0
                                ((indices & 0xf) << 4);
1254
0
                            indices >>= 4;
1255
0
                            --i;
1256
0
                        }
1257
                        /* Now 0 <= i <= 8. */
1258
0
                        for (; (i -= 2) >= 0; indices >>= 8)
1259
0
                            *--dest = (byte)indices;
1260
                        /* Check for final odd nibble. */
1261
0
                        if (i & 1)
1262
0
                            *--dest = indices & 0xf;
1263
3.28M
                    } else {
1264
                        /* Other 4-bit pixel */
1265
3.28M
                        i = nx;
1266
3.28M
                        if ((x + nx) & 1) {
1267
                            /* First pixel is even nibble. */
1268
58.6k
                            *dest = (*dest & 0xf) +
1269
58.6k
                                ((byte)colors[indices & 0xf] << 4);
1270
58.6k
                            indices >>= 4;
1271
58.6k
                            --i;
1272
58.6k
                        }
1273
                        /* Now 0 <= i <= 8. */
1274
16.2M
                        for (; (i -= 2) >= 0; indices >>= 8)
1275
12.9M
                            *--dest =
1276
12.9M
                                (byte)colors[indices & 0xf] +
1277
12.9M
                                ((byte)colors[(indices >> 4) & 0xf]
1278
12.9M
                                 << 4);
1279
                        /* Check for final odd nibble. */
1280
3.28M
                        if (i & 1)
1281
29.5k
                            *--dest = (byte)colors[indices & 0xf];
1282
3.28M
                    }
1283
3.28M
                    break;
1284
0
                case 4: /* 32 */
1285
0
                    for (i = nx; --i >= 0; indices >>= 4) {
1286
0
                        bits32 tcolor = (bits32)colors[indices & 0xf];
1287
1288
0
                        dest -= 4;
1289
0
                        dest[3] = (byte)tcolor;
1290
0
                        dest[2] = (byte)(tcolor >> 8);
1291
0
                        tcolor >>= 16;
1292
0
                        dest[1] = (byte)tcolor;
1293
0
                        dest[0] = (byte)(tcolor >> 8);
1294
0
                    }
1295
0
                    break;
1296
0
                case 3: /* 24 */
1297
0
                    for (i = nx; --i >= 0; indices >>= 4) {
1298
0
                        bits32 tcolor = (bits32)colors[indices & 0xf];
1299
1300
0
                        dest -= 3;
1301
0
                        dest[2] = (byte) tcolor;
1302
0
                        dest[1] = (byte)(tcolor >> 8);
1303
0
                        dest[0] = (byte)(tcolor >> 16);
1304
0
                    }
1305
0
                    break;
1306
0
                case 2: /* 16 */
1307
0
                    for (i = nx; --i >= 0; indices >>= 4) {
1308
0
                        uint tcolor =
1309
0
                            (uint)colors[indices & 0xf];
1310
1311
0
                        dest -= 2;
1312
0
                        dest[1] = (byte)tcolor;
1313
0
                        dest[0] = (byte)(tcolor >> 8);
1314
0
                    }
1315
0
                    break;
1316
0
                case 1: /* 8 */
1317
0
                    for (i = nx; --i >= 0; indices >>= 4)
1318
0
                        *--dest = (byte)colors[indices & 0xf];
1319
0
                    break;
1320
3.28M
            }
1321
3.28M
        }
1322
63.2k
        if (y == 0)
1323
50.4k
            break;
1324
1325
12.8k
        if (plane_mask & 1)
1326
12.8k
            STEP_ROW(cursor[0], 0);
1327
12.8k
        if (plane_mask & 2)
1328
12.8k
            STEP_ROW(cursor[1], 1);
1329
12.8k
        if (plane_mask & 4)
1330
12.8k
            STEP_ROW(cursor[2], 2);
1331
12.8k
        if (plane_mask & 8)
1332
12.8k
            STEP_ROW(cursor[3], 3);
1333
12.8k
    }
1334
50.4k
}
1335
1336
/*
1337
 * Render the combined halftone for nplanes > 4.  This routine assumes
1338
 * that we can form a gx_color_index value by the bitwise or index values
1339
 * for each of the individual components.
1340
 */
1341
static void
1342
set_color_ht_gt_4(byte *dest_data, uint dest_raster, int px, int py,
1343
                  int w, int h, int depth, int special, int num_planes,
1344
                  gx_color_index plane_mask, gx_device *dev,
1345
                  const color_values_pair_t *pvp,
1346
                  gx_color_index colors[MAX_DCC_16],
1347
                  const gx_const_strip_bitmap * sbits[MAX_DCC_16])
1348
0
{
1349
0
    int x, y;
1350
0
    tile_cursor_t cursor[MAX_DCC];
1351
0
    int dbytes = depth >> 3;
1352
0
    byte *dest_row =
1353
0
        dest_data + dest_raster * (h - 1) + (w * depth) / 8;
1354
0
    int pmin, pmax;
1355
0
    gx_color_index base_color = 0;
1356
1357
    /* Compute the range of active planes. */
1358
0
    if (plane_mask == 0)
1359
0
        pmin = 0, pmax = -1;
1360
0
    else {
1361
0
        for (pmin = 0; !((plane_mask >> pmin) & 1); )
1362
0
            ++pmin;
1363
0
        for (pmax = 0; (plane_mask >> pmax) > 1; )
1364
0
            ++pmax;
1365
0
    }
1366
0
    if_debug6('h',
1367
0
              "[h]color_ht_gt_4: x=%d y=%d w=%d h=%d plane_mask=0x%lu depth=%d\n",
1368
0
              px, py, w, h, (ulong)plane_mask, depth);
1369
1370
    /* Do one-time cursor initialization. */
1371
0
    {
1372
0
        int endx = w + px;
1373
0
        int lasty = h - 1 + py;
1374
0
        int i;
1375
1376
0
        for (i = pmin; i <= pmax; ++i)
1377
0
            if ((plane_mask >> i) & 1)
1378
0
                init_tile_cursor(i, &cursor[i], sbits[i], endx, lasty);
1379
0
    }
1380
1381
    /* Pre-load the color value for the non halftoning planes. */
1382
0
    {
1383
0
        int i;
1384
1385
0
        for (i = 0; i < num_planes; ++i)
1386
0
            if ((~plane_mask >> i) & 1)
1387
0
                base_color |= colors[2 * i];
1388
0
    }
1389
1390
    /* Now compute the actual tile. */
1391
0
    for (y = h; ; dest_row -= dest_raster) {
1392
0
        byte *dest = dest_row;
1393
0
        int i;
1394
1395
0
        --y;
1396
0
        for (x = w; x > 0;) {
1397
0
            gx_color_index tcolor = base_color;
1398
1399
0
            for (i = pmin; i <= pmax; ++i)
1400
0
                if ((plane_mask >> i) & 1) {
1401
                    /* Get the next bit from an individual mask. */
1402
0
                    tile_cursor_t *ptc = &cursor[i];
1403
0
                    byte tile_bit;
1404
1405
0
b:        if (ptc->bit_shift < 8)
1406
0
                        tile_bit = *ptc->data >> ptc->bit_shift++;
1407
0
                    else if (ptc->data > ptc->row) {
1408
0
                        tile_bit = *--(ptc->data);
1409
0
                        ptc->bit_shift = 1;
1410
0
                    } else {
1411
                        /* Wrap around. */
1412
0
                        ptc->data += ptc->xbytes;
1413
0
                        ptc->bit_shift = 8 - ptc->xbits;
1414
0
                        goto b;
1415
0
                    }
1416
0
                    tcolor |= colors[2 * i + (tile_bit & 1)];
1417
0
                }
1418
0
            --x;
1419
0
            switch (dbytes) {
1420
0
                case 0: /* 4 -- might be 2, but we don't support this */
1421
0
                    if (x & 1) { /* odd nibble */
1422
0
                        *--dest = (byte)tcolor;
1423
0
                    } else { /* even nibble */
1424
0
                        *dest = (*dest & 0xf) + ((byte)tcolor << 4);
1425
0
                    }
1426
0
                    break;
1427
0
                case 4: /* 32 */
1428
0
                    dest[-4] = (byte)(tcolor >> 24);
1429
0
                case 3: /* 24 */
1430
0
                    dest[-3] = (byte)(tcolor >> 16);
1431
0
                case 2: /* 16 */
1432
0
                    dest[-2] = (byte)(tcolor >> 8);
1433
0
                case 1: /* 8 */
1434
0
                    dest[-1] = (byte)tcolor;
1435
0
                    dest -= dbytes;
1436
0
                    break;
1437
0
            }
1438
0
        }
1439
0
        if (y == 0)
1440
0
            break;
1441
0
        for (i = pmin; i <= pmax; ++i)
1442
0
            if ((plane_mask >> i) & 1)
1443
0
                STEP_ROW(cursor[i], i);
1444
0
    }
1445
0
}