Coverage Report

Created: 2025-06-10 06:56

/src/ghostpdl/base/gxclrast.c
Line
Count
Source (jump to first uncovered line)
1
/* Copyright (C) 2001-2025 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
/* Command list interpreter/rasterizer */
18
#include "memory_.h"
19
#include "gx.h"
20
#include "gp.h"                 /* for gp_fmode_rb */
21
#include "gpcheck.h"
22
#include "gserrors.h"
23
#include "gscdefs.h"            /* for image type table */
24
#include "gsbitops.h"
25
#include "gsparams.h"
26
#include "gsstate.h"            /* (should only be gs_gstate) */
27
#include "gstrans.h"    /* for gs_is_pdf14trans_compositor */
28
#include "gxdcolor.h"
29
#include "gxdevice.h"
30
#include "gscoord.h"            /* requires gsmatrix.h */
31
#include "gsdevice.h"           /* for gs_deviceinitialmatrix */
32
#include "gsiparm4.h"
33
#include "gxdevmem.h"           /* must precede gxcldev.h */
34
#include "gxcldev.h"
35
#include "gxclpath.h"
36
#include "gxcmap.h"
37
#include "gxcolor2.h"
38
#include "gxcspace.h"           /* for gs_color_space_type */
39
#include "gxdhtres.h"
40
#include "gxgetbit.h"
41
#include "gxpaint.h"            /* for gx_fill/stroke_params */
42
#include "gxpcolor.h"
43
#include "gxhttile.h"
44
#include "gxiparam.h"
45
#include "gximask.h"
46
#include "gzpath.h"
47
#include "gzcpath.h"
48
#include "gzacpath.h"
49
#include "stream.h"
50
#include "strimpl.h"
51
#include "gxcomp.h"
52
#include "gsserial.h"
53
#include "gxdhtserial.h"
54
#include "gzht.h"
55
#include "gxshade.h"
56
#include "gxshade4.h"
57
#include "gsicc_manage.h"
58
#include "gsicc.h"
59
60
extern_gx_device_halftone_list();
61
extern_gx_image_type_table();
62
63
/* We need color space types for constructing temporary color spaces. */
64
extern const gs_color_space_type gs_color_space_type_Indexed;
65
66
/* Print a bitmap for tracing */
67
#ifdef DEBUG
68
static void
69
cmd_print_bits(gs_memory_t *mem, const byte * data, int width, int height, int raster)
70
{
71
    int i, j;
72
73
    dmlprintf3(mem, "[L]width=%d, height=%d, raster=%d\n",
74
              width, height, raster);
75
    for (i = 0; i < height; i++) {
76
        const byte *row = data + i * raster;
77
78
        dmlprintf(mem, "[L]");
79
        for (j = 0; j < raster; j++)
80
            dmprintf1(mem, " %02x", row[j]);
81
        dmputc(mem, '\n');
82
    }
83
}
84
#else
85
#  define cmd_print_bits(mem, data, width, height, raster) DO_NOTHING
86
#endif
87
88
/* Get a variable-length integer operand. */
89
#define cmd_getw(var, p)\
90
140M
  BEGIN\
91
140M
    if ( *p < 0x80 ) var = *p++;\
92
140M
    else { const byte *_cbp; var = cmd_get_w(p, &_cbp); p = _cbp; }\
93
140M
  END
94
95
static long
96
cmd_get_w(const byte * p, const byte ** rp)
97
119M
{
98
119M
    int val = *p++ & 0x7f;
99
119M
    int shift = 7;
100
101
228M
    for (; val |= (int)(*p & 0x7f) << shift, *p++ > 0x7f; shift += 7);
102
119M
    *rp = p;
103
119M
    return val;
104
119M
}
105
106
/* Get a variable-length fractional operand. */
107
#define cmd_getfrac(var, p)\
108
0
  BEGIN\
109
0
    if ( !(*p & 1) ) var = (*p++) << 24;\
110
0
    else { const byte *_cbp; var = cmd_get_frac31(p, &_cbp); p = _cbp; }\
111
0
  END
112
static frac31
113
cmd_get_frac31(const byte * p, const byte ** rp)
114
0
{
115
0
    frac31 val = (*p++ & 0xFE) << 24;
116
0
    int shift = 24 - 7;
117
118
0
    for (; val |= (frac31)(*p & 0xFE) << shift, *p++ & 1; shift -= 7);
119
0
    *rp = p;
120
0
    return val;
121
0
}
122
123
/*
124
 * Define the structure for keeping track of the command reading buffer.
125
 *
126
 * The ptr member is only used for passing the current pointer to, and
127
 * receiving an updated pointer from, commands implemented as separate
128
 * procedures: normally it is kept in a register.
129
 */
130
typedef struct command_buf_s {
131
    byte *data;                 /* actual buffer, guaranteed aligned */
132
    uint size;
133
    const byte *ptr;            /* next byte to be read (see above) */
134
    const byte *warn_limit;     /* refill warning point */
135
    const byte *end;            /* byte just beyond valid data */
136
    stream *s;                  /* for refilling buffer */
137
    int end_status;
138
} command_buf_t;
139
140
/* Set the end of a command buffer. */
141
static void
142
set_cb_end(command_buf_t *pcb, const byte *end)
143
1.25M
{
144
1.25M
    pcb->end = end;
145
1.25M
    pcb->warn_limit = pcb->data + (pcb->size - cmd_largest_size + 1);
146
1.25M
    if ( pcb->warn_limit > pcb->end )
147
151k
        pcb->warn_limit = pcb->end;     /**** This is dangerous. Other places ****/
148
                                        /**** assume that the limit is a soft ****/
149
                                        /**** limit and should check 'end'    ****/
150
1.25M
}
151
152
static inline void
153
advance_buffer(command_buf_t *pcb, const byte *cbp)
154
1.10M
{
155
#ifdef DEBUG
156
    stream_state *st = pcb->s->state;
157
158
    top_up_offset_map(st, pcb->data, cbp, pcb->end);
159
#endif
160
1.10M
    memmove(pcb->data, cbp, pcb->end - cbp);
161
1.10M
}
162
163
static inline void
164
next_is_skip(command_buf_t *pcb)
165
7.02k
{
166
#ifdef DEBUG
167
    stream_state *st = pcb->s->state;
168
169
    offset_map_next_data_out_of_band(st);
170
#endif
171
7.02k
}
172
173
/* Read more data into a command buffer. */
174
static int
175
top_up_cbuf(command_buf_t *pcb, const byte **pcbp)
176
1.87M
{
177
1.87M
    uint nread;
178
1.87M
    const byte *cbp = *pcbp;
179
1.87M
    byte *cb_top = pcb->data + (pcb->end - cbp);
180
181
1.87M
    if (cbp < pcb->data || cbp > pcb->end) {
182
0
        errprintf(pcb->s->memory, "Clist I/O error: cbp outside of buffer\n");
183
0
        return (gs_error_ioerror);
184
0
    }
185
186
1.87M
    if (seofp(pcb->s)) {
187
        /* Can't use offset_map, because s_close resets s->state. Don't top up. */
188
776k
        pcb->end_status = pcb->s->end_status;
189
776k
        return 0;
190
776k
    }
191
1.10M
    advance_buffer(pcb, cbp);
192
1.10M
    nread = pcb->end - cb_top;
193
1.10M
    pcb->end_status = sgets(pcb->s, cb_top, nread, &nread);
194
1.10M
    if ( nread == 0 ) {
195
        /* No data for this band at all. */
196
43
        if (cb_top >= pcb->end) {
197
            /* should not happen */
198
0
            *pcbp = pcb->data;
199
0
            pcb->data[0] = cmd_opv_end_run;
200
0
            return_error(gs_error_ioerror);
201
0
        }
202
43
        *cb_top = cmd_opv_end_run;
203
43
        nread = 1;
204
43
    }
205
1.10M
    set_cb_end(pcb, cb_top + nread);
206
1.10M
    process_interrupts(pcb->s->memory);
207
1.10M
    *pcbp = pcb->data;
208
1.10M
    return 0;
209
1.10M
}
210
211
/* Read data from the command buffer and stream. */
212
/* From the command_buffer pcb, read rsize bytes to ptr, starting from cbp.
213
 * Return the new value for pcb->ptr. */
214
static const byte *
215
cmd_read_data(command_buf_t *pcb, byte *ptr, uint rsize, const byte *cbp)
216
1.65M
{
217
1.65M
    if (pcb->end - cbp >= rsize) {
218
1.64M
        memmove(ptr, cbp, rsize);
219
1.64M
        return cbp + rsize;
220
1.64M
    } else {
221
9.58k
        uint cleft = pcb->end - cbp;
222
9.58k
        uint rleft = rsize - cleft;
223
224
9.58k
        memmove(ptr, cbp, cleft);
225
9.58k
        sgets(pcb->s, ptr + cleft, rleft, &rleft);
226
#ifdef DEBUG
227
        {
228
            stream_state *st = pcb->s->state;
229
230
            adjust_offset_map_for_skipped_data(st, (uint)(pcb->end - pcb->data), rleft);
231
        }
232
#endif
233
9.58k
        return pcb->end;
234
9.58k
    }
235
1.65M
}
236
237
/* Read a fixed-size value from the command buffer. */
238
static inline const byte *
239
cmd_copy_value(void *pvar, int var_size, const byte *cbp)
240
271k
{
241
271k
    memcpy(pvar, cbp, var_size);
242
271k
    return cbp + var_size;
243
271k
}
244
#define cmd_get_value(var, cbp)\
245
271k
  cbp = cmd_copy_value(&var, sizeof(var), cbp)
246
247
/*
248
 * Define a buffer structure to hold a serialized halftone. This is
249
 * used only if the serialized halftone is too large to fit into
250
 * the command buffer.
251
 */
252
typedef struct ht_buff_s {
253
    uint    ht_size, read_size;
254
    byte *  pcurr;
255
    byte *  pbuff;
256
} ht_buff_t;
257
258
/*
259
 * Render one band to a specified target device.  Note that if
260
 * action == setup, target may be 0.
261
 */
262
static int read_set_tile_size(command_buf_t *pcb, tile_slot *bits, bool for_pattern);
263
static int read_set_bits(command_buf_t *pcb, tile_slot *bits,
264
                          int compress, gx_clist_state *pcls,
265
                          gx_strip_bitmap *tile, tile_slot **pslot,
266
                          gx_device_clist_reader *cdev, gs_memory_t *mem);
267
static int read_set_misc2(command_buf_t *pcb, gs_gstate *pgs,
268
                           segment_notes *pnotes);
269
static int read_set_color_space(command_buf_t *pcb, gs_gstate *pgs,
270
                                 gx_device_clist_reader *cdev, gs_memory_t *mem);
271
static int read_begin_image(command_buf_t *pcb, gs_image_common_t *pic,
272
                             gs_color_space *pcs);
273
static int read_put_params(command_buf_t *pcb, gs_gstate *pgs,
274
                            gx_device_clist_reader *cdev,
275
                            gs_memory_t *mem);
276
static int read_composite(command_buf_t *pcb, gs_memory_t *mem, gs_composite_t **ppcomp);
277
static int apply_composite(gx_device_clist_reader *cdev, gs_gstate *pgs,
278
                                   gs_memory_t *mem, gs_composite_t *pcomp,
279
                                   int x0, int y0, gx_device **ptarget);
280
static int read_alloc_ht_buff(ht_buff_t *, uint, gs_memory_t *);
281
static int read_ht_segment(ht_buff_t *, command_buf_t *, gs_gstate *,
282
                            gx_device *, gs_memory_t *);
283
284
static const byte *cmd_read_rect(int, gx_cmd_rect *, const byte *);
285
static const byte *cmd_read_short_bits(command_buf_t *pcb, byte *data, int tot_bytes,
286
                                        int width_bytes, int height,
287
                                        uint raster, const byte *cbp);
288
static int cmd_select_map(cmd_map_index, cmd_map_contents,
289
                           gs_gstate *, int **,
290
                           frac **, uint *, gs_memory_t *);
291
static int cmd_create_dev_ht(gx_device_halftone **, gs_memory_t *);
292
static int cmd_resize_halftone(gx_device_halftone **, uint,
293
                                gs_memory_t *);
294
static int clist_decode_segment(gx_path *, int, fixed[6],
295
                                 gs_fixed_point *, int, int,
296
                                 segment_notes);
297
static int clist_do_polyfill(gx_device *, gx_path *,
298
                              const gx_drawing_color *,
299
                              gs_logical_operation_t);
300
301
static inline void
302
enqueue_compositor(gs_composite_t **ppcomp_first, gs_composite_t **ppcomp_last, gs_composite_t *pcomp)
303
12.6M
{
304
12.6M
    if (*ppcomp_last == NULL) {
305
1.38M
        pcomp->prev = pcomp->next = NULL;
306
1.38M
        *ppcomp_last = *ppcomp_first = pcomp;
307
11.2M
    } else {
308
11.2M
        (*ppcomp_last)->next = pcomp;
309
11.2M
        pcomp->prev = *ppcomp_last;
310
11.2M
        pcomp->next = NULL;
311
11.2M
        *ppcomp_last = pcomp;
312
11.2M
    }
313
12.6M
}
314
315
#if 0 /* Appears unused - keep for a while. */
316
static inline gs_composite_t *
317
dequeue_last_compositor(gs_composite_t **ppcomp_first, gs_composite_t **ppcomp_last)
318
{
319
    gs_composite_t *pcomp = *ppcomp_last;
320
321
    if (*ppcomp_first == *ppcomp_last)
322
        *ppcomp_first = *ppcomp_last = NULL;
323
    else {
324
        *ppcomp_last = (*ppcomp_last)->prev;
325
        pcomp->prev = NULL;
326
        (*ppcomp_last)->next = NULL;
327
    }
328
    return pcomp;
329
}
330
331
static inline gs_composite_t *
332
dequeue_first_compositor(gs_composite_t **ppcomp_first, gs_composite_t **ppcomp_last)
333
{
334
    gs_composite_t *pcomp = *ppcomp_first;
335
336
    if (*ppcomp_first == *ppcomp_last)
337
        *ppcomp_first = *ppcomp_last = NULL;
338
    else {
339
        *ppcomp_first = (*ppcomp_first)->next;
340
        pcomp->next = NULL;
341
        (*ppcomp_last)->prev = NULL;
342
    }
343
    return pcomp;
344
}
345
#endif
346
347
static inline int
348
dequeue_compositor(gs_composite_t **ppcomp_first, gs_composite_t **ppcomp_last, gs_composite_t *pcomp)
349
12.6M
{
350
12.6M
    if (*ppcomp_last == *ppcomp_first) {
351
1.38M
        if (*ppcomp_last == pcomp) {
352
1.38M
            *ppcomp_last = *ppcomp_first = NULL;
353
1.38M
            return 0;
354
1.38M
        } else
355
0
            return_error(gs_error_unregistered); /* Must not happen. */
356
11.2M
    } else {
357
11.2M
        gs_composite_t *pcomp_next = pcomp->next, *pcomp_prev = pcomp->prev;
358
359
11.2M
        if (*ppcomp_last == pcomp)
360
1.33M
            *ppcomp_last = pcomp->prev;
361
9.89M
        else
362
9.89M
            pcomp_next->prev = pcomp_prev;
363
11.2M
        if (*ppcomp_first == pcomp)
364
9.89M
            *ppcomp_first = pcomp->next;
365
1.33M
        else
366
1.33M
            pcomp_prev->next = pcomp_next;
367
11.2M
        pcomp->next = pcomp->prev = NULL;
368
11.2M
        return 0;
369
11.2M
    }
370
12.6M
}
371
372
static inline void
373
free_compositor(gs_composite_t *pcomp, gs_memory_t *mem)
374
1.91M
{
375
1.91M
    gs_free_object(mem, pcomp, "free_compositor");
376
1.91M
}
377
378
static inline bool
379
is_null_compositor_op(const byte *cbp, int *length)
380
7.76M
{
381
7.76M
    if (cbp[0] == cmd_opv_end_run) {
382
6.84M
        *length = 1;
383
6.84M
        return true;
384
6.84M
    }
385
925k
    return false;
386
7.76M
}
387
388
static int
389
execute_compositor_queue(gx_device_clist_reader *cdev, gx_device **target, gx_device **tdev, gs_gstate *pgs,
390
                         gs_composite_t **ppcomp_first, gs_composite_t **ppcomp_last, gs_composite_t *pcomp_from,
391
                         int x0, int y0, gs_memory_t *mem, bool idle)
392
850k
{
393
11.5M
    while (pcomp_from != NULL) {
394
10.7M
        gs_composite_t *pcomp = pcomp_from;
395
10.7M
        int code;
396
397
10.7M
        pcomp_from = pcomp->next;
398
10.7M
        code = dequeue_compositor(ppcomp_first, ppcomp_last, pcomp);
399
10.7M
        if (code < 0)
400
0
            return code;
401
10.7M
        pcomp->idle |= idle;
402
10.7M
        code = apply_composite(cdev, pgs, mem, pcomp, x0, y0, target); /* Releases the compositor. */
403
10.7M
        if (code < 0)
404
1
            return code;
405
10.7M
        *tdev = *target;
406
10.7M
    }
407
850k
    return 0;
408
850k
}
409
410
static void
411
mark_as_idle(gs_composite_t *pcomp_start, gs_composite_t *pcomp_end)
412
148k
{
413
148k
    gs_composite_t *pcomp = pcomp_start;
414
415
319k
    while (pcomp != NULL) {
416
319k
        pcomp->idle = true;
417
319k
        if (pcomp == pcomp_end)
418
148k
            break;
419
171k
        pcomp = pcomp->next;
420
171k
    }
421
148k
}
422
423
static inline int
424
drop_compositor_queue(gs_composite_t **ppcomp_first, gs_composite_t **ppcomp_last,
425
                      gs_composite_t *pcomp_from, gs_memory_t *mem, int x0, int y0,
426
                      gs_gstate *pgs)
427
15.0k
{
428
15.0k
    gs_composite_t *pcomp;
429
430
93.0k
    do {
431
93.0k
        int code;
432
433
93.0k
        pcomp = *ppcomp_last;
434
93.0k
        if (pcomp == NULL)
435
0
            return 0;
436
93.0k
        dequeue_compositor(ppcomp_first, ppcomp_last, *ppcomp_last);
437
93.0k
        code = pcomp->type->procs.adjust_ctm(pcomp, x0, y0, pgs);
438
93.0k
        if (code < 0)
439
0
            return code;
440
93.0k
        free_compositor(pcomp, mem);
441
93.0k
    } while (pcomp != pcomp_from);
442
15.0k
    return 0;
443
15.0k
}
444
445
static int
446
read_set_misc_map(byte cb, command_buf_t *pcb, gs_gstate *pgs, gs_memory_t *mem)
447
422k
{
448
422k
    const byte *cbp = pcb->ptr;
449
422k
    frac *mdata;
450
422k
    int *pcomp_num;
451
422k
    uint count = 0;   /* quiet compiler */
452
422k
    cmd_map_contents cont =
453
422k
        (cmd_map_contents)(cb & 0x30) >> 4;
454
422k
    int code;
455
456
422k
    code = cmd_select_map(cb & 0xf, cont,
457
422k
                          pgs,
458
422k
                          &pcomp_num,
459
422k
                          &mdata, &count, mem);
460
461
422k
    if (code < 0)
462
0
        return code;
463
    /* Get component number if relevant */
464
422k
    if (pcomp_num == NULL)
465
422k
        cbp++;
466
0
    else {
467
0
        *pcomp_num = (int) *cbp++;
468
0
        if_debug1m('L', mem, " comp_num=%d", *pcomp_num);
469
0
    }
470
422k
    if (cont == cmd_map_other) {
471
422k
        cbp = cmd_read_data(pcb, (byte *)mdata, count, cbp);
472
473
#ifdef DEBUG
474
        if (gs_debug_c('L')) {
475
            uint i;
476
477
            for (i = 0; i < count / sizeof(*mdata); ++i)
478
                dmprintf1(mem, " 0x%04x", mdata[i]);
479
            dmputc(mem, '\n');
480
        }
481
    } else {
482
        if_debug0m('L', mem, " none\n");
483
#endif
484
422k
    }
485
    /* Recompute the effective transfer, */
486
    /* in case this was a transfer map. */
487
422k
    gx_gstate_set_effective_xfer(pgs);
488
422k
    pcb->ptr = cbp;
489
422k
    return 0;
490
422k
}
491
492
#ifdef DEBUG
493
void clist_debug_op(gs_memory_t *mem, const unsigned char *cbp)
494
{
495
    unsigned char op = *cbp++;
496
    const char *const *sub = cmd_sub_op_names[op >> 4];
497
    if (op == cmd_opv_extend) {
498
        unsigned char op2 = *cbp;
499
        if (cmd_extend_op_names[op2])
500
            dmlprintf1(mem, " %s", cmd_extend_op_names[op2]);
501
        else
502
            dmlprintf1(mem, " ?0x%02x?", (int)op2);
503
    } else if (sub)
504
        dmlprintf1(mem, " %s", sub[op & 0xf]);
505
    else
506
        dmlprintf2(mem, " %s %d", cmd_op_names[op >> 4], op & 0xf);
507
}
508
#endif
509
510
int
511
clist_playback_band(clist_playback_action playback_action, /* lgtm [cpp/use-of-goto] */
512
                    gx_device_clist_reader *cdev, stream *s,
513
                    gx_device *target, int x0, int y0,
514
                    gs_memory_t * mem)
