Coverage Report

Created: 2022-04-16 11:23

/src/ghostpdl/base/gspaint.c
Line
Count
Source (jump to first uncovered line)
1
/* Copyright (C) 2001-2022 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.,  1305 Grant Avenue - Suite 200, Novato,
13
   CA 94945, U.S.A., +1(415)492-9861, for further information.
14
*/
15
16
17
/* Painting procedures for Ghostscript library */
18
#include "math_.h"    /* for fabs */
19
#include "gx.h"
20
#include "gpcheck.h"
21
#include "gserrors.h"
22
#include "gsropt.h"   /* for gxpaint.h */
23
#include "gxfixed.h"
24
#include "gxmatrix.h"   /* for gs_gstate */
25
#include "gspaint.h"
26
#include "gspath.h"
27
#include "gzpath.h"
28
#include "gxpaint.h"
29
#include "gxpcolor.h"   /* for do_fill_stroke */
30
#include "gzstate.h"
31
#include "gxdevice.h"
32
#include "gxdevmem.h"
33
#include "gzcpath.h"
34
#include "gxhldevc.h"
35
#include "gsutil.h"
36
#include "gxscanc.h"
37
#include "gxdevsop.h"
38
#include "gsicc_cms.h"
39
#include "gdevepo.h"
40
#include "assert_.h"
41
42
/* Define the nominal size for alpha buffers. */
43
#define abuf_nominal_SMALL 500
44
0
#define abuf_nominal_LARGE 2000
45
#if ARCH_SMALL_MEMORY
46
#  define abuf_nominal abuf_nominal_SMALL
47
#else
48
#ifdef DEBUG
49
#  define abuf_nominal\
50
     (gs_debug_c('.') ? abuf_nominal_SMALL : abuf_nominal_LARGE)
51
#else
52
0
#  define abuf_nominal abuf_nominal_LARGE
53
#endif
54
#endif
55
56
/* Erase the page */
57
int
58
gs_erasepage(gs_gstate * pgs)
59
3
{
60
    /*
61
     * We can't just fill with device white; we must take the
62
     * transfer function into account.
63
     */
64
3
    int code;
65
66
3
    if ((code = gs_gsave(pgs)) < 0)
67
0
        return code;
68
3
    if ((code = gs_setgray(pgs, 1.0)) >= 0) {
69
        /* Fill the page directly, ignoring clipping. */
70
3
        code = gs_fillpage(pgs);
71
3
    }
72
3
    gs_grestore(pgs);
73
3
    return code;
74
3
}
75
76
/* Fill the page with the current color. */
77
int
78
gs_fillpage(gs_gstate * pgs)
79
5.59k
{
80
5.59k
    gx_device *dev = gs_currentdevice(pgs);
81
5.59k
    int code;
82
83
    /*
84
     * No need to check for returning error code,
85
     * existing device will continue to operate as before.
86
     */
87
5.59k
    epo_check_and_install(dev);
88
89
    /* Deliberately use the terminal device here */
90
5.59k
    if (dev_proc(dev, get_color_mapping_procs) ==  gx_error_get_color_mapping_procs) {
91
0
        emprintf1(dev->memory,
92
0
                  "\n   *** Error: No get_color_mapping_procs for device: %s\n",
93
0
                  dev->dname);
94
0
        return_error(gs_error_Fatal);
95
0
    }
96
    /* Processing a fill object operation, but this counts as "UNTOUCHED" */
97
5.59k
    gx_unset_dev_color(pgs);    /* force update so we pick up the new tag */
98
5.59k
    gx_unset_alt_dev_color(pgs);
99
5.59k
    dev_proc(pgs->device, set_graphics_type_tag)(pgs->device, GS_UNTOUCHED_TAG);
100
101
5.59k
    code = gx_set_dev_color(pgs);
102
5.59k
    if (code != 0)
103
0
        return code;
104
105
5.59k
    code = (*dev_proc(dev, fillpage))(dev, pgs, gs_currentdevicecolor_inline(pgs));
106
5.59k
    if (code < 0)
107
0
        return code;
108
109
    /* If GrayDetection is set, make sure monitoring is enabled. */
110
5.59k
    if (dev->icc_struct != NULL &&
111
5.59k
            dev->icc_struct->graydetection && !dev->icc_struct->pageneutralcolor) {
112
0
        dev->icc_struct->pageneutralcolor = true; /* start detecting again */
113
0
        code = gsicc_mcm_begin_monitor(pgs->icc_link_cache, dev);
114
0
    }
115
5.59k
    if (code < 0)
116
0
        return code;
117
5.59k
    return (*dev_proc(dev, sync_output)) (dev);
118
5.59k
}
119
/*
120
 * Set up an alpha buffer for a stroke or fill operation.  Return 0
121
 * if no buffer could be allocated, 1 if a buffer was installed,
122
 * or the usual negative error code.
123
 *
124
 * The fill/stroke code sets up a clipping device if needed; however,
125
 * since we scale up all the path coordinates, we either need to scale up
126
 * the clipping region, or do clipping after, rather than before,
127
 * alpha buffering.  Either of these is a little inconvenient, but
128
 * the former is less inconvenient.
129
 */