515
154k
{
516
154k
    byte *cbuf_storage;
517
154k
    command_buf_t cbuf;
518
    /* data_bits is for short copy_* bits and copy_* compressed, */
519
    /* must be aligned */
520
154k
    byte *data_bits = 0;
521
154k
    const byte *cbp;
522
154k
    int dev_depth;              /* May vary due to compositing devices */
523
154k
    int dev_depth_bytes;
524
154k
    int odd_delta_shift;
525
154k
    int num_zero_bytes;
526
154k
    gx_device *tdev;
527
154k
    gx_clist_state state;
528
154k
    gx_color_index *set_colors;
529
154k
    gx_device_color *set_dev_colors;
530
154k
    tile_slot *state_slot;
531
154k
    gx_strip_bitmap state_tile; /* parameters for reading tiles */
532
154k
    tile_slot tile_bits;        /* parameters of current tile */
533
154k
    gs_int_point tile_phase;
534
154k
    gx_path path;
535
154k
    bool in_path;
536
154k
    gs_fixed_point ppos;
537
154k
    gx_clip_path clip_path;
538
154k
    bool use_clip;
539
154k
    gx_clip_path *pcpath;
540
154k
    gx_device_cpath_accum clip_accum;
541
154k
    gs_fixed_rect target_box;
542
154k
    struct _cas {
543
154k
        bool lop_enabled;
544
154k
        gx_device_color dcolor;
545
154k
        gs_fixed_point fa_save;
546
154k
    } clip_save;
547
154k
    bool in_clip = false;
548
154k
    gs_gstate gs_gstate;
549
154k
    gx_device_color fill_color = { 0 };
550
154k
    gx_device_color stroke_color = { 0 };
551
154k
    float dash_pattern[cmd_max_dash];
552
154k
    gx_fill_params fill_params;
553
154k
    gx_stroke_params stroke_params;
554
#ifdef DEBUG
555
    gs_halftone_type halftone_type;
556
#endif
557
154k
    union im_ {
558
154k
        gs_image_common_t c;
559
154k
        gs_data_image_t d;
560
154k
        gs_image1_t i1;
561
154k
        gs_image4_t i4;
562
154k
    } image;
563
154k
    gs_int_rect image_rect;
564
154k
    gs_color_space *pcs = NULL;
565
154k
    gx_image_enum_common_t *image_info;
566
154k
    gx_image_plane_t planes[32];
567
154k
    uint data_height;
568
154k
    uint data_size;
569
154k
    byte *data_on_heap;
570
154k
    fixed vs[6];
571
154k
    segment_notes notes;
572
154k
    int data_x;
573
154k
    int code = 0;
574
154k
    ht_buff_t  ht_buff;
575
154k
    gx_device *const orig_target = target;
576
154k
    gx_device_clip clipper_dev;
577
154k
    bool clipper_dev_open = false;
578
154k
    patch_fill_state_t pfs;
579
154k
    int op = 0;
580
154k
    int plane_height = 0;
581
582
#ifdef DEBUG
583
    stream_state *st = s->state; /* Save because s_close resets s->state. */
584
#endif
585
154k
    gs_composite_t *pcomp_first = NULL, *pcomp_last = NULL;
586
154k
    tile_slot bits;             /* parameters for reading bits */
587
588
    /* pad the cbuf data area a bit (just in case) */
589
154k
    if ((cbuf_storage = gs_alloc_bytes(mem, cbuf_size + sizeof(double),
590
154k
                               "clist_playback_band(cbuf_storage)")) == NULL) {
591
0
        return_error(gs_error_VMerror);
592
0
    }
593
154k
    cbuf.data = (byte *)cbuf_storage;
594
154k
    cbuf.size = cbuf_size;
595
154k
    cbuf.s = s;
596
154k
    cbuf.end_status = 0;
597
154k
    set_cb_end(&cbuf, cbuf.data + cbuf.size);
598
154k
    cbp = cbuf.end;
599
600
154k
    pfs.dev = NULL; /* Indicate "not initialized". */
601
154k
    memset(&ht_buff, 0, sizeof(ht_buff));
602
603
    /* The following initializations are to quiet gcc warnings. */
604
154k
    memset(&bits, 0, sizeof(bits));
605
154k
    memset(&tile_bits, 0, sizeof(tile_bits));
606
154k
    memset(&clip_save, 0, sizeof(clip_save));
607
154k
    memset(&state_slot, 0, sizeof(state_slot));
608
154k
    ppos.x = ppos.y = 0;
609
610
154k
in:                             /* Initialize for a new page. */
611
154k
    tdev = target;
612
154k
    set_colors = state.colors;
613
154k
    set_dev_colors = state.tile_color_devn;
614
154k
    use_clip = false;
615
154k
    pcpath = NULL;
616
154k
    if (clipper_dev_open)
617
0
        gx_destroy_clip_device_on_stack(&clipper_dev);
618
154k
    clipper_dev_open = false;
619
154k
    notes = sn_none;
620
154k
    data_x = 0;
621
154k
    {
622
154k
        static const gx_clist_state cls_initial = { cls_initial_values };
623
624
154k
        state = cls_initial;
625
154k
    }
626
154k
    state_tile.id = gx_no_bitmap_id;
627
154k
    state_tile.shift = state_tile.rep_shift = 0;
628
154k
    state_tile.size.x = state_tile.size.y = 0;
629
154k
    state_tile.num_planes = 1;
630
154k
    tile_phase.x = x0;
631
154k
    tile_phase.y = y0;
632
154k
    gx_path_init_local(&path, mem);
633
154k
    in_path = false;
634
    /*
635
     * Initialize the clipping region to the full page.
636
     * (Since we also initialize use_clip to false, this is arbitrary.)
637
     */
638
154k
    {
639
154k
        gs_fixed_rect cbox;
640
641
154k
        gx_cpath_init_local(&clip_path, mem);
642
154k
        cbox.p.x = 0;
643
154k
        cbox.p.y = 0;
644
154k
        cbox.q.x = cdev->width;
645
154k
        cbox.q.y = cdev->height;
646
154k
        gx_cpath_from_rectangle(&clip_path, &cbox);
647
154k
    }
648
154k
    if (target != 0)
649
154k
        (*dev_proc(target, get_clipping_box))(target, &target_box);
650
154k
    memset(&gs_gstate, 0, sizeof(gs_gstate));
651
154k
    GS_STATE_INIT_VALUES_CLIST((&gs_gstate));
652
154k
    code = gs_gstate_initialize(&gs_gstate, mem);
653
154k
    if (code < 0)
654
0
        goto out;
655
154k
    gs_gstate.device = tdev;
656
154k
    gs_gstate.view_clip = NULL; /* Avoid issues in pdf14 fill stroke */
657
154k
    gs_gstate.clip_path = &clip_path;
658
154k
    pcs = gs_cspace_new_DeviceGray(mem);
659
154k
    if (pcs == NULL) {
660
0
        code = gs_note_error(gs_error_VMerror);
661
0
        goto out;
662
0
    }
663
154k
    code = pcs->type->install_cspace(pcs, &gs_gstate);
664
154k
    if (code < 0) {
665
0
        rc_decrement(pcs, "clist_playback_band");
666
0
        goto out;
667
0
    }
668
154k
    gs_gstate.color[0].color_space = pcs; /* we already have one ref */
669
154k
    gs_gstate.color[1].color_space = pcs;
670
154k
    rc_increment_cs(pcs); /* increment for second ref */
671
    /* Initialize client color and device color */
672
154k
    gs_gstate.color[0].ccolor =
673
154k
        gs_alloc_struct(mem, gs_client_color, &st_client_color, "clist_playback_band");
674
154k
    gs_gstate.color[1].ccolor =
675
154k
        gs_alloc_struct(mem, gs_client_color, &st_client_color, "clist_playback_band");
676
154k
    gs_gstate.color[0].dev_color =
677
154k
        gs_alloc_struct(mem, gx_device_color, &st_device_color, "clist_playback_band");
678
154k
    gs_gstate.color[1].dev_color =
679
154k
        gs_alloc_struct(mem, gx_device_color, &st_device_color, "clist_playback_band");
680
154k
    if (gs_gstate.color[0].ccolor == 0 || gs_gstate.color[0].dev_color == 0 ||
681
154k
        gs_gstate.color[1].ccolor == 0 || gs_gstate.color[1].dev_color == 0
682
154k
        ) {
683
0
        gs_free_object(mem, gs_gstate.color[0].ccolor, "clist_playback_band");
684
0
        gs_free_object(mem, gs_gstate.color[1].ccolor, "clist_playback_band");
685
0
        gs_free_object(mem, gs_gstate.color[0].dev_color, "clist_playback_band");
686
0
        gs_free_object(mem, gs_gstate.color[1].dev_color, "clist_playback_band");
687
0
        if (clipper_dev_open)
688
0
            gx_destroy_clip_device_on_stack(&clipper_dev);
689
0
        return_error(gs_error_VMerror);
690
0
    }
691
154k
    gs_gstate.color[0].color_space->pclient_color_space_data =
692
154k
        pcs->pclient_color_space_data;
693
154k
    cs_full_init_color(gs_gstate.color[0].ccolor, pcs);
694
154k
    gx_unset_dev_color(&gs_gstate);
695
696
154k
    gs_gstate.color[1].color_space->pclient_color_space_data =
697
154k
        pcs->pclient_color_space_data;
698
154k
    cs_full_init_color(gs_gstate.color[1].ccolor, pcs);
699
154k
    gx_unset_dev_color(&gs_gstate);
700
701
    /* Remove the ICC link cache and replace with the device link cache
702
       so that we share the cache across bands */
703
154k
    rc_decrement(gs_gstate.icc_link_cache,"clist_playback_band");
704
154k
    gs_gstate.icc_link_cache = cdev->icc_cache_cl;
705
    /* Need to lock during the increment of the link cache */
706
154k
    gx_monitor_enter(cdev->icc_cache_cl->lock);
707
154k
    rc_increment(cdev->icc_cache_cl);
708
154k
    gx_monitor_leave(cdev->icc_cache_cl->lock); /* let everyone run */
709
154k
    if (code < 0)
710
0
        goto out;
711
712
154k
    gs_gstate.line_params.dash.pattern = dash_pattern;
713
154k
    if (tdev != 0) {
714
154k
        gx_set_cmap_procs(&gs_gstate, tdev);
715
154k
    }
716
154k
    gx_gstate_setscreenphase(&gs_gstate, -x0, -y0, gs_color_select_all);
717
#ifdef DEBUG
718
    halftone_type = ht_type_none;
719
#endif
720
154k
    fill_color.ccolor_valid = false;
721
154k
    color_unset(&fill_color);
722
154k
    data_bits = gs_alloc_bytes(mem, data_bits_size,
723
154k
                               "clist_playback_band(data_bits)");
724
154k
    if (data_bits == 0) {
725
0
        code = gs_note_error(gs_error_VMerror);
726
0
        goto out;
727
0
    }
728
54.1M
    while (code >= 0) {
729
54.1M
        int compress;
730
54.1M
        int depth = 0x7badf00d; /* Initialize against indeterminizm. */
731
54.1M
        int raster = 0x7badf00d; /* Initialize against indeterminizm. */
732
54.1M
        byte *source = NULL;  /* Initialize against indeterminizm. */
733
54.1M
        gx_color_index colors[2];
734
54.1M
        gx_color_index *pcolor;
735
54.1M
        gx_device_color *pdcolor = NULL;
736
54.1M
        gs_logical_operation_t log_op;
737
738
        /* Make sure the buffer contains a full command. */
739
54.1M
        if (cbp >= cbuf.warn_limit) {
740
281k
            if (cbuf.end_status < 0) {  /* End of file or error. */
741
2.80k
                if (cbp >= cbuf.end) {
742
0
                    code = (cbuf.end_status == EOFC ? 0 :
743
0
                            gs_note_error(gs_error_ioerror));
744
0
                    break;
745
0
                }
746
278k
            } else {
747
278k
                code = top_up_cbuf(&cbuf, &cbp);
748
278k
                if (code < 0)
749
0
                    goto top_up_failed;
750
278k
            }
751
281k
        }
752
54.1M
        op = *cbp++;
753
#ifdef DEBUG
754
        if (gs_debug_c('L')) {
755
            int64_t offset = clist_file_offset(st, cbp - 1 - cbuf.data);
756
757
            dmlprintf1(mem, "[L] %"PRIu64":", offset);
758
            clist_debug_op(mem, cbp-1);
759
        }
760
#endif
761
54.1M
        switch (op >> 4) {
762
9.62M
            case cmd_op_misc >> 4:
763
9.62M
                switch (op) {
764
658k
                    case cmd_opv_end_run:
765
658k
                        if_debug0m('L', mem, "\n");
766
658k
                        continue;
767
124
                    case cmd_opv_set_tile_size:
768
124
                        cbuf.ptr = cbp;
769
124
                        code = read_set_tile_size(&cbuf, &tile_bits,
770
124
                                    gx_device_is_pattern_clist((gx_device *)cdev));
771
124
                        cbp = cbuf.ptr;
772
124
                        if (code < 0)
773
0
                            goto out;
774
124
                        continue;
775
5.26k
                    case cmd_opv_set_tile_phase:
776
5.26k
                        cmd_getw(state.tile_phase.x, cbp);
777
5.26k
                        cmd_getw(state.tile_phase.y, cbp);
778
5.26k
                        if_debug2m('L', mem, " (%d,%d)\n",
779
5.26k
                                   state.tile_phase.x,
780
5.26k
                                   state.tile_phase.y);
781
5.26k
                        goto set_tile_phase;
782
4.36k
                    case cmd_opv_set_screen_phaseT:
783
4.36k
                        cmd_getw(state.screen_phase[gs_color_select_texture].x, cbp);
784
4.36k
                        cmd_getw(state.screen_phase[gs_color_select_texture].y, cbp);
785
4.36k
                        if_debug2m('L', mem, " (%d,%d)\n",
786
4.36k
                                   state.screen_phase[0].x,
787
4.36k
                                   state.screen_phase[gs_color_select_texture].y);
788
4.36k
                        gx_gstate_setscreenphase(&gs_gstate,
789
4.36k
                                                 state.screen_phase[gs_color_select_texture].x - x0,
790
4.36k
                                                 state.screen_phase[gs_color_select_texture].y - y0,
791
4.36k
                                                 gs_color_select_texture);
792
4.36k
                        continue;
793
0
                    case cmd_opv_set_screen_phaseS:
794
0
                        cmd_getw(state.screen_phase[gs_color_select_source].x, cbp);
795
0
                        cmd_getw(state.screen_phase[gs_color_select_source].y, cbp);
796
0
                        if_debug2m('L', mem, " (%d,%d)\n",
797
0
                                   state.screen_phase[gs_color_select_source].x,
798
0
                                   state.screen_phase[gs_color_select_source].y);
799
0
                        gx_gstate_setscreenphase(&gs_gstate,
800
0
                                                 state.screen_phase[gs_color_select_source].x - x0,
801
0
                                                 state.screen_phase[gs_color_select_source].y - y0,
802
0
                                                 gs_color_select_source);
803
0
                        continue;
804
502
                    case cmd_opv_set_tile_bits:
805
502
                        bits = tile_bits;
806
502
                        compress = 0;
807
1.30M
                      stb:
808
1.30M
                        cbuf.ptr = cbp;
809
1.30M
                        code = read_set_bits(&cbuf, &bits, compress,
810
1.30M
                                             &state, &state_tile, &state_slot,
811
1.30M
                                             cdev, mem);
812
1.30M
                        cbp = cbuf.ptr;
813
1.30M
                        if (code < 0)
814
0
                            goto out;
815
1.30M
                        goto stp;
816
1.30M
                    case cmd_opv_set_bits:
817
1.30M
do_opv_set_bits:
818
1.30M
                        compress = *cbp & 3;
819
1.30M
                        bits.head.depth = *cbp++ >> 2;
820
1.30M
                        cmd_getw(bits.width, cbp);
821
1.30M
                        cmd_getw(bits.height, cbp);
822
1.30M
                        if (op == cmd_opv_set_bits_planar)
823
1.30M
                            cmd_getw(bits.num_planes, cbp);
824
1.30M
                        else
825
1.30M
                            bits.num_planes = 1;
826
1.30M
                        if_debug5m('L', mem, " compress=%d depth=%d size=(%d,%d) planes=%d",
827
1.30M
                                   compress, bits.head.depth,
828
1.30M
                                   bits.width, bits.height, bits.num_planes);
829
1.30M
                        bits.raster =
830
1.30M
                            bitmap_raster(bits.width * bits.head.depth);
831
1.30M
                        bits.x_reps = bits.y_reps = 1;
832
1.30M
                        bits.shift = bits.rep_shift = 0;
833
1.30M
                        goto stb;
834
239
                    case cmd_opv_set_tile_color:
835
239
                        set_colors = state.tile_colors;
836
239
                        if_debug0m('L', mem, "\n");
837
239
                        continue;
838
415k
                    case cmd_opv_set_misc:
839
415k
                        {
840
415k
                            uint cb = *cbp++;
841
842
415k
                            switch (cb >> 6) {
843
41.2k
                                case cmd_set_misc_lop >> 6:
844
41.2k
                                    cmd_getw(state.lop, cbp);
845
41.2k
                                    state.lop = (state.lop << 6) + (cb & 0x3f);
846
41.2k
                                    if_debug1m('L', mem, " lop=0x%x\n", state.lop);
847
41.2k
                                    if (state.lop_enabled)
848
14.1k
                                        gs_gstate.log_op = state.lop;
849
41.2k
                                    break;
850
31.8k
                                case cmd_set_misc_data_x >> 6:
851
31.8k
                                    if (cb & 0x20)
852
31.8k
                                        cmd_getw(data_x, cbp);
853
31.8k
                                    else
854
31.8k
                                        data_x = 0;
855
31.8k
                                    data_x = (data_x << 5) + (cb & 0x1f);
856
31.8k
                                    if_debug1m('L', mem, " data_x=%d\n", data_x);
857
31.8k
                                    break;
858
342k
                                case cmd_set_misc_map >> 6:
859
342k
                                    cbuf.ptr = cbp;
860
342k
                                    code = read_set_misc_map(cb, &cbuf, &gs_gstate, mem);
861
342k
                                    if (code < 0)
862
0
                                        goto out;
863
342k
                                    cbp = cbuf.ptr;
864
342k
                                    break;
865
0
                                case cmd_set_misc_halftone >> 6: {
866
0
                                    uint num_comp;
867
#ifdef DEBUG
868
                                    halftone_type = cb & 0x3f;
869
#endif
870
0
                                    cmd_getw(num_comp, cbp);
871
#ifdef DEBUG
872
                                    if_debug2m('L', mem, " halftone type=%d num_comp=%u\n",
873
                                               halftone_type, num_comp);
874
#endif
875
0
                                    code = cmd_resize_halftone(
876
0
                                                        &gs_gstate.dev_ht[HT_OBJTYPE_DEFAULT],
877
0
                                                        num_comp, mem);
878
0
                                    if (code < 0)
879
0
                                        goto out;
880
0
                                    break;
881
0
                                }
882
0
                                default:
883
0
                                    goto bad_op;
884
415k
                            }
885
415k
                        }
886
415k
                        continue;
887
415k
                    case cmd_opv_enable_lop:
888
27.0k
                        state.lop_enabled = true;
889
27.0k
                        gs_gstate.log_op = state.lop;
890
27.0k
                        if_debug0m('L', mem, "\n");
891
27.0k
                        continue;
892
22.1k
                    case cmd_opv_disable_lop:
893
22.1k
                        state.lop_enabled = false;
894
22.1k
                        gs_gstate.log_op = lop_default;
895
22.1k
                        if_debug0m('L', mem, "\n");
896
22.1k
                        continue;
897
154k
                    case cmd_opv_end_page:
898
154k
                        if_debug0m('L', mem, "\n");
899
                        /*
900
                         * Do end-of-page cleanup, then reinitialize if
901
                         * there are more pages to come.
902
                         */
903
154k
                        goto out;
904
0
                    case cmd_opv_delta_color0:
905
0
                        pcolor = &set_colors[0];
906
0
                        goto delta2_c;
907
7.02M
                    case cmd_opv_delta_color1:
908
7.02M
                        pcolor = &set_colors[1];
909
7.02M
                      delta2_c:set_colors = state.colors;
910
                        /* See comments for cmd_put_color() in gxclutil.c. */
911
7.02M
                        {
912
7.02M
                            gx_color_index delta = 0;
913
7.02M
                            uint data;
914
915
7.02M
                            dev_depth = (tdev->color_info.depth <= 8*sizeof(gx_color_index) ?
916
7.02M
                                         tdev->color_info.depth : 8*sizeof(gx_color_index));
917
7.02M
                            dev_depth_bytes = (dev_depth + 7) >> 3;
918
7.02M
                            switch (dev_depth_bytes) {
919
                                /* For cases with an even number of bytes */
920
0
                                case 8:
921
0
                                    data = *cbp++;
922
0
                                    delta = (((gx_color_index)
923
0
                                        ((data & 0xf0) << 4) + (data & 0x0f)) << 24) << 24;
924
                                    /* fall through */
925
0
                                case 6:
926
0
                                    data = *cbp++;
927
0
                                    delta |= (((gx_color_index)
928
0
                                        ((data & 0xf0) << 4) + (data & 0x0f)) << 16) << 16;
929
                                    /* fall through */
930
5.24M
                                case 4:
931
5.24M
                                    data = *cbp++;
932
5.24M
                                    delta |= ((gx_color_index)
933
5.24M
                                        ((data & 0xf0) << 4) + (data & 0x0f)) << 16;
934
                                    /* fall through */
935
5.24M
                                case 2:
936
5.24M
                                    data = *cbp++;
937
5.24M
                                    delta |= ((gx_color_index)
938
5.24M
                                        ((data & 0xf0) << 4) + (data & 0x0f));
939
5.24M
                                    break;
940
                                /* For cases with an odd number of bytes */
941
0
                                case 7:
942
0
                                    data = *cbp++;
943
0
                                    delta = ((gx_color_index)
944
0
                                        ((data & 0xf0) << 4) + (data & 0x0f)) << 16;
945
                                    /* fall through */
946
0
                                case 5:
947
0
                                    data = *cbp++;
948
0
                                    delta |= ((gx_color_index)
949
0
                                        ((data & 0xf0) << 4) + (data & 0x0f));
950
                                    /* fall through */
951
1.78M
                                case 3:
952
1.78M
                                    data = *cbp++;
953
1.78M
                                    odd_delta_shift = (dev_depth_bytes - 3) * 8;
954
1.78M
                                    delta |= ((gx_color_index)
955
1.78M
                                        ((data & 0xe0) << 3) + (data & 0x1f)) << odd_delta_shift;
956
1.78M
                                    data = *cbp++;
957
1.78M
                                    delta |= ((gx_color_index) ((data & 0xf8) << 2) + (data & 0x07))
958
1.78M
                                                        << (odd_delta_shift + 11);
959
7.02M
                            }
960
7.02M
                            *pcolor += delta - cmd_delta_offsets[dev_depth_bytes];
961
7.02M
                        }
962
7.02M
                        if (sizeof(*pcolor) <= sizeof(ulong))
963
7.02M
                            if_debug1m('L', mem, " 0x%lx\n", (ulong)*pcolor);
964
0
                        else
965
7.02M
                            if_debug2m('L', mem, " 0x%8lx%08lx\n",
966
7.02M
                                       (ulong)(*pcolor >> 8*(sizeof(*pcolor) - sizeof(ulong))), (ulong)*pcolor);
967
7.02M
                        continue;
968
0
                    case cmd_opv_set_copy_color:
969
0
                        state.color_is_alpha = 0;
970
0
                        if_debug0m('L', mem, "\n");
971
0
                        continue;
972
0
                    case cmd_opv_set_copy_alpha:
973
0
                        state.color_is_alpha = 1;
974
0
                        if_debug0m('L', mem, "\n");
975
0
                        continue;
976
0
                    default:
977
0
                        goto bad_op;
978
9.62M
                }
979
                /*NOTREACHED */
980
417
            case cmd_op_set_color0 >> 4:
981
417
                pcolor = &set_colors[0];
982
417
                goto set_color;
983
3.32M
            case cmd_op_set_color1 >> 4:
984
3.32M
                pcolor = &set_colors[1];
985
3.32M
              set_color:set_colors = state.colors;
986
                /*
987
                 * We have a special case for gx_no_color_index. If the low
988
                 * order 4 bits are "cmd_no_color_index" then we really
989
                 * have a value of gx_no_color_index.  Otherwise the these
990
                 * bits indicate the number of low order zero bytes in the
991
                 * value.  See comments for cmd_put_color() in gxclutil.c.
992
                 */
993
3.32M
                num_zero_bytes = op & 0x0f;
994
995
3.32M
                if (num_zero_bytes == cmd_no_color_index)
996
0
                    *pcolor = gx_no_color_index;
997
3.32M
                else {
998
3.32M
                    gx_color_index color = 0;
999
1000
3.32M
                    dev_depth = (tdev->color_info.depth < 8*sizeof(gx_color_index) ?
1001
3.32M
                                 tdev->color_info.depth : 8*sizeof(gx_color_index));
1002
3.32M
                    dev_depth_bytes = (dev_depth + 7) >> 3;
1003
3.32M
                    switch (dev_depth_bytes - num_zero_bytes) {
1004
0
                        case 8:
1005
0
                            color = (gx_color_index) * cbp++;
1006
0
                        case 7:
1007
0
                            color = (color << 8) | (gx_color_index) * cbp++;
1008
0
                        case 6:
1009
0
                            color = (color << 8) | (gx_color_index) * cbp++;
1010
0
                        case 5:
1011
0
                            color = (color << 8) | (gx_color_index) * cbp++;
1012
458k
                        case 4:
1013
458k
                            color = (color << 8) | (gx_color_index) * cbp++;
1014
613k
                        case 3:
1015
613k
                            color = (color << 8) | (gx_color_index) * cbp++;
1016
678k
                        case 2:
1017
678k
                            color = (color << 8) | (gx_color_index) * cbp++;
1018
3.19M
                        case 1:
1019
3.19M
                            color = (color << 8) | (gx_color_index) * cbp++;
1020
3.32M
                        default:
1021
3.32M
                            break;
1022
3.32M
                    }
1023
3.32M
                    color <<= num_zero_bytes * 8;
1024
3.32M
                    *pcolor = color;
1025
3.32M
                }
1026
3.32M
                if (sizeof(*pcolor) <= sizeof(ulong))
1027
3.32M
                    if_debug1m('L', mem, " 0x%lx\n", (ulong)*pcolor);
1028
0
                else
1029
3.32M
                    if_debug2m('L', mem, " 0x%8lx%08lx\n",
1030
3.32M
                               (ulong)(*pcolor >> 8*(sizeof(*pcolor) - sizeof(ulong))), (ulong)*pcolor);
1031
3.32M
                continue;
1032
394k
            case cmd_op_fill_rect >> 4:
1033
422k
            case cmd_op_tile_rect >> 4:
1034
422k
                cbp = cmd_read_rect(op, &state.rect, cbp);
1035
422k
                break;
1036
1.00M
            case cmd_op_fill_rect_short >> 4:
1037
1.19M
            case cmd_op_tile_rect_short >> 4:
1038
1.19M
                state.rect.x += *cbp + cmd_min_short;
1039
1.19M
                state.rect.width += cbp[1] + cmd_min_short;
1040
1.19M
                if (op & 0xf) {
1041
463k
                    state.rect.height += (op & 0xf) + cmd_min_dxy_tiny;
1042
463k
                    cbp += 2;
1043
730k
                } else {
1044
730k
                    state.rect.y += cbp[2] + cmd_min_short;
1045
730k
                    state.rect.height += cbp[3] + cmd_min_short;
1046
730k
                    cbp += 4;
1047
730k
                }
1048
1.19M
                break;
1049
12.2M
            case cmd_op_fill_rect_tiny >> 4:
1050
12.5M
            case cmd_op_tile_rect_tiny >> 4:
1051
12.5M
                if (op & 8)
1052
8.58M
                    state.rect.x += state.rect.width;
1053
3.93M
                else {
1054
3.93M
                    int txy = *cbp++;
1055
1056
3.93M
                    state.rect.x += (txy >> 4) + cmd_min_dxy_tiny;
1057
3.93M
                    state.rect.y += (txy & 0xf) + cmd_min_dxy_tiny;
1058
3.93M
                }
1059
12.5M
                state.rect.width += (op & 7) + cmd_min_dw_tiny;
1060
12.5M
                break;
1061
4.79M
            case cmd_op_copy_mono_planes >> 4:
1062
4.79M
                cmd_getw(plane_height, cbp);
1063
4.79M
                if (plane_height == 0) {
1064
                    /* We are doing a copy mono */
1065
4.79M
                    depth = 1;
1066
4.79M
                } else {
1067
0
                    depth = tdev->color_info.depth;
1068
0
                }
1069
4.79M
                if_debug1m('L', mem, " plane_height=0x%x", plane_height);
1070
4.79M
                goto copy;
1071
4.55k
            case cmd_op_copy_color_alpha >> 4:
1072
4.55k
                if (state.color_is_alpha) {
1073
0
                    if (!(op & 8))
1074
0
                        depth = *cbp++;
1075
0
                } else
1076
4.55k
                    depth = tdev->color_info.depth;
1077
4.55k
                plane_height = 0;
1078
4.80M
              copy:cmd_getw(state.rect.x, cbp);
1079
4.80M
                cmd_getw(state.rect.y, cbp);
1080
4.80M
                if (op & cmd_copy_use_tile) {   /* Use the current "tile". */
1081
#ifdef DEBUG
1082
                    if (state_slot->index != state.tile_index) {
1083
                        mlprintf2(mem, "state_slot->index = %d, state.tile_index = %d!\n",
1084
                                  state_slot->index,
1085
                                  state.tile_index);
1086
                        code = gs_note_error(gs_error_ioerror);
1087
                        goto out;
1088
                    }
1089
#endif
1090
4.67M
                    depth = state_slot->head.depth;
1091
4.67M
                    state.rect.width = state_slot->width;
1092
4.67M
                    state.rect.height = state_slot->height;
1093
4.67M
                    if (state.rect.y + state.rect.height > cdev->height)
1094
2.73k
                        state.rect.height = cdev->height - state.rect.y; /* clamp as writer did */
1095
4.67M
                    raster = state_slot->raster;
1096
4.67M
                    source = (byte *) (state_slot + 1);
1097
4.67M
                } else {        /* Read width, height, bits. */
1098
                    /* depth was set already. */
1099
127k
                    uint width_bits, width_bytes;
1100
127k
                    uint bytes;
1101
127k
                    uchar planes = 1;
1102
127k
                    uint plane_depth = depth;
1103
127k
                    uint pln;
1104
127k
                    byte compression = op & 3;
1105
127k
                    uint out_bytes;
1106
1107
127k
                    cmd_getw(state.rect.width, cbp);
1108
127k
                    cmd_getw(state.rect.height, cbp);
1109
127k
                    if (plane_height != 0) {
1110
0
                        planes = tdev->color_info.num_components;
1111
0
                        plane_depth /= planes;
1112
0
                    }
1113
127k
                    width_bits = state.rect.width * plane_depth;
1114
127k
                    bytes = clist_bitmap_bytes(width_bits,
1115
127k
                                               state.rect.height,
1116
127k
                                               op & 3, &width_bytes,
1117
127k
                                               (uint *)&raster);
1118
127k
                    if (planes > 1) {
1119
0
                        out_bytes = raster * state.rect.height;
1120
0
                        plane_height = state.rect.height;
1121
127k
                    } else {
1122
127k
                        out_bytes = bytes;
1123
127k
                    }
1124
                    /* copy_mono and copy_color/alpha */
1125
                    /* ensure that the bits will fit in a single buffer, */
1126
                    /* even after decompression if compressed. */
1127
#ifdef DEBUG
1128
                    if (planes * out_bytes > data_bits_size) {
1129
                        mlprintf6(mem, "bitmap size exceeds buffer!  width=%d raster=%d height=%d\n    file pos %"PRId64" buf pos %d/%d\n",
1130
                                  state.rect.width, raster,
1131
                                  state.rect.height,
1132
                                  stell(s), (int)(cbp - cbuf.data),
1133
                                  (int)(cbuf.end - cbuf.data));
1134
                        code = gs_note_error(gs_error_ioerror);
1135
                        goto out;
1136
                    }
1137
#endif
1138
255k
                    for (pln = 0; pln < planes; pln++) {
1139
127k
                        byte *plane_bits = data_bits + pln * plane_height * raster;
1140
1141
                        /* Fill the cbuf if needed to get the data for the plane */
1142
127k
                        if (cbp + out_bytes >= cbuf.warn_limit) {
1143
2.89k
                            code = top_up_cbuf(&cbuf, &cbp);
1144
2.89k
                            if (code < 0)
1145
0
                                goto top_up_failed;
1146
2.89k
                        }
1147
127k
                        if (pln)
1148
0
                            compression = *cbp++;
1149
1150
127k
                        if (compression == cmd_compress_const) {
1151
0
                            cbp = cmd_read_data(&cbuf, plane_bits, 1, cbp);
1152
0
                            if (width_bytes > 0 && state.rect.height > 0)
1153
0
                                memset(plane_bits+1, *plane_bits, width_bytes * state.rect.height - 1);
1154
0
                            if (pln == 0)
1155
0
                                source = data_bits;
1156
1157
127k
                        } else if (compression) {       /* Decompress the image data. */
1158
0
                            stream_cursor_read r;
1159
0
                            stream_cursor_write w;
1160
1161
                            /* We don't know the data length a priori, */
1162
                            /* so to be conservative, we read */
1163
                            /* the uncompressed size. */
1164
0
                            uint cleft = cbuf.end - cbp;
1165
1166
0
                            if (cleft < bytes  && !cbuf.end_status) {
1167
0
                                uint nread = cbuf_size - cleft;
1168
1169
0
                                advance_buffer(&cbuf, cbp);
1170
0
                                cbuf.end_status = sgets(s, cbuf.data + cleft, nread, &nread);
1171
0
                                set_cb_end(&cbuf, cbuf.data + cleft + nread);
1172
0
                                cbp = cbuf.data;
1173
0
                            }
1174
0
                            r.ptr = cbp - 1;
1175
0
                            r.limit = cbuf.end - 1;
1176
0
                            w.ptr = plane_bits - 1;
1177
0
                            w.limit = w.ptr + data_bits_size;
1178
0
                            switch (compression) {
1179
0
                                case cmd_compress_rle:
1180
0
                                    {
1181
0
                                        stream_RLD_state sstate;
1182
1183
0
                                        clist_rld_init(&sstate);
1184
                                        /* The process procedure can't fail. */
1185
0
                                        (*s_RLD_template.process)
1186
0
                                            ((stream_state *)&sstate, &r, &w, true);
1187
0
                                    }
1188
0
                                    break;
1189
0
                                case cmd_compress_cfe:
1190
0
                                    {
1191
0
                                        stream_CFD_state sstate;
1192
1193
0
                                        clist_cfd_init(&sstate,
1194
0
                                        width_bytes << 3 /*state.rect.width */ ,
1195
0
                                                       state.rect.height, mem);
1196
                                        /* The process procedure can't fail. */
1197
0
                                        (*s_CFD_template.process)
1198
0
                                            ((stream_state *)&sstate, &r, &w, true);
1199
0
                                        (*s_CFD_template.release)
1200
0
                                            ((stream_state *)&sstate);
1201
0
                                    }
1202
0
                                    break;
1203
0
                                default:
1204
0
                                    goto bad_op;
1205
0
                            }
1206
0
                            cbp = r.ptr + 1;
1207
0
                            if (pln == 0)
1208
0
                                source = data_bits;
1209
127k
                        } else if ((state.rect.height > 1 && width_bytes != raster) ||
1210
127k
                                   (plane_height != 0)) {
1211
4.30k
                            cbp = cmd_read_short_bits(&cbuf, plane_bits, bytes, width_bytes,
1212
4.30k
                                                      state.rect.height, raster, cbp);
1213
4.30k
                            if (pln == 0)
1214
4.30k
                                source = data_bits;
1215
123k
                        } else {
1216
                            /* Never used for planar data */
1217
123k
                            cbp = cmd_read_data(&cbuf, cbuf.data, bytes, cbp);
1218
123k
                            source = cbuf.data;
1219
123k
                        }
1220
127k
                    }
1221
#ifdef DEBUG
1222
                    if (gs_debug_c('L')) {
1223
                        dmprintf2(mem, " depth=%d, data_x=%d\n",
1224
                                  depth, data_x);
1225
                        cmd_print_bits(mem, source, state.rect.width,
1226
                                       state.rect.height, raster);
1227
                    }
1228
#endif
1229
127k
                }
1230
4.80M
                break;
1231
4.80M
            case cmd_op_delta_tile_index >> 4:
1232
1.05M
                state.tile_index += (int)(op & 0xf) - 8;
1233
1.05M
                goto sti;
1234
2.16M
            case cmd_op_set_tile_index >> 4:
1235
2.16M
                state.tile_index =
1236
2.16M
                    ((op & 0xf) << 8) + *cbp++;
1237
3.21M
              sti:state_slot =
1238
3.21M
                    (tile_slot *) (cdev->cache_chunk->data +
1239
3.21M
                                 cdev->tile_table[state.tile_index].offset);
1240
3.21M
                if_debug2m('L', mem, " index=%u offset=%lu\n",
1241
3.21M
                           state.tile_index,
1242
3.21M
                           cdev->tile_table[state.tile_index].offset);
1243
3.21M
                state_tile.data = (byte *) (state_slot + 1);
1244
4.52M
              stp:state_tile.size.x = state_slot->width;
1245
4.52M
                state_tile.size.y = state_slot->height;
1246
4.52M
                state_tile.raster = state_slot->raster;
1247
4.52M
                state_tile.rep_width = state_tile.size.x /
1248
4.52M
                    state_slot->x_reps;
1249
4.52M
                state_tile.rep_height = state_tile.size.y /
1250
4.52M
                    state_slot->y_reps;
1251
4.52M
                state_tile.rep_shift = state_slot->rep_shift;
1252
4.52M
                state_tile.shift = state_slot->shift;
1253
4.52M
                state_tile.id = state_slot->id;
1254
4.52M
                state_tile.num_planes = state_slot->num_planes;
1255
4.53M
set_tile_phase:
1256
4.53M
                if (state_tile.size.x)
1257
4.53M
                    tile_phase.x =
1258
4.53M
                        (state.tile_phase.x + x0) % state_tile.size.x;
1259
                /*
1260
                 * The true tile height for shifted tiles is not
1261
                 * size.y: see gxbitmap.h for the computation.
1262
                 */
1263
4.53M
                if (state_tile.size.y) {
1264
4.53M
                    int full_height;
1265
1266
4.53M
                    if (state_tile.shift == 0)
1267
4.53M
                        full_height = state_tile.size.y;
1268
0
                    else
1269
0
                        full_height = state_tile.rep_height *
1270
0
                                    (state_tile.rep_width /
1271
0
                                     igcd(state_tile.rep_shift,
1272
0
                                          state_tile.rep_width));
1273
4.53M
                    tile_phase.y = (state.tile_phase.y + y0) % full_height;
1274
4.53M
                }
1275
4.53M
                continue;
1276
3.62M
            case cmd_op_misc2 >> 4:
1277
3.62M
                switch (op) {
1278
0
                    case cmd_opv_set_bits_planar:
1279
0
                        goto do_opv_set_bits;
1280
3.46k
                    case cmd_opv_set_fill_adjust:
1281
3.46k
                        cmd_get_value(gs_gstate.fill_adjust.x, cbp);
1282
3.46k
                        cmd_get_value(gs_gstate.fill_adjust.y, cbp);
1283
3.46k
                        if_debug2m('L', mem, " (%g,%g)\n",
1284
3.46k
                                   fixed2float(gs_gstate.fill_adjust.x),
1285
3.46k
                                   fixed2float(gs_gstate.fill_adjust.y));
1286
3.46k
                        continue;
1287
241k
                    case cmd_opv_set_ctm:
1288
241k
                        {
1289
241k
                            gs_matrix mat;
1290
1291
241k
                            cbp = cmd_read_matrix(&mat, cbp);
1292
241k
                            if_debug6m('L', mem, " [%g %g %g %g %g %g]\n",
1293
241k
                                       mat.xx, mat.xy, mat.yx, mat.yy,
1294
241k
                                       mat.tx, mat.ty);
1295
241k
                            mat.tx -= x0;
1296
241k
                            mat.ty -= y0;
1297
241k
                            gs_gstate_setmatrix(&gs_gstate, &mat);
1298
241k
                        }
1299
241k
                        continue;
1300
176k
                    case cmd_opv_set_misc2:
1301
176k
                        cbuf.ptr = cbp;
1302
176k
                        code = read_set_misc2(&cbuf, &gs_gstate, &notes);
1303
176k
                        cbp = cbuf.ptr;
1304
176k
                        if (code < 0)
1305
0
                            goto out;
1306
176k
                        continue;
1307
176k
                    case cmd_opv_set_dash:
1308
32.0k
                        {
1309
32.0k
                            int nb = *cbp++;
1310
32.0k
                            int n = nb & 0x3f;
1311
32.0k
                            float dot_length, offset;
1312
1313
32.0k
                            cmd_get_value(dot_length, cbp);
1314
32.0k
                            cmd_get_value(offset, cbp);
1315
32.0k
                            memcpy(dash_pattern, cbp, n * sizeof(float));
1316
1317
32.0k
                            gx_set_dash(&gs_gstate.line_params.dash,
1318
32.0k
                                        dash_pattern, n, offset,
1319
32.0k
                                        NULL);
1320
32.0k
                            gx_set_dash_adapt(&gs_gstate.line_params.dash,
1321
32.0k
                                              (nb & 0x80) != 0);
1322
32.0k
                            gx_set_dot_length(&gs_gstate.line_params,
1323
32.0k
                                              dot_length,
1324
32.0k
                                              (nb & 0x40) != 0);
1325
#ifdef DEBUG
1326
                            if (gs_debug_c('L')) {
1327
                                int i;
1328
1329
                                dmprintf4(mem, " dot=%g(mode %d) adapt=%d offset=%g [",
1330
                                         dot_length,
1331
                                         (nb & 0x40) != 0,
1332
                                         (nb & 0x80) != 0, offset);
1333
                                for (i = 0; i < n; ++i)
1334
                                    dmprintf1(mem, "%g ", dash_pattern[i]);
1335
                                dmputs(mem, "]\n");
1336
                            }
1337
#endif
1338
32.0k
                            cbp += n * sizeof(float);
1339
32.0k
                        }
1340
32.0k
                        break;
1341
475
                    case cmd_opv_enable_clip:
1342
475
                        pcpath = (use_clip ? &clip_path : NULL);
1343
475
                        if (pcpath) {
1344
46
                            code = gx_cpath_ensure_path_list(pcpath);
1345
46
                            if (code < 0)
1346
0
                                goto out;
1347
46
                        }
1348
475
                        if (clipper_dev_open)
1349
0
                            gx_destroy_clip_device_on_stack(&clipper_dev);
1350
475
                        clipper_dev_open = false;
1351
475
                        if_debug0m('L', mem, "\n");
1352
475
                        break;
1353
956
                    case cmd_opv_disable_clip:
1354
956
                        pcpath = NULL;
1355
956
                        if (clipper_dev_open)
1356
0
                            gx_destroy_clip_device_on_stack(&clipper_dev);
1357
956
                        clipper_dev_open = false;
1358
956
                        if_debug0m('L', mem, "\n");
1359
956
                        break;
1360
393k
                    case cmd_opv_begin_clip:
1361
393k
                        pcpath = NULL;
1362
393k
                        if (clipper_dev_open)
1363
100
                            gx_destroy_clip_device_on_stack(&clipper_dev);
1364
393k
                        clipper_dev_open = false;
1365
393k
                        in_clip = true;
1366
393k
                        if_debug0m('L', mem, "\n");
1367
393k
                        code = gx_cpath_reset(&clip_path);
1368
393k
                        if (code < 0)
1369
0
                            goto out;
1370
393k
                        gx_cpath_accum_begin(&clip_accum, mem, false);
1371
393k
                        gx_cpath_accum_set_cbox(&clip_accum,
1372
393k
                                                &target_box);
1373
393k
                        tdev = (gx_device *)&clip_accum;
1374
393k
                        clip_save.lop_enabled = state.lop_enabled;
1375
393k
                        clip_save.dcolor = fill_color;
1376
393k
                        clip_save.fa_save.x = gs_gstate.fill_adjust.x;
1377
393k
                        clip_save.fa_save.y = gs_gstate.fill_adjust.y;
1378
393k
                        cmd_getw(gs_gstate.fill_adjust.x, cbp);
1379
393k
                        cmd_getw(gs_gstate.fill_adjust.y, cbp);
1380
                        /* temporarily set a solid color */
1381
393k
                        color_set_pure(&fill_color, (gx_color_index)1);
1382
393k
                        state.lop_enabled = false;
1383
393k
                        gs_gstate.log_op = lop_default;
1384
393k
                        break;
1385
393k
                    case cmd_opv_end_clip:
1386
393k
                        if_debug0m('L', mem, "\n");
1387
393k
                        gx_cpath_accum_end(&clip_accum, &clip_path);
1388
393k
                        tdev = target;
1389
                        /*
1390
                         * If the entire band falls within the clip
1391
                         * path, no clipping is needed.
1392
                         */
1393
393k
                        {
1394
393k
                            gs_fixed_rect cbox;
1395
1396
393k
                            gx_cpath_inner_box(&clip_path, &cbox);
1397
393k
                            use_clip =
1398
393k
                                !(cbox.p.x <= target_box.p.x &&
1399
393k
                                  cbox.q.x >= target_box.q.x &&
1400
393k
                                  cbox.p.y <= target_box.p.y &&
1401
393k
                                  cbox.q.y >= target_box.q.y);
1402
393k
                        }
1403
393k
                        pcpath = (use_clip ? &clip_path : NULL);
1404
393k
                        if (pcpath) {
1405
259k
                            code = gx_cpath_ensure_path_list(pcpath);
1406
259k
                            if (code < 0)
1407
0
                                goto out;
1408
259k
                        }
1409
393k
                        if (clipper_dev_open)
1410
0
                            gx_destroy_clip_device_on_stack(&clipper_dev);
1411
393k
                        clipper_dev_open = false;
1412
393k
                        state.lop_enabled = clip_save.lop_enabled;
1413
393k
                        gs_gstate.log_op =
1414
393k
                            (state.lop_enabled ? state.lop :
1415
393k
                             lop_default);
1416
393k
                        fill_color = clip_save.dcolor;
1417
                        /* restore the fill_adjust if it was changed by begin_clip */
1418
393k
                        gs_gstate.fill_adjust.x = clip_save.fa_save.x;
1419
393k
                        gs_gstate.fill_adjust.y = clip_save.fa_save.y;
1420
393k
                        in_clip = false;
1421
393k
                        break;
1422
35.6k
                    case cmd_opv_set_color_space:
1423
35.6k
                        cbuf.ptr = cbp;
1424
35.6k
                        code = read_set_color_space(&cbuf, &gs_gstate, cdev, mem);
1425
35.6k
                        pcs = gs_gstate.color[0].color_space;
1426
35.6k
                        cbp = cbuf.ptr;
1427
35.6k
                        if (code < 0) {
1428
0
                            if (code == gs_error_rangecheck)
1429
0
                                goto bad_op;
1430
0
                            goto out;
1431
0
                        }
1432
35.6k
                        break;
1433
35.6k
                    case cmd_op_fill_rect_hl:
1434
0
                        {
1435
0
                            gs_fixed_rect rect_hl;
1436
1437
0
                            cbp = cmd_read_rect(op & 0xf0, &state.rect, cbp);
1438
0
                            if (fill_color.type != gx_dc_type_devn) {
1439
0
                                if_debug0m('L', mem, "hl rect fill without devn color\n");
1440
0
                                code = gs_note_error(gs_error_typecheck);
1441
0
                                goto out;
1442
0
                            }
1443
0
                            if_debug4m('L', mem, " x=%d y=%d w=%d h=%d\n",
1444
0
                                       state.rect.x, state.rect.y,
1445
0
                                       state.rect.width,state.rect.height);
1446
0
                            rect_hl.p.x = int2fixed(state.rect.x - x0);
1447
0
                            rect_hl.p.y = int2fixed(state.rect.y - y0);
1448
0
                            rect_hl.q.x = int2fixed(state.rect.width) + rect_hl.p.x;
1449
0
                            rect_hl.q.y = int2fixed(state.rect.height) + rect_hl.p.y;
1450
0
                            code = dev_proc(tdev, fill_rectangle_hl_color) (tdev,
1451
0
                                                        &rect_hl, NULL,
1452
0
                                                        &fill_color, NULL);
1453
0
                        }
1454
0
                        continue;
1455
34.7k
                    case cmd_opv_begin_image_rect:
1456
34.7k
                        cbuf.ptr = cbp;
1457
34.7k
                        code = read_begin_image(&cbuf, &image.c, pcs);
1458
34.7k
                        cbp = cbuf.ptr;
1459
34.7k
                        if (code < 0)
1460
0
                            goto out;
1461
34.7k
                        {
1462
34.7k
                            uint diff;
1463
1464
34.7k
                            cmd_getw(image_rect.p.x, cbp);
1465
34.7k
                            cmd_getw(image_rect.p.y, cbp);
1466
34.7k
                            cmd_getw(diff, cbp);
1467
34.7k
                            image_rect.q.x = image.d.Width - diff;
1468
34.7k
                            cmd_getw(diff, cbp);
1469
34.7k
                            image_rect.q.y = image.d.Height - diff;
1470
34.7k
                            if_debug4m('L', mem, " rect=(%d,%d),(%d,%d)",
1471
34.7k
                                       image_rect.p.x, image_rect.p.y,
1472
34.7k
                                       image_rect.q.x, image_rect.q.y);
1473
34.7k
                        }
1474
34.7k
                        goto ibegin;
1475
10.2k
                    case cmd_opv_begin_image:
1476
10.2k
                        cbuf.ptr = cbp;
1477
10.2k
                        code = read_begin_image(&cbuf, &image.c, pcs);
1478
10.2k
                        cbp = cbuf.ptr;
1479
10.2k
                        if (code < 0)
1480
0
                            goto out;
1481
10.2k
                        image_rect.p.x = 0;
1482
10.2k
                        image_rect.p.y = 0;
1483
10.2k
                        image_rect.q.x = image.d.Width;
1484
10.2k
                        image_rect.q.y = image.d.Height;
1485
10.2k
                        if_debug2m('L', mem, " size=(%d,%d)",
1486
10.2k
                                  image.d.Width, image.d.Height);
1487
44.9k
ibegin:                 if_debug0m('L', mem, "\n");
1488
44.9k
                        {
1489
                            /* Processing an image operation */
1490
44.9k
                            dev_proc(tdev, set_graphics_type_tag)(tdev, GS_IMAGE_TAG);/* FIXME: what about text bitmaps? */
1491
44.9k
                            image.i4.override_in_smask = 0;
1492
44.9k
                            code = (*dev_proc(tdev, begin_typed_image))
1493
44.9k
                                (tdev, &gs_gstate, NULL,
1494
44.9k
                                 (const gs_image_common_t *)&image,
1495
44.9k
                                 &image_rect, &fill_color, pcpath, mem,
1496
44.9k
                                 &image_info);
1497
44.9k
                        }
1498
44.9k
                        if (code < 0)
1499
0
                            goto out;
1500
44.9k
                        break;
1501
44.9k
                    case cmd_opv_image_plane_data:
1502
0
                        cmd_getw(data_height, cbp);
1503
0
                        if (data_height == 0) {
1504
0
                            if_debug0m('L', mem, " done image\n");
1505
0
                            code = gx_image_end(image_info, true);
1506
0
                            if (code < 0)
1507
0
                                goto out;
1508
0
                            continue;
1509
0
                        }
1510
0
                        {
1511
0
                            uint flags;
1512
0
                            int plane;
1513
0
                            uint raster1 = 0xbaadf00d; /* Initialize against indeterminizm. */
1514
1515
0
                            cmd_getw(flags, cbp);
1516
0
                            for (plane = 0;
1517
0
                                 plane < image_info->num_planes;
1518
0
                                 ++plane, flags >>= 1) {
1519
0
                                if (flags & 1) {
1520
0
                                    if (cbuf.end - cbp <
1521
0
                                        2 * cmd_max_intsize(sizeof(uint))) {
1522
0
                                        code = top_up_cbuf(&cbuf, &cbp);
1523
0
                                        if (code < 0)
1524
0
                                            goto top_up_failed;
1525
0
                                    }
1526
0
                                    cmd_getw(planes[plane].raster, cbp);
1527
0
                                    if ((raster1 = planes[plane].raster) != 0)
1528
0
                                        cmd_getw(data_x, cbp);
1529
0
                                } else {
1530
0
                                    planes[plane].raster = raster1;
1531
0
                                }
1532
0
                                planes[plane].data_x = data_x;
1533
0
                            }
1534
0
                        }
1535
0
                        goto idata;
1536
256k
                    case cmd_opv_image_data:
1537
256k
                        cmd_getw(data_height, cbp);
1538
256k
                        if (data_height == 0) {
1539
44.9k
                            if_debug0m('L', mem, " done image\n");
1540
44.9k
                            code = gx_image_end(image_info, true);
1541
44.9k
                            if (code < 0)
1542
0
                                goto out;
1543
44.9k
                            continue;
1544
44.9k
                        }
1545
211k
                        {
1546
211k
                            uint bytes_per_plane;
1547
211k
                            int plane;
1548
1549
211k
                            cmd_getw(bytes_per_plane, cbp);
1550
211k
                            if_debug2m('L', mem, " height=%u raster=%u\n",
1551
211k
                                       data_height, bytes_per_plane);
1552
211k
                            for (plane = 0;
1553
422k
                                 plane < image_info->num_planes;
1554
211k
                                 ++plane
1555
211k
                                 ) {
1556
211k
                                planes[plane].data_x = data_x;
1557
211k
                                planes[plane].raster = bytes_per_plane;
1558
211k
                            }
1559
211k
                        }
1560
211k
idata:                  data_size = 0;
1561
211k
                        {
1562
211k
                            int plane;
1563
1564
422k
                            for (plane = 0; plane < image_info->num_planes;
1565
211k
                                 ++plane)
1566
211k
                                data_size += planes[plane].raster;
1567
211k
                        }
1568
211k
                        data_size *= data_height;
1569
211k
                        data_on_heap = 0;
1570
211k
                        if (cbuf.end - cbp < data_size) {
1571
42.7k
                            code = top_up_cbuf(&cbuf, &cbp);
1572
42.7k
                            if (code < 0)
1573
0
                                goto top_up_failed;
1574
42.7k
                        }
1575
211k
                        if (cbuf.end - cbp >= data_size) {
1576
204k
                            planes[0].data = cbp;
1577
204k
                            cbp += data_size;
1578
204k
                        } else {
1579
7.02k
                            uint cleft = cbuf.end - cbp;
1580
7.02k
                            uint rleft = data_size - cleft;
1581
7.02k
                            byte *rdata;
1582
1583
7.02k
                            if (data_size > cbuf.end - cbuf.data) {
1584
                                /* Allocate a separate buffer. */
1585
7.02k
                                rdata = data_on_heap =
1586
7.02k
                                    gs_alloc_bytes(mem, data_size,
1587
7.02k
                                                   "clist image_data");
1588
7.02k
                                if (rdata == 0) {
1589
0
                                    code = gs_note_error(gs_error_VMerror);
1590
0
                                    goto out;
1591
0
                                }
1592
7.02k
                            } else
1593
0
                                rdata = cbuf.data;
1594
7.02k
                            memmove(rdata, cbp, cleft);
1595
7.02k
                            if (data_on_heap)
1596
7.02k
                                next_is_skip(&cbuf);
1597
7.02k
                            if (sgets(s, rdata + cleft, rleft, &rleft) < 0) {
1598
0
                                code = gs_note_error(gs_error_unregistered); /* Must not happen. */
1599
0
                                goto out;
1600
0
                            }
1601
7.02k
                            planes[0].data = rdata;
1602
7.02k
                            cbp = cbuf.end;     /* force refill */
1603
7.02k
                        }
1604
211k
                        {
1605
211k
                            int plane;
1606
211k
                            const byte *data = planes[0].data;
1607
1608
211k
                            for (plane = 0;
1609
422k
                                 plane < image_info->num_planes;
1610
211k
                                 ++plane
1611
211k
                                 ) {
1612
211k
                                if (planes[plane].raster == 0)
1613
0
                                    planes[plane].data = 0;
1614
211k
                                else {
1615
211k
                                    planes[plane].data = data;
1616
211k
                                    data += planes[plane].raster *
1617
211k
                                        data_height;
1618
211k
                                }
1619
211k
                            }
1620
211k
                        }
1621
#ifdef DEBUG
1622
                        if (gs_debug_c('L')) {
1623
                            int plane;
1624
1625
                            for (plane = 0; plane < image_info->num_planes;
1626
                                 ++plane)
1627
                                if (planes[plane].data != 0)
1628
                                    cmd_print_bits(mem,
1629
                                                   planes[plane].data,
1630
                                                   image_rect.q.x -
1631
                                                   image_rect.p.x,
1632
                                                   data_height,
1633
                                                   planes[plane].raster);
1634
                        }
1635
#endif
1636
211k
                        code = gx_image_plane_data(image_info, planes,
1637
211k
                                                   data_height);
1638
211k
                        if (code < 0)
1639
0
                            gx_image_end(image_info, false);
1640
211k
                        if (data_on_heap)
1641
7.02k
                            gs_free_object(mem, data_on_heap,
1642
211k
                                           "clist image_data");
1643
211k
                        data_x = 0;
1644
211k
                        if (code < 0)
1645
0
                            goto out;
1646
211k
                        continue;
1647
2.04M
                    case cmd_opv_extend:
1648
2.04M
                        switch (*cbp++) {
1649
0
                            case cmd_opv_ext_put_params:
1650
0
                                if_debug0m('L', mem, "put_params\n");
1651
0
                                cbuf.ptr = cbp;
1652
0
                                code = read_put_params(&cbuf, &gs_gstate,
1653
0
                                                        cdev, mem);
1654
0
                                cbp = cbuf.ptr;
1655
0
                                if (code > 0)
1656
0
                                    break; /* empty list */
1657
0
                                if (code < 0)
1658
0
                                    goto out;
1659
0
                                if (playback_action == playback_action_setup)
1660
0
                                    goto out;
1661
0
                                break;
1662
768k
                            case cmd_opv_ext_composite:
1663
768k
                                if_debug0m('L', mem, " ext_composite\n");
1664
768k
                                cbuf.ptr = cbp;
1665
                                /*
1666
                                 * The screen phase may have been changed during
1667
                                 * the processing of masked images.
1668
                                 */
1669
768k
                                gx_gstate_setscreenphase(&gs_gstate,
1670
768k
                                            -x0, -y0, gs_color_select_all);
1671
768k
                                cbp -= 2; /* Step back to simplify the cycle invariant below. */
1672
20.3M
                                for (;;) {
1673
                                    /* This internal loop looks ahead for compositor commands and
1674
                                       copies them into a temporary queue. Compositors, which do not paint something,
1675
                                       are marked as idle and later executed with a reduced functionality
1676
                                       for reducing time and memory expense. */
1677
20.3M
                                    int len;
1678
1679
20.3M
                                    if (cbp >= cbuf.warn_limit) {
1680
6.27k
                                        code = top_up_cbuf(&cbuf, &cbp);
1681
6.27k
                                        if (code < 0)
1682
0
                                            goto out;
1683
6.27k
                                    }
1684
#ifdef DEBUG
1685
                                    if (gs_debug_c('L')) {
1686
                                       long offset = (long)clist_file_offset(st, cbp - cbuf.data);
1687
1688
                                       dmlprintf1(mem, "[L]  %ld:", offset);
1689
                                       clist_debug_op(mem, cbp);
1690
                                       dmlprintf(mem, "\n");
1691
                                    }
1692
#endif
1693
20.3M
                                    if (cbp[0] == cmd_opv_extend && cbp[1] == cmd_opv_ext_composite) {
1694
12.6M
                                        gs_composite_t *pcomp, *pcomp_opening;
1695
12.6M
                                        gs_compositor_closing_state closing_state;
1696
1697
12.6M
                                        cbuf.ptr = cbp += 2;
1698
12.6M
                                        code = read_composite(&cbuf, mem, &pcomp);
1699
12.6M
                                        if (code < 0)
1700
0
                                            goto out;
1701
12.6M
                                        cbp = cbuf.ptr;
1702
12.6M
                                        if (pcomp == NULL)
1703
0
                                            continue;
1704
12.6M
                                        if (gs_is_pdf14trans_compositor(pcomp) &&
1705
12.6M
                                            playback_action == playback_action_render_no_pdf14) {
1706
                                            /* free the compositor object */
1707
0
                                            gs_free_object(mem, pcomp, "read_composite");
1708
0
                                            pcomp = NULL;
1709
0
                                            continue;
1710
0
                                        }
1711
12.6M
                                        pcomp_opening = pcomp_last;
1712
12.6M
                                        closing_state = pcomp->type->procs.is_closing(pcomp, &pcomp_opening, tdev);
1713
12.6M
                                        switch(closing_state)
1714
12.6M
                                        {
1715
0
                                        default:
1716
0
                                            code = (int)closing_state;
1717
0
                                            if (code >= 0)
1718
0
                                                code = gs_note_error(gs_error_unregistered); /* Must not happen. */
1719
0
                                            goto out;
1720
10.5M
                                        case COMP_ENQUEUE:
1721
                                            /* Enqueue. */
1722
10.5M
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1723
10.5M
                                            break;
1724
0
                                        case COMP_EXEC_IDLE:
1725
                                            /* Execute idle. */
1726
0
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1727
0
                                            code = execute_compositor_queue(cdev, &target, &tdev,
1728
0
                                                &gs_gstate, &pcomp_first, &pcomp_last, pcomp_opening, x0, y0, mem, true);
1729
0
                                            if (code < 0)
1730
0
                                                goto out;
1731
0
                                            break;
1732
81.8k
                                        case COMP_EXEC_QUEUE:
1733
                                            /* The opening command was executed. Execute the queue. */
1734
81.8k
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1735
81.8k
                                            code = execute_compositor_queue(cdev, &target, &tdev,
1736
81.8k
                                                &gs_gstate, &pcomp_first, &pcomp_last, pcomp_first, x0, y0, mem, false);
1737
81.8k
                                            if (code < 0)
1738
0
                                                goto out;
1739
81.8k
                                            break;
1740
81.8k
                                        case COMP_REPLACE_PREV:
1741
                                            /* Replace last compositors. */
1742
0
                                            code = execute_compositor_queue(cdev, &target, &tdev,
1743
0
                                                &gs_gstate, &pcomp_first, &pcomp_last, pcomp_opening, x0, y0, mem, true);
1744
0
                                            if (code < 0)
1745
0
                                                goto out;
1746
0
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1747
0
                                            break;
1748
1.82M
                                        case COMP_REPLACE_CURR:
1749
                                            /* Replace specific compositor. */
1750
1.82M
                                            code = dequeue_compositor(&pcomp_first, &pcomp_last, pcomp_opening);
1751
1.82M
                                            if (code < 0)
1752
0
                                                goto out;
1753
1.82M
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1754
1.82M
                                            free_compositor(pcomp_opening, mem);
1755
1.82M
                                            break;
1756
15.0k
                                        case COMP_DROP_QUEUE:
1757
                                            /* Annihilate the last compositors. */
1758
15.0k
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1759
15.0k
                                            code = drop_compositor_queue(&pcomp_first, &pcomp_last, pcomp_opening, mem, x0, y0, &gs_gstate);
1760
15.0k
                                            if (code < 0)
1761
0
                                                goto out;
1762
15.0k
                                            break;
1763
148k
                                        case COMP_MARK_IDLE:
1764
                                            /* Mark as idle. */
1765
148k
                                            enqueue_compositor(&pcomp_first, &pcomp_last, pcomp);
1766
148k
                                            mark_as_idle(pcomp_opening, pcomp);
1767
12.6M
                                        }
1768
12.6M
                                    } else if (is_null_compositor_op(cbp, &len)) {
1769
6.84M
                                        cbuf.ptr = cbp += len;
1770
6.84M
                                    } else if (cbp[0] == cmd_opv_end_page) {
1771
                                        /* End page, drop the queue. */
1772
138k
                                        code = execute_compositor_queue(cdev, &target, &tdev,
1773
138k
                                                &gs_gstate, &pcomp_first, &pcomp_last, pcomp_first, x0, y0, mem, true);
1774
138k
                                        if (code < 0)
1775
1
                                            goto out;
1776
138k
                                        break;
1777
786k
                                    } else if (pcomp_last != NULL &&
1778
786k
                                            pcomp_last->type->procs.is_friendly(pcomp_last, cbp[0], cbp[1])) {
1779
                                        /* Immediately execute friendly commands
1780
                                           inside the compositor lookahead loop.
1781
                                           Currently there are few friendly commands for the pdf14 compositor only
1782
                                           due to the logic defined in c_pdf14trans_is_friendly.
1783
                                           This code duplicates some code portions from the main loop,
1784
                                           but we have no better idea with no slowdown to the main loop.
1785
                                         */
1786
156k
                                        uint cb;
1787
1788
156k
                                        switch (*cbp++) {
1789
77.0k
                                            case cmd_opv_extend:
1790
77.0k
                                                switch (*cbp++) {
1791
38.5k
                                                    case cmd_opv_ext_put_halftone:
1792
38.5k
                                                        {
1793
38.5k
                                                            uint    ht_size;
1794
1795
38.5k
                                                            enc_u_getw(ht_size, cbp);
1796
38.5k
                                                            code = read_alloc_ht_buff(&ht_buff, ht_size, mem);
1797
38.5k
                                                            if (code < 0)
1798
0
                                                                goto out;
1799
38.5k
                                                        }
1800
38.5k
                                                        break;
1801
38.5k
                                                    case cmd_opv_ext_put_ht_seg:
1802
38.5k
                                                        cbuf.ptr = cbp;
1803
38.5k
                                                        code = read_ht_segment(&ht_buff, &cbuf,
1804
38.5k
                                                                               &gs_gstate, tdev,
1805
38.5k
                                                                               mem);
1806
38.5k
                                                        cbp = cbuf.ptr;
1807
38.5k
                                                        if (code < 0)
1808
0
                                                            goto out;
1809
38.5k
                                                        break;
1810
38.5k
                                                    default:
1811
0
                                                        code = gs_note_error(gs_error_unregistered); /* Must not happen. */
1812
0
                                                        goto out;
1813
77.0k
                                                }
1814
77.0k
                                                break;
1815
79.7k
                                            case cmd_opv_set_misc:
1816
79.7k
                                                cb = *cbp++;
1817
79.7k
                                                switch (cb >> 6) {
1818
79.7k
                                                    case cmd_set_misc_map >> 6:
1819
79.7k
                                                        cbuf.ptr = cbp;
1820
79.7k
                                                        code = read_set_misc_map(cb, &cbuf, &gs_gstate, mem);
1821
79.7k
                                                        if (code < 0)
1822
0
                                                            goto out;
1823
79.7k
                                                        cbp = cbuf.ptr;
1824
79.7k
                                                        break;
1825
0
                                                    default:
1826
0
                                                        code = gs_note_error(gs_error_unregistered); /* Must not happen. */
1827
0
                                                        goto out;
1828
79.7k
                                                }
1829
79.7k
                                                break;
1830
79.7k
                                            default:
1831
0
                                                code = gs_note_error(gs_error_unregistered); /* Must not happen. */
1832
0
                                                goto out;
1833
156k
                                        }
1834
630k
                                    } else {
1835
                                        /* A drawing command, execute entire queue. */
1836
630k
                                        code = execute_compositor_queue(cdev, &target, &tdev,
1837
630k
                                            &gs_gstate, &pcomp_first, &pcomp_last, pcomp_first, x0, y0, mem, false);
1838
630k
                                        if (code < 0)
1839
0
                                            goto out;
1840
630k
                                        break;
1841
630k
                                    }
1842
20.3M
                                }
1843
768k
                                if (pcomp_last != NULL) {
1844
0
                                    code = gs_note_error(gs_error_unregistered);
1845
0
                                    goto out;
1846
0
                                }
1847
768k
                                break;
1848
768k
                            case cmd_opv_ext_put_halftone:
1849
105k
                                {
1850
105k
                                    uint    ht_size;
1851
1852
105k
                                    if_debug0m('L', mem, " ext_put_halftone\n");
1853
105k
                                    enc_u_getw(ht_size, cbp);
1854
105k
                                    code = read_alloc_ht_buff(&ht_buff, ht_size, mem);
1855
105k
                                    if (code < 0)
1856
0
                                        goto out;
1857
105k
                                }
1858
105k
                                break;
1859
105k
                            case cmd_opv_ext_put_ht_seg:
1860
105k
                                if_debug0m('L', mem, " ext_put_ht_seg\n");
1861
105k
                                cbuf.ptr = cbp;
1862
105k
                                code = read_ht_segment(&ht_buff, &cbuf,
1863
105k
                                                       &gs_gstate, tdev,
1864
105k
                                                       mem);
1865
105k
                                cbp = cbuf.ptr;
1866
105k
                                if (code < 0)
1867
0
                                    goto out;
1868
105k
                                break;
1869
105k
                            case cmd_opv_ext_set_color_is_devn:
1870
0
                                state.color_is_devn = true;
1871
0
                                if_debug0m('L', mem, " ext_set_color_is_devn\n");
1872
0
                                break;
1873
0
                            case cmd_opv_ext_unset_color_is_devn:
1874
0
                                state.color_is_devn = false;
1875
0
                                if_debug0m('L', mem, " ext_unset_color_is_devn\n");
1876
0
                                break;
1877
0
                            case cmd_opv_ext_tile_rect_hl:
1878
                                /* Strip tile with devn colors */
1879
0
                                cbp = cmd_read_rect(op & 0xf0, &state.rect, cbp);
1880
0
                                if_debug4m('L', mem, " x=%d y=%d w=%d h=%d\n",
1881
0
                                           state.rect.x, state.rect.y,
1882
0
                                           state.rect.width,state.rect.height);
1883
0
                                code = (*dev_proc(tdev, strip_tile_rect_devn))
1884
0
                                    (tdev, &state_tile,
1885
0
                                     state.rect.x - x0, state.rect.y - y0,
1886
0
                                     state.rect.width, state.rect.height,
1887
0
                                     &(state.tile_color_devn[0]),
1888
0
                                     &(state.tile_color_devn[1]),
1889
0
                                     tile_phase.x, tile_phase.y);
1890
0
                                break;
1891
949k
                            case cmd_opv_ext_put_fill_dcolor:
1892
949k
                                pdcolor = &fill_color;
1893
949k
                                goto load_dcolor;
1894
113k
                            case cmd_opv_ext_put_stroke_dcolor:
1895
113k
                                pdcolor = &stroke_color;
1896
113k
                                goto load_dcolor;
1897
0
                            case cmd_opv_ext_put_tile_devn_color0:
1898
0
                                pdcolor = &set_dev_colors[0];
1899
0
                                goto load_dcolor;
1900
0
                            case cmd_opv_ext_put_tile_devn_color1:
1901
0
                                pdcolor = &set_dev_colors[1];
1902
1.06M
                    load_dcolor:{
1903
1.06M
                                    uint    color_size;
1904
1.06M
                                    int left, offset, l;
1905
1.06M
                                    const gx_device_color_type_t *  pdct;
1906
1.06M
                                    byte type_and_flag = *cbp++;
1907
1.06M
                                    byte is_continuation = type_and_flag & 0x80;
1908
1909
1.06M
                                    if_debug0m('L', mem, " cmd_opv_ext_put_drawing_color\n");
1910
1.06M
                                    pdct = gx_get_dc_type_from_index(type_and_flag & 0x7F);
1911
1.06M
                                    if (pdct == 0) {
1912
0
                                        code = gs_note_error(gs_error_rangecheck);
1913
0
                                        goto out;
1914
0
                                    }
1915
1.06M
                                    offset = 0;
1916
1.06M
                                    if (is_continuation)
1917
1.06M
                                        enc_u_getw(offset, cbp);
1918
1.06M
                                    enc_u_getw(color_size, cbp);
1919
1.06M
                                    left = color_size;
1920
1.06M
                                    if (!left) {
1921
                                        /* We still need to call pdct->read because it may change dev_color.type -
1922
                                           see gx_dc_null_read.*/
1923
100k
                                        code = pdct->read(pdcolor, &gs_gstate,
1924
100k
                                                          pdcolor, tdev, offset,
1925
100k
                                                          cbp, 0, mem, x0, y0);
1926
100k
                                        if (code < 0)
1927
0
                                            goto out;
1928
100k
                                    }
1929
2.68M
                                    while (left) {
1930
1.62M
                                        if (cbuf.warn_limit - cbp < (int)left) {  /* cbp can be past warn_limit */
1931
692k
                                            code = top_up_cbuf(&cbuf, &cbp);
1932
692k
                                            if (code < 0)
1933
0
                                                goto top_up_failed;
1934
692k
                                        }
1935
1.62M
                                        l = min(left, cbuf.end - cbp);
1936
1.62M
                                        code = pdct->read(pdcolor, &gs_gstate,
1937
1.62M
                                                          pdcolor, tdev, offset,
1938
1.62M
                                                          cbp, l, mem, x0, y0);
1939
1.62M
                                        if (code < 0)
1940
0
                                            goto out;
1941
1.62M
                                        l = code;
1942
1.62M
                                        cbp += l;
1943
1.62M
                                        offset += l;
1944
1.62M
                                        left -= l;
1945
1.62M
                                    }
1946
1.06M
                                    code = gx_color_load(pdcolor, &gs_gstate,
1947
1.06M
                                                         tdev);
1948
1.06M
                                    if (code < 0)
1949
0
                                        goto out;
1950
1.06M
                                }
1951
1.06M
                                break;
1952
1.06M
                            default:
1953
0
                                goto bad_op;
1954
2.04M
                        }
1955
2.04M
                        break;
1956
2.04M
                    default:
1957
0
                        goto bad_op;
1958
3.62M
                }
1959
2.94M
                continue;
1960
3.73M
            case cmd_op_segment >> 4:
1961
3.73M
                {
1962
3.73M
                    int i;
1963
3.73M
                    static const byte op_num_operands[] = {
1964
3.73M
                        cmd_segment_op_num_operands_values
1965
3.73M
                    };
1966
3.73M
                  rgapto:
1967
3.73M
                    if (!in_path) {
1968
756k
                        ppos.x = int2fixed(state.rect.x);
1969
756k
                        ppos.y = int2fixed(state.rect.y);
1970
756k
                        if_debug2m('L', mem, " (%d,%d)", state.rect.x,
1971
756k
                                   state.rect.y);
1972
756k
                        notes = sn_none;
1973
756k
                        in_path = true;
1974
756k
                    }
1975
8.96M
                    for (i = 0; i < op_num_operands[op & 0xf]; ++i) {
1976
5.23M
                        fixed v;
1977
5.23M
                        int b = *cbp;
1978
1979
5.23M
                        switch (b >> 5) {
1980
1.17M
                            case 0:
1981
2.05M
                            case 1:
1982
2.05M
                                vs[i++] =
1983
2.05M
                                    ((fixed) ((b ^ 0x20) - 0x20) << 13) +
1984
2.05M
                                    ((int)cbp[1] << 5) + (cbp[2] >> 3);
1985
2.05M
                                if_debug1m('L', mem, " %g", fixed2float(vs[i - 1]));
1986
2.05M
                                cbp += 2;
1987
2.05M
                                v = (int)((*cbp & 7) ^ 4) - 4;
1988
2.05M
                                break;
1989
1.32M
                            case 2:
1990
2.45M
                            case 3:
1991
2.45M
                                v = (b ^ 0x60) - 0x20;
1992
2.45M
                                break;
1993
123k
                            case 4:
1994
249k
                            case 5:
1995
                                /*
1996
                                 * Without the following cast, C's
1997
                                 * brain-damaged coercion rules cause the
1998
                                 * result to be considered unsigned, and not
1999
                                 * sign-extended on machines where
2000
                                 * sizeof(long) > sizeof(int).
2001
                                 */
2002
249k
                                v = (((b ^ 0xa0) - 0x20) << 8) + (int)*++cbp;
2003
249k
                                break;
2004
388k
                            case 6:
2005
388k
                                v = (b ^ 0xd0) - 0x10;
2006
388k
                                vs[i] =
2007
388k
                                    ((v << 8) + cbp[1]) << (_fixed_shift - 2);
2008
388k
                                if_debug1m('L', mem, " %g", fixed2float(vs[i]));
2009
388k
                                cbp += 2;
2010
388k
                                continue;
2011
84.1k
                            default /*case 7 */ :
2012
84.1k
                                v = (int)(*++cbp ^ 0x80) - 0x80;
2013
168k
                                for (b = 0; b < sizeof(fixed) - 3; ++b)
2014
84.1k
                                    v = (v << 8) + *++cbp;
2015
84.1k
                                break;
2016
5.23M
                        }
2017
4.84M
                        cbp += 3;
2018
                        /* Absent the cast in the next statement, */
2019
                        /* the Borland C++ 4.5 compiler incorrectly */
2020
                        /* sign-extends the result of the shift. */
2021
4.84M
                        vs[i] = (v << 16) + (uint) (cbp[-2] << 8) + cbp[-1];
2022
4.84M
                        if_debug1m('L', mem, " %g", fixed2float(vs[i]));
2023
4.84M
                    }
2024
3.73M
                    if_debug0m('L', mem, "\n");
2025
3.73M
                    code = clist_decode_segment(&path, op, vs, &ppos,
2026
3.73M
                                                x0, y0, notes);
2027
3.73M
                    if (code < 0)
2028
0
                        goto out;
2029
3.73M
                }
2030
3.73M
                continue;
2031
11.7M
            case cmd_op_path >> 4:
2032
11.7M
                if (op == cmd_opv_rgapto)
2033
0
                    goto rgapto;
2034
11.7M
                else if (op == cmd_opv_lock_pattern) {
2035
80
                    gs_id id;
2036
80
                    int lock = *cbp++;
2037
80
                    cmd_get_value(id, cbp);
2038
80
                    if_debug2m('L', mem, "id=0x%lx, lock=%d\n", id, lock);
2039
                    /* We currently lock the pattern in all the bands, even in ones
2040
                     * where we haven't used the pattern. This can cause the following
2041
                     * call to return with 'undefined' because the pattern is not
2042
                     * found. Just swallow this error and continue. */
2043
80
                    code = gx_pattern_cache_entry_set_lock(&gs_gstate, id, lock);
2044
80
                    if (code == gs_error_undefined)
2045
0
                        code = 0;
2046
80
                    if (code < 0)
2047
0
                        goto out;
2048
80
                    continue;
2049
11.7M
                } else {
2050
11.7M
                    gx_path fpath;
2051
11.7M
                    gx_path *ppath = &path;
2052
2053
11.7M
                    if_debug0m('L', mem, "\n");
2054
                    /* if in clip, flatten path first */
2055
11.7M
                    if (in_clip) {
2056
164k
                        gx_path_init_local(&fpath, mem);
2057
164k
                        code = gx_path_add_flattened_accurate(&path, &fpath,
2058
164k
                                             gs_currentflat_inline(&gs_gstate),
2059
164k
                                             gs_gstate.accurate_curves);
2060
164k
                        if (code < 0)
2061
0
                            goto out;
2062
164k
                        ppath = &fpath;
2063
164k
                    }
2064
11.7M
                    switch (op) {
2065
486k
                        case cmd_opv_fill:
2066
486k
                            fill_params.rule = gx_rule_winding_number;
2067
486k
                            goto fill;
2068
17.1k
                        case cmd_opv_eofill:
2069
17.1k
                            fill_params.rule = gx_rule_even_odd;
2070
503k
                        fill:
2071
503k
                            fill_params.adjust = gs_gstate.fill_adjust;
2072
503k
                            fill_params.flatness = gs_gstate.flatness;
2073
503k
                            code = (*dev_proc(tdev, fill_path))(tdev, &gs_gstate, ppath,
2074
503k
                                                                &fill_params, &fill_color, pcpath);
2075
503k
                            break;
2076
13.5k
                        case cmd_opv_fill_stroke:
2077
13.5k
                            fill_params.rule = gx_rule_winding_number;
2078
13.5k
                            goto fill_stroke;
2079
777
                        case cmd_opv_eofill_stroke:
2080
777
                            fill_params.rule = gx_rule_even_odd;
2081
14.3k
                        fill_stroke:
2082
14.3k
                            fill_params.adjust = gs_gstate.fill_adjust;
2083
14.3k
                            fill_params.flatness = gs_gstate.flatness;
2084
14.3k
                            stroke_params.flatness = gs_gstate.flatness;
2085
14.3k
                            stroke_params.traditional = false;
2086
14.3k
                            code = (*dev_proc(tdev, fill_stroke_path))(tdev, &gs_gstate, ppath,
2087
14.3k
                                                                &fill_params, &fill_color,
2088
14.3k
                                                                &stroke_params, &stroke_color, pcpath);
2089
14.3k
                            break;
2090
527k
                        case cmd_opv_stroke:
2091
527k
                            stroke_params.flatness = gs_gstate.flatness;
2092
527k
                            stroke_params.traditional = false;
2093
527k
                            code = (*dev_proc(tdev, stroke_path))
2094
527k
                                                       (tdev, &gs_gstate,
2095
527k
                                                       ppath, &stroke_params,
2096
527k
                                                       &stroke_color, pcpath);
2097
527k
                            break;
2098
3.02k
                        case cmd_opv_polyfill:
2099
3.02k
                            code = clist_do_polyfill(tdev, ppath, &fill_color,
2100
3.02k
                                                     gs_gstate.log_op);
2101
3.02k
                            break;
2102
10.6M
                        case cmd_opv_fill_trapezoid:
2103
10.6M
                            {
2104
10.6M
                                gs_fixed_edge left, right;
2105
10.6M
                                fixed ybot, ytop;
2106
10.6M
                                int options, swap_axes, wh;
2107
10.6M
                                fixed x0f;
2108
10.6M
                                fixed y0f;
2109
10.6M
                                gx_device *ttdev = tdev;
2110
2111
10.6M
                                if (pcpath != NULL && !clipper_dev_open) {
2112
192
                                    gx_make_clip_device_on_stack(&clipper_dev, pcpath, tdev);
2113
192
                                    clipper_dev_open = true;
2114
192
                                }
2115
10.6M
                                if (clipper_dev_open)
2116
8.49M
                                    ttdev = (gx_device *)&clipper_dev;
2117
                                /* Note that if we have transparency present, the clipper device may need to have
2118
                                   its color information updated to be synced up with the target device.
2119
                                   This can occur if we had fills of a path first with a transparency mask to get
2120
                                   an XPS opacity followed by a fill with a transparency group. This occurs in
2121
                                   the XPS gradient code */
2122
10.6M
                                if (tdev->color_info.num_components != ttdev->color_info.num_components){
2123
                                    /* Reset the clipper device color information. Only worry about
2124
                                       the information that is used in the trap code */
2125
0
                                    ttdev->color_info.num_components = tdev->color_info.num_components;
2126
0
                                    ttdev->color_info.depth = tdev->color_info.depth;
2127
0
                                    ttdev->color_info.polarity = tdev->color_info.polarity;
2128
0
                                    memcpy(&(ttdev->color_info.comp_bits),&(tdev->color_info.comp_bits),GX_DEVICE_COLOR_MAX_COMPONENTS);
2129
0
                                    memcpy(&(ttdev->color_info.comp_shift),&(tdev->color_info.comp_shift),GX_DEVICE_COLOR_MAX_COMPONENTS);
2130
0
                                }
2131
10.6M
                                cmd_getw(left.start.x, cbp);
2132
10.6M
                                cmd_getw(left.start.y, cbp);
2133
10.6M
                                cmd_getw(left.end.x, cbp);
2134
10.6M
                                cmd_getw(left.end.y, cbp);
2135
10.6M
                                cmd_getw(right.start.x, cbp);
2136
10.6M
                                cmd_getw(right.start.y, cbp);
2137
10.6M
                                cmd_getw(right.end.x, cbp);
2138
10.6M
                                cmd_getw(right.end.y, cbp);
2139
10.6M
                                cmd_getw(options, cbp);
2140
10.6M
                                if (!(options & 4)) {
2141
10.6M
                                    cmd_getw(ybot, cbp);
2142
10.6M
                                    cmd_getw(ytop, cbp);
2143
10.6M
                                } else
2144
0
                                    ytop = ybot = 0; /* Unused, but quiet gcc warning. */
2145
10.6M
                                swap_axes = options & 1;
2146
10.6M
                                wh = swap_axes ? tdev->width : tdev->height;
2147
10.6M
                                x0f = int2fixed(swap_axes ? y0 : x0);
2148
10.6M
                                y0f = int2fixed(swap_axes ? x0 : y0);
2149
10.6M
                                left.start.x -= x0f;
2150
10.6M
                                left.start.y -= y0f;
2151
10.6M
                                left.end.x -= x0f;
2152
10.6M
                                left.end.y -= y0f;
2153
10.6M
                                right.start.x -= x0f;
2154
10.6M
                                right.start.y -= y0f;
2155
10.6M
                                right.end.x -= x0f;
2156
10.6M
                                right.end.y -= y0f;
2157
10.6M
                                if (options & 2) {
2158
0
                                    uchar num_components = tdev->color_info.num_components;
2159
0
                                    frac31 c[4][GX_DEVICE_COLOR_MAX_COMPONENTS], *cc[4];
2160
0
                                    byte colors_mask, i, j, m = 1;
2161
0
                                    gs_fill_attributes fa;
2162
0
                                    gs_fixed_rect clip;
2163
0
                                    fixed hh = int2fixed(swap_axes ? target->width : target->height);
2164
2165
0
                                    if (cbuf.end - cbp < 5 * cmd_max_intsize(sizeof(frac31))) {
2166
0
                                        code = top_up_cbuf(&cbuf, &cbp);
2167
0
                                        if (code < 0)
2168
0
                                            goto top_up_failed;
2169
0
                                    }
2170
0
                                    cmd_getw(clip.p.x, cbp);
2171
0
                                    cmd_getw(clip.p.y, cbp);
2172
0
                                    cmd_getw(clip.q.x, cbp);
2173
0
                                    cmd_getw(clip.q.y, cbp);
2174
0
                                    clip.p.x -= x0f;
2175
0
                                    clip.p.y -= y0f;
2176
0
                                    clip.q.x -= x0f;
2177
0
                                    clip.q.y -= y0f;
2178
0
                                    if (clip.p.y < 0)
2179
0
                                        clip.p.y = 0;
2180
0
                                    if (clip.q.y > hh)
2181
0
                                        clip.q.y = hh;
2182
0
                                    fa.clip = &clip;
2183
0
                                    fa.swap_axes = swap_axes;
2184
0
                                    fa.ht = NULL;
2185
0
                                    fa.lop = lop_default; /* fgixme: gs_gstate.log_op; */
2186
0
                                    fa.ystart = ybot - y0f;
2187
0
                                    fa.yend = ytop - y0f;
2188
0
                                    cmd_getw(colors_mask, cbp);
2189
0
                                    for (i = 0; i < 4; i++, m <<= 1) {
2190
0
                                        if (colors_mask & m) {
2191
0
                                            if (cbuf.end - cbp < num_components * cmd_max_intsize(sizeof(frac31))) {
2192
0
                                                code = top_up_cbuf(&cbuf, &cbp);
2193
0
                                                if (code < 0)
2194
0
                                                    goto top_up_failed;
2195
0
                                            }
2196
0
                                            cc[i] = c[i];
2197
0
                                            for (j = 0; j < num_components; j++)
2198
0
                                                cmd_getfrac(c[i][j], cbp);
2199
0
                                        } else
2200
0
                                            cc[i] = NULL;
2201
0
                                    }
2202
0
                                    if (options & 4) {
2203
0
#                                       if 1 /* Disable to debug gx_fill_triangle_small. */
2204
0
                                        code = dev_proc(ttdev, fill_linear_color_triangle)(ttdev, &fa,
2205
0
                                                        &left.start, &left.end, &right.start,
2206
0
                                                        cc[0], cc[1], cc[2]);
2207
#                                       else
2208
                                        code = 0;
2209
#                                       endif
2210
0
                                        if (code == 0) {
2211
                                            /* The target device didn't fill the trapezoid and
2212
                                               requests a decomposition. Subdivide into smaller triangles : */
2213
0
                                            if (pfs.dev == NULL)
2214
0
                                                code = gx_init_patch_fill_state_for_clist(tdev, &pfs, mem);
2215
0
                                            if (code >= 0) {
2216
0
                                                pfs.dev = ttdev;
2217
0
                                                pfs.rect = clip; /* fixme: eliminate 'clip'. */
2218
0
                                                fa.pfs = &pfs;
2219
0
                                                code = gx_fill_triangle_small(ttdev, &fa,
2220
0
                                                            &left.start, &left.end, &right.start,
2221
0
                                                            cc[0], cc[1], cc[2]);
2222
0
                                            }
2223
0
                                        }
2224
0
                                    } else {
2225
0
                                        code = dev_proc(ttdev, fill_linear_color_trapezoid)(ttdev, &fa,
2226
0
                                                        &left.start, &left.end, &right.start, &right.end,
2227
0
                                                        cc[0], cc[1], cc[2], cc[3]);
2228
0
                                        if (code == 0) {
2229
                                            /* Fixme : The target device didn't fill the trapezoid and
2230
                                               requests a decomposition.
2231
                                               Currently we never call it with 4 colors (see gxshade6.c)
2232
                                               and 2 colors must not return 0 - see comment to
2233
                                               dev_t_proc_fill_linear_color_trapezoid in gxdevcli.c .
2234
                                               Must not happen. */
2235
0
                                            code = gs_note_error(gs_error_unregistered);
2236
0
                                        }
2237
0
                                    }
2238
0
                                } else
2239
10.6M
                                    code = gx_default_fill_trapezoid(ttdev, &left, &right,
2240
10.6M
                                        max(ybot - y0f, fixed_half),
2241
10.6M
                                        min(ytop - y0f, int2fixed(wh)), swap_axes,
2242
10.6M
                                        &fill_color, gs_gstate.log_op);
2243
10.6M
                            }
2244
10.6M
                           break;
2245
10.6M
                        default:
2246
0
                            goto bad_op;
2247
11.7M
                    }
2248
11.7M
                    if (ppath != &path)
2249
164k
                        gx_path_free(ppath, "clist_render_band");
2250
11.7M
                }
2251
11.7M
                if (in_path) {  /* path might be empty! */
2252
756k
                    state.rect.x = fixed2int_var(ppos.x);
2253
756k
                    state.rect.y = fixed2int_var(ppos.y);
2254
756k
                    in_path = false;
2255
756k
                }
2256
11.7M
                gx_path_free(&path, "clist_render_band");
2257
11.7M
                gx_path_init_local(&path, mem);
2258
11.7M
                if (code < 0)
2259
0
                    goto out;
2260
11.7M
                continue;
2261
11.7M
            default:
2262
0
              bad_op:mlprintf5(mem, "Bad op %02x band y0 = %d file pos %"PRId64" buf pos %d/%d\n",
2263
0
                 op, y0, stell(s), (int)(cbp - cbuf.data), (int)(cbuf.end - cbuf.data));
2264
0
                {
2265
0
                    const byte *pp;
2266
2267
0
                    for (pp = cbuf.data; pp < cbuf.end; pp += 10) {
2268
0
                        dmlprintf1(mem, "%4d:", (int)(pp - cbuf.data));
2269
0
                        dmprintf10(mem, " %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x\n",
2270
0
                                  pp[0], pp[1], pp[2], pp[3], pp[4],
2271
0
                                  pp[5], pp[6], pp[7], pp[8], pp[9]);
2272
0
                    }
2273
0
                }
2274
0
                code = gs_note_error(gs_error_Fatal);
2275
0
                goto out;
2276
54.1M
        }
2277
54.1M
        if_debug4m('L', mem, " x=%d y=%d w=%d h=%d\n",
2278
18.9M
                  state.rect.x, state.rect.y, state.rect.width,
2279
18.9M
                  state.rect.height);
2280
18.9M
        switch (op >> 4) {
2281
394k
            case cmd_op_fill_rect >> 4:
2282
394k
                if (state.rect.width == 0 && state.rect.height == 0 &&
2283
394k
                    state.rect.x == 0 && state.rect.y == 0) {
2284
                    /* FIXME: This test should be unnecessary. Bug 692076
2285
                     * is open pending a proper fix. */
2286
152k
                    code = (dev_proc(tdev, fillpage) == NULL ? 0 :
2287
152k
                            (*dev_proc(tdev, fillpage))(tdev, &gs_gstate,
2288
152k
                                                        &fill_color));
2289
152k
                    break;
2290
152k
                }
2291
1.24M
            case cmd_op_fill_rect_short >> 4:
2292
13.4M
            case cmd_op_fill_rect_tiny >> 4:
2293
13.4M
                if (!state.lop_enabled) {
2294
13.4M
                    code = (*dev_proc(tdev, fill_rectangle))
2295
13.4M
                        (tdev, state.rect.x - x0, state.rect.y - y0,
2296
13.4M
                         state.rect.width, state.rect.height,
2297
13.4M
                         state.colors[1]);
2298
13.4M
                    break;
2299
13.4M
                }
2300
0
                source = NULL;
2301
0
                data_x = 0;
2302
0
                raster = 0;
2303
0
                colors[0] = colors[1] = state.colors[1];
2304
0
                log_op = state.lop;
2305
0
                pcolor = colors;
2306
0
         do_rop:code = (*dev_proc(tdev, strip_copy_rop2))
2307
0
                                (tdev, source, data_x, raster, gx_no_bitmap_id,
2308
0
                                 pcolor, &state_tile,
2309
0
                                 (state.tile_colors[0] == gx_no_color_index &&
2310
0
                                  state.tile_colors[1] == gx_no_color_index ?
2311
0
                                  NULL : state.tile_colors),
2312
0
                                 state.rect.x - x0, state.rect.y - y0,
2313
0
                                 state.rect.width - data_x, state.rect.height,
2314
0
                                 tile_phase.x, tile_phase.y, log_op,
2315
0
                                 plane_height);
2316
0
                     plane_height = 0;
2317
0
                data_x = 0;
2318
0
                break;
2319
27.1k
            case cmd_op_tile_rect >> 4:
2320
27.1k
                if (state.rect.width == 0 && state.rect.height == 0 &&
2321
27.1k
                    state.rect.x == 0 && state.rect.y == 0) {
2322
0
                    code = (*dev_proc(tdev, fillpage))(tdev, &gs_gstate, &fill_color);
2323
0
                    break;
2324
0
                }
2325
214k
            case cmd_op_tile_rect_short >> 4:
2326
490k
            case cmd_op_tile_rect_tiny >> 4:
2327
                /* Currently we don't use lop with strip_tile_rectangle. */
2328
490k
                code = (*dev_proc(tdev, strip_tile_rectangle))
2329
490k
                    (tdev, &state_tile,
2330
490k
                     state.rect.x - x0, state.rect.y - y0,
2331
490k
                     state.rect.width, state.rect.height,
2332
490k
                     state.tile_colors[0], state.tile_colors[1],
2333
490k
                     tile_phase.x, tile_phase.y);
2334
490k
                break;
2335
4.79M
            case cmd_op_copy_mono_planes >> 4:
2336
4.79M
                if (state.lop_enabled) {
2337
0
                    pcolor = state.colors;
2338
0
                    log_op = state.lop;
2339
0
                    goto do_rop;
2340
0
                }
2341
4.79M
                if ((op & cmd_copy_use_tile) || pcpath != NULL) {       /*
2342
                                                                         * This call of copy_mono originated as a call
2343
                                                                         * of fill_mask.
2344
                                                                         */
2345
4.67M
                    code = gx_image_fill_masked
2346
4.67M
                        (tdev, source, data_x, raster, gx_no_bitmap_id,
2347
4.67M
                         state.rect.x - x0, state.rect.y - y0,
2348
4.67M
                         state.rect.width - data_x, state.rect.height,
2349
4.67M
                         &fill_color, 1, gs_gstate.log_op, pcpath);
2350
4.67M
                } else {
2351
123k
                    if (plane_height == 0) {
2352
123k
                        code = (*dev_proc(tdev, copy_mono))
2353
123k
                             (tdev, source, data_x, raster, gx_no_bitmap_id,
2354
123k
                              state.rect.x - x0, state.rect.y - y0,
2355
123k
                              state.rect.width - data_x, state.rect.height,
2356
123k
                              state.colors[0], state.colors[1]);
2357
123k
                    } else {
2358
0
                        code = (*dev_proc(tdev, copy_planes))
2359
0
                             (tdev, source, data_x, raster, gx_no_bitmap_id,
2360
0
                              state.rect.x - x0, state.rect.y - y0,
2361
0
                              state.rect.width - data_x, state.rect.height,
2362
0
                              plane_height);
2363
0
                    }
2364
123k
                }
2365
4.79M
                plane_height = 0;
2366
4.79M
                data_x = 0;
2367
4.79M
                break;
2368
4.55k
            case cmd_op_copy_color_alpha >> 4:
2369
4.55k
                if (state.color_is_alpha) {
2370
/****** CAN'T DO ROP WITH ALPHA ******/
2371
0
                    if (state.color_is_devn &&
2372
0
                        dev_proc(tdev, copy_alpha_hl_color) != gx_default_no_copy_alpha_hl_color) { /* FIXME */
2373
0
                        code = (*dev_proc(tdev, copy_alpha_hl_color))
2374
0
                            (tdev, source, data_x, raster, gx_no_bitmap_id,
2375
0
                             state.rect.x - x0, state.rect.y - y0,
2376
0
                             state.rect.width - data_x, state.rect.height,
2377
0
                             &fill_color, depth);
2378
0
                    } else {
2379
0
                        code = (*dev_proc(tdev, copy_alpha))
2380
0
                            (tdev, source, data_x, raster, gx_no_bitmap_id,
2381
0
                             state.rect.x - x0, state.rect.y - y0,
2382
0
                             state.rect.width - data_x, state.rect.height,
2383
0
                             state.colors[1], depth);
2384
0
                    }
2385
4.55k
                } else {
2386
4.55k
                    if (state.lop_enabled) {
2387
0
                        pcolor = NULL;
2388
0
                        log_op = state.lop;
2389
0
                        goto do_rop;
2390
0
                    }
2391
4.55k
                    code = (*dev_proc(tdev, copy_color))
2392
4.55k
                        (tdev, source, data_x, raster, gx_no_bitmap_id,
2393
4.55k
                         state.rect.x - x0, state.rect.y - y0,
2394
4.55k
                         state.rect.width - data_x, state.rect.height);
2395
4.55k
                }
2396
4.55k
                data_x = 0;
2397
4.55k
                break;
2398
0
            default:            /* can't happen */
2399
0
                goto bad_op;
2400
18.9M
        }
2401
18.9M
    }
2402
    /* Clean up before we exit. */
2403
154k
  out:
2404
154k
    if (ht_buff.pbuff != 0) {
2405
0
        gs_free_object(mem, ht_buff.pbuff, "clist_playback_band(ht_buff)");
2406
0
        ht_buff.pbuff = 0;
2407
0
        ht_buff.pcurr = 0;
2408
0
    }
2409
154k
    ht_buff.ht_size = 0;
2410
154k
    ht_buff.read_size = 0;
2411
2412
154k
    if (pcomp_last != NULL) {
2413
0
        int code1 = drop_compositor_queue(&pcomp_first, &pcomp_last, NULL, mem, x0, y0, &gs_gstate);
2414
2415
0
        if (code == 0)
2416
0
            code = code1;
2417
0
    }
2418
154k
    gx_cpath_free(&clip_path, "clist_render_band exit");
2419
154k
    gx_path_free(&path, "clist_render_band exit");
2420
154k
    if (gs_gstate.pattern_cache != NULL) {
2421
4.46k
        gx_pattern_cache_free(gs_gstate.pattern_cache);
2422
4.46k
        gs_gstate.pattern_cache = NULL;
2423
4.46k
    }
2424
    /* Free the client color and device colors allocated upon entry */
2425
154k
    gs_free_object(mem, gs_gstate.color[0].ccolor, "clist_playback_band");
2426
154k
    gs_free_object(mem, gs_gstate.color[1].ccolor, "clist_playback_band");
2427
154k
    gs_free_object(mem, gs_gstate.color[0].dev_color, "clist_playback_band");
2428
154k
    gs_free_object(mem, gs_gstate.color[1].dev_color, "clist_playback_band");
2429
154k
    gs_gstate.color[0].ccolor = gs_gstate.color[1].ccolor = NULL;
2430
154k
    gs_gstate.color[0].dev_color = gs_gstate.color[1].dev_color = NULL;
2431
2432
    /* The imager state release will decrement the icc link cache.  To avoid
2433
       race conditions lock the cache */
2434
154k
    gx_monitor_enter(cdev->icc_cache_cl->lock);
2435
154k
    gs_gstate_release(&gs_gstate);
2436
154k
    gx_monitor_leave(cdev->icc_cache_cl->lock); /* done with increment, let everyone run */
2437
154k
    gs_free_object(mem, data_bits, "clist_playback_band(data_bits)");
2438
154k
    if (target != orig_target) {
2439
123k
        if (target->rc.ref_count != 1) {
2440
            /* This can occur if we are coming from a pattern clist that
2441
               includes transparency.  In this case, we do not want to
2442
               free the compositor since it is really the main target that
2443
               we are tiling into.  i.e. the tile itself does not have
2444
               a pdf14 device, but rather we push a trans group, draw and
2445
               then pop the group to properly blend */
2446
0
            rc_decrement(target, "gxclrast(target compositor)");
2447
123k
        } else {
2448
            /* Ref count was 1. close the device and then free it */
2449
123k
            if (target->is_open)
2450
0
                dev_proc(target, close_device)(target);
2451
123k
            gs_free_object(target->memory, target, "gxclrast discard compositor");
2452
123k
        }
2453
123k
        target = orig_target;
2454
123k
    }
2455
154k
    if (code < 0) {
2456
1
        if (pfs.dev != NULL)
2457
0
            term_patch_fill_state(&pfs);
2458
1
        rc_decrement(gs_gstate.color[0].color_space, "clist_playback_band");
2459
1
        rc_decrement(gs_gstate.color[1].color_space, "clist_playback_band");
2460
1
        gs_free_object(mem, cbuf_storage, "clist_playback_band(cbuf_storage)");
2461
1
        gx_cpath_free(&clip_path, "clist_playback_band");
2462
1
        if (pcpath != &clip_path)
2463
1
            gx_cpath_free(pcpath, "clist_playback_band");
2464
1
        if (clipper_dev_open)
2465
0
            gx_destroy_clip_device_on_stack(&clipper_dev);
2466
1
        return_error(code);
2467
1
    }
2468
    /* Check whether we have more pages to process. */
2469
154k
    if ((playback_action != playback_action_setup &&
2470
154k
        (cbp < cbuf.end || !seofp(s)) && (op != cmd_opv_end_page) )
2471
154k
        )
2472
0
        goto in;
2473
154k
    if (pfs.dev != NULL)
2474
0
        term_patch_fill_state(&pfs);
2475
154k
    rc_decrement(gs_gstate.color[0].color_space, "clist_playback_band");
2476
154k
    rc_decrement(gs_gstate.color[1].color_space, "clist_playback_band");
2477
154k
    gs_free_object(mem, cbuf_storage, "clist_playback_band(cbuf_storage)");
2478
154k
    gx_cpath_free(&clip_path, "clist_playback_band");
2479
154k
    if (pcpath != &clip_path)
2480
127k
        gx_cpath_free(pcpath, "clist_playback_band");
2481
154k
    if (clipper_dev_open)
2482
92
        gx_destroy_clip_device_on_stack(&clipper_dev);
2483
154k
    return code;
2484
0
top_up_failed:
2485
0
    gx_cpath_free(&clip_path, "clist_playback_band");
2486
0
    if (pcpath != &clip_path)
2487
0
        gx_cpath_free(pcpath, "clist_playback_band");
2488
0
    if (clipper_dev_open)
2489
0
        gx_destroy_clip_device_on_stack(&clipper_dev);
2490
0
    return code;
2491
154k
}
2492
2493
/* ---------------- Individual commands ---------------- */
2494
2495
/*
2496
 * These single-use procedures implement a few large individual commands,
2497
 * primarily for readability but also to avoid overflowing compilers'
2498
 * optimization limits.  They all take the command buffer as their first
2499
 * parameter (pcb), assume that the current buffer pointer is in pcb->ptr,
2500
 * and update it there.
2501
 */