130
static int
131
scale_paths(gs_gstate * pgs, int log2_scale_x, int log2_scale_y, bool do_path)
132
0
{
133
    /*
134
     * Because of clip and clippath, any of path, clip_path, and view_clip
135
     * may be aliases for each other.  The only reliable way to detect
136
     * this is by comparing the segments pointers.  Note that we must
137
     * scale the non-segment parts of the paths even if the segments are
138
     * aliased.
139
     */
140
0
    const gx_path_segments *seg_clip =
141
0
        (pgs->clip_path->path_valid ? pgs->clip_path->path.segments : 0);
142
0
    const gx_clip_rect_list *list_clip = pgs->clip_path->rect_list;
143
0
    const gx_path_segments *seg_view_clip;
144
0
    const gx_clip_rect_list *list_view_clip;
145
0
    const gx_path_segments *seg_effective_clip =
146
0
        (pgs->effective_clip_path->path_valid ?
147
0
         pgs->effective_clip_path->path.segments : 0);
148
0
    const gx_clip_rect_list *list_effective_clip =
149
0
        pgs->effective_clip_path->rect_list;
150
151
0
    gx_cpath_scale_exp2_shared(pgs->clip_path, log2_scale_x, log2_scale_y,
152
0
                               false, false);
153
0
    if (pgs->view_clip != 0 && pgs->view_clip != pgs->clip_path) {
154
0
        seg_view_clip =
155
0
            (pgs->view_clip->path_valid ? pgs->view_clip->path.segments : 0);
156
0
        list_view_clip = pgs->view_clip->rect_list;
157
0
        gx_cpath_scale_exp2_shared(pgs->view_clip, log2_scale_x, log2_scale_y,
158
0
                                   list_view_clip == list_clip,
159
0
                                   seg_view_clip && seg_view_clip == seg_clip);
160
0
    } else
161
0
        seg_view_clip = 0, list_view_clip = 0;
162
0
    if (pgs->effective_clip_path != pgs->clip_path &&
163
0
        pgs->effective_clip_path != pgs->view_clip
164
0
        )
165
0
        gx_cpath_scale_exp2_shared(pgs->effective_clip_path, log2_scale_x,
166
0
                                   log2_scale_y,
167
0
                                   list_effective_clip == list_clip ||
168
0
                                   list_effective_clip == list_view_clip,
169
0
                                   seg_effective_clip &&
170
0
                                   (seg_effective_clip == seg_clip ||
171
0
                                    seg_effective_clip == seg_view_clip));
172
0
    if (do_path) {
173
0
        const gx_path_segments *seg_path = pgs->path->segments;
174
175
0
        gx_path_scale_exp2_shared(pgs->path, log2_scale_x, log2_scale_y,
176
0
                                  seg_path == seg_clip ||
177
0
                                  seg_path == seg_view_clip ||
178
0
                                  seg_path == seg_effective_clip);
179
0
    }
180
0
    return 0;
181
0
}
182
static void
183
scale_dash_pattern(gs_gstate * pgs, double scale)
184
0
{
185
0
    int i;
186
187
0
    for (i = 0; i < pgs->line_params.dash.pattern_size; ++i)
188
0
        pgs->line_params.dash.pattern[i] *= scale;
189
0
    pgs->line_params.dash.offset *= scale;
190
0
    pgs->line_params.dash.pattern_length *= scale;
191
0
    pgs->line_params.dash.init_dist_left *= scale;
192
0
    if (pgs->line_params.dot_length_absolute)
193
0
        pgs->line_params.dot_length *= scale;
194
0
}
195
196
/*
197
 Returns 0 for OK.
198
 Returns 1 for "OK, buffer needs releasing"
199
 Returns 2 for "Empty region"
200
 Returns -ve for error
201
 */
202
static int
203
alpha_buffer_init(gs_gstate * pgs, fixed extra_x, fixed extra_y, int alpha_bits,
204
                  bool devn)