2502
2503
static int
2504
read_set_tile_size(command_buf_t *pcb, tile_slot *bits, bool for_pattern)
2505
124
{
2506
124
    const byte *cbp = pcb->ptr;
2507
124
    uint rep_width, rep_height;
2508
124
    uint pdepth;
2509
124
    byte bd = *cbp++;
2510
2511
124
    bits->head.depth = cmd_code_to_depth(bd);
2512
124
    if (for_pattern)
2513
124
        cmd_getw(bits->id, cbp);
2514
124
    cmd_getw(rep_width, cbp);
2515
124
    cmd_getw(rep_height, cbp);
2516
124
    if (bd & 0x20) {
2517
124
        cmd_getw(bits->x_reps, cbp);
2518
124
        bits->width = rep_width * bits->x_reps;
2519
124
    } else {
2520
0
        bits->x_reps = 1;
2521
0
        bits->width = rep_width;
2522
0
    }
2523
124
    if (bd & 0x40) {
2524
0
        cmd_getw(bits->y_reps, cbp);
2525
0
        bits->height = rep_height * bits->y_reps;
2526
124
    } else {
2527
124
        bits->y_reps = 1;
2528
124
        bits->height = rep_height;
2529
124
    }
2530
124
    if (bd & 0x80)
2531
124
        cmd_getw(bits->rep_shift, cbp);
2532
124
    else
2533
124
        bits->rep_shift = 0;
2534
124
    if (bd & 0x10)
2535
0
        bits->num_planes = *cbp++;
2536
124
    else
2537
124
        bits->num_planes = 1;
2538
124
    if_debug7('L', " depth=%d size=(%d,%d), rep_size=(%d,%d), rep_shift=%d, num_planes=%d\n",
2539
124
              bits->head.depth, bits->width,
2540
124
              bits->height, rep_width,
2541
124
              rep_height, bits->rep_shift, bits->num_planes);
2542
124
    bits->shift =
2543
124
        (bits->rep_shift == 0 ? 0 :
2544
124
         (bits->rep_shift * (bits->height / rep_height)) % rep_width);
2545
124
    pdepth = bits->head.depth;
2546
124
    if (bits->num_planes != 1)
2547
0
        pdepth /= bits->num_planes;
2548
124
    bits->raster = bitmap_raster(bits->width * pdepth);
2549
124
    pcb->ptr = cbp;
2550
124
    return 0;
2551
124
}
2552
2553
static int
2554
read_set_bits(command_buf_t *pcb, tile_slot *bits, int compress,
2555
              gx_clist_state *pcls, gx_strip_bitmap *tile, tile_slot **pslot,
2556
              gx_device_clist_reader *cdev, gs_memory_t *mem)
2557
1.30M
{
2558
1.30M
    const byte *cbp = pcb->ptr;
2559
1.30M
    uint rep_width = bits->width / bits->x_reps;
2560
1.30M
    uint rep_height = bits->height / bits->y_reps;
2561
1.30M
    uint index;
2562
1.30M
    ulong offset;
2563
1.30M
    uint width_bits;
2564
1.30M
    uint width_bytes;
2565
1.30M
    uint raster;
2566
1.30M
    uint bytes;
2567
1.30M
    byte *data;
2568
1.30M
    tile_slot *slot;
2569
1.30M
    uint depth = bits->head.depth;
2570
2571
1.30M
    if (bits->num_planes != 1)
2572
0
        depth /= bits->num_planes;
2573
1.30M
    width_bits = rep_width * depth;
2574
2575
1.30M
    bytes = clist_bitmap_bytes(width_bits, rep_height * bits->num_planes,
2576
1.30M
                               compress |
2577
1.30M
                               (rep_width < bits->width ?
2578
1.30M
                                decompress_spread : 0) |
2579
1.30M
                               decompress_elsewhere,
2580
1.30M
                               &width_bytes,
2581
1.30M
                               (uint *)&raster);
2582
2583
1.30M
    cmd_getw(index, cbp);
2584
1.30M
    cmd_getw(offset, cbp);
2585
1.30M
    if_debug2m('L', mem, " index=%d offset=%lu\n", index, offset);
2586
1.30M
    pcls->tile_index = index;
2587
1.30M
    cdev->tile_table[pcls->tile_index].offset = offset;
2588
1.30M
    slot = (tile_slot *)(cdev->cache_chunk->data + offset);
2589
1.30M
    *pslot = slot;
2590
1.30M
    *slot = *bits;
2591
1.30M
    tile->data = data = (byte *)(slot + 1);
2592
#ifdef DEBUG
2593
    slot->index = pcls->tile_index;
2594
#endif
2595
1.30M
    if (compress == cmd_compress_const) {
2596
0
        cbp = cmd_read_data(pcb, data, 1, cbp);
2597
0
        if (width_bytes > 0 && rep_height > 0)
2598
0
            memset(data+1, *data, width_bytes * rep_height - 1);
2599
1.30M
    } else if (compress) {
2600
        /*
2601
         * Decompress the image data.  We'd like to share this code with the
2602
         * similar code in copy_*, but right now we don't see how.
2603
         */
2604
211k
        stream_cursor_read r;
2605
211k
        stream_cursor_write w;
2606
        /*
2607
         * We don't know the data length a priori, so to be conservative, we
2608
         * read the uncompressed size.
2609
         */
2610
211k
        uint cleft = pcb->end - cbp;
2611
2612
211k
        if (cleft < bytes && !pcb->end_status) {
2613
1.57k
            uint nread = cbuf_size - cleft;
2614
2615
1.57k
            advance_buffer(pcb, cbp);
2616
1.57k
            pcb->end_status = sgets(pcb->s, pcb->data + cleft, nread, &nread);
2617
1.57k
            set_cb_end(pcb, pcb->data + cleft + nread);
2618
1.57k
            cbp = pcb->data;
2619
1.57k
        }
2620
211k
        r.ptr = cbp - 1;
2621
211k
        r.limit = pcb->end - 1;
2622
211k
        w.ptr = data - 1;
2623
211k
        w.limit = w.ptr + bytes;
2624
211k
        switch (compress) {
2625
0
        case cmd_compress_rle:
2626
0
            {
2627
0
                stream_RLD_state sstate;
2628
2629
0
                clist_rld_init(&sstate);
2630
0
                (*s_RLD_template.process)
2631
0
                    ((stream_state *)&sstate, &r, &w, true);
2632
0
            }
2633
0
            break;
2634
211k
        case cmd_compress_cfe:
2635
211k
            {
2636
211k
                stream_CFD_state sstate;
2637
2638
211k
                clist_cfd_init(&sstate,
2639
211k
                               width_bytes << 3 /*width_bits */ ,
2640
211k
                               rep_height, mem);
2641
211k
                (*s_CFD_template.process)
2642
211k
                    ((stream_state *)&sstate, &r, &w, true);
2643
211k
                (*s_CFD_template.release)
2644
211k
                    ((stream_state *)&sstate);
2645
211k
            }
2646
211k
            break;
2647
0
        default:
2648
0
            return_error(gs_error_unregistered);
2649
211k
        }
2650
211k
        cbp = r.ptr + 1;
2651
1.09M
    } else if (rep_height * bits->num_planes > 1 && width_bytes != bits->raster) {
2652
1.09M
        cbp = cmd_read_short_bits(pcb, data, bytes,
2653
1.09M
                                  width_bytes, rep_height * bits->num_planes,
2654
1.09M
                                  bits->raster, cbp);
2655
1.09M
    } else {
2656
4.58k
        cbp = cmd_read_data(pcb, data, bytes, cbp);
2657
4.58k
    }
2658
1.30M
    if (bits->width > rep_width)
2659
502
        bits_replicate_horizontally(data,
2660
502
                                    rep_width * depth, rep_height * bits->num_planes,
2661
502
                                    bits->raster,
2662
502
                                    bits->width * depth,
2663
502
                                    bits->raster);
2664
1.30M
    if (bits->height > rep_height)
2665
0
        bits_replicate_vertically(data,
2666
0
                                  rep_height, bits->raster,
2667
0
                                  bits->height);
2668
#ifdef DEBUG
2669
    if (gs_debug_c('L'))
2670
        cmd_print_bits(mem, data, bits->width, bits->height, bits->raster);
2671
#endif
2672
1.30M
    pcb->ptr = cbp;
2673
1.30M
    return 0;
2674
1.30M
}
2675
2676
/* if necessary, allocate a buffer to hold a serialized halftone */
2677
static int
2678
read_alloc_ht_buff(ht_buff_t * pht_buff, uint ht_size, gs_memory_t * mem)
2679
144k
{
2680
    /* free the existing buffer, if any (usually none) */
2681
144k
    if (pht_buff->pbuff != 0) {
2682
0
        gs_free_object(mem, pht_buff->pbuff, "read_alloc_ht_buff");
2683
0
        pht_buff->pbuff = 0;
2684
0
    }
2685
2686
    /*
2687
     * If the serialized halftone fits in the command buffer, no
2688
     * additional buffer is required.
2689
     */
2690
144k
    if (ht_size > cbuf_ht_seg_max_size) {
2691
0
        pht_buff->pbuff = gs_alloc_bytes(mem, ht_size, "read_alloc_ht_buff");
2692
0
        if (pht_buff->pbuff == 0)
2693
0
            return_error(gs_error_VMerror);
2694
0
    }
2695
144k
    pht_buff->ht_size = ht_size;
2696
144k
    pht_buff->read_size = 0;
2697
144k
    pht_buff->pcurr = pht_buff->pbuff;
2698
144k
    return 0;
2699
144k
}
2700
2701
/* read a halftone segment; if it is the final segment, build the halftone */
2702
static int
2703
read_ht_segment(
2704
    ht_buff_t *                 pht_buff,
2705
    command_buf_t *             pcb,
2706
    gs_gstate *           pgs,
2707
    gx_device *                 dev,
2708
    gs_memory_t *               mem )