205
0
{
206
0
    gx_device *dev = gs_currentdevice_inline(pgs);
207
0
    int log2_alpha_bits = ilog2(alpha_bits);
208
0
    gs_fixed_rect bbox;
209
0
    gs_int_rect ibox;
210
0
    uint width, raster, band_space;
211
0
    uint height, height2;
212
0
    gs_log2_scale_point log2_scale;
213
0
    gs_memory_t *mem;
214
0
    gx_device_memory *mdev;
215
216
0
    log2_scale.x = log2_scale.y = log2_alpha_bits;
217
0
    gx_path_bbox(pgs->path, &bbox);
218
0
    ibox.p.x = fixed2int(bbox.p.x - extra_x) - 1;
219
0
    ibox.p.y = fixed2int(bbox.p.y - extra_y) - 1;
220
0
    ibox.q.x = fixed2int_ceiling(bbox.q.x + extra_x) + 1;
221
0
    ibox.q.y = fixed2int_ceiling(bbox.q.y + extra_y) + 1;
222
0
    (void)dev_proc(dev, dev_spec_op)(dev, gxdso_restrict_bbox, &ibox, sizeof(ibox));
223
0
    if ((ibox.q.y <= ibox.p.y) || (ibox.q.x <= ibox.p.x))
224
0
        return 2;
225
0
    width = (ibox.q.x - ibox.p.x) << log2_scale.x;
226
0
    raster = bitmap_raster(width);
227
0
    band_space = raster << log2_scale.y;
228
0
    height2 = (ibox.q.y - ibox.p.y);
229
0
    height = (abuf_nominal / band_space);
230
0
    if (height == 0)
231
0
        height = 1;
232
0
    if (height > height2)
233
0
        height = height2;
234
0
    height <<= log2_scale.y;
235
0
    mem = pgs->memory;
236
0
    mdev = gs_alloc_struct(mem, gx_device_memory, &st_device_memory,
237
0
                           "alpha_buffer_init");
238
0
    if (mdev == 0)
239
0
        return 0;   /* if no room, don't buffer */
240
    /* We may have to update the marking parameters if we have a pdf14 device
241
       as our target.  Need to do while dev is still active in pgs */
242
0
    if (dev_proc(dev, dev_spec_op)(dev, gxdso_is_pdf14_device, NULL, 0) > 0) {
243
0
        gs_update_trans_marking_params(pgs);
244
0
    }
245
0
    gs_make_mem_abuf_device(mdev, mem, dev, &log2_scale,
246
0
                            alpha_bits, ibox.p.x << log2_scale.x, devn);
247
0
    mdev->width = width;
248
0
    mdev->height = height;
249
0
    mdev->bitmap_memory = mem;
250
0
    if ((*dev_proc(mdev, open_device)) ((gx_device *) mdev) < 0) {
251
        /* No room for bits, punt. */
252
0
        gs_free_object(mem, mdev, "alpha_buffer_init");
253
0
        return 0;
254
0
    }
255
0
    gx_set_device_only(pgs, (gx_device *) mdev);
256
0
    scale_paths(pgs, log2_scale.x, log2_scale.y, true);
257
0
    return 1;
258
0
}
259
260
/* Release an alpha buffer. */
261
static int
262
alpha_buffer_release(gs_gstate * pgs, bool newpath)
263
0
{
264
0
    gx_device_memory *mdev =
265
0
        (gx_device_memory *) gs_currentdevice_inline(pgs);
266
0
    int code = (*dev_proc(mdev, close_device)) ((gx_device *) mdev);
267
268
0
    if (code >= 0)
269
0
        scale_paths(pgs, -mdev->log2_scale.x, -mdev->log2_scale.y,
270
0
                !(newpath && !gx_path_is_shared(pgs->path)));
271
    /* Reference counting will free mdev. */
272
0
    gx_set_device_only(pgs, mdev->target);
273
0
    return code;
274
0
}
275
276
/* Setup for black vector handling */
277
static inline bool black_vectors(gs_gstate *pgs, gx_device *dev)
278
194k
{
279
194k
    if (dev->icc_struct != NULL && dev->icc_struct->blackvector &&
280
194k
        pgs->black_textvec_state == NULL) {
281
0
        return gsicc_setup_black_textvec(pgs, dev, false);
282
0
    }
283
194k
    return false;
284
194k
}
285
286
static int do_fill(gs_gstate *pgs, int rule)
287
44.2k
{
288
44.2k
    int code, abits, acode, rcode = 0;
289
44.2k
    bool devn;
290
44.2k
    bool black_vector = false;
291
44.2k
    bool in_smask =
292
44.2k
        (dev_proc(pgs->device, dev_spec_op)(pgs->device, gxdso_in_smask_construction, NULL, 0)) > 0;
293
294
    /* We need to distinguish text from vectors to set the object tag.
295
296
       To make that determination, we check for the show graphics state being stored
297
       in the current graphics state. This works even in the case of a glyph from a
298
       Type 3 Postscript/PDF font which has multiple, nested gsave/grestore pairs in
299
       the BuildGlyph/BuildChar procedure. Also, it works in the case of operating
300
       without a glyph cache or bypassing the cache because the glyph is too large or
301
       the cache being already full.
302
303
       Note that it doesn't work for a construction like:
304
       "(xyz) true charpath fill/stroke"
305
       where the show machinations have completed before we get to the fill operation.
306
       This has implications for how we handle PDF text rendering modes 1 and 2. To
307
       handle that, we'll have to add a flag to the path structure, or to the path
308
       segment structure (depending on how fine grained we require it to be).
309
     */
310
44.2k
    if (pgs->show_gstate == NULL && !in_smask) {
311
41.3k
        ensure_tag_is_set(pgs, pgs->device, GS_VECTOR_TAG); /* NB: may unset_dev_color */
312
41.3k
        black_vector = black_vectors(pgs, pgs->device); /* Set vector fill to black */
313
41.3k
    } else
314
2.86k
        ensure_tag_is_set(pgs, pgs->device, GS_TEXT_TAG); /* NB: may unset_dev_color */
315
316
44.2k
    code = gx_set_dev_color(pgs);
317
44.2k
    if (code != 0)
318
6
        goto out;
319
44.2k
    code = gs_gstate_color_load(pgs);
320
44.2k
    if (code < 0)
321
0
        goto out;
322
323
44.2k
    if (pgs->overprint || (!pgs->overprint && dev_proc(pgs->device, dev_spec_op)(pgs->device,
324
44.2k
        gxdso_overprint_active, NULL, 0))) {
325
0
        gs_overprint_params_t op_params = { 0 };
326
327
0
        if_debug0m(gs_debug_flag_overprint, pgs->memory,
328
0
            "[overprint] Fill Overprint\n");
329
0
        code = gs_do_set_overprint(pgs);
330
0
        if (code < 0)
331
0
            goto out;
332
333
0
        op_params.op_state = OP_STATE_FILL;
334
0
        gs_gstate_update_overprint(pgs, &op_params);
335
0
    }
336
337
44.2k
    abits = 0;
338
44.2k
    {
339
44.2k
        gx_device_color *col = gs_currentdevicecolor_inline(pgs);
340
44.2k
        devn = color_is_devn(col);
341
44.2k
        if (color_is_pure(col) || devn)
342
36.6k
            abits = alpha_buffer_bits(pgs);
343
44.2k
    }
344
44.2k
    if (abits > 1) {
345
0
        acode = alpha_buffer_init(pgs, pgs->fill_adjust.x,
346
0
                                  pgs->fill_adjust.y, abits, devn);
347
0
        if (acode == 2) { /* Special case for no fill required */
348
0
            code = 0;
349
0
            goto out;
350
0
        }
351
0
        if (acode < 0) {
352
0
            code = acode;
353
0
            goto out;
354
0
        }
355
0
    } else
356
44.2k
        acode = 0;
357
44.2k
    code = gx_fill_path(pgs->path, gs_currentdevicecolor_inline(pgs), pgs, rule,
358
44.2k
                        pgs->fill_adjust.x, pgs->fill_adjust.y);
359
44.2k
    if (acode > 0)
360
0
        rcode = alpha_buffer_release(pgs, code >= 0);
361
44.2k
    if (code >= 0 && rcode < 0)
362
0
        code = rcode;
363
364
44.2k
out:
365
44.2k
    if (black_vector) {
366
        /* Restore color */
367
0
        gsicc_restore_blacktextvec(pgs, false);
368
0
    }
369
370
44.2k
    return code;
371
44.2k
}
372
373
/* Fill the current path using a specified rule. */
374
static int
375
fill_with_rule(gs_gstate * pgs, int rule)
376
44.2k
{
377
44.2k
    int code;
378
379
    /* If we're inside a charpath, just merge the current path */
380
    /* into the parent's path. */
381
44.2k
    if (pgs->in_charpath)
382
0
        code = gx_path_add_char_path(pgs->show_gstate->path, pgs->path,
383
0
                                     pgs->in_charpath);
384
            /* If we're rendering a glyph cached, the show machinery decides
385
             * whether to actually image it on the output or not, but uncached
386
             * will render directly to the output, so for text rendering
387
             * mode 3, we have to short circuit it here, but keep the
388
             * current point
389
             */
390
44.2k
    else if (gs_is_null_device(pgs->device)
391
44.2k
            || (pgs->show_gstate && pgs->text_rendering_mode == 3
392
44.2k
            && pgs->in_cachedevice == CACHE_DEVICE_NOT_CACHING)) {
393
        /* Handle separately to prevent gs_gstate_color_load - bug 688308. */
394
0
        gs_newpath(pgs);
395
0
        code = 0;
396
44.2k
    } else {
397
44.2k
        code = do_fill(pgs, rule);
398
44.2k
        if (code >= 0)
399
44.2k
            code = gs_newpath(pgs);
400
44.2k
    }
401
44.2k
    return code;
402
44.2k
}
403
/* Fill using the winding number rule */
404
int
405
gs_fill(gs_gstate * pgs)
406
41.5k
{
407
41.5k
    pgs->device->sgr.stroke_stored = false;
408
41.5k
    return fill_with_rule(pgs, gx_rule_winding_number);
409
41.5k
}
410
/* Fill using the even/odd rule */
411
int
412
gs_eofill(gs_gstate * pgs)
413
2.67k
{
414
2.67k
    pgs->device->sgr.stroke_stored = false;
415
2.67k
    return fill_with_rule(pgs, gx_rule_even_odd);
416
2.67k
}
417
418
static int
419
do_stroke(gs_gstate * pgs)
420
151k
{
421
151k
    int code, abits, acode, rcode = 0;
422
151k
    bool devn;
423
151k
    bool is_fill_correct = true;
424
151k
    bool black_vector = false;
425
151k
    bool in_smask =
426
151k
        (dev_proc(pgs->device, dev_spec_op)(pgs->device, gxdso_in_smask_construction, NULL, 0)) > 0;
427
428
429
    /* We need to distinguish text from vectors to set the object tag.
430
431
       To make that determination, we check for the show graphics state being stored
432
       in the current graphics state. This works even in the case of a glyph from a
433
       Type 3 Postscript/PDF font which has multiple, nested gsave/grestore pairs in
434
       the BuildGlyph/BuildChar procedure. Also, it works in the case of operating
435
       without a glyph cache or bypassing the cache because the glyph is too large or
436
       the cache being already full.
437
438
       Note that it doesn't work for a construction like:
439
       "(xyz) true charpath fill/stroke"
440
       where the show machinations have completed before we get to the fill operation.
441
       This has implications for how we handle PDF text rendering modes 1 and 2. To
442
       handle that, we'll have to add a flag to the path structure, or to the path
443
       segment structure (depending on how fine grained we require it to be).
444
     */
445
151k
    if (pgs->show_gstate == NULL && !in_smask) {
446
151k
        ensure_tag_is_set(pgs, pgs->device, GS_VECTOR_TAG); /* NB: may unset_dev_color */
447
151k
        black_vector = black_vectors(pgs, pgs->device);
448
151k
    } else
449
0
        ensure_tag_is_set(pgs, pgs->device, GS_TEXT_TAG); /* NB: may unset_dev_color */
450
451
151k
    code = gx_set_dev_color(pgs);
452
151k
    if (code != 0)
453
0
        goto out;
454
151k
    code = gs_gstate_color_load(pgs);
455
151k
    if (code < 0)
456
0
        goto out;
457
458
459
151k
    if (pgs->stroke_overprint || (!pgs->stroke_overprint && dev_proc(pgs->device, dev_spec_op)(pgs->device,
460
151k
        gxdso_overprint_active, NULL, 0))) {
461
1
        gs_overprint_params_t op_params = { 0 };
462
463
        /* PS2 does not have the concept of fill and stroke colors. Here we need to possibly correct
464
           for that in the graphic state during this operation */
465
1
        if (pgs->is_fill_color) {
466
0
            is_fill_correct = false;
467
0
            pgs->is_fill_color = false;
468
0
        }
469
470
471
1
        if_debug0m(gs_debug_flag_overprint, pgs->memory,
472
1
            "[overprint] Stroke Overprint\n");
473
1
        code = gs_do_set_overprint(pgs);
474
1
        if (code < 0) {
475
0
            if (!is_fill_correct) {
476
0
                pgs->is_fill_color = true;
477
0
            }
478
0
            goto out;
479
0
        }
480
481
1
        op_params.op_state = OP_STATE_STROKE;
482
1
        gs_gstate_update_overprint(pgs, &op_params);
483
1
    }
484
485
151k
    abits = 0;
486
151k
    {
487
151k
        gx_device_color *col = gs_currentdevicecolor_inline(pgs);
488
151k
        devn = color_is_devn(col);
489
151k
        if (color_is_pure(col) || devn)
490
113k
            abits = alpha_buffer_bits(pgs);
491
151k
    }
492
151k
    if (abits > 1) {
493
        /*
494
         * Expand the bounding box by the line width.
495
         * This is expensive to compute, so we only do it
496
         * if we know we're going to buffer.
497
         */
498
0
        float xxyy = fabs(pgs->ctm.xx) + fabs(pgs->ctm.yy);
499
0
        float xyyx = fabs(pgs->ctm.xy) + fabs(pgs->ctm.yx);
500
0
        float scale = (float)(1 << (abits / 2));
501
0
        float orig_width = gs_currentlinewidth(pgs);
502
0
        float new_width = orig_width * scale;
503
0
        fixed extra_adjust =
504
0
                float2fixed(max(xxyy, xyyx) * new_width / 2);
505
0
        float orig_flatness = gs_currentflat(pgs);
506
0
        gx_path spath;
507
508
        /* Scale up the line width, dash pattern, and flatness. */
509
0
        if (extra_adjust < fixed_1)
510
0
            extra_adjust = fixed_1;
511
0
        acode = alpha_buffer_init(pgs,
512
0
                                  pgs->fill_adjust.x + extra_adjust,
513
0
                                  pgs->fill_adjust.y + extra_adjust,
514
0
                                  abits, devn);
515
0
        if (acode == 2) {            /* Special code meaning no fill required */
516
0
            if (!is_fill_correct) {
517
0
                pgs->is_fill_color = true;
518
0
            }
519
0
            code = 0;
520
0
            goto out;
521
0
        }
522
0
        if (acode < 0) {
523
0
            if (!is_fill_correct) {
524
0
                pgs->is_fill_color = true;
525
0
            }
526
0
            code = acode;
527
0
            goto out;
528
0
        }
529
0
        gs_setlinewidth(pgs, new_width);
530
0
        scale_dash_pattern(pgs, scale);
531
0
        gs_setflat(pgs, (double)(orig_flatness * scale));
532
        /*
533
         * The alpha-buffer device requires that we fill the
534
         * entire path as a single unit.
535
         */
536
0
        gx_path_init_local(&spath, pgs->memory);
537
0
        code = gx_stroke_add(pgs->path, &spath, pgs, false);
538
0
        gs_setlinewidth(pgs, orig_width);
539
0
        scale_dash_pattern(pgs, 1.0 / scale);
540
0
        if (code >= 0)
541
0
            code = gx_fill_path(&spath, gs_currentdevicecolor_inline(pgs), pgs,
542
0
                                gx_rule_winding_number,
543
0
                                pgs->fill_adjust.x,
544
0
                                pgs->fill_adjust.y);
545
0
        gs_setflat(pgs, orig_flatness);
546
0
        gx_path_free(&spath, "gs_stroke");
547
0
        if (acode > 0)
548
0
            rcode = alpha_buffer_release(pgs, code >= 0);
549
0
    } else
550
151k
        code = gx_stroke_fill(pgs->path, pgs);
551
151k
    if (code >= 0 && rcode < 0)
552
0
        code = rcode;
553
554
151k
    if (!is_fill_correct) {
555
0
        pgs->is_fill_color = true;
556
0
    }
557
558
151k
out:
559
151k
    if (black_vector) {
560
        /* Restore color */
561
0
        gsicc_restore_blacktextvec(pgs, false);
562
0
    }
563
151k
    return code;
564
151k
}
565
566
/* Stroke the current path */
567
int
568
gs_stroke(gs_gstate * pgs)
569
151k
{
570
151k
    int code;
571
572
    /*
573
     * If we're inside a charpath, just merge the current path
574
     * into the parent's path.
575
     */
576
151k
    if (pgs->in_charpath) {
577
0
        if (pgs->in_charpath == cpm_true_charpath) {
578
            /*
579
             * A stroke inside a true charpath should do the
580
             * equivalent of strokepath.
581
             */
582
0
            code = gs_strokepath(pgs);
583
0
            if (code < 0)
584
0
                return code;
585
0
        }
586
0
        code = gx_path_add_char_path(pgs->show_gstate->path, pgs->path,
587
0
                                     pgs->in_charpath);
588
0
        if (code < 0)
589
0
            return code;
590
0
    }
591
151k
    if (!gs_is_null_device(pgs->device)) {
592
151k
        code = do_stroke(pgs);
593
151k
        if (code < 0)
594
0
            return code;
595
151k
    }
596
151k
    return gs_newpath(pgs);
597
151k
}
598
599
/* Compute the stroked outline of the current path */
600
static int
601
gs_strokepath_aux(gs_gstate * pgs, bool traditional)
602
13
{
603
13
    gx_path spath;
604
13
    int code;
605
606
13
    gx_path_init_local(&spath, pgs->path->memory);
607
13
    code = gx_stroke_add(pgs->path, &spath, pgs, traditional);
608
13
    if (code < 0) {
609
0
        gx_path_free(&spath, "gs_strokepath");
610
0
        return code;
611
0
    }
612
13
    pgs->device->sgr.stroke_stored = false;
613
13
    code = gx_path_assign_free(pgs->path, &spath);
614
13
    if (code < 0)
615
0
        return code;
616
    /* NB: needs testing with PCL */
617
13
    if (gx_path_is_void(pgs->path))
618
4
        pgs->current_point_valid = false;
619
9
    else {
620
9
        gx_setcurrentpoint(pgs, fixed2float(spath.position.x), fixed2float(spath.position.y));
621
9
    }
622
13
    return 0;
623
624
13
}
625
626
int
627
gs_strokepath(gs_gstate * pgs)
628
13
{
629
13
    return gs_strokepath_aux(pgs, true);
630
13
}
631
632
int
633
gs_strokepath2(gs_gstate * pgs)
634
0
{
635
0
    return gs_strokepath_aux(pgs, false);
636
0
}
637
638
static int do_fill_stroke(gs_gstate *pgs, int rule, int *restart)
639
1.66k
{
640
1.66k
    int code, abits, acode = 0, rcode = 0;
641
1.66k
    bool devn;
642
1.66k
    float orig_width, scale, orig_flatness;
643
1.66k
    bool black_vector = false;
644
1.66k
    bool in_smask =
645
1.66k
        (dev_proc(pgs->device, dev_spec_op)(pgs->device, gxdso_in_smask_construction, NULL, 0)) > 0;
646
647
648
    /* It is either our first time, or the stroke was a pattern and
649
       we are coming back from the error if restart < 1 (0 is first
650
       time, 1 stroke is set, and we only need to finish out fill */
651
1.66k
    if (pgs->is_fill_color) {
652
        /* if the fill_color is a pattern, make sure the tile is locked so that */
653
        /* it does not get evicted as the stroke color is loaded.   */
654
1.66k
        if (gx_dc_is_pattern1_color(gs_currentdevicecolor_inline(pgs))) {
655
0
            gs_id id;
656
657
0
            if(gs_currentdevicecolor_inline(pgs)->colors.pattern.p_tile != NULL) {
658
0
                id = gs_currentdevicecolor_inline(pgs)->colors.pattern.p_tile->id;
659
0
                code = dev_proc(pgs->device, lock_pattern)(pgs->device, pgs, id, true);
660
0
            } else {
661
0
                code = 0;
662
0
            }
663
0
      if (code < 0)
664
0
    return code; /* lock failed -- tile not in cache? */
665
0
        }
666
1.66k
        gs_swapcolors_quick(pgs); /* switch to the stroke color */
667
1.66k
    }
668
669
1.66k
    if (*restart < 1) {
670
671
        /* We need to distinguish text from vectors to set the object tag.
672
673
           To make that determination, we check for the show graphics state being stored
674
           in the current graphics state. This works even in the case of a glyph from a
675
           Type 3 Postscript/PDF font which has multiple, nested gsave/grestore pairs in
676
           the BuildGlyph/BuildChar procedure. Also, it works in the case of operating
677
           without a glyph cache or bypassing the cache because the glyph is too large or
678
           the cache being already full.
679
680
           Note that it doesn't work for a construction like:
681
           "(xyz) true charpath fill/stroke"
682
           where the show machinations have completed before we get to the fill operation.
683
           This has implications for how we handle PDF text rendering modes 1 and 2. To
684
           handle that, we'll have to add a flag to the path structure, or to the path
685
           segment structure (depending on how fine grained we require it to be).
686
         */
687
1.66k
        if (pgs->show_gstate == NULL && !in_smask) {
688
1.66k
            ensure_tag_is_set(pgs, pgs->device, GS_VECTOR_TAG); /* NB: may unset_dev_color */
689
1.66k
            black_vector = black_vectors(pgs, pgs->device);
690
1.66k
        } else
691
0
            ensure_tag_is_set(pgs, pgs->device, GS_TEXT_TAG); /* NB: may unset_dev_color */
692
693
        /* if we are at restart == 0, we set the stroke color. */
694
1.66k
        code = gx_set_dev_color(pgs);
695
1.66k
        if (code != 0)
696
0
            goto out2;   /* may be gs_error_Remap_color or real error */
697
1.66k
        code = gs_gstate_color_load(pgs);
698
1.66k
        if (code < 0)
699
0
            goto out2;
700
        /* If this was a pattern color, make sure and lock it in the pattern_cache */
701
1.66k
        if (gx_dc_is_pattern1_color(gs_currentdevicecolor_inline(pgs))) {
702
0
            gs_id id;
703
704
0
            if(gs_currentdevicecolor_inline(pgs)->colors.pattern.p_tile != NULL) {
705
0
                id = gs_currentdevicecolor_inline(pgs)->colors.pattern.p_tile->id;
706
0
                code = dev_proc(pgs->device, lock_pattern)(pgs->device, pgs, id, true);
707
0
            } else {
708
0
                code = 0;
709
0
            }
710
0
            if (code < 0)
711
0
                goto out2; /* lock failed -- tile not in cache? */
712
0
        }
713
1.66k
    }
714
715
1.66k
    if (pgs->stroke_overprint || (!pgs->stroke_overprint && dev_proc(pgs->device, dev_spec_op)(pgs->device,
716
1.66k
        gxdso_overprint_active, NULL, 0))) {
717
0
        if_debug0m(gs_debug_flag_overprint, pgs->memory,
718
0
            "[overprint] StrokeFill Stroke Set Overprint\n");
719
0
        code = gs_do_set_overprint(pgs);
720
0
        if (code < 0)
721
0
            goto out2;
722
0
    }
723
1.66k
    *restart = 1;   /* finished, successfully with stroke_color */
724
725
1.66k
    gs_swapcolors_quick(pgs); /* switch to fill color */
726
727
    /* Have to set the fill color too */
728
1.66k
    if (pgs->show_gstate == NULL)
729
1.66k
        ensure_tag_is_set(pgs, pgs->device, GS_VECTOR_TAG);  /* NB: may unset_dev_color */
730
0
    else
731
0
        ensure_tag_is_set(pgs, pgs->device, GS_TEXT_TAG); /* NB: may unset_dev_color */
732
733
1.66k
    code = gx_set_dev_color(pgs);
734
1.66k
    if (code != 0) {
735
0
        goto out2;
736
0
    }
737
1.66k
    code = gs_gstate_color_load(pgs);
738
1.66k
    if (code < 0) {
739
        /* color is set for fill, but a failure here is a problem */
740
        /* i.e., something other than error_Remap_Color */
741
0
        *restart = 2; /* we shouldn't re-enter with '2' */
742
0
        goto out;
743
0
    }
744
745
1.66k
    if (pgs->overprint || (!pgs->overprint && dev_proc(pgs->device, dev_spec_op)(pgs->device,
746
1.66k
        gxdso_overprint_active, NULL, 0))) {
747
0
        if_debug0m(gs_debug_flag_overprint, pgs->memory,
748
0
            "[overprint] StrokeFill Fill Set Overprint\n");
749
0
        code = gs_do_set_overprint(pgs);
750
0
        if (code < 0)
751
0
            goto out;   /* fatal */
752
0
    }
753
754
1.66k
    abits = 0;
755
1.66k
    {
756
1.66k
        gx_device_color *col_fill = gs_currentdevicecolor_inline(pgs);
757
1.66k
        gx_device_color *col_stroke = gs_swappeddevicecolor_inline(pgs);
758
1.66k
        devn = color_is_devn(col_fill) && color_is_devn(col_stroke);
759
        /* could be devn and masked_devn */
760
1.66k
        if ((color_is_pure(col_fill) && color_is_pure(col_stroke)) || devn)
761
1.63k
            abits = alpha_buffer_bits(pgs);
762
1.66k
    }
763
1.66k
    if (abits > 1) {
764
        /*
765
         * Expand the bounding box by the line width.
766
         * This is expensive to compute, so we only do it
767
         * if we know we're going to buffer.
768
         */
769
0
        float new_width;
770
0
        fixed extra_adjust;
771
0
        float xxyy = fabs(pgs->ctm.xx) + fabs(pgs->ctm.yy);
772
0
        float xyyx = fabs(pgs->ctm.xy) + fabs(pgs->ctm.yx);
773
0
        gs_logical_operation_t orig_lop = pgs->log_op;
774
0
        pgs->log_op |= lop_pdf14; /* Force stroking to happen all in 1 go */
775
0
        scale = (float)(1 << (abits / 2));
776
0
        orig_width = gs_currentlinewidth(pgs);
777
0
        new_width = orig_width * scale;
778
0
        extra_adjust =
779
0
                float2fixed(max(xxyy, xyyx) * new_width / 2);
780
0
        orig_flatness = gs_currentflat(pgs);
781
782
        /* Scale up the line width, dash pattern, and flatness. */
783
0
        if (extra_adjust < fixed_1)
784
0
            extra_adjust = fixed_1;
785
0
        acode = alpha_buffer_init(pgs,
786
0
                                  pgs->fill_adjust.x + extra_adjust,
787
0
                                  pgs->fill_adjust.y + extra_adjust,
788
0
                                  abits, devn);
789
0
        if (acode == 2) /* Special case for no fill required */
790
0
            goto out;
791
0
        if (acode < 0)
792
0
            goto out;
793
0
        gs_setlinewidth(pgs, new_width);
794
0
        scale_dash_pattern(pgs, scale);
795
0
        gs_setflat(pgs, (double)(orig_flatness * scale));
796
0
        pgs->log_op = orig_lop;
797
0
    } else
798
1.66k
        acode = 0;
799
1.66k
    code = gx_fill_stroke_path(pgs, rule);
800
1.66k
    if (abits > 1)
801
0
    {
802
0
        gs_setlinewidth(pgs, orig_width);
803
0
        scale_dash_pattern(pgs, 1.0 / scale);
804
0
        gs_setflat(pgs, orig_flatness);
805
0
        acode = alpha_buffer_release(pgs, code >= 0);
806
0
    }
807
1.66k
    if (pgs->is_fill_color) {
808
        /* The color _should_ be the fill color, so make sure it is unlocked  */
809
1.66k
        if (gx_dc_is_pattern1_color(gs_currentdevicecolor_inline(pgs))) {
810
0
            gs_id id;
811
812
0
            if(gs_currentdevicecolor_inline(pgs)->colors.pattern.p_tile != NULL) {
813
0
                id = gs_currentdevicecolor_inline(pgs)->colors.pattern.p_tile->id;
814
0
                code = dev_proc(pgs->device, lock_pattern)(pgs->device, pgs, id, false);
815
0
            } else {
816
0
                code = 0;
817
0
            }
818
0
      if (code < 0)
819
0
        goto out2; /* lock failed -- tile not in cache? */
820
0
        }
821
1.66k
    }
822
1.66k
out:
823
1.66k
    if (black_vector) {
824
        /* Restore color */
825
0
        gsicc_restore_blacktextvec(pgs, false);
826
0
    }
827
828
1.66k
    if (gx_dc_is_pattern1_color(gs_swappeddevicecolor_inline(pgs))) {
829
0
        gs_id id;
830
831
0
        if (gs_swappeddevicecolor_inline(pgs)->colors.pattern.p_tile != NULL) {
832
0
            id = gs_swappeddevicecolor_inline(pgs)->colors.pattern.p_tile->id;
833
0
            rcode = dev_proc(pgs->device, lock_pattern)(pgs->device, pgs, id, false);
834
0
            if (rcode < 0)
835
0
          return rcode; /* unlock failed -- shouldn't be possible */
836
0
        } else {
837
0
            code = 0;
838
0
        }
839
0
    }
840
1.66k
    if (code >= 0 && acode < 0)
841
0
        code = acode;
842
1.66k
    return code;
843
844
0
out2:
845
0
    if (black_vector) {
846
        /* Restore color */
847
0
        gsicc_restore_blacktextvec(pgs, false);
848
0
    }
849
0
    return code;
850
1.66k
}
851
852
/* Fill the current path using a specified rule. */
853
static int
854
fill_stroke_with_rule(gs_gstate * pgs, int rule, int *restart)
855
1.66k
{
856
1.66k
    int code;
857
858
    /* If we're inside a charpath, just merge the current path */
859
    /* into the parent's path. */
860
1.66k
    if (pgs->in_charpath) {
861
        /* If we're rendering a glyph cached, the show machinery decides
862
         * whether to actually image it on the output or not, but uncached
863
         * will render directly to the output, so for text rendering
864
         * mode 3, we have to short circuit it here, but keep the
865
         * current point
866
         */
867
0
        *restart = 0;
868
0
        code = gx_path_add_char_path(pgs->show_gstate->path, pgs->path,
869
0
                                     pgs->in_charpath);
870
0
        if (code < 0)
871
0
            return code;
872
0
        if (pgs->in_charpath == cpm_true_charpath) {
873
            /*
874
             * A stroke inside a true charpath should do the
875
             * equivalent of strokepath.
876
             */
877
0
            code = gs_strokepath(pgs);
878
0
            if (code < 0)
879
0
                return code;
880
0
            code = gx_path_add_char_path(pgs->show_gstate->path, pgs->path,
881
0
                                         pgs->in_charpath);
882
0
            if (code < 0)
883
0
                return code;
884
0
        }
885
0
    }
886
1.66k
    else if (gs_is_null_device(pgs->device) ||
887
1.66k
             (pgs->show_gstate && pgs->text_rendering_mode == 3 &&
888
1.66k
              pgs->in_cachedevice == CACHE_DEVICE_NOT_CACHING)) {
889
        /* Text Rendering Mode = 3 => Neither stroke, nor fill */
890
        /* Handle separately to prevent gs_gstate_color_load - bug 688308. */
891
0
        *restart = 0;
892
0
        gs_newpath(pgs);
893
0
        code = 0;
894
1.66k
    } else {
895
1.66k
        code = do_fill_stroke(pgs, rule, restart);
896
1.66k
        if (code >= 0)
897
1.66k
            gs_newpath(pgs);
898
1.66k
    }
899
1.66k
    return code;
900
1.66k
}
901
/* Fill using the winding number rule */
902
int
903
gs_fillstroke(gs_gstate * pgs, int *restart)
904
1.66k
{
905
1.66k
    pgs->device->sgr.stroke_stored = false;
906
1.66k
    return fill_stroke_with_rule(pgs, gx_rule_winding_number, restart);
907
1.66k
}
908
/* Fill using the even/odd rule */
909
int
910
gs_eofillstroke(gs_gstate * pgs, int *restart)
911
0
{
912
0
    pgs->device->sgr.stroke_stored = false;
913
0
    return fill_stroke_with_rule(pgs, gx_rule_even_odd, restart);
914
0
}