2709
144k
{
2710
144k
    const byte *                cbp = pcb->ptr;
2711
144k
    const byte *                pbuff = 0;
2712
144k
    uint                        ht_size = pht_buff->ht_size, seg_size;
2713
144k
    int                         code = 0;
2714
2715
    /* get the segment size; refill command buffer if necessary */
2716
144k
    enc_u_getw(seg_size, cbp);
2717
144k
    if (pcb->warn_limit - cbp < (int)seg_size) { /* cbp can be past warn_limit */
2718
1.15k
        code = top_up_cbuf(pcb, &cbp);
2719
1.15k
        if (code < 0)
2720
0
            return code;
2721
1.15k
        if (pcb->end - cbp < (int)seg_size) {
2722
0
            emprintf(mem, " *** ht segment size doesn't fit in buffer ***\n");
2723
0
            return_error(gs_error_unknownerror);
2724
0
        }
2725
1.15k
    }
2726
2727
144k
    if (pht_buff->pbuff == 0) {
2728
        /* if not separate buffer, must be only one segment */
2729
144k
        if (seg_size != ht_size)
2730
0
            return_error(gs_error_unknownerror);
2731
144k
        pbuff = cbp;
2732
144k
    } else {
2733
0
        if (seg_size + pht_buff->read_size > pht_buff->ht_size)
2734
0
            return_error(gs_error_unknownerror);
2735
0
        memcpy(pht_buff->pcurr, cbp, seg_size);
2736
0
        pht_buff->pcurr += seg_size;
2737
0
        if ((pht_buff->read_size += seg_size) == ht_size)
2738
0
            pbuff = pht_buff->pbuff;
2739
0
    }
2740
2741
    /* if everything has been read, convert back to a halftone */
2742
144k
    if (pbuff != 0) {
2743
144k
        code = gx_ht_read_and_install(pgs, dev, pbuff, ht_size, mem);
2744
2745
        /* release any buffered information */
2746
144k
        if (pht_buff->pbuff != 0) {
2747
0
            gs_free_object(mem, pht_buff->pbuff, "read_alloc_ht_buff");
2748
0
            pht_buff->pbuff = 0;
2749
0
            pht_buff->pcurr = 0;
2750
0
        }
2751
144k
        pht_buff->ht_size = 0;
2752
144k
        pht_buff->read_size = 0;
2753
144k
    }
2754
2755
    /* update the command buffer ponter */
2756
144k
    pcb->ptr = cbp + seg_size;
2757
2758
144k
    return code;
2759
144k
}
2760
2761
static int
2762
read_set_misc2(command_buf_t *pcb, gs_gstate *pgs, segment_notes *pnotes)
2763
176k
{
2764
176k
    const byte *cbp = pcb->ptr;
2765
176k
    uint mask, cb;
2766
2767
176k
    if_debug0m('L', pgs->memory, "\n");
2768
176k
    cmd_getw(mask, cbp);
2769
176k
    if (mask & cap_join_known) {
2770
30.3k
        cb = *cbp++;
2771
30.3k
        pgs->line_params.start_cap = (gs_line_cap)((cb >> 3) & 7);
2772
30.3k
        pgs->line_params.join = (gs_line_join)(cb & 7);
2773
30.3k
        if_debug2m('L', pgs->memory, "[L]      start_cap=%d join=%d\n",
2774
30.3k
                   pgs->line_params.start_cap, pgs->line_params.join);
2775
30.3k
        cb = *cbp++;
2776
30.3k
        pgs->line_params.end_cap = (gs_line_cap)((cb >> 3) & 7);
2777
30.3k
        pgs->line_params.dash_cap = (gs_line_cap)(cb & 7);
2778
30.3k
        if_debug2m('L', pgs->memory, "[L]      end_cap=%d dash_cap=%d\n",
2779
30.3k
                   pgs->line_params.end_cap, pgs->line_params.dash_cap);
2780
30.3k
    }
2781
176k
    if (mask & cj_ac_sa_known) {
2782
8.09k
        cb = *cbp++;
2783
8.09k
        pgs->line_params.curve_join = ((cb >> 2) & 7) - 1;
2784
8.09k
        pgs->accurate_curves = (cb & 2) != 0;
2785
8.09k
        pgs->stroke_adjust = cb & 1;
2786
8.09k
        if_debug3m('L', pgs->memory, "[L]      CJ=%d AC=%d SA=%d\n",
2787
8.09k
                   pgs->line_params.curve_join, pgs->accurate_curves,
2788
8.09k
                   pgs->stroke_adjust);
2789
8.09k
    }
2790
176k
    if (mask & flatness_known) {
2791
12.6k
        cmd_get_value(pgs->flatness, cbp);
2792
12.6k
        if_debug1m('L', pgs->memory, "[L]      flatness=%g\n", pgs->flatness);
2793
12.6k
    }
2794
176k
    if (mask & line_width_known) {
2795
72.8k
        float width;
2796
2797
72.8k
        cmd_get_value(width, cbp);
2798
72.8k
        if_debug1m('L', pgs->memory, "[L]      line_width=%g\n", width);
2799
72.8k
        gx_set_line_width(&pgs->line_params, width);
2800
72.8k
    }
2801
176k
    if (mask & miter_limit_known) {
2802
1.24k
        float limit;
2803
2804
1.24k
        cmd_get_value(limit, cbp);
2805
1.24k
        if_debug1m('L', pgs->memory, "[L]      miter_limit=%g\n", limit);
2806
1.24k
        gx_set_miter_limit(&pgs->line_params, limit);
2807
1.24k
    }
2808
176k
    if (mask & op_bm_tk_known) {
2809
75.7k
        cb = *cbp++;
2810
75.7k
        pgs->blend_mode = cb >> 3;
2811
75.7k
        pgs->text_knockout = cb & 1;
2812
        /* the following usually have no effect; see gxclpath.c */
2813
75.7k
        cb = *cbp++;
2814
75.7k
        pgs->overprint_mode = (cb >> 2) & 1;
2815
75.7k
        pgs->stroke_overprint = (cb >> 1) & 1;
2816
75.7k
        pgs->overprint = cb & 1;
2817
75.7k
        cb = *cbp++;
2818
75.7k
        pgs->renderingintent = cb;
2819
75.7k
        if_debug6m('L', pgs->memory, "[L]      BM=%d TK=%d OPM=%d OP=%d op=%d RI=%d\n",
2820
75.7k
                   pgs->blend_mode, pgs->text_knockout, pgs->overprint_mode,
2821
75.7k
                   pgs->stroke_overprint, pgs->overprint, pgs->renderingintent);
2822
75.7k
    }
2823
176k
    if (mask & segment_notes_known) {
2824
0
        cb = *cbp++;
2825
0
        *pnotes = (segment_notes)(cb & 0x3f);
2826
0
        if_debug1m('L', pgs->memory, "[L]      notes=%d\n", *pnotes);
2827
0
    }
2828
176k
    if (mask & ais_known) {
2829
4.88k
        cmd_get_value(pgs->alphaisshape, cbp);
2830
4.88k
        if_debug1m('L', pgs->memory, "[L]      alphaisshape=%d\n", pgs->alphaisshape);
2831
4.88k
    }
2832
176k
    if (mask & stroke_alpha_known) {
2833
52.6k
        cmd_get_value(pgs->strokeconstantalpha, cbp);
2834
52.6k
        if_debug1m('L', pgs->memory, "[L]      strokeconstantalpha=%g\n", pgs->strokeconstantalpha);
2835
52.6k
    }
2836
176k
    if (mask & fill_alpha_known) {
2837
56.1k
        cmd_get_value(pgs->fillconstantalpha, cbp);
2838
56.1k
        if_debug1m('L', pgs->memory, "[L]      fillconstantalpha=%u\n", (uint)(pgs->fillconstantalpha));
2839
56.1k
    }
2840
176k
    pcb->ptr = cbp;
2841
176k
    return 0;
2842
176k
}
2843
2844
static int
2845
read_set_color_space(command_buf_t *pcb, gs_gstate *pgs,
2846
                     gx_device_clist_reader *cdev, gs_memory_t *mem)
2847
35.6k
{
2848
35.6k
    const byte *cbp = pcb->ptr;
2849
35.6k
    byte b = *cbp++;
2850
35.6k
    int index = b >> 4;
2851
35.6k
    gs_color_space *pcs;
2852
35.6k
    int code = 0;
2853
35.6k
    cmm_profile_t *picc_profile;
2854
35.6k
    clist_icc_color_t icc_information;
2855
2856
35.6k
    if_debug3m('L', mem, " %d%s%s\n", index,
2857
35.6k
               (b & 8 ? " (indexed)" : ""),
2858
35.6k
               (b & 4 ? "(proc)" : ""));
2859
    /* They all store the ICC information.  Even if it is NULL
2860
       it is used in the ICC case to avoid reading from the
2861
       serialized profile data which is stored elsewhere in the
2862
       clist.  Hence we avoid jumping around in the file. */
2863
35.6k
    memcpy(&icc_information, cbp, sizeof(clist_icc_color_t));
2864
35.6k
    cbp = cbp + sizeof(clist_icc_color_t);
2865
35.6k
    switch (index) {
2866
0
    case gs_color_space_index_DeviceGray:
2867
0
        pcs = gs_cspace_new_DeviceGray(mem);
2868
0
        break;
2869
0
    case gs_color_space_index_DeviceRGB:
2870
0
        pcs = gs_cspace_new_DeviceRGB(mem);
2871
0
        break;
2872
0
    case gs_color_space_index_DeviceCMYK:
2873
0
        pcs = gs_cspace_new_DeviceCMYK(mem);
2874
0
        break;
2875
35.6k
    case gs_color_space_index_ICC:
2876
        /* build the color space object */
2877
35.6k
        code = gs_cspace_build_ICC(&pcs, NULL, mem);
2878
        /* Don't bother getting the ICC stuff from the clist yet */
2879
35.6k
        picc_profile = gsicc_profile_new(NULL, cdev->memory, NULL, 0);
2880
35.6k
        if (picc_profile == NULL)
2881
0
            return gs_rethrow(-1, "Failed to find ICC profile during clist read");
2882
35.6k
        picc_profile->num_comps = icc_information.icc_num_components;
2883
35.6k
        picc_profile->hashcode = icc_information.icc_hash;
2884
35.6k
        picc_profile->hash_is_valid = true;
2885
35.6k
        picc_profile->islab = icc_information.is_lab;
2886
35.6k
        picc_profile->default_match = icc_information.default_match;
2887
35.6k
        picc_profile->data_cs = icc_information.data_cs;
2888
        /* Store the clist reader address in the profile
2889
           structure so that we can get to the buffer
2890
           data if we really neeed it.  Ideally, we
2891
           will use a cached link and only access this once. */
2892
35.6k
        picc_profile->dev = (gx_device*) cdev;
2893
        /* Assign it to the colorspace */
2894
35.6k
        code = gsicc_set_gscs_profile(pcs, picc_profile, mem);
2895
        /* And we no longer need our reference to the profile */
2896
35.6k
        gsicc_adjust_profile_rc(picc_profile, -1, "read_set_color_space");
2897
35.6k
        break;
2898
0
    default:
2899
0
        code = gs_note_error(gs_error_rangecheck);      /* others are NYI */
2900
0
        goto out;
2901
35.6k
    }
2902
2903
35.6k
    if (pcs == NULL) {
2904
0
        code = gs_note_error(gs_error_VMerror);
2905
0
        goto out;
2906
0
    }
2907
2908
35.6k
    if (b & 8) {
2909
2.15k
        bool use_proc = (b & 4) != 0;
2910
2.15k
        int hival;
2911
2.15k
        int num_values;
2912
2.15k
        byte *data;
2913
2.15k
        uint data_size;
2914
2.15k
        gs_color_space *pcs_indexed;
2915
2916
2.15k
        pcs_indexed = gs_cspace_alloc(mem, &gs_color_space_type_Indexed);
2917
2.15k
        if (pcs_indexed == 0) {
2918
0
            rc_decrement_cs(pcs, "read_set_color_space");
2919
0
            code = gs_note_error(gs_error_VMerror);
2920
0
            goto out;
2921
0
        }
2922
2.15k
        pcs_indexed->base_space = pcs;
2923
2.15k
        pcs = pcs_indexed;
2924
2.15k
        pcs->params.indexed.use_proc = 0;
2925
2.15k
        pcs->params.indexed.lookup.table.data = 0;
2926
2.15k
        pcs->params.indexed.lookup.table.size = 0;
2927
2.15k
        cmd_getw(hival, cbp);
2928
2.15k
        pcs->params.indexed.n_comps = gs_color_space_num_components(pcs->base_space);
2929
2.15k
        num_values = (hival + 1) * pcs->params.indexed.n_comps;
2930
2.15k
        if (use_proc) {
2931
0
            gs_indexed_map *map;
2932
2933
0
            code = alloc_indexed_map(&map, num_values, mem, "indexed map");
2934
0
            if (code < 0) {
2935
0
                rc_decrement_cs(pcs, "read_set_color_space");
2936
0
                goto out;
2937
0
            }
2938
0
            map->proc.lookup_index = lookup_indexed_map;
2939
0
            pcs->params.indexed.lookup.map = map;
2940
0
            data = (byte *)map->values;
2941
0
            data_size = num_values * sizeof(map->values[0]);
2942
2.15k
        } else {
2943
2.15k
            byte *table = gs_alloc_string(mem, num_values, "color_space indexed table");
2944
2945
2.15k
            if (table == 0) {
2946
0
                code = gs_note_error(gs_error_VMerror);
2947
0
                rc_decrement_cs(pcs, "read_set_color_space");
2948
0
                goto out;
2949
0
            }
2950
2.15k
            pcs->params.indexed.lookup.table.data = table;
2951
2.15k
            pcs->params.indexed.lookup.table.size = num_values;
2952
2.15k
            data = table;
2953
2.15k
            data_size = num_values;
2954
2.15k
        }
2955
2.15k
        cbp = cmd_read_data(pcb, data, data_size, cbp);
2956
2.15k
        pcs->params.indexed.hival = hival;
2957
2.15k
        pcs->params.indexed.use_proc = use_proc;
2958
2.15k
    }
2959
2960
    /* Release reference to old color space before installing new one. */
2961
35.6k
    if (pgs->color[0].color_space != NULL)
2962
35.6k
        rc_decrement_only_cs(pgs->color[0].color_space, "read_set_color_space");
2963
35.6k
    pgs->color[0].color_space = pcs;
2964
35.6k
out:
2965
35.6k
    pcb->ptr = cbp;
2966
35.6k
    return code;
2967
35.6k
}
2968
2969
static int
2970
read_begin_image(command_buf_t *pcb, gs_image_common_t *pic,
2971
                 gs_color_space *pcs)
2972
44.9k
{
2973
44.9k
    uint index = *(pcb->ptr)++;
2974
44.9k
    const gx_image_type_t *image_type = gx_image_type_table[index];
2975
44.9k
    stream s;
2976
44.9k
    int code;
2977
2978
    /* This is sloppy, but we don't have enough information to do better. */
2979
44.9k
    code = top_up_cbuf(pcb, &pcb->ptr);
2980
44.9k
    if (code < 0)
2981
0
        return code;
2982
44.9k
    s_init(&s, NULL);
2983
44.9k
    sread_string(&s, pcb->ptr, pcb->end - pcb->ptr);
2984
44.9k
    code = image_type->sget(pic, &s, pcs);
2985
44.9k
    pcb->ptr = sbufptr(&s);
2986
44.9k
    pic->imagematrices_are_untrustworthy = 0;
2987
44.9k
    return code;
2988
44.9k
}
2989
2990
static int
2991
read_put_params(command_buf_t *pcb, gs_gstate *pgs,
2992
                gx_device_clist_reader *cdev, gs_memory_t *mem)
2993
0
{
2994
0
    const byte *cbp = pcb->ptr;
2995
0
    gs_c_param_list param_list;
2996
0
    uint cleft;
2997
0
    uint rleft;
2998
0
    bool alloc_data_on_heap = false;
2999
0
    byte *param_buf;
3000
0
    uint param_length;
3001
0
    int code;
3002
3003
0
    cmd_get_value(param_length, cbp);
3004
0
    if_debug1m('L', mem, " length=%d\n", param_length);
3005
0
    if (param_length == 0) {
3006
0
        code = 1;               /* empty list */
3007
0
        goto out;
3008
0
    }
3009
3010
    /* Make sure entire serialized param list is in cbuf */
3011
    /* + force void* alignment */
3012
0
    code = top_up_cbuf(pcb, &cbp);
3013
0
    if (code < 0)
3014
0
        return code;
3015
0
    if (pcb->end - cbp >= param_length) {
3016
0
        param_buf = (byte *)cbp;
3017
0
        cbp += param_length;
3018
0
    } else {
3019
        /* NOTE: param_buf must be maximally aligned */
3020
0
        param_buf = gs_alloc_bytes(mem, param_length,
3021
0
                                   "clist put_params");
3022
0
        if (param_buf == 0) {
3023
0
            code = gs_note_error(gs_error_VMerror);
3024
0
            goto out;
3025
0
        }
3026
0
        alloc_data_on_heap = true;
3027
0
        cleft = pcb->end - cbp;
3028
0
        rleft = param_length - cleft;
3029
0
        memmove(param_buf, cbp, cleft);
3030
0
        next_is_skip(pcb);
3031
0
        pcb->end_status = sgets(pcb->s, param_buf + cleft, rleft, &rleft);
3032
0
        cbp = pcb->end;  /* force refill */
3033
0
    }
3034
3035
    /*
3036
     * Create a gs_c_param_list & expand into it.
3037
     * NB that gs_c_param_list doesn't copy objects into
3038
     * it, but rather keeps *pointers* to what's passed.
3039
     * That's OK because the serialized format keeps enough
3040
     * space to hold expanded versions of the structures,
3041
     * but this means we cannot deallocate source buffer
3042
     * until the gs_c_param_list is deleted.
3043
     */
3044
0
    gs_c_param_list_write(&param_list, mem);
3045
0
    code = gs_param_list_unserialize
3046
0
        ( (gs_param_list *)&param_list, param_buf );
3047
0
    if (code >= 0 && code != param_length)
3048
0
        code = gs_error_unknownerror;  /* must match */
3049
0
    if (code >= 0) {
3050
0
        gs_c_param_list_read(&param_list);
3051
0
        code = gs_gstate_putdeviceparams(pgs, (gx_device *)cdev,
3052
0
                                         (gs_param_list *)&param_list);
3053
0
    }
3054
0
    gs_c_param_list_release(&param_list);
3055
0
    if (alloc_data_on_heap)
3056
0
        gs_free_object(mem, param_buf, "clist put_params");
3057
3058
0
out:
3059
0
    pcb->ptr = cbp;
3060
0
    return code;
3061
0
}
3062
3063
/*
3064
 * Read a "composite" command, and execute the command.
3065
 *
3066
 * This code assumes that a the largest create compositor command,
3067
 * including the compositor name size, is smaller than the data buffer
3068
 * size. This assumption is inherent in the basic design of the coding
3069
 * and the de-serializer interface, as no length field is provided.
3070
 *
3071
 * At the time of this writing, no compositor violates this assumption.
3072
 * The largest composite is currently 1275 bytes, while the command
3073
 * data buffer is 4096 bytes.
3074
 *
3075
 * In the event that this assumption is violated, a change in the encoding
3076
 * would be called for.
3077
 *
3078
 * See comment in gdevp14.c c_pdf14trans_read PDF14_BEGIN_TRANS_MASK case.
3079
 */
3080
extern_gs_find_compositor();
3081
3082
static int
3083
read_composite(
3084
    command_buf_t *pcb,  gs_memory_t *mem, gs_composite_t **ppcomp)
3085
12.6M
{
3086
12.6M
    const byte *                cbp = pcb->ptr;
3087
12.6M
    int                         comp_id = 0, code = 0;
3088
12.6M
    const gs_composite_type_t * pcomp_type = 0;
3089
3090
    /* fill the command buffer (see comment above) */
3091
12.6M
    if (pcb->end - cbp < MAX_CLIST_COMPOSITOR_SIZE + sizeof(comp_id)) {
3092
807k
        code = top_up_cbuf(pcb, &cbp);
3093
807k
        if (code < 0)
3094
0
            return code;
3095
807k
    }
3096
3097
    /* find the appropriate compositor method vector */
3098
12.6M
    comp_id = *cbp++;
3099
12.6M
    if ((pcomp_type = gs_find_compositor(comp_id)) == 0)
3100
0
        return_error(gs_error_unknownerror);
3101
3102
    /* de-serialize the compositor */
3103
12.6M
    code = pcomp_type->procs.read(ppcomp, cbp, pcb->end - cbp, mem);
3104
3105
    /* If we read more than the maximum expected, return a rangecheck error */
3106
12.6M
    if ( code > MAX_CLIST_COMPOSITOR_SIZE )
3107
0
        return_error(gs_error_rangecheck);
3108
3109
12.6M
    if (code > 0)
3110
12.6M
        cbp += code;
3111
12.6M
    pcb->ptr = cbp;
3112
12.6M
    return code;
3113
12.6M
}
3114
3115
static int apply_composite(gx_device_clist_reader *cdev, gs_gstate *pgs,
3116
                                   gs_memory_t *mem, gs_composite_t *pcomp,
3117
                                   int x0, int y0, gx_device **ptarget)
3118
10.7M
{
3119
10.7M
    gx_device *tdev = *ptarget;
3120
10.7M
    int code;
3121
3122
10.7M
    code = pcomp->type->procs.adjust_ctm(pcomp, x0, y0, pgs);
3123
10.7M
    if (code < 0)
3124
0
        goto exit;
3125
    /*
3126
     * Apply the compositor to the target device; note that this may
3127
     * change the target device.
3128
     */
3129
10.7M
    code = dev_proc(tdev, composite)(tdev, &tdev, pcomp, pgs, mem, (gx_device*) cdev);
3130
10.7M
    if (code == 1) {
3131
        /* A new compositor was created that wrapped tdev. This should
3132
         * be our new target. */
3133
123k
        *ptarget = tdev;
3134
123k
        code = 0;
3135
123k
    }
3136
10.7M
    if (code < 0)
3137
1
        goto exit;
3138
3139
    /* Perform any updates for the clist device required */
3140
10.7M
    code = pcomp->type->procs.clist_compositor_read_update(pcomp,
3141
10.7M
                                        (gx_device *)cdev, tdev, pgs, mem);
3142
10.7M
exit:
3143
    /* free the compositor object */
3144
10.7M
    gs_free_object(mem, pcomp, "read_composite");
3145
3146
10.7M
    return code;
3147
10.7M
}
3148
3149
/* ---------------- Utilities ---------------- */
3150
3151
/* Read and unpack a short bitmap */
3152
/*
3153
 * The 'raster' in the dest buffer may be larger than the 'width_bytes'
3154
 * in the src, so after reading we memmove data down to the proper
3155
 * alignment from the last line backwards.
3156
 * THIS RELIES on width_bytes <= raster to work.
3157
 */
3158
static const byte *
3159
cmd_read_short_bits(command_buf_t *pcb, byte *data, int tot_bytes,
3160
                    int width_bytes, int height, uint raster, const byte *cbp)
3161
1.09M
{
3162
    /* Note the following may read from the file past the end of the buffer */
3163
    /* leaving cbp at pcb->end. No further reading using cbp can be done    */
3164
    /* without top_up_cbuf to reload the buffer.                            */
3165
1.09M
    cbp = cmd_read_data(pcb, data, tot_bytes, cbp);
3166
3167
    /* if needed, adjust buffer contents for dest raster > width_bytes */
3168
1.09M
    if (width_bytes < raster) {
3169
1.09M
        const byte *pdata = data /*src*/ + width_bytes * height;
3170
1.09M
        byte *udata = data /*dest*/ + height * raster;
3171
3172
17.1M
        while (--height > 0) { /* don't need to move the first line to itself */
3173
16.0M
            udata -= raster, pdata -= width_bytes;
3174
16.0M
            switch (width_bytes) {
3175
0
                default:
3176
0
                    memmove(udata, pdata, width_bytes);
3177
0
                    break;
3178
4.59k
                case 6:
3179
4.59k
                    udata[5] = pdata[5];
3180
9.85k
                case 5:
3181
9.85k
                    udata[4] = pdata[4];
3182
92.2k
                case 4:
3183
92.2k
                    udata[3] = pdata[3];
3184
2.18M
                case 3:
3185
2.18M
                    udata[2] = pdata[2];
3186
12.7M
                case 2:
3187
12.7M
                    udata[1] = pdata[1];
3188
16.0M
                case 1:
3189
16.0M
                    udata[0] = pdata[0];
3190
16.0M
                case 0:;            /* shouldn't happen */
3191
16.0M
            }
3192
16.0M
        }
3193
1.09M
    }
3194
1.09M
    return cbp;
3195
1.09M
}
3196
3197
/* Read a rectangle. */
3198
static const byte *
3199
cmd_read_rect(int op, gx_cmd_rect * prect, const byte * cbp)
3200
422k
{
3201
422k
    cmd_getw(prect->x, cbp);
3202
422k
    if (op & 0xf)
3203
92.7k
        prect->y += ((op >> 2) & 3) - 2;
3204
329k
    else {
3205
329k
        cmd_getw(prect->y, cbp);
3206
329k
    }
3207
422k
    cmd_getw(prect->width, cbp);
3208
422k
    if (op & 0xf)
3209
92.7k
        prect->height += (op & 3) - 2;
3210
329k
    else {
3211
329k
        cmd_getw(prect->height, cbp);
3212
329k
    }
3213
422k
    return cbp;
3214
422k
}
3215
3216
/*
3217
 * Select a map for loading with data.
3218
 *
3219
 * This routine has three outputs:
3220
 *   *pmdata - points to the map data.
3221
 *   *pcomp_num - points to a component number if the map is a transfer
3222
 *               map which has been set via the setcolortransfer operator.
3223
 *               A. value of NULL indicates that no component number is to
3224
 *               be sent for this map.
3225
 *   *pcount - the size of the map (in bytes).
3226
 */
3227
static int
3228
cmd_select_map(cmd_map_index map_index, cmd_map_contents cont,
3229
               gs_gstate * pgs, int ** pcomp_num, frac ** pmdata,
3230
               uint * pcount, gs_memory_t * mem)
3231
422k
{
3232
422k
    gx_transfer_map *map;
3233
422k
    gx_transfer_map **pmap;
3234
422k
    const char *cname;
3235
3236
422k
    *pcomp_num = NULL;          /* Only used for color transfer maps */
3237
422k
    switch (map_index) {
3238
140k
        case cmd_map_transfer:
3239
140k
            if_debug0m('L', mem, " transfer");
3240
140k
            rc_unshare_struct(pgs->set_transfer.gray, gx_transfer_map,
3241
140k
                &st_transfer_map, mem, return_error(gs_error_VMerror),
3242
140k
                "cmd_select_map(default_transfer)");
3243
140k
            map = pgs->set_transfer.gray;
3244
            /* Release all current maps */
3245
140k
            rc_decrement(pgs->set_transfer.red, "cmd_select_map(red)");
3246
140k
            pgs->set_transfer.red = NULL;
3247
140k
            pgs->set_transfer.red_component_num = -1;
3248
140k
            rc_decrement(pgs->set_transfer.green, "cmd_select_map(green)");
3249
140k
            pgs->set_transfer.green = NULL;
3250
140k
            pgs->set_transfer.green_component_num = -1;
3251
140k
            rc_decrement(pgs->set_transfer.blue, "cmd_select_map(blue)");
3252
140k
            pgs->set_transfer.blue = NULL;
3253
140k
            pgs->set_transfer.blue_component_num = -1;
3254
140k
            goto transfer2;
3255
0
        case cmd_map_transfer_0:
3256
0
            pmap = &pgs->set_transfer.red;
3257
0
            *pcomp_num = &pgs->set_transfer.red_component_num;
3258
0
            goto transfer1;
3259
0
        case cmd_map_transfer_1:
3260
0
            pmap = &pgs->set_transfer.green;
3261
0
            *pcomp_num = &pgs->set_transfer.green_component_num;
3262
0
            goto transfer1;
3263
0
        case cmd_map_transfer_2:
3264
0
            pmap = &pgs->set_transfer.blue;
3265
0
            *pcomp_num = &pgs->set_transfer.blue_component_num;
3266
0
            goto transfer1;
3267
0
        case cmd_map_transfer_3:
3268
0
            pmap = &pgs->set_transfer.gray;
3269
0
            *pcomp_num = &pgs->set_transfer.gray_component_num;
3270
0
transfer1:  if_debug1m('L', mem, " transfer[%d]", (int)(map_index - cmd_map_transfer_0));
3271
0
            rc_unshare_struct(*pmap, gx_transfer_map, &st_transfer_map, mem,
3272
0
                return_error(gs_error_VMerror), "cmd_select_map(transfer)");
3273
0
            map = *pmap;
3274
3275
140k
transfer2:  if (cont != cmd_map_other) {
3276
0
                gx_set_identity_transfer(map);
3277
0
                *pmdata = 0;
3278
0
                *pcount = 0;
3279
0
                return 0;
3280
0
            }
3281
140k
            break;
3282
140k
        case cmd_map_black_generation:
3283
140k
            if_debug0m('L', mem, " black generation");
3284
140k
            pmap = &pgs->black_generation;
3285
140k
            cname = "cmd_select_map(black generation)";
3286
140k
            goto alloc;
3287
140k
        case cmd_map_undercolor_removal:
3288
140k
            if_debug0m('L', mem, " undercolor removal");
3289
140k
            pmap = &pgs->undercolor_removal;
3290
140k
            cname = "cmd_select_map(undercolor removal)";
3291
281k
alloc:      if (cont == cmd_map_none) {
3292
0
                rc_decrement(*pmap, cname);
3293
0
                *pmap = 0;
3294
0
                *pmdata = 0;
3295
0
                *pcount = 0;
3296
0
                return 0;
3297
0
            }
3298
281k
            rc_unshare_struct(*pmap, gx_transfer_map, &st_transfer_map,
3299
281k
                              mem, return_error(gs_error_VMerror), cname);
3300
281k
            map = *pmap;
3301
281k
            if (cont == cmd_map_identity) {
3302
0
                gx_set_identity_transfer(map);
3303
0
                *pmdata = 0;
3304
0
                *pcount = 0;
3305
0
                return 0;
3306
0
            }
3307
281k
            break;
3308
281k
        default:
3309
0
            *pmdata = 0;
3310
0
            return 0;
3311
422k
    }
3312
422k
    map->proc = gs_mapped_transfer;
3313
422k
    *pmdata = map->values;
3314
422k
    *pcount = sizeof(map->values);
3315
422k
    return 0;
3316
422k
}
3317
3318
/* Create a device halftone for the imager if necessary. */
3319
static int
3320
cmd_create_dev_ht(gx_device_halftone **ppdht, gs_memory_t *mem)
3321
0
{
3322
0
    gx_device_halftone *pdht = *ppdht;
3323
3324
0
    if (pdht == 0) {
3325
0
        rc_header rc;
3326
3327
0
        rc_alloc_struct_1(pdht, gx_device_halftone, &st_device_halftone, mem,
3328
0
                          return_error(gs_error_VMerror),
3329
0
                          "cmd_create_dev_ht");
3330
0
        rc = pdht->rc;
3331
0
        memset(pdht, 0, sizeof(*pdht));
3332
0
        pdht->rc = rc;
3333
0
        *ppdht = pdht;
3334
0
    }
3335
0
    return 0;
3336
0
}
3337
3338
/* Resize the halftone components array if necessary. */
3339
static int
3340
cmd_resize_halftone(gx_device_halftone **ppdht, uint num_comp,
3341
                    gs_memory_t * mem)
3342
0
{
3343
0
    int code = cmd_create_dev_ht(ppdht, mem);
3344
0
    gx_device_halftone *pdht = *ppdht;
3345
3346
0
    if (code < 0)
3347
0
        return code;
3348
0
    if (num_comp != pdht->num_comp) {
3349
0
        gx_ht_order_component *pcomp;
3350
3351
        /*
3352
         * We must be careful not to shrink or free the components array
3353
         * before releasing any relevant elements.
3354
         */
3355
0
        if (num_comp < pdht->num_comp) {
3356
0
            uint i;
3357
3358
            /* Don't release the default order. */
3359
0
            for (i = pdht->num_comp; i-- > num_comp;)
3360
0
                if (pdht->components[i].corder.bit_data != pdht->order.bit_data)
3361
0
                    gx_ht_order_release(&pdht->components[i].corder, mem, true);
3362
0
            if (num_comp == 0) {
3363
0
                gs_free_object(mem, pdht->components, "cmd_resize_halftone");
3364
0
                pcomp = 0;
3365
0
            } else {
3366
0
                pcomp = gs_resize_object(mem, pdht->components, num_comp,
3367
0
                                         "cmd_resize_halftone");
3368
0
                if (pcomp == 0) {
3369
0
                    pdht->num_comp = num_comp;  /* attempt consistency */
3370
0
                    return_error(gs_error_VMerror);
3371
0
                }
3372
0
            }
3373
0
        } else {
3374
            /* num_comp > pdht->num_comp */
3375
0
            if (pdht->num_comp == 0)
3376
0
                pcomp = gs_alloc_struct_array(mem, num_comp,
3377
0
                                              gx_ht_order_component,
3378
0
                                              &st_ht_order_component_element,
3379
0
                                              "cmd_resize_halftone");
3380
0
            else
3381
0
                pcomp = gs_resize_object(mem, pdht->components, num_comp,
3382
0
                                         "cmd_resize_halftone");
3383
0
            if (pcomp == 0)
3384
0
                return_error(gs_error_VMerror);
3385
0
            memset(&pcomp[pdht->num_comp], 0,
3386
0
                   sizeof(*pcomp) * (num_comp - pdht->num_comp));
3387
0
        }
3388
0
        pdht->num_comp = num_comp;
3389
0
        pdht->components = pcomp;
3390
0
    }
3391
0
    return 0;
3392
0
}
3393
3394
/* ------ Path operations ------ */
3395
3396
/* Decode a path segment. */
3397
static int
3398
clist_decode_segment(gx_path * ppath, int op, fixed vs[6],
3399
                 gs_fixed_point * ppos, int x0, int y0, segment_notes notes)
3400
3.73M
{
3401
3.73M
    fixed px = ppos->x - int2fixed(x0);
3402
3.73M
    fixed py = ppos->y - int2fixed(y0);
3403
3.73M
    int code;
3404
3405
4.28M
#define A vs[0]
3406
3.73M
#define B vs[1]
3407
3.73M
#define C vs[2]
3408
3.73M
#define D vs[3]
3409
3.73M
#define E vs[4]
3410
3.73M
#define F vs[5]
3411
3412
3.73M
    switch (op) {
3413
706k
        case cmd_opv_rmoveto:
3414
706k
            code = gx_path_add_point(ppath, px += A, py += B);
3415
706k
            break;
3416
326k
        case cmd_opv_rlineto:
3417
326k
            code = gx_path_add_line_notes(ppath, px += A, py += B, notes);
3418
326k
            break;
3419
0
        case cmd_opv_rgapto:
3420
0
            code = gx_path_add_gap_notes(ppath, px += A, py += B, notes);
3421
0
            break;
3422
816k
        case cmd_opv_hlineto:
3423
816k
            code = gx_path_add_line_notes(ppath, px += A, py, notes);
3424
816k
            break;
3425
916k
        case cmd_opv_vlineto:
3426
916k
            code = gx_path_add_line_notes(ppath, px, py += A, notes);
3427
916k
            break;
3428
159k
        case cmd_opv_rmlineto:
3429
159k
            if ((code = gx_path_add_point(ppath, px += A, py += B)) < 0)
3430
0
                break;
3431
159k
            code = gx_path_add_line_notes(ppath, px += C, py += D, notes);
3432
159k
            break;
3433
66.9k
        case cmd_opv_rm2lineto:
3434
66.9k
            if ((code = gx_path_add_point(ppath, px += A, py += B)) < 0 ||
3435
66.9k
                (code = gx_path_add_line_notes(ppath, px += C, py += D,
3436
66.9k
                                               notes)) < 0
3437
66.9k
                )
3438
0
                break;
3439
66.9k
            code = gx_path_add_line_notes(ppath, px += E, py += F, notes);
3440
66.9k
            break;
3441
2.08k
        case cmd_opv_rm3lineto:
3442
2.08k
            if ((code = gx_path_add_point(ppath, px += A, py += B)) < 0 ||
3443
2.08k
                (code = gx_path_add_line_notes(ppath, px += C, py += D,
3444
2.08k
                                               notes)) < 0 ||
3445
2.08k
                (code = gx_path_add_line_notes(ppath, px += E, py += F,
3446
2.08k
                                               notes)) < 0
3447
2.08k
                )
3448
0
                break;
3449
2.08k
            code = gx_path_add_line_notes(ppath, px -= C, py -= D, notes);
3450
2.08k
            break;
3451
353k
        case cmd_opv_rrcurveto: /* a b c d e f => a b a+c b+d a+c+e b+d+f */
3452
354k
rrc:        E += (C += A);
3453
354k
            F += (D += B);
3454
438k
curve:      code = gx_path_add_curve_notes(ppath, px + A, py + B,
3455
438k
                                           px + C, py + D,
3456
438k
                                           px + E, py + F, notes);
3457
438k
            px += E, py += F;
3458
438k
            break;
3459
35.4k
        case cmd_opv_hvcurveto: /* a b c d => a 0 a+b c a+b c+d */
3460
38.0k
hvc:        F = C + D, D = C, E = C = A + B, B = 0;
3461
38.0k
            goto curve;
3462
36.6k
        case cmd_opv_vhcurveto: /* a b c d => 0 a b a+c b+d a+c */
3463
41.0k
vhc:        E = B + D, F = D = A + C, C = B, B = A, A = 0;
3464
41.0k
            goto curve;
3465
2.12k
        case cmd_opv_nrcurveto: /* a b c d => 0 0 a b a+c b+d */
3466
2.12k
            F = B + D, E = A + C, D = B, C = A, B = A = 0;
3467
2.12k
            goto curve;
3468
2.71k
        case cmd_opv_rncurveto: /* a b c d => a b a+c b+d a+c b+d */
3469
2.71k
            F = D += B, E = C += A;
3470
2.71k
            goto curve;
3471
4.41k
        case cmd_opv_vqcurveto: /* a b => VH a b TS(a,b) TS(b,a) */
3472
4.41k
            if ((A ^ B) < 0)
3473
1.47k
                C = -B, D = -A;
3474
2.93k
            else
3475
2.93k
                C = B, D = A;
3476
4.41k
            goto vhc;
3477
2.59k
        case cmd_opv_hqcurveto: /* a b => HV a TS(a,b) b TS(b,a) */
3478
2.59k
            if ((A ^ B) < 0)
3479
682
                D = -A, C = B, B = -B;
3480
1.91k
            else
3481
1.91k
                D = A, C = B;
3482
2.59k
            goto hvc;
3483
1.56k
        case cmd_opv_scurveto: /* (a b c d e f) => */
3484
1.56k
            {
3485
1.56k
                fixed a = A, b = B;
3486
3487
                /* See gxclpath.h for details on the following. */
3488
1.56k
                if (A == 0) {
3489
                    /* Previous curve was vh or vv */
3490
1.42k
                    A = E - C, B = D - F, C = C - a, D = b - D, E = a, F = -b;
3491
1.42k
                } else {
3492
                    /* Previous curve was hv or hh */
3493
141
                    A = C - E, B = F - D, C = a - C, D = D - b, E = -a, F = b;
3494
141
                }
3495
1.56k
            }
3496
1.56k
            goto rrc;
3497
303k
        case cmd_opv_closepath:
3498
303k
            if ((code = gx_path_close_subpath(ppath)) < 0)
3499
303k
                return code;;
3500
303k
            if ((code = gx_path_current_point(ppath, (gs_fixed_point *) vs)) < 0)
3501
303k
                return code;;
3502
303k
            px = A, py = B;
3503
303k
            break;
3504
0
        default:
3505
0
            return_error(gs_error_rangecheck);
3506
3.73M
    }
3507
3.73M
#undef A
3508
3.73M
#undef B
3509
3.73M
#undef C
3510
3.73M
#undef D
3511
3.73M
#undef E
3512
3.73M
#undef F
3513
3.73M
    ppos->x = px + int2fixed(x0);
3514
3.73M
    ppos->y = py + int2fixed(y0);
3515
3.73M
    return code;
3516
3.73M
}
3517
3518
/*
3519
 * Execute a polyfill -- either a fill_parallelogram or a fill_triangle.
3520
 *
3521
 * Note that degenerate parallelograms or triangles may collapse into
3522
 * a single line or point.  We must check for this so we don't try to
3523
 * access non-existent segments.
3524
 */
3525
static int
3526
clist_do_polyfill(gx_device *dev, gx_path *ppath,
3527
                  const gx_drawing_color *pdcolor,
3528
                  gs_logical_operation_t lop)
3529
3.02k
{
3530
3.02k
    const subpath *psub = ppath->first_subpath;
3531
3.02k
    const segment *pseg1;
3532
3.02k
    const segment *pseg2;
3533
3.02k
    int code;
3534
3535
3.02k
    if (psub && (pseg1 = psub->next) != 0 && (pseg2 = pseg1->next) != 0) {
3536
3.02k
        fixed px = psub->pt.x, py = psub->pt.y;
3537
3.02k
        fixed ax = pseg1->pt.x - px, ay = pseg1->pt.y - py;
3538
3.02k
        fixed bx, by;
3539
        /*
3540
         * We take advantage of the fact that the parameter lists for
3541
         * fill_parallelogram and fill_triangle are identical.
3542
         */
3543
3.02k
        dev_proc_fill_parallelogram((*fill));
3544
3545
        /* close_path of 3 point triangle adds 4th point, detected here.*/
3546
        /* close_path on parallelogram adds 5th point also ignored. */
3547
3.02k
        if (pseg2->next && !(px == pseg2->next->pt.x && py == pseg2->next->pt.y)) {
3548
            /* Parallelogram */
3549
3.02k
            fill = dev_proc(dev, fill_parallelogram);
3550
3.02k
            bx = pseg2->pt.x - pseg1->pt.x;
3551
3.02k
            by = pseg2->pt.y - pseg1->pt.y;
3552
3.02k
        } else {
3553
            /* Triangle */
3554
0
            fill = dev_proc(dev, fill_triangle);
3555
0
            bx = pseg2->pt.x - px;
3556
0
            by = pseg2->pt.y - py;
3557
0
        }
3558
3.02k
        code = fill(dev, px, py, ax, ay, bx, by, pdcolor, lop);
3559
3.02k
    } else
3560
0
        code = 0;
3561
3.02k
    gx_path_new(ppath);
3562
3.02k
    return code;
3563
3.02k
}