Coverage Report

Created: 2022-04-16 11:23

/src/ghostpdl/base/gsdparam.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
/* Default device parameters for Ghostscript library */
17
#include "memory_.h"    /* for memcpy */
18
#include "string_.h"    /* for strlen */
19
#include "gx.h"
20
#include "gserrors.h"
21
#include "gsdevice.h"   /* for prototypes */
22
#include "gsparam.h"
23
#include "gsparamx.h"   /* for param_put_enum */
24
#include "gxdevice.h"
25
#include "gxdevsop.h"
26
#include "gxfixed.h"
27
#include "gsicc_manage.h"
28
#include "gdevnup.h"    /* to install N-up subclass device */
29
extern gx_device_nup gs_nup_device;
30
31
/* Define whether we accept PageSize as a synonym for MediaSize. */
32
/* This is for backward compatibility only. */
33
#define PAGESIZE_IS_MEDIASIZE
34
35
/* Names corresponding to gs_overprint_control_t enum */
36
static const char *const overprint_control_names[] = {
37
    gs_overprint_control_names, 0
38
};
39
40
/* ================ Getting parameters ================ */
41
42
/* Forward references */
43
static bool param_HWColorMap(gx_device *, byte *);
44
45
/* Get the device parameters. */
46
int
47
gs_get_device_or_hw_params(gx_device * orig_dev, gs_param_list * plist,
48
                           bool is_hardware)
49
13.8k
{
50
    /*
51
     * We must be prepared to copy the device if it is the read-only
52
     * prototype.
53
     */
54
13.8k
    gx_device *dev;
55
13.8k
    int code = 0;
56
57
13.8k
    if (orig_dev->memory)
58
13.8k
        dev = orig_dev;
59
0
    else {
60
0
        code = gs_copydevice(&dev, orig_dev, plist->memory);
61
0
        if (code < 0)
62
0
            return code;
63
0
    }
64
13.8k
    fill_dev_proc(dev, get_params, gx_default_get_params);
65
13.8k
    fill_dev_proc(dev, get_page_device, gx_default_get_page_device);
66
13.8k
    fill_dev_proc(dev, get_alpha_bits, gx_default_get_alpha_bits);
67
13.8k
    if (is_hardware) {
68
0
        if (dev_proc(dev, get_hardware_params) != NULL)
69
0
            code = (*dev_proc(dev, get_hardware_params)) (dev, plist);
70
13.8k
    } else {
71
13.8k
        if (dev_proc(dev, get_params) != NULL)
72
13.8k
            code = (*dev_proc(dev, get_params)) (dev, plist);
73
13.8k
    }
74
13.8k
    if (dev != orig_dev)
75
0
        gx_device_retain(dev, false);  /* frees the copy */
76
13.8k
    return code;
77
13.8k
}
78
79
int gx_default_get_param(gx_device *dev, char *Param, void *list)
80
31.4k
{
81
31.4k
    gs_param_list * plist = (gs_param_list *)list;
82
31.4k
    int k, colors = dev->color_info.num_components;
83
31.4k
    gs_param_string profile_array[NUM_DEVICE_PROFILES];
84
31.4k
    gs_param_string postren_profile, blend_profile;
85
31.4k
    gs_param_string proof_profile, link_profile, icc_colorants;
86
31.4k
    gsicc_rendering_intents_t profile_intents[NUM_DEVICE_PROFILES];
87
31.4k
    gsicc_blackptcomp_t blackptcomps[NUM_DEVICE_PROFILES];
88
31.4k
    gsicc_blackpreserve_t blackpreserve[NUM_DEVICE_PROFILES];
89
31.4k
    int color_accuracy = MAX_COLOR_ACCURACY;
90
31.4k
    int depth = dev->color_info.depth;
91
31.4k
    cmm_dev_profile_t *dev_profile;
92
31.4k
    char null_str[1]={'\0'};
93
31.4k
#define set_param_array(a, d, s)\
94
31.4k
  (a.data = d, a.size = s, a.persistent = false);
95
31.4k
    bool devicegraytok = true;  /* Default if device profile stuct not set */
96
31.4k
    bool graydetection = false;
97
31.4k
    bool usefastcolor = false;  /* set for unmanaged color */
98
31.4k
    bool blacktext = false;
99
31.4k
    bool blackvector = false;
100
    /* By default overprinting only valid with cmyk devices */
101
31.4k
    gs_overprint_control_t overprint_control = gs_overprint_control_enable;
102
31.4k
    bool prebandthreshold = true, temp_bool = false;
103
104
31.4k
    if(strcmp(Param, "OutputDevice") == 0){
105
0
        gs_param_string dns;
106
0
        param_string_from_string(dns, dev->dname);
107
0
        return param_write_name(plist, "OutputDevice", &dns);
108
0
    }
109
31.4k
#ifdef PAGESIZE_IS_MEDIASIZE
110
31.4k
    if (strcmp(Param, "PageSize") == 0) {
111
683
        gs_param_float_array msa;
112
683
        set_param_array(msa, dev->MediaSize, 2);
113
683
        return param_write_float_array(plist, "PageSize", &msa);
114
683
    }
115
30.8k
#endif
116
30.8k
    if (strcmp(Param, "ProcessColorModel") == 0) {
117
0
        const char *cms = get_process_color_model_name(dev);
118
119
        /* We might have an uninitialized device with */
120
        /* color_info.num_components = 0.... */
121
0
        if ((cms != NULL) && (*cms != '\0')) {
122
0
            gs_param_string pcms;
123
0
            param_string_from_string(pcms, cms);
124
0
            return param_write_name(plist, "ProcessColorModel", &pcms);
125
0
        }
126
0
    }
127
30.8k
    if (strcmp(Param, "HWResolution") == 0) {
128
0
        gs_param_float_array hwra;
129
0
        set_param_array(hwra, dev->HWResolution, 2);
130
0
        return param_write_float_array(plist, "HWResolution", &hwra);
131
0
    }
132
30.8k
    if (strcmp(Param, "ImagingBBox") == 0) {
133
0
        gs_param_float_array ibba;
134
0
        set_param_array(ibba, dev->ImagingBBox, 4);
135
0
        if (dev->ImagingBBox_set)
136
0
            return param_write_float_array(plist, "ImagingBBox", &ibba);
137
0
        else
138
0
            return param_write_null(plist, "ImagingBBox");
139
0
    }
140
30.8k
    if (strcmp(Param, "Margins") == 0) {
141
0
        gs_param_float_array ma;
142
0
        set_param_array(ma, dev->Margins, 2);
143
0
        return param_write_float_array(plist, "Margins", &ma);
144
0
    }
145
30.8k
    if (strcmp(Param, "MaxSeparations") == 0) {
146
0
        int max_sep = dev->color_info.max_components;
147
0
        return param_write_int(plist, "MaxSeparations", &max_sep);
148
0
    }
149
30.8k
    if (strcmp(Param, "NumCopies") == 0) {
150
0
        if (dev->NumCopies_set < 0 || (*dev_proc(dev, get_page_device))(dev) == 0) {
151
0
            return_error(gs_error_undefined);
152
0
        } else {
153
0
            if (dev->NumCopies_set)
154
0
                return param_write_int(plist, "NumCopies", &dev->NumCopies);
155
0
            else
156
0
                return param_write_null(plist, "NumCopies");
157
0
        }
158
0
    }
159
30.8k
    if (strcmp(Param, "SeparationColorNames") == 0) {
160
0
        gs_param_string_array scna;
161
0
        set_param_array(scna, NULL, 0);
162
0
        return param_write_name_array(plist, "SeparationColorNames", &scna);
163
0
    }
164
30.8k
    if (strcmp(Param, "Separations") == 0) {
165
0
        bool seprs = false;
166
0
        return param_write_bool(plist, "Separations", &seprs);
167
0
    }
168
30.8k
    if (strcmp(Param, "UseCIEColor") == 0) {
169
0
        return param_write_bool(plist, "UseCIEColor", &dev->UseCIEColor);
170
0
    }
171
172
    /* Non-standard parameters */
173
30.8k
    if (strcmp(Param, "HWSize") == 0) {
174
0
        int HWSize[2];
175
0
        gs_param_int_array hwsa;
176
177
0
        HWSize[0] = dev->width;
178
0
        HWSize[1] = dev->height;
179
0
        set_param_array(hwsa, HWSize, 2);
180
0
        return param_write_int_array(plist, "HWSize", &hwsa);
181
0
    }
182
30.8k
    if (strcmp(Param, ".HWMargins") == 0) {
183
0
        gs_param_float_array hwma;
184
0
        set_param_array(hwma, dev->HWMargins, 4);
185
0
        return param_write_float_array(plist, ".HWMargins", &hwma);
186
0
    }
187
30.8k
    if (strcmp(Param, ".MediaSize") == 0) {
188
0
        gs_param_float_array msa;
189
0
        set_param_array(msa, dev->MediaSize, 2);
190
0
        return param_write_float_array(plist, ".MediaSize", &msa);
191
0
    }
192
30.8k
    if (strcmp(Param, "Name") == 0) {
193
0
        gs_param_string dns;
194
0
        param_string_from_string(dns, dev->dname);
195
0
        return param_write_string(plist, "Name", &dns);
196
0
    }
197
30.8k
    if (strcmp(Param, "Colors") == 0) {
198
0
        int colors = dev->color_info.num_components;
199
0
        return param_write_int(plist, "Colors", &colors);
200
0
    }
201
30.8k
    if (strcmp(Param, "BitsPerPixel") == 0) {
202
0
        return param_write_int(plist, "BitsPerPixel", &depth);
203
0
    }
204
30.8k
    if (strcmp(Param, "GrayValues") == 0) {
205
0
        int GrayValues = dev->color_info.max_gray + 1;
206
0
        return param_write_int(plist, "GrayValues", &GrayValues);
207
0
    }
208
30.8k
    if (strcmp(Param, "PageCount") == 0) {
209
0
        return param_write_long(plist, "PageCount", &dev->PageCount);
210
0
    }
211
30.8k
    if (strcmp(Param, ".IgnoreNumCopies") == 0) {
212
0
        return param_write_bool(plist, ".IgnoreNumCopies", &dev->IgnoreNumCopies);
213
0
    }
214
30.8k
    if (strcmp(Param, "TextAlphaBits") == 0) {
215
0
        return param_write_int(plist, "TextAlphaBits",
216
0
                                &dev->color_info.anti_alias.text_bits);
217
0
    }
218
30.8k
    if (strcmp(Param, "GraphicsAlphaBits") == 0) {
219
0
        return param_write_int(plist, "GraphicsAlphaBits",
220
0
                                &dev->color_info.anti_alias.graphics_bits);
221
0
    }
222
30.8k
    if (strcmp(Param, "AntidropoutDownscaler") == 0) {
223
0
        return param_write_bool(plist, "AntidropoutDownscaler",
224
0
                                &dev->color_info.use_antidropout_downscaler);
225
0
    }
226
30.8k
    if (strcmp(Param, ".LockSafetyParams") == 0) {
227
0
        return param_write_bool(plist, ".LockSafetyParams", &dev->LockSafetyParams);
228
0
    }
229
30.8k
    if (strcmp(Param, "MaxPatternBitmap") == 0) {
230
0
        return param_write_size_t(plist, "MaxPatternBitmap", &dev->MaxPatternBitmap);
231
0
    }
232
30.8k
    if (strcmp(Param, "PageUsesTransparency") == 0) {
233
0
        return param_write_bool(plist, "PageUsesTransparency", &dev->page_uses_transparency);
234
0
    }
235
30.8k
    if (strcmp(Param, "PageUsesOverprint") == 0) {
236
0
        return param_write_bool(plist, "PageUsesOverprint", &dev->page_uses_overprint);
237
0
    }
238
30.8k
    if (strcmp(Param, "MaxBitmap") == 0) {
239
0
        return param_write_size_t(plist, "MaxBitmap", &(dev->space_params.MaxBitmap));
240
0
    }
241
30.8k
    if (strcmp(Param, "BandBufferSpace") == 0) {
242
0
        return param_write_size_t(plist, "BandBufferSpace", &dev->space_params.band.BandBufferSpace);
243
0
    }
244
30.8k
    if (strcmp(Param, "BandHeight") == 0) {
245
0
        return param_write_int(plist, "BandHeight", &dev->space_params.band.BandHeight);
246
0
    }
247
30.8k
    if (strcmp(Param, "BandWidth") == 0) {
248
0
        return param_write_int(plist, "BandWidth", &dev->space_params.band.BandWidth);
249
0
    }
250
30.8k
    if (strcmp(Param, "BufferSpace") == 0) {
251
0
        return param_write_size_t(plist, "BufferSpace", &dev->space_params.BufferSpace);
252
0
    }
253
30.8k
    if (strcmp(Param, "InterpolateControl") == 0) {
254
0
        int interpolate_control = dev->interpolate_control;
255
0
        return param_write_int(plist, "InterpolateControl", &interpolate_control);
256
0
    }
257
30.8k
    if (strcmp(Param, "LeadingEdge") == 0) {
258
0
        if (dev->LeadingEdge & LEADINGEDGE_SET_MASK) {
259
0
            int leadingedge = dev->LeadingEdge & LEADINGEDGE_MASK;
260
0
            return param_write_int(plist, "LeadingEdge", &leadingedge);
261
0
        } else
262
0
            return param_write_null(plist, "LeadingEdge");
263
0
    }
264
265
30.8k
    if (dev->color_info.num_components > 1) {
266
30.8k
        int RGBValues = dev->color_info.max_color + 1;
267
30.8k
        long ColorValues = (depth >= 32 ? -1 : 1L << depth); /* value can only be 32 bits */
268
269
30.8k
        if (strcmp(Param, "RedValues") == 0) {
270
0
            return param_write_int(plist, "RedValues", &RGBValues);
271
0
        }
272
30.8k
        if (strcmp(Param, "GreenValues") == 0) {
273
0
            return param_write_int(plist, "GreenValues", &RGBValues);
274
0
        }
275
30.8k
        if (strcmp(Param, "BlueValues") == 0) {
276
0
            return param_write_int(plist, "BlueValues", &RGBValues);
277
0
        }
278
30.8k
        if (strcmp(Param, "ColorValues") == 0) {
279
0
            return param_write_long(plist, "ColorValues", &ColorValues);
280
0
        }
281
30.8k
    }
282
30.8k
    if (strcmp(Param, "HWColorMap") == 0) {
283
0
        byte palette[3 << 8];
284
285
0
        if (param_HWColorMap(dev, palette)) {
286
0
            gs_param_string hwcms;
287
288
0
            hwcms.data = palette, hwcms.size = colors << depth,
289
0
                hwcms.persistent = false;
290
0
            return param_write_string(plist, "HWColorMap", &hwcms);
291
0
        }
292
0
    }
293
294
    /* ICC profiles */
295
    /* Check if the device profile is null.  If it is, then we need to
296
       go ahead and get it set up at this time.  If the proc is not
297
       set up yet then we are not going to do anything yet */
298
    /* Although device methods should not be NULL, they are not completely filled in until
299
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
300
     * happens, so we *must* make sure the method is not NULL before we use it.
301
     */
302
30.8k
    if (dev_proc(dev, get_profile) != NULL) {
303
30.8k
        int code;
304
30.8k
        code = dev_proc(dev, get_profile)(dev,  &dev_profile);
305
30.8k
        if (code < 0)
306
0
            return code;
307
30.8k
        if (dev_profile == NULL) {
308
0
            code = gsicc_init_device_profile_struct(dev, NULL, 0);
309
0
            if (code < 0)
310
0
                return code;
311
0
            code = dev_proc(dev, get_profile)(dev,  &dev_profile);
312
0
            if (code < 0)
313
0
                return code;
314
0
        }
315
154k
        for (k = 0; k < NUM_DEVICE_PROFILES; k++) {
316
123k
            if (dev_profile->device_profile[k] == NULL
317
123k
                || dev_profile->device_profile[k]->name == NULL) {
318
92.4k
                param_string_from_string(profile_array[k], null_str);
319
92.4k
                profile_intents[k] = gsRINOTSPECIFIED;
320
92.4k
                blackptcomps[k] = gsBPNOTSPECIFIED;
321
92.4k
                blackpreserve[k] = gsBKPRESNOTSPECIFIED;
322
92.4k
            } else {
323
30.8k
                param_string_from_transient_string(profile_array[k],
324
30.8k
                    dev_profile->device_profile[k]->name);
325
30.8k
                profile_intents[k] = dev_profile->rendercond[k].rendering_intent;
326
30.8k
                blackptcomps[k] = dev_profile->rendercond[k].black_point_comp;
327
30.8k
                blackpreserve[k] = dev_profile->rendercond[k].preserve_black;
328
30.8k
            }
329
123k
        }
330
30.8k
        if (dev_profile->blend_profile == NULL) {
331
30.8k
            param_string_from_string(blend_profile, null_str);
332
30.8k
        } else {
333
0
            param_string_from_transient_string(blend_profile,
334
0
                dev_profile->blend_profile->name);
335
0
        }
336
30.8k
        if (dev_profile->postren_profile == NULL) {
337
30.8k
            param_string_from_string(postren_profile, null_str);
338
30.8k
        } else {
339
0
            param_string_from_transient_string(postren_profile,
340
0
                dev_profile->postren_profile->name);
341
0
        }
342
30.8k
        if (dev_profile->proof_profile == NULL) {
343
30.8k
            param_string_from_string(proof_profile, null_str);
344
30.8k
        } else {
345
0
            param_string_from_transient_string(proof_profile,
346
0
                                     dev_profile->proof_profile->name);
347
0
        }
348
30.8k
        if (dev_profile->link_profile == NULL) {
349
30.8k
            param_string_from_string(link_profile, null_str);
350
30.8k
        } else {
351
0
            param_string_from_transient_string(link_profile,
352
0
                                     dev_profile->link_profile->name);
353
0
        }
354
30.8k
        devicegraytok = dev_profile->devicegraytok;
355
30.8k
        graydetection = dev_profile->graydetection;
356
30.8k
        usefastcolor = dev_profile->usefastcolor;
357
30.8k
        blacktext = dev_profile->blacktext;
358
30.8k
        blackvector = dev_profile->blackvector;
359
30.8k
        overprint_control = dev_profile->overprint_control;
360
30.8k
        prebandthreshold = dev_profile->prebandthreshold;
361
        /* With respect to Output profiles that have non-standard colorants,
362
           we rely upon the default profile to give us the colorants if they do
363
           exist. */
364
30.8k
        if (dev_profile->spotnames == NULL) {
365
30.8k
            param_string_from_string(icc_colorants, null_str);
366
30.8k
        } else {
367
0
            char *colorant_names;
368
369
0
            colorant_names =
370
0
                gsicc_get_dev_icccolorants(dev_profile);
371
0
            if (colorant_names != NULL) {
372
0
                param_string_from_transient_string(icc_colorants, colorant_names);
373
0
            } else {
374
0
                param_string_from_string(icc_colorants, null_str);
375
0
            }
376
0
        }
377
30.8k
    } else {
378
0
        for (k = 0; k < NUM_DEVICE_PROFILES; k++) {
379
0
            param_string_from_string(profile_array[k], null_str);
380
0
            profile_intents[k] = gsRINOTSPECIFIED;
381
0
            blackptcomps[k] = gsBPNOTSPECIFIED;
382
0
            blackpreserve[k] = gsBKPRESNOTSPECIFIED;
383
0
        }
384
0
        param_string_from_string(blend_profile, null_str);
385
0
        param_string_from_string(postren_profile, null_str);
386
0
        param_string_from_string(proof_profile, null_str);
387
0
        param_string_from_string(link_profile, null_str);
388
0
        param_string_from_string(icc_colorants, null_str);
389
0
    }
390
30.8k
    if (strcmp(Param, "DeviceGrayToK") == 0) {
391
0
        return param_write_bool(plist, "DeviceGrayToK", &devicegraytok);
392
0
    }
393
30.8k
    if (strcmp(Param, "GrayDetection") == 0) {
394
0
        return param_write_bool(plist, "GrayDetection", &graydetection);
395
0
    }
396
30.8k
    if (strcmp(Param, "UseFastColor") == 0) {
397
0
        return param_write_bool(plist, "UseFastColor", &usefastcolor);
398
0
    }
399
30.8k
    if (strcmp(Param, "BlackText") == 0) {
400
0
        return param_write_bool(plist, "BlackText", &blacktext);
401
0
    }
402
30.8k
    if (strcmp(Param, "BlackVector") == 0) {
403
0
        return param_write_bool(plist, "BlackVector", &blackvector);
404
0
    }
405
30.8k
    if (strcmp(Param, "Overprint") == 0) {
406
0
        gs_param_string opc_name;
407
0
        const char *s = overprint_control_names[(int)overprint_control];
408
409
0
        param_string_from_string(opc_name, s);
410
0
        return param_write_name(plist, "Overprint", &opc_name);
411
0
    }
412
30.8k
    if (strcmp(Param, "PreBandThreshold") == 0) {
413
0
        return param_write_bool(plist, "PreBandThreshold", &prebandthreshold);
414
0
    }
415
30.8k
    if (strcmp(Param, "PostRenderProfile") == 0) {
416
0
        return param_write_string(plist, "PostRenderProfile", &(postren_profile));
417
0
    }
418
30.8k
    if (strcmp(Param, "BlendColorProfile") == 0) {
419
0
        return param_write_string(plist, "BlendColorProfile", &(blend_profile));
420
0
    }
421
30.8k
    if (strcmp(Param, "ProofProfile") == 0) {
422
0
        return param_write_string(plist,"ProofProfile", &(proof_profile));
423
0
    }
424
30.8k
    if (strcmp(Param, "DeviceLinkProfile") == 0) {
425
0
        return param_write_string(plist,"DeviceLinkProfile", &(link_profile));
426
0
    }
427
30.8k
    if (strcmp(Param, "ICCOutputColors") == 0) {
428
0
        return param_write_string(plist,"ICCOutputColors", &(icc_colorants));
429
0
    }
430
30.8k
    if (strcmp(Param, "OutputICCProfile") == 0) {
431
0
        return param_write_string(plist,"OutputICCProfile", &(profile_array[0]));
432
0
    }
433
30.8k
    if (strcmp(Param, "VectorICCProfile") == 0) {
434
0
        return param_write_string(plist,"VectorICCProfile", &(profile_array[1]));
435
0
    }
436
30.8k
    if (strcmp(Param, "ImageICCProfile") == 0) {
437
0
        return param_write_string(plist,"ImageICCProfile", &(profile_array[2]));
438
0
    }
439
30.8k
    if (strcmp(Param, "TextICCProfile") == 0) {
440
0
        return param_write_string(plist,"TextICCProfile", &(profile_array[3]));
441
0
    }
442
30.8k
    if (strcmp(Param, "ColorAccuracy") == 0) {
443
0
        return param_write_int(plist, "ColorAccuracy", (const int *)(&(color_accuracy)));
444
0
    }
445
30.8k
    if (strcmp(Param, "RenderIntent") == 0) {
446
0
        return param_write_int(plist,"RenderIntent", (const int *) (&(profile_intents[0])));
447
0
    }
448
30.8k
    if (strcmp(Param, "VectorIntent") == 0) {
449
0
        return param_write_int(plist,"VectorIntent", (const int *) &(profile_intents[1]));
450
0
    }
451
30.8k
    if (strcmp(Param, "ImageIntent") == 0) {
452
0
        return param_write_int(plist,"ImageIntent", (const int *) &(profile_intents[2]));
453
0
    }
454
30.8k
    if (strcmp(Param, "TextIntent") == 0) {
455
0
        return param_write_int(plist,"TextIntent", (const int *) &(profile_intents[3]));
456
0
    }
457
30.8k
    if (strcmp(Param, "BlackPtComp") == 0) {
458
0
        return param_write_int(plist,"BlackPtComp", (const int *) (&(blackptcomps[0])));
459
0
    }
460
30.8k
    if (strcmp(Param, "VectorBlackPt") == 0) {
461
0
        return param_write_int(plist,"VectorBlackPt", (const int *) &(blackptcomps[1]));
462
0
    }
463
30.8k
    if (strcmp(Param, "ImageBlackPt") == 0) {
464
0
        return param_write_int(plist,"ImageBlackPt", (const int *) &(blackptcomps[2]));
465
0
    }
466
30.8k
    if (strcmp(Param, "TextBlackPt") == 0) {
467
0
        return param_write_int(plist,"TextBlackPt", (const int *) &(blackptcomps[3]));
468
0
    }
469
30.8k
    if (strcmp(Param, "KPreserve") == 0) {
470
0
        return param_write_int(plist,"KPreserve", (const int *) (&(blackpreserve[0])));
471
0
    }
472
30.8k
    if (strcmp(Param, "VectorKPreserve") == 0) {
473
0
        return param_write_int(plist,"VectorKPreserve", (const int *) &(blackpreserve[1]));
474
0
    }
475
30.8k
    if (strcmp(Param, "ImageKPreserve") == 0) {
476
0
        return param_write_int(plist,"ImageKPreserve", (const int *) &(blackpreserve[2]));
477
0
    }
478
30.8k
    if (strcmp(Param, "TextKPreserve") == 0) {
479
0
        return param_write_int(plist,"TextKPreserve", (const int *) &(blackpreserve[3]));
480
0
    }
481
30.8k
    if (strcmp(Param, "FirstPage") == 0) {
482
0
        return param_write_int(plist, "FirstPage", &dev->FirstPage);
483
0
    }
484
30.8k
    if (strcmp(Param, "LastPage") == 0) {
485
0
        return param_write_int(plist, "LastPage", &dev->LastPage);
486
0
    }
487
30.8k
    if (strcmp(Param, "DisablePageHandler") == 0) {
488
0
        temp_bool = dev->DisablePageHandler;
489
0
        return param_write_bool(plist, "DisablePageHandler", &temp_bool);
490
0
    }
491
30.8k
    if (strcmp(Param, "NupControl") == 0){
492
0
        gs_param_string nupcontrol;
493
494
0
        if (dev->NupControl) {
495
0
            gdev_nupcontrol *p = (gdev_nupcontrol *)dev->NupControl;
496
0
            param_string_from_string(nupcontrol, p->nupcontrol_str);
497
0
        }
498
0
        else
499
0
            param_string_from_string(nupcontrol, null_str);
500
0
        return param_write_string(plist, "NupControl", &nupcontrol);
501
0
    }
502
30.8k
    if (strcmp(Param, "PageList") == 0){
503
0
        gs_param_string pagelist;
504
0
        if (dev->PageList) {
505
0
            gdev_pagelist *p = (gdev_pagelist *)dev->PageList;
506
0
            param_string_from_string(pagelist, p->Pages);
507
0
        }
508
0
        else
509
0
            param_string_from_string(pagelist, null_str);
510
0
        return param_write_string(plist, "PageList", &pagelist);
511
0
    }
512
30.8k
    if (strcmp(Param, "FILTERIMAGE") == 0) {
513
0
        temp_bool = dev->ObjectFilter & FILTERIMAGE;
514
0
        return param_write_bool(plist, "FILTERIMAGE", &temp_bool);
515
0
    }
516
30.8k
    if (strcmp(Param, "FILTERTEXT") == 0) {
517
0
        temp_bool = dev->ObjectFilter & FILTERTEXT;
518
0
        return param_write_bool(plist, "FILTERTEXT", &temp_bool);
519
0
    }
520
30.8k
    if (strcmp(Param, "FILTERVECTOR") == 0) {
521
0
        temp_bool = dev->ObjectFilter & FILTERVECTOR;
522
0
        return param_write_bool(plist, "FILTERVECTOR", &temp_bool);
523
0
    }
524
525
30.8k
    return_error(gs_error_undefined);
526
30.8k
}
527
528
/* Get standard parameters. */
529
int
530
gx_default_get_params(gx_device * dev, gs_param_list * plist)
531
13.8k
{
532
13.8k
    int code;
533
534
    /* Standard page device parameters: */
535
536
13.8k
    bool seprs = false;
537
13.8k
    gs_param_string dns, pcms, profile_array[NUM_DEVICE_PROFILES];
538
13.8k
    gs_param_string blend_profile, postren_profile, pagelist, nuplist;
539
13.8k
    gs_param_string proof_profile, link_profile, icc_colorants;
540
13.8k
    gsicc_rendering_intents_t profile_intents[NUM_DEVICE_PROFILES];
541
13.8k
    gsicc_blackptcomp_t blackptcomps[NUM_DEVICE_PROFILES];
542
13.8k
    gsicc_blackpreserve_t blackpreserve[NUM_DEVICE_PROFILES];
543
13.8k
    bool devicegraytok = true;  /* Default if device profile stuct not set */
544
13.8k
    bool graydetection = false;
545
13.8k
    bool usefastcolor = false;  /* set for unmanaged color */
546
13.8k
    bool blacktext = false;
547
13.8k
    bool blackvector = false;
548
    /* By default, only overprint if the device supports it */
549
13.8k
    gs_overprint_control_t overprint_control = gs_overprint_control_enable;
550
13.8k
    bool prebandthreshold = true, temp_bool;
551
13.8k
    int k;
552
13.8k
    int color_accuracy = MAX_COLOR_ACCURACY;
553
13.8k
    gs_param_float_array msa, ibba, hwra, ma;
554
13.8k
    gs_param_string_array scna;
555
13.8k
    char null_str[1]={'\0'};
556
557
13.8k
#define set_param_array(a, d, s)\
558
96.6k
  (a.data = d, a.size = s, a.persistent = false);
559
560
    /* Non-standard parameters: */
561
13.8k
    int colors = dev->color_info.num_components;
562
13.8k
    int mns = dev->color_info.max_components;
563
13.8k
    int depth = dev->color_info.depth;
564
13.8k
    int GrayValues = dev->color_info.max_gray + 1;
565
13.8k
    int HWSize[2];
566
13.8k
    gs_param_int_array hwsa;
567
13.8k
    gs_param_float_array hwma;
568
13.8k
    cmm_dev_profile_t *dev_profile;
569
570
    /* Fill in page device parameters. */
571
572
13.8k
    param_string_from_string(dns, dev->dname);
573
13.8k
    {
574
13.8k
        const char *cms = get_process_color_model_name(dev);
575
576
        /* We might have an uninitialized device with */
577
        /* color_info.num_components = 0.... */
578
13.8k
        if ((cms != NULL) && (*cms != '\0'))
579
13.8k
            param_string_from_string(pcms, cms);
580
0
        else
581
0
            pcms.data = 0;
582
13.8k
    }
583
584
13.8k
    set_param_array(hwra, dev->HWResolution, 2);
585
13.8k
    set_param_array(msa, dev->MediaSize, 2);
586
13.8k
    set_param_array(ibba, dev->ImagingBBox, 4);
587
13.8k
    set_param_array(ma, dev->Margins, 2);
588
13.8k
    set_param_array(scna, NULL, 0);
589
590
    /* Fill in non-standard parameters. */
591
13.8k
    HWSize[0] = dev->width;
592
13.8k
    HWSize[1] = dev->height;
593
13.8k
    set_param_array(hwsa, HWSize, 2);
594
13.8k
    set_param_array(hwma, dev->HWMargins, 4);
595
    /* Check if the device profile is null.  If it is, then we need to
596
       go ahead and get it set up at this time.  If the proc is not
597
       set up yet then we are not going to do anything yet */
598
    /* Although device methods should not be NULL, they are not completely filled in until
599
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
600
     * happens, so we *must* make sure the method is not NULL before we use it.
601
     */
602
13.8k
    if (dev_proc(dev, get_profile) != NULL) {
603
12.4k
        code = dev_proc(dev, get_profile)(dev,  &dev_profile);
604
12.4k
        if (code < 0)
605
0
            return code;
606
607
12.4k
        if (dev_profile == NULL) {
608
0
            code = gsicc_init_device_profile_struct(dev, NULL, 0);
609
0
            if (code < 0)
610
0
                return code;
611
0
            code = dev_proc(dev, get_profile)(dev,  &dev_profile);
612
0
            if (code < 0)
613
0
                return code;
614
0
        }
615
        /* It is possible that the current device profile name is NULL if we
616
           have a pdf14 device in line with a transparency group that is in a
617
           color space specified from a source defined ICC profile. Check for
618
           that here to avoid any access violations.  Bug 692558 */
619
62.1k
        for (k = 0; k < NUM_DEVICE_PROFILES; k++) {
620
49.7k
            if (dev_profile->device_profile[k] == NULL
621
49.7k
                || dev_profile->device_profile[k]->name == NULL) {
622
37.3k
                param_string_from_string(profile_array[k], null_str);
623
37.3k
                profile_intents[k] = gsRINOTSPECIFIED;
624
37.3k
                blackptcomps[k] = gsBPNOTSPECIFIED;
625
37.3k
                blackpreserve[k] = gsBKPRESNOTSPECIFIED;
626
37.3k
            } else {
627
12.4k
                param_string_from_transient_string(profile_array[k],
628
12.4k
                    dev_profile->device_profile[k]->name);
629
12.4k
                profile_intents[k] = dev_profile->rendercond[k].rendering_intent;
630
12.4k
                blackptcomps[k] = dev_profile->rendercond[k].black_point_comp;
631
12.4k
                blackpreserve[k] = dev_profile->rendercond[k].preserve_black;
632
12.4k
            }
633
49.7k
        }
634
        /* The proof, link and post render profile */
635
12.4k
        if (dev_profile->proof_profile == NULL) {
636
12.4k
            param_string_from_string(proof_profile, null_str);
637
12.4k
        } else {
638
0
            param_string_from_transient_string(proof_profile,
639
0
                                     dev_profile->proof_profile->name);
640
0
        }
641
12.4k
        if (dev_profile->link_profile == NULL) {
642
12.4k
            param_string_from_string(link_profile, null_str);
643
12.4k
        } else {
644
0
            param_string_from_transient_string(link_profile,
645
0
                                     dev_profile->link_profile->name);
646
0
        }
647
12.4k
        if (dev_profile->postren_profile == NULL) {
648
12.4k
            param_string_from_string(postren_profile, null_str);
649
12.4k
        } else {
650
0
            param_string_from_transient_string(postren_profile,
651
0
                dev_profile->postren_profile->name);
652
0
        }
653
12.4k
        if (dev_profile->blend_profile == NULL) {
654
12.4k
            param_string_from_string(blend_profile, null_str);
655
12.4k
        } else {
656
0
            param_string_from_transient_string(blend_profile,
657
0
                dev_profile->blend_profile->name);
658
0
        }
659
12.4k
        devicegraytok = dev_profile->devicegraytok;
660
12.4k
        graydetection = dev_profile->graydetection;
661
12.4k
        usefastcolor = dev_profile->usefastcolor;
662
12.4k
        blacktext = dev_profile->blacktext;
663
12.4k
        blackvector = dev_profile->blackvector;
664
12.4k
        overprint_control = dev_profile->overprint_control;
665
12.4k
        prebandthreshold = dev_profile->prebandthreshold;
666
        /* With respect to Output profiles that have non-standard colorants,
667
           we rely upon the default profile to give us the colorants if they do
668
           exist. */
669
12.4k
        if (dev_profile->spotnames == NULL) {
670
12.4k
            param_string_from_string(icc_colorants, null_str);
671
12.4k
        } else {
672
0
            char *colorant_names;
673
674
0
            colorant_names =
675
0
                gsicc_get_dev_icccolorants(dev_profile);
676
0
            if (colorant_names != NULL) {
677
0
                param_string_from_transient_string(icc_colorants, colorant_names);
678
0
            } else {
679
0
                param_string_from_string(icc_colorants, null_str);
680
0
            }
681
0
        }
682
12.4k
    } else {
683
6.83k
        for (k = 0; k < NUM_DEVICE_PROFILES; k++) {
684
5.46k
            param_string_from_string(profile_array[k], null_str);
685
5.46k
            profile_intents[k] = gsRINOTSPECIFIED;
686
5.46k
            blackptcomps[k] = gsBPNOTSPECIFIED;
687
5.46k
            blackpreserve[k] = gsBKPRESNOTSPECIFIED;
688
5.46k
        }
689
1.36k
        param_string_from_string(proof_profile, null_str);
690
1.36k
        param_string_from_string(link_profile, null_str);
691
1.36k
        param_string_from_string(icc_colorants, null_str);
692
1.36k
        param_string_from_string(postren_profile, null_str);
693
1.36k
        param_string_from_string(blend_profile, null_str);
694
1.36k
    }
695
    /* Transmit the values. */
696
    /* Standard parameters */
697
13.8k
    if (
698
13.8k
        (code = param_write_name(plist, "OutputDevice", &dns)) < 0 ||
699
13.8k
#ifdef PAGESIZE_IS_MEDIASIZE
700
13.8k
        (code = param_write_float_array(plist, "PageSize", &msa)) < 0 ||
701
13.8k
#endif
702
13.8k
        (code = (pcms.data == 0 ? 0 :
703
13.8k
                 param_write_name(plist, "ProcessColorModel", &pcms))) < 0 ||
704
13.8k
        (code = param_write_float_array(plist, "HWResolution", &hwra)) < 0 ||
705
13.8k
        (code = (dev->ImagingBBox_set ?
706
0
                 param_write_float_array(plist, "ImagingBBox", &ibba) :
707
13.8k
                 param_write_null(plist, "ImagingBBox"))) < 0 ||
708
13.8k
        (code = param_write_float_array(plist, "Margins", &ma)) < 0 ||
709
13.8k
        (code = param_write_int(plist, "MaxSeparations", &mns)) < 0 ||
710
13.8k
        (code = (dev->NumCopies_set < 0 ||
711
13.8k
                 (*dev_proc(dev, get_page_device))(dev) == 0 ? 0:
712
13.8k
                 dev->NumCopies_set ?
713
0
                 param_write_int(plist, "NumCopies", &dev->NumCopies) :
714
13.8k
                 param_write_null(plist, "NumCopies"))) < 0 ||
715
13.8k
        (code = param_write_name_array(plist, "SeparationColorNames", &scna)) < 0 ||
716
13.8k
        (code = param_write_bool(plist, "Separations", &seprs)) < 0 ||
717
13.8k
        (code = param_write_bool(plist, "UseCIEColor", &dev->UseCIEColor)) < 0 ||
718
        /* Non-standard parameters */
719
        /* Note:  if change is made in NUM_DEVICE_PROFILES we need to name
720
           that profile here for the device parameter on the command line */
721
13.8k
        (code = param_write_bool(plist, "DeviceGrayToK", &devicegraytok)) < 0 ||
722
13.8k
        (code = param_write_bool(plist, "GrayDetection", &graydetection)) < 0 ||
723
13.8k
        (code = param_write_bool(plist, "UseFastColor", &usefastcolor)) < 0 ||
724
13.8k
        (code = param_write_bool(plist, "BlackText", &blacktext)) < 0 ||
725
13.8k
        (code = param_write_bool(plist, "BlackVector", &blackvector)) < 0 ||
726
13.8k
        (code = param_write_bool(plist, "PreBandThreshold", &prebandthreshold)) < 0 ||
727
13.8k
        (code = param_write_string(plist,"OutputICCProfile", &(profile_array[0]))) < 0 ||
728
13.8k
        (code = param_write_string(plist,"VectorICCProfile", &(profile_array[1]))) < 0 ||
729
13.8k
        (code = param_write_string(plist,"ImageICCProfile", &(profile_array[2]))) < 0 ||
730
13.8k
        (code = param_write_string(plist,"TextICCProfile", &(profile_array[3]))) < 0 ||
731
13.8k
        (code = param_write_string(plist,"ProofProfile", &(proof_profile))) < 0 ||
732
13.8k
        (code = param_write_string(plist, "PostRenderProfile", &(postren_profile))) < 0 ||
733
13.8k
        (code = param_write_string(plist, "BlendColorProfile", &(blend_profile))) < 0 ||
734
13.8k
        (code = param_write_string(plist,"DeviceLinkProfile", &(link_profile))) < 0 ||
735
13.8k
        (code = param_write_string(plist,"ICCOutputColors", &(icc_colorants))) < 0 ||
736
13.8k
        (code = param_write_int(plist, "RenderIntent", (const int *)(&(profile_intents[0])))) < 0 ||
737
13.8k
        (code = param_write_int(plist, "ColorAccuracy", (const int *)(&(color_accuracy)))) < 0 ||
738
13.8k
        (code = param_write_int(plist,"VectorIntent", (const int *) &(profile_intents[1]))) < 0 ||
739
13.8k
        (code = param_write_int(plist,"ImageIntent", (const int *) &(profile_intents[2]))) < 0 ||
740
13.8k
        (code = param_write_int(plist,"TextIntent", (const int *) &(profile_intents[3]))) < 0 ||
741
13.8k
        (code = param_write_int(plist,"BlackPtComp", (const int *) (&(blackptcomps[0])))) < 0 ||
742
13.8k
        (code = param_write_int(plist,"VectorBlackPt", (const int *) &(blackptcomps[1]))) < 0 ||
743
13.8k
        (code = param_write_int(plist,"ImageBlackPt", (const int *) &(blackptcomps[2]))) < 0 ||
744
13.8k
        (code = param_write_int(plist,"TextBlackPt", (const int *) &(blackptcomps[3]))) < 0 ||
745
13.8k
        (code = param_write_int(plist,"KPreserve", (const int *) (&(blackpreserve[0])))) < 0 ||
746
13.8k
        (code = param_write_int(plist,"VectorKPreserve", (const int *) &(blackpreserve[1]))) < 0 ||
747
13.8k
        (code = param_write_int(plist,"ImageKPreserve", (const int *) &(blackpreserve[2]))) < 0 ||
748
13.8k
        (code = param_write_int(plist,"TextKPreserve", (const int *) &(blackpreserve[3]))) < 0 ||
749
13.8k
        (code = param_write_int_array(plist, "HWSize", &hwsa)) < 0 ||
750
13.8k
        (code = param_write_float_array(plist, ".HWMargins", &hwma)) < 0 ||
751
13.8k
        (code = param_write_float_array(plist, ".MediaSize", &msa)) < 0 ||
752
13.8k
        (code = param_write_string(plist, "Name", &dns)) < 0 ||
753
13.8k
        (code = param_write_int(plist, "Colors", &colors)) < 0 ||
754
13.8k
        (code = param_write_int(plist, "BitsPerPixel", &depth)) < 0 ||
755
13.8k
        (code = param_write_int(plist, "GrayValues", &GrayValues)) < 0 ||
756
13.8k
        (code = param_write_long(plist, "PageCount", &dev->PageCount)) < 0 ||
757
13.8k
        (code = param_write_bool(plist, ".IgnoreNumCopies", &dev->IgnoreNumCopies)) < 0 ||
758
13.8k
        (code = param_write_int(plist, "TextAlphaBits",
759
13.8k
                                &dev->color_info.anti_alias.text_bits)) < 0 ||
760
13.8k
        (code = param_write_int(plist, "GraphicsAlphaBits",
761
13.8k
                                &dev->color_info.anti_alias.graphics_bits)) < 0 ||
762
13.8k
        (code = param_write_bool(plist, "AntidropoutDownscaler",
763
13.8k
                                &dev->color_info.use_antidropout_downscaler)) < 0 ||
764
13.8k
        (code = param_write_bool(plist, ".LockSafetyParams", &dev->LockSafetyParams)) < 0 ||
765
13.8k
        (code = param_write_size_t(plist, "MaxPatternBitmap", &dev->MaxPatternBitmap)) < 0 ||
766
13.8k
        (code = param_write_bool(plist, "PageUsesTransparency", &dev->page_uses_transparency)) < 0 ||
767
13.8k
        (code = param_write_bool(plist, "PageUsesOverprint", &dev->page_uses_overprint)) < 0 ||
768
13.8k
        (code = param_write_size_t(plist, "MaxBitmap", &(dev->space_params.MaxBitmap))) < 0 ||
769
13.8k
        (code = param_write_size_t(plist, "BandBufferSpace", &dev->space_params.band.BandBufferSpace)) < 0 ||
770
13.8k
        (code = param_write_int(plist, "BandHeight", &dev->space_params.band.BandHeight)) < 0 ||
771
13.8k
        (code = param_write_int(plist, "BandWidth", &dev->space_params.band.BandWidth)) < 0 ||
772
13.8k
        (code = param_write_size_t(plist, "BufferSpace", &dev->space_params.BufferSpace)) < 0 ||
773
13.8k
        (code = param_write_int(plist, "InterpolateControl", &dev->interpolate_control)) < 0
774
13.8k
        )
775
0
        return code;
776
13.8k
    {
777
13.8k
        gs_param_string opc_name;
778
13.8k
        const char *s = overprint_control_names[(int)overprint_control];
779
780
13.8k
        param_string_from_string(opc_name, s);
781
13.8k
        param_write_name(plist, "Overprint", &opc_name);
782
13.8k
    }
783
    /* If LeadingEdge was set explicitly, report it here. */
784
13.8k
    if (dev->LeadingEdge & LEADINGEDGE_SET_MASK) {
785
0
        int leadingedge = dev->LeadingEdge & LEADINGEDGE_MASK;
786
0
        code = param_write_int(plist, "LeadingEdge", &leadingedge);
787
0
    } else
788
13.8k
        code = param_write_null(plist, "LeadingEdge");
789
13.8k
    if (code < 0)
790
0
        return code;
791
792
13.8k
    if ((code = param_write_int(plist, "FirstPage", &dev->FirstPage)) < 0)
793
0
        return code;
794
13.8k
    if ((code = param_write_int(plist, "LastPage", &dev->LastPage)) < 0)
795
0
        return code;
796
797
13.8k
    temp_bool = dev->DisablePageHandler;
798
13.8k
    if ((code = param_write_bool(plist, "DisablePageHandler", &temp_bool)) < 0)
799
0
        return code;
800
801
13.8k
    if (dev->NupControl) {
802
0
        gdev_nupcontrol *p = (gdev_nupcontrol *)dev->NupControl;
803
0
        param_string_from_string(nuplist, p->nupcontrol_str);
804
13.8k
    } else {
805
13.8k
        param_string_from_string(nuplist, null_str);
806
13.8k
    }
807
13.8k
    if ((code = param_write_string(plist, "NupControl", &nuplist)) < 0)
808
0
        return code;
809
810
13.8k
    if (dev->PageList) {
811
0
        gdev_pagelist *p = (gdev_pagelist *)dev->PageList;
812
0
        param_string_from_transient_string(pagelist, p->Pages);
813
13.8k
    } else {
814
13.8k
        param_string_from_string(pagelist, null_str);
815
13.8k
    }
816
13.8k
    if ((code = param_write_string(plist, "PageList", &pagelist)) < 0)
817
0
        return code;
818
819
13.8k
    temp_bool = dev->ObjectFilter & FILTERIMAGE;
820
13.8k
    if ((code = param_write_bool(plist, "FILTERIMAGE", &temp_bool)) < 0)
821
0
        return code;
822
13.8k
    temp_bool = dev->ObjectFilter & FILTERTEXT;
823
13.8k
    if ((code = param_write_bool(plist, "FILTERTEXT", &temp_bool)) < 0)
824
0
        return code;
825
13.8k
    temp_bool = dev->ObjectFilter & FILTERVECTOR;
826
13.8k
    if ((code = param_write_bool(plist, "FILTERVECTOR", &temp_bool)) < 0)
827
0
        return code;
828
829
    /* Fill in color information. */
830
831
13.8k
    if (colors > 1) {
832
12.4k
        int RGBValues = dev->color_info.max_color + 1;
833
12.4k
        long ColorValues = (depth >= 32 ? -1 : 1L << depth); /* value can only be 32 bits */
834
835
12.4k
        if ((code = param_write_int(plist, "RedValues", &RGBValues)) < 0 ||
836
12.4k
            (code = param_write_int(plist, "GreenValues", &RGBValues)) < 0 ||
837
12.4k
            (code = param_write_int(plist, "BlueValues", &RGBValues)) < 0 ||
838
12.4k
            (code = param_write_long(plist, "ColorValues", &ColorValues)) < 0
839
12.4k
            )
840
0
            return code;
841
12.4k
    }
842
13.8k
    if (param_requested(plist, "HWColorMap")) {
843
1.36k
        byte palette[3 << 8];
844
845
1.36k
        if (param_HWColorMap(dev, palette)) {
846
1.36k
            gs_param_string hwcms;
847
848
1.36k
            hwcms.data = palette, hwcms.size = colors << depth,
849
1.36k
                hwcms.persistent = false;
850
1.36k
            if ((code = param_write_string(plist, "HWColorMap", &hwcms)) < 0)
851
0
                return code;
852
1.36k
        }
853
1.36k
    }
854
855
13.8k
    return 0;
856
13.8k
}
857
858
/* Get the color map for a device.  Return true if there is one. */
859
static bool
860
param_HWColorMap(gx_device * dev, byte * palette /* 3 << 8 */ )
861
1.36k
{
862
1.36k
    int depth = dev->color_info.depth;
863
1.36k
    int colors = dev->color_info.num_components;
864
865
1.36k
    if (depth <= 8 && colors <= 3) {
866
1.36k
        byte *p = palette;
867
1.36k
        gx_color_value rgb[3];
868
1.36k
        gx_color_index i;
869
870
1.36k
        fill_dev_proc(dev, map_color_rgb, gx_default_map_color_rgb);
871
13.6k
        for (i = 0; (i >> depth) == 0; i++) {
872
12.2k
            int j;
873
874
12.2k
            if ((*dev_proc(dev, map_color_rgb)) (dev, i, rgb) < 0)
875
0
                return false;
876
46.4k
            for (j = 0; j < colors; j++)
877
34.1k
                *p++ = gx_color_value_to_byte(rgb[j]);
878
12.2k
        }
879
1.36k
        return true;
880
1.36k
    }
881
0
    return false;
882
1.36k
}
883
884
/* Get hardware-detected parameters. Default action is no hardware params. */
885
int
886
gx_default_get_hardware_params(gx_device * dev, gs_param_list * plist)
887
0
{
888
0
    return 0;
889
0
}
890
891
/* ---------------- Input and output media ---------------- */
892
893
/* Finish defining input or output media. */
894
static int
895
finish_media(gs_param_list * mlist, gs_param_name key, const char *media_type)
896
0
{
897
0
    int code = 0;
898
899
0
    if (media_type != 0) {
900
0
        gs_param_string as;
901
902
0
        param_string_from_string(as, media_type);
903
0
        code = param_write_string(mlist, key, &as);
904
0
    }
905
0
    return code;
906
0
}
907
908
/* Define input media. */
909
910
const gdev_input_media_t gdev_input_media_default =
911
{
912
    gdev_input_media_default_values
913
};
914
915
int
916
gdev_begin_input_media(gs_param_list * mlist, gs_param_dict * pdict,
917
                       int count)
918
0
{
919
0
    pdict->size = count;
920
0
    return param_begin_write_dict(mlist, "InputAttributes", pdict, true);
921
0
}
922
923
int
924
gdev_write_input_media(int index, gs_param_dict * pdict,
925
                       const gdev_input_media_t * pim)
926
0
{
927
0
    char key[25];
928
0
    gs_param_dict mdict;
929
0
    int code;
930
0
    gs_param_string as;
931
932
0
    gs_snprintf(key, sizeof(key), "%d", index);
933
0
    mdict.size = 4;
934
0
    code = param_begin_write_dict(pdict->list, key, &mdict, false);
935
0
    if (code < 0)
936
0
        return code;
937
0
    if ((pim->PageSize[0] != 0 && pim->PageSize[1] != 0) ||
938
0
        (pim->PageSize[2] != 0 && pim->PageSize[3] != 0)
939
0
        ) {
940
0
        gs_param_float_array psa;
941
942
0
        psa.data = pim->PageSize;
943
0
        psa.size =
944
0
            (pim->PageSize[0] == pim->PageSize[2] &&
945
0
             pim->PageSize[1] == pim->PageSize[3] ? 2 : 4);
946
0
        psa.persistent = false;
947
0
        code = param_write_float_array(mdict.list, "PageSize",
948
0
                                       &psa);
949
0
        if (code < 0)
950
0
            return code;
951
0
    }
952
0
    if (pim->MediaColor != 0) {
953
0
        param_string_from_string(as, pim->MediaColor);
954
0
        code = param_write_string(mdict.list, "MediaColor",
955
0
                                  &as);
956
0
        if (code < 0)
957
0
            return code;
958
0
    }
959
0
    if (pim->MediaWeight != 0) {
960
        /*
961
         * We do the following silly thing in order to avoid
962
         * having to work around the 'const' in the arg list.
963
         */
964
0
        float weight = pim->MediaWeight;
965
966
0
        code = param_write_float(mdict.list, "MediaWeight",
967
0
                                 &weight);
968
0
        if (code < 0)
969
0
            return code;
970
0
    }
971
0
    code = finish_media(mdict.list, "MediaType", pim->MediaType);
972
0
    if (code < 0)
973
0
        return code;
974
0
    return param_end_write_dict(pdict->list, key, &mdict);
975
0
}
976
977
int
978
gdev_write_input_page_size(int index, gs_param_dict * pdict,
979
                           double width_points, double height_points)
980
0
{
981
0
    gdev_input_media_t media;
982
983
0
    media.PageSize[0] = media.PageSize[2] = (float) width_points;
984
0
    media.PageSize[1] = media.PageSize[3] = (float) height_points;
985
0
    media.MediaColor = 0;
986
0
    media.MediaWeight = 0;
987
0
    media.MediaType = 0;
988
0
    return gdev_write_input_media(index, pdict, &media);
989
0
}
990
991
int
992
gdev_end_input_media(gs_param_list * mlist, gs_param_dict * pdict)
993
0
{
994
0
    return param_end_write_dict(mlist, "InputAttributes", pdict);
995
0
}
996
997
/* Define output media. */
998
999
const gdev_output_media_t gdev_output_media_default =
1000
{
1001
    gdev_output_media_default_values
1002
};
1003
1004
int
1005
gdev_begin_output_media(gs_param_list * mlist, gs_param_dict * pdict,
1006
                        int count)
1007
0
{
1008
0
    pdict->size = count;
1009
0
    return param_begin_write_dict(mlist, "OutputAttributes", pdict, true);
1010
0
}
1011
1012
int
1013
gdev_write_output_media(int index, gs_param_dict * pdict,
1014
                        const gdev_output_media_t * pom)
1015
0
{
1016
0
    char key[25];
1017
0
    gs_param_dict mdict;
1018
0
    int code;
1019
1020
0
    gs_snprintf(key, sizeof(key), "%d", index);
1021
0
    mdict.size = 4;
1022
0
    code = param_begin_write_dict(pdict->list, key, &mdict, false);
1023
0
    if (code < 0)
1024
0
        return code;
1025
0
    code = finish_media(mdict.list, "OutputType", pom->OutputType);
1026
0
    if (code < 0)
1027
0
        return code;
1028
0
    return param_end_write_dict(pdict->list, key, &mdict);
1029
0
}
1030
1031
int
1032
gdev_end_output_media(gs_param_list * mlist, gs_param_dict * pdict)
1033
0
{
1034
0
    return param_end_write_dict(mlist, "OutputAttributes", pdict);
1035
0
}
1036
1037
/* ================ Putting parameters ================ */
1038
1039
/* Forward references */
1040
static int param_normalize_anti_alias_bits( uint max_gray, int bits );
1041
static int param_anti_alias_bits(gs_param_list *, gs_param_name, int *);
1042
static int param_MediaSize(gs_param_list *, gs_param_name,
1043
                            const float *, gs_param_float_array *);
1044
1045
static int param_check_bool(gs_param_list *, gs_param_name, bool, bool);
1046
static int param_check_long(gs_param_list *, gs_param_name, long, bool);
1047
#define param_check_int(plist, pname, ival, is_defined)\
1048
37.9k
  param_check_long(plist, pname, (long)(ival), is_defined)
1049
static int param_check_bytes(gs_param_list *, gs_param_name, const byte *,
1050
                              uint, bool);
1051
#define param_check_string(plist, pname, str, is_defined)\
1052
18.9k
  param_check_bytes(plist, pname, (const byte *)(str), \
1053
18.9k
                    (is_defined) ? strlen(str) : 0, is_defined)
1054
1055
/* Set the device parameters. */
1056
/* If the device was open and the put_params procedure closed it, */
1057
/* return 1; otherwise, return 0 or an error code as usual. */
1058
int
1059
gs_putdeviceparams(gx_device * dev, gs_param_list * plist)
1060
6.32k
{
1061
6.32k
    bool was_open = dev->is_open;
1062
6.32k
    int code;
1063
1064
    /* gs_param_list_dump(plist); */
1065
1066
6.32k
    fill_dev_proc(dev, put_params, gx_default_put_params);
1067
6.32k
    fill_dev_proc(dev, get_alpha_bits, gx_default_get_alpha_bits);
1068
6.32k
    code = (*dev_proc(dev, put_params)) (dev, plist);
1069
6.32k
    return (code < 0 ? code : was_open && !dev->is_open ? 1 : code);
1070
6.32k
}
1071
1072
static int
1073
gx_default_put_graydetection(bool graydetection, gx_device * dev)
1074
5.09k
{
1075
5.09k
    int code = 0;
1076
5.09k
    cmm_dev_profile_t *profile_struct;
1077
1078
    /* Although device methods should not be NULL, they are not completely filled in until
1079
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1080
     * happens, so we *must* make sure the method is not NULL before we use it.
1081
     */
1082
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1083
        /* This is an odd case where the device has not yet fully been
1084
           set up with its procedures yet.  We want to make sure that
1085
           we catch this so we assume here that we are dealing with
1086
           the target device.  For now allocate the profile structure
1087
           but do not intialize the profile yet as the color info
1088
           may not be fully set up at this time.  */
1089
1.36k
        if (dev->icc_struct == NULL) {
1090
            /* Allocate at this time the structure */
1091
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1092
0
        }
1093
1.36k
        dev->icc_struct->graydetection = graydetection;
1094
1.36k
        dev->icc_struct->pageneutralcolor = graydetection;
1095
3.72k
    } else {
1096
3.72k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1097
3.72k
        if (profile_struct == NULL) {
1098
            /* Create now  */
1099
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1100
0
            profile_struct =  dev->icc_struct;
1101
0
        }
1102
3.72k
        profile_struct->graydetection = graydetection;
1103
3.72k
        profile_struct->pageneutralcolor = graydetection;
1104
3.72k
    }
1105
5.09k
    return code;
1106
5.09k
}
1107
1108
static int
1109
gx_default_put_graytok(bool graytok, gx_device * dev)
1110
5.09k
{
1111
5.09k
    int code = 0;
1112
5.09k
    cmm_dev_profile_t *profile_struct;
1113
1114
    /* Although device methods should not be NULL, they are not completely filled in until
1115
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1116
     * happens, so we *must* make sure the method is not NULL before we use it.
1117
     */
1118
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1119
        /* This is an odd case where the device has not yet fully been
1120
           set up with its procedures yet.  We want to make sure that
1121
           we catch this so we assume here that we are dealing with
1122
           the target device.  For now allocate the profile structure
1123
           but do not intialize the profile yet as the color info
1124
           may not be fully set up at this time.  */
1125
1.36k
        if (dev->icc_struct == NULL) {
1126
            /* Allocate at this time the structure */
1127
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1128
0
            if (dev->icc_struct == NULL)
1129
0
                return_error(gs_error_VMerror);
1130
0
        }
1131
1.36k
        dev->icc_struct->devicegraytok = graytok;
1132
3.72k
    } else {
1133
3.72k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1134
3.72k
        if (profile_struct == NULL) {
1135
            /* Create now  */
1136
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1137
0
            profile_struct =  dev->icc_struct;
1138
0
            if (profile_struct == NULL)
1139
0
                return_error(gs_error_VMerror);
1140
0
        }
1141
3.72k
        profile_struct->devicegraytok = graytok;
1142
3.72k
    }
1143
5.09k
    return code;
1144
5.09k
}
1145
1146
static int
1147
gx_default_put_prebandthreshold(bool prebandthreshold, gx_device * dev)
1148
5.09k
{
1149
5.09k
    int code = 0;
1150
5.09k
    cmm_dev_profile_t *profile_struct;
1151
1152
    /* Although device methods should not be NULL, they are not completely filled in until
1153
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1154
     * happens, so we *must* make sure the method is not NULL before we use it.
1155
     */
1156
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1157
        /* This is an odd case where the device has not yet fully been
1158
           set up with its procedures yet.  We want to make sure that
1159
           we catch this so we assume here that we are dealing with
1160
           the target device.  For now allocate the profile structure
1161
           but do not intialize the profile yet as the color info
1162
           may not be fully set up at this time.  */
1163
1.36k
        if (dev->icc_struct == NULL) {
1164
            /* Allocate at this time the structure */
1165
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1166
0
            if (dev->icc_struct == NULL)
1167
0
                return_error(gs_error_VMerror);
1168
0
        }
1169
1.36k
        dev->icc_struct->prebandthreshold = prebandthreshold;
1170
3.72k
    } else {
1171
3.72k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1172
3.72k
        if (profile_struct == NULL) {
1173
            /* Create now  */
1174
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1175
0
            profile_struct =  dev->icc_struct;
1176
0
            if (profile_struct == NULL)
1177
0
                return_error(gs_error_VMerror);
1178
0
        }
1179
3.72k
        profile_struct->prebandthreshold = prebandthreshold;
1180
3.72k
    }
1181
5.09k
    return code;
1182
5.09k
}
1183
1184
static int
1185
gx_default_put_usefastcolor(bool fastcolor, gx_device * dev)
1186
5.09k
{
1187
5.09k
    int code = 0;
1188
5.09k
    cmm_dev_profile_t *profile_struct;
1189
1190
    /* Although device methods should not be NULL, they are not completely filled in until
1191
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1192
     * happens, so we *must* make sure the method is not NULL before we use it.
1193
     */
1194
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1195
        /* This is an odd case where the device has not yet fully been
1196
           set up with its procedures yet.  We want to make sure that
1197
           we catch this so we assume here that we are dealing with
1198
           the target device.  For now allocate the profile structure
1199
           but do not intialize the profile yet as the color info
1200
           may not be fully set up at this time.  */
1201
1.36k
        if (dev->icc_struct == NULL) {
1202
            /* Allocate at this time the structure */
1203
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1204
0
            if (dev->icc_struct == NULL)
1205
0
                return_error(gs_error_VMerror);
1206
0
        }
1207
1.36k
        dev->icc_struct->usefastcolor = fastcolor;
1208
3.72k
    } else {
1209
3.72k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1210
3.72k
        if (profile_struct == NULL) {
1211
            /* Create now  */
1212
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1213
0
            profile_struct =  dev->icc_struct;
1214
0
            if (profile_struct == NULL)
1215
0
                return_error(gs_error_VMerror);
1216
0
        }
1217
3.72k
        profile_struct->usefastcolor = fastcolor;
1218
3.72k
    }
1219
5.09k
    return code;
1220
5.09k
}
1221
1222
static int
1223
gx_default_put_blacktext(bool blacktext, gx_device* dev)
1224
5.09k
{
1225
5.09k
    int code = 0;
1226
5.09k
    cmm_dev_profile_t* profile_struct;
1227
1228
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1229
1.36k
        if (dev->icc_struct == NULL) {
1230
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1231
0
            if (dev->icc_struct == NULL)
1232
0
                return_error(gs_error_VMerror);
1233
0
        }
1234
1.36k
        dev->icc_struct->blacktext = blacktext;
1235
3.72k
    } else {
1236
3.72k
        code = dev_proc(dev, get_profile)(dev, &profile_struct);
1237
3.72k
        if (profile_struct == NULL) {
1238
            /* Create now  */
1239
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1240
0
            profile_struct = dev->icc_struct;
1241
0
            if (profile_struct == NULL)
1242
0
                return_error(gs_error_VMerror);
1243
0
        }
1244
3.72k
        profile_struct->blacktext = blacktext;
1245
3.72k
    }
1246
5.09k
    return code;
1247
5.09k
}
1248
1249
static int
1250
gx_default_put_blackvector(bool blackvector, gx_device* dev)
1251
5.09k
{
1252
5.09k
    int code = 0;
1253
5.09k
    cmm_dev_profile_t* profile_struct;
1254
1255
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1256
1.36k
        if (dev->icc_struct == NULL) {
1257
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1258
0
            if (dev->icc_struct == NULL)
1259
0
                return_error(gs_error_VMerror);
1260
0
        }
1261
1.36k
        dev->icc_struct->blackvector = blackvector;
1262
3.72k
    } else {
1263
3.72k
        code = dev_proc(dev, get_profile)(dev, &profile_struct);
1264
3.72k
        if (profile_struct == NULL) {
1265
            /* Create now  */
1266
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1267
0
            profile_struct = dev->icc_struct;
1268
0
            if (profile_struct == NULL)
1269
0
                return_error(gs_error_VMerror);
1270
0
        }
1271
3.72k
        profile_struct->blackvector = blackvector;
1272
3.72k
    }
1273
5.09k
    return code;
1274
5.09k
}
1275
1276
static int
1277
gx_default_put_overprint_control(gs_overprint_control_t overprint_control, gx_device * dev)
1278
5.09k
{
1279
5.09k
    int code = 0;
1280
5.09k
    cmm_dev_profile_t *profile_struct;
1281
1282
    /* Although device methods should not be NULL, they are not completely filled in until
1283
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1284
     * happens, so we *must* make sure the method is not NULL before we use it.
1285
     */
1286
5.09k
    if (dev_proc(dev, get_profile) == NULL) {
1287
        /* This is an odd case where the device has not yet fully been
1288
           set up with its procedures yet.  We want to make sure that
1289
           we catch this so we assume here that we are dealing with
1290
           the target device.  For now allocate the profile structure
1291
           but do not intialize the profile yet as the color info
1292
           may not be fully set up at this time.  */
1293
1.36k
        if (dev->icc_struct == NULL) {
1294
            /* Allocate at this time the structure */
1295
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1296
0
            if (dev->icc_struct == NULL)
1297
0
                return_error(gs_error_VMerror);
1298
0
        }
1299
1.36k
        dev->icc_struct->overprint_control = overprint_control;
1300
3.72k
    } else {
1301
3.72k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1302
3.72k
        if (profile_struct == NULL) {
1303
            /* Create now  */
1304
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1305
0
            profile_struct =  dev->icc_struct;
1306
0
            if (profile_struct == NULL)
1307
0
                return_error(gs_error_VMerror);
1308
0
        }
1309
3.72k
        profile_struct->overprint_control = overprint_control;
1310
3.72k
    }
1311
5.09k
    return code;
1312
5.09k
}
1313
1314
static int
1315
gx_default_put_intent(gsicc_rendering_intents_t icc_intent, gx_device * dev,
1316
                   gsicc_profile_types_t index)
1317
20.3k
{
1318
20.3k
    int code;
1319
20.3k
    cmm_dev_profile_t *profile_struct;
1320
1321
    /* Although device methods should not be NULL, they are not completely filled in until
1322
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1323
     * happens, so we *must* make sure the method is not NULL before we use it.
1324
     */
1325
20.3k
    if (dev_proc(dev, get_profile) == NULL) {
1326
        /* This is an odd case where the device has not yet fully been
1327
           set up with its procedures yet.  We want to make sure that
1328
           we catch this so we assume here that we are dealing with
1329
           the target device */
1330
5.46k
        if (dev->icc_struct == NULL) {
1331
            /* Intializes the device structure.  Not the profile though for index */
1332
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1333
0
            if (dev->icc_struct == NULL)
1334
0
                return_error(gs_error_VMerror);
1335
0
        }
1336
5.46k
        code = gsicc_set_device_profile_intent(dev, icc_intent, index);
1337
14.9k
    } else {
1338
14.9k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1339
14.9k
        if (code < 0)
1340
0
            return code;
1341
14.9k
        if (profile_struct == NULL) {
1342
            /* Create now  */
1343
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1344
0
            if (dev->icc_struct == NULL)
1345
0
                return_error(gs_error_VMerror);
1346
0
        }
1347
14.9k
        code = gsicc_set_device_profile_intent(dev, icc_intent, index);
1348
14.9k
    }
1349
20.3k
    return code;
1350
20.3k
}
1351
1352
static int
1353
gx_default_put_blackpreserve(gsicc_blackpreserve_t blackpreserve, gx_device * dev,
1354
                           gsicc_profile_types_t index)
1355
20.3k
{
1356
20.3k
    int code;
1357
20.3k
    cmm_dev_profile_t *profile_struct;
1358
1359
    /* Although device methods should not be NULL, they are not completely filled in until
1360
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1361
     * happens, so we *must* make sure the method is not NULL before we use it.
1362
     */
1363
20.3k
    if (dev_proc(dev, get_profile) == NULL) {
1364
        /* This is an odd case where the device has not yet fully been
1365
           set up with its procedures yet.  We want to make sure that
1366
           we catch this so we assume here that we are dealing with
1367
           the target device */
1368
5.46k
        if (dev->icc_struct == NULL) {
1369
            /* Intializes the device structure.  Not the profile though for index */
1370
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1371
0
            if (dev->icc_struct == NULL)
1372
0
                return_error(gs_error_VMerror);
1373
0
        }
1374
5.46k
        code = gsicc_set_device_blackpreserve(dev, blackpreserve, index);
1375
14.9k
    } else {
1376
14.9k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1377
14.9k
        if (code < 0)
1378
0
            return code;
1379
14.9k
        if (profile_struct == NULL) {
1380
            /* Create now  */
1381
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1382
0
            if (dev->icc_struct == NULL)
1383
0
                return_error(gs_error_VMerror);
1384
0
        }
1385
14.9k
        code = gsicc_set_device_blackpreserve(dev, blackpreserve, index);
1386
14.9k
    }
1387
20.3k
    return code;
1388
20.3k
}
1389
1390
1391
1392
1393
static int
1394
gx_default_put_blackptcomp(gsicc_blackptcomp_t blackptcomp, gx_device * dev,
1395
                           gsicc_profile_types_t index)
1396
20.3k
{
1397
20.3k
    int code;
1398
20.3k
    cmm_dev_profile_t *profile_struct;
1399
1400
    /* Although device methods should not be NULL, they are not completely filled in until
1401
     * gx_device_fill_in_procs is called, and its possible for us to get here before this
1402
     * happens, so we *must* make sure the method is not NULL before we use it.
1403
     */
1404
20.3k
    if (dev_proc(dev, get_profile) == NULL) {
1405
        /* This is an odd case where the device has not yet fully been
1406
           set up with its procedures yet.  We want to make sure that
1407
           we catch this so we assume here that we are dealing with
1408
           the target device */
1409
5.46k
        if (dev->icc_struct == NULL) {
1410
            /* Intializes the device structure.  Not the profile though for index */
1411
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1412
0
            if (dev->icc_struct == NULL)
1413
0
                return_error(gs_error_VMerror);
1414
0
        }
1415
5.46k
        code = gsicc_set_device_blackptcomp(dev, blackptcomp, index);
1416
14.9k
    } else {
1417
14.9k
        code = dev_proc(dev, get_profile)(dev,  &profile_struct);
1418
14.9k
        if (code < 0)
1419
0
            return code;
1420
14.9k
        if (profile_struct == NULL) {
1421
            /* Create now  */
1422
0
            dev->icc_struct = gsicc_new_device_profile_array(dev);
1423
0
            if (dev->icc_struct == NULL)
1424
0
                return_error(gs_error_VMerror);
1425
0
        }
1426
14.9k
        code = gsicc_set_device_blackptcomp(dev, blackptcomp, index);
1427
14.9k
    }
1428
20.3k
    return code;
1429
20.3k
}
1430
1431
static int
1432
gx_default_put_icc_colorants(gs_param_string *colorants, gx_device * dev)
1433
1.22k
{
1434
1.22k
    char *tempstr;
1435
1.22k
    int code;
1436
1437
1.22k
    if (colorants->size == 0) return 0;
1438
1439
    /* See below about this device fill proc */
1440
0
    fill_dev_proc(dev, get_profile, gx_default_get_profile);
1441
0
    tempstr = (char *) gs_alloc_bytes(dev->memory, colorants->size+1,
1442
0
                                      "gx_default_put_icc_colorants");
1443
0
    memcpy(tempstr, colorants->data, colorants->size);
1444
    /* Set last position to NULL. */
1445
0
    tempstr[colorants->size] = 0;
1446
0
    code = gsicc_set_device_profile_colorants(dev, tempstr);
1447
0
    gs_free_object(dev->memory, tempstr, "gx_default_put_icc_colorants");
1448
0
    return code;
1449
1.22k
}
1450
1451
static int
1452
gx_default_put_icc(gs_param_string *icc_pro, gx_device * dev,
1453
                   gsicc_profile_types_t index)
1454
9.83k
{
1455
9.83k
    char *tempstr;
1456
9.83k
    int code = 0;
1457
1458
9.83k
    if (icc_pro->size == 0) return 0;
1459
    /* If this has not yet been set, then set it to the default.
1460
       I don't like doing this here but if we are in here trying to
1461
       set a profile for our device and if the proc for this has not
1462
       yet been set, we are going to lose the chance to set the profile.
1463
       Much like open, this proc should be set early on.  I leave that
1464
       exercise to the device start-up experts */
1465
1.22k
    fill_dev_proc(dev, get_profile, gx_default_get_profile);
1466
1.22k
    if (icc_pro->size < gp_file_name_sizeof) {
1467
1.22k
        tempstr = (char *) gs_alloc_bytes(dev->memory, icc_pro->size+1,
1468
1.22k
                                          "gx_default_put_icc");
1469
1.22k
        if (tempstr == NULL)
1470
0
            return_error(gs_error_VMerror);
1471
1.22k
        memcpy(tempstr, icc_pro->data, icc_pro->size);
1472
        /* Set last position to NULL. */
1473
1.22k
        tempstr[icc_pro->size] = 0;
1474
1.22k
        code = gsicc_init_device_profile_struct(dev, tempstr, index);
1475
1.22k
        gs_free_object(dev->memory, tempstr, "gx_default_put_icc");
1476
1.22k
    }
1477
1.22k
    return code;
1478
1.22k
}
1479
1480
void rc_free_NupControl(gs_memory_t * mem, void *ptr_in, client_name_t cname);  /* silence warning */
1481
/* Exported for use by nup_put_params in gdevnup.c */
1482
void
1483
rc_free_NupControl(gs_memory_t * mem, void *ptr_in, client_name_t cname)
1484
0
{
1485
0
    gdev_nupcontrol *pnupc = (gdev_nupcontrol *)ptr_in;
1486
1487
0
    if (pnupc->rc.ref_count <= 1) {
1488
0
        gs_free(mem->non_gc_memory, pnupc->nupcontrol_str, 1, strlen(pnupc->nupcontrol_str), "free nupcontrol string");
1489
0
        gs_free(mem->non_gc_memory, pnupc, 1, sizeof(gdev_nupcontrol), "free structure to hold nupcontrol string");
1490
0
    }
1491
0
}
1492
1493
static void
1494
rc_free_pages_list(gs_memory_t * mem, void *ptr_in, client_name_t cname)
1495
0
{
1496
0
    gdev_pagelist *PageList = (gdev_pagelist *)ptr_in;
1497
1498
0
    if (PageList->rc.ref_count <= 1) {
1499
0
        gs_free(mem->non_gc_memory, PageList->Pages, 1, PagesSize, "free page list");
1500
0
        gs_free(mem->non_gc_memory, PageList, 1, sizeof(gdev_pagelist), "free structure to hold page list");
1501
0
    }
1502
0
}
1503
1504
/* Set standard parameters. */
1505
/* Note that setting the size or resolution closes the device. */
1506
/* Window devices that don't want this to happen must temporarily */
1507
/* set is_open to false before calling gx_default_put_params, */
1508
/* and then taking appropriate action afterwards. */
1509
int
1510
gx_default_put_params(gx_device * dev, gs_param_list * plist)
1511
6.32k
{
1512
6.32k
    int ecode = 0;
1513
6.32k
    int code;
1514
6.32k
    gs_param_name param_name;
1515
6.32k
    gs_param_float_array hwra;
1516
6.32k
    gs_param_int_array hwsa;
1517
6.32k
    gs_param_float_array msa;
1518
6.32k
    gs_param_float_array ma;
1519
6.32k
    gs_param_float_array hwma;
1520
6.32k
    gs_param_string_array scna;
1521
6.32k
    int nci = dev->NumCopies;
1522
6.32k
    int ncset = dev->NumCopies_set;
1523
6.32k
    bool ignc = dev->IgnoreNumCopies;
1524
6.32k
    bool ucc = dev->UseCIEColor;
1525
6.32k
    gs_param_string icc_pro;
1526
6.32k
    bool locksafe = dev->LockSafetyParams;
1527
6.32k
    gs_param_float_array ibba;
1528
6.32k
    bool ibbnull = false;
1529
6.32k
    int colors = dev->color_info.num_components;
1530
6.32k
    int depth = dev->color_info.depth;
1531
6.32k
    int GrayValues = dev->color_info.max_gray + 1;
1532
6.32k
    int RGBValues = dev->color_info.max_color + 1;
1533
6.32k
    long ColorValues = (depth >= 32 ? -1 : 1L << depth);
1534
6.32k
    int tab = dev->color_info.anti_alias.text_bits;
1535
6.32k
    int gab = dev->color_info.anti_alias.graphics_bits;
1536
6.32k
    size_t mpbm = dev->MaxPatternBitmap;
1537
6.32k
    int ic = dev->interpolate_control;
1538
6.32k
    bool page_uses_transparency = dev->page_uses_transparency;
1539
6.32k
    bool page_uses_overprint = dev->page_uses_overprint;
1540
6.32k
    gdev_space_params sp = dev->space_params;
1541
6.32k
    gdev_space_params save_sp = dev->space_params;
1542
6.32k
    int rend_intent[NUM_DEVICE_PROFILES];
1543
6.32k
    int blackptcomp[NUM_DEVICE_PROFILES];
1544
6.32k
    int blackpreserve[NUM_DEVICE_PROFILES];
1545
6.32k
    gs_param_string cms, pagelist, nuplist;
1546
6.32k
    int leadingedge = dev->LeadingEdge;
1547
6.32k
    int k;
1548
6.32k
    int color_accuracy;
1549
6.32k
    bool devicegraytok = true;
1550
6.32k
    bool graydetection = false;
1551
6.32k
    bool usefastcolor = false;
1552
6.32k
    bool blacktext = false;
1553
6.32k
    bool blackvector = false;
1554
6.32k
    gs_overprint_control_t overprint_control = gs_overprint_control_enable;
1555
6.32k
    bool prebandthreshold = false;
1556
6.32k
    bool use_antidropout = dev->color_info.use_antidropout_downscaler;
1557
6.32k
    bool temp_bool;
1558
6.32k
    int  profile_types[NUM_DEVICE_PROFILES] = {gsDEFAULTPROFILE,
1559
6.32k
                                               gsGRAPHICPROFILE,
1560
6.32k
                                               gsIMAGEPROFILE,
1561
6.32k
                                               gsTEXTPROFILE};
1562
1563
6.32k
    color_accuracy = gsicc_currentcoloraccuracy(dev->memory);
1564
6.32k
    if (dev->icc_struct != NULL) {
1565
31.6k
        for (k = 0; k < NUM_DEVICE_PROFILES; k++) {
1566
25.3k
            rend_intent[k] = dev->icc_struct->rendercond[k].rendering_intent;
1567
25.3k
            blackptcomp[k] = dev->icc_struct->rendercond[k].black_point_comp;
1568
25.3k
            blackpreserve[k] = dev->icc_struct->rendercond[k].preserve_black;
1569
25.3k
        }
1570
6.32k
        graydetection = dev->icc_struct->graydetection;
1571
6.32k
        devicegraytok = dev->icc_struct->devicegraytok;
1572
6.32k
        usefastcolor = dev->icc_struct->usefastcolor;
1573
6.32k
        blacktext = dev->icc_struct->blacktext;
1574
6.32k
        blackvector = dev->icc_struct->blackvector;
1575
6.32k
        prebandthreshold = dev->icc_struct->prebandthreshold;
1576
6.32k
        overprint_control = dev->icc_struct->overprint_control;
1577
6.32k
    } else {
1578
0
        for (k = 0; k < NUM_DEVICE_PROFILES; k++) {
1579
0
            rend_intent[k] = gsRINOTSPECIFIED;
1580
0
            blackptcomp[k] = gsBPNOTSPECIFIED;
1581
0
            blackpreserve[k] = gsBKPRESNOTSPECIFIED;
1582
0
        }
1583
0
    }
1584
1585
    /*
1586
     * Template:
1587
     *   BEGIN_ARRAY_PARAM(param_read_xxx_array, "pname", pxxa, size, pxxe) {
1588
     *     ... check value if desired ...
1589
     *     if (success)
1590
     *       break;
1591
     *     ... set ecode ...
1592
     *   } END_ARRAY_PARAM(pxxa, pxxe);
1593
     */
1594
1595
6.32k
#define BEGIN_ARRAY_PARAM(pread, pname, pa, psize, e)\
1596
44.2k
    BEGIN\
1597
44.2k
    switch (code = pread(plist, (param_name = pname), &(pa))) {\
1598
11.7k
      case 0:\
1599
11.7k
        if ((pa).size != psize) {\
1600
0
          ecode = gs_note_error(gs_error_rangecheck);\
1601
0
          (pa).data = 0;  /* mark as not filled */\
1602
0
        } else
1603
6.32k
#define END_ARRAY_PARAM(pa, e)\
1604
6.32k
        goto e;\
1605
11.7k
      default:\
1606
0
        ecode = code;\
1607
0
e:  param_signal_error(plist, param_name, ecode);\
1608
32.5k
      case 1:\
1609
32.5k
        (pa).data = 0;   /* mark as not filled */\
1610
88.5k
    }\
1611
88.5k
    END
1612
1613
    /*
1614
     * The actual value of LeadingEdge must be changed inside this routine,
1615
     * so that we can detect that it has been changed. Thus, instead of a
1616
     * device setting the value itself, it signals a request, which is
1617
     * now executed.
1618
     */
1619
6.32k
    if (leadingedge & LEADINGEDGE_REQ_BIT) {
1620
0
        leadingedge = (leadingedge & LEADINGEDGE_SET_MASK) |
1621
0
            ((leadingedge >> LEADINGEDGE_REQ_VAL_SHIFT) & LEADINGEDGE_MASK);
1622
0
    }
1623
1624
    /*
1625
     * The HWResolution, HWSize, and MediaSize parameters interact in
1626
     * the following way:
1627
     *      1. Setting HWResolution recomputes HWSize from MediaSize.
1628
     *      2. Setting HWSize recomputes MediaSize from HWResolution.
1629
     *      3. Setting MediaSize recomputes HWSize from HWResolution.
1630
     * If more than one parameter is being set, we apply these rules
1631
     * in the order 1, 2, 3.  This does the right thing in the most
1632
     * common case of setting more than one parameter, namely,
1633
     * setting both HWResolution and HWSize.
1634
     *
1635
     * Changing of LeadingEdge is treated exactly the same as a
1636
     * change in HWResolution. In typical usage, MediaSize is
1637
     * short-edge (MediaSize[0] < MediaSize[1]), so if LeadingEdge
1638
     * is 1 or 3, then HWSize will become long-edge. For nonsquare
1639
     * resolutions, HWResolution[0] always corresponds with width
1640
     * (scan length), and [1] with height (number of scans).
1641
     */
1642
1643
8.23k
    BEGIN_ARRAY_PARAM(param_read_float_array, "HWResolution", hwra, 2, hwre) {
1644
1.91k
        if (hwra.data[0] <= 0 || hwra.data[1] <= 0)
1645
0
            ecode = gs_note_error(gs_error_rangecheck);
1646
1.91k
        else
1647
1.91k
            break;
1648
1.91k
    } END_ARRAY_PARAM(hwra, hwre);
1649
7.55k
    BEGIN_ARRAY_PARAM(param_read_int_array, "HWSize", hwsa, 2, hwsa) {
1650
        /* We need a special check to handle the nullpage device, */
1651
        /* whose size is legitimately [0 0]. */
1652
1.22k
        if ((hwsa.data[0] <= 0 && hwsa.data[0] != dev->width) ||
1653
1.22k
            (hwsa.data[1] <= 0 && hwsa.data[1] != dev->height)
1654
1.22k
        )
1655
0
            ecode = gs_note_error(gs_error_rangecheck);
1656
3.68k
#define max_coord (max_fixed / fixed_1)
1657
1.22k
#if max_coord < max_int
1658
1.22k
        else if (hwsa.data[0] > max_coord || hwsa.data[1] > max_coord)
1659
0
            ecode = gs_note_error(gs_error_limitcheck);
1660
1.22k
#endif
1661
1.22k
#undef max_coord
1662
1.22k
        else
1663
1.22k
            break;
1664
1.22k
    } END_ARRAY_PARAM(hwsa, hwse);
1665
6.32k
    {
1666
6.32k
        int t;
1667
1668
6.32k
        code = param_read_int(plist, "LeadingEdge", &t);
1669
6.32k
        if (code < 0) {
1670
1.22k
            if (param_read_null(plist, "LeadingEdge") == 0) {
1671
                /* if param is null, clear explicitly-set flag */
1672
1.22k
                leadingedge &= ~LEADINGEDGE_SET_MASK;
1673
1.22k
            } else {
1674
0
                ecode = code;
1675
0
            }
1676
5.09k
        } else if (code == 0) {
1677
0
            if (t < 0 || t > 3)
1678
0
                param_signal_error(plist, "LeadingEdge",
1679
0
                                   ecode = gs_error_rangecheck);
1680
0
            else
1681
0
                leadingedge = LEADINGEDGE_SET_MASK | t;
1682
0
        }
1683
6.32k
    }
1684
6.32k
    {
1685
6.32k
        const float *res = (hwra.data == 0 ? dev->HWResolution : hwra.data);
1686
1687
6.32k
#ifdef PAGESIZE_IS_MEDIASIZE
1688
6.32k
        const float *data;
1689
1690
        /* .MediaSize takes precedence over PageSize, so */
1691
        /* we read PageSize first. */
1692
6.32k
        code = param_MediaSize(plist, "PageSize", res, &msa);
1693
6.32k
        if (code < 0)
1694
0
            ecode = code;
1695
        /* Prevent data from being set to 0 if PageSize is specified */
1696
        /* but .MediaSize is not. */
1697
6.32k
        data = msa.data;
1698
6.32k
        code = param_MediaSize(plist, ".MediaSize", res, &msa);
1699
6.32k
        if (code < 0)
1700
0
            ecode = code;
1701
6.32k
        else if (msa.data == 0)
1702
1.40k
            msa.data = data;
1703
#else
1704
        code = param_MediaSize(plist, ".MediaSize", res, &msa);
1705
        if (code < 0)
1706
            ecode = code;
1707
#endif
1708
6.32k
    }
1709
1710
7.55k
    BEGIN_ARRAY_PARAM(param_read_float_array, "Margins", ma, 2, me) {
1711
1.22k
        break;
1712
1.22k
    } END_ARRAY_PARAM(ma, me);
1713
7.55k
    BEGIN_ARRAY_PARAM(param_read_float_array, ".HWMargins", hwma, 4, hwme) {
1714
1.22k
        break;
1715
1.22k
    } END_ARRAY_PARAM(hwma, hwme);
1716
6.32k
    switch (code = param_read_bool(plist, (param_name = ".IgnoreNumCopies"), &ignc)) {
1717
0
        default:
1718
0
            ecode = code;
1719
0
            param_signal_error(plist, param_name, ecode);
1720
1.22k
        case 0:
1721
6.32k
        case 1:
1722
6.32k
            break;
1723
6.32k
    }
1724
6.32k
    if (dev->NumCopies_set >= 0 &&
1725
6.32k
        (*dev_proc(dev, get_page_device))(dev) != 0
1726
6.32k
        ) {
1727
6.32k
        switch (code = param_read_int(plist, (param_name = "NumCopies"), &nci)) {
1728
0
            case 0:
1729
0
                if (nci < 0)
1730
0
                    ecode = gs_error_rangecheck;
1731
0
                else {
1732
0
                    ncset = 1;
1733
0
                    break;
1734
0
                }
1735
0
                goto nce;
1736
1.22k
            default:
1737
1.22k
                if ((code = param_read_null(plist, param_name)) == 0) {
1738
1.22k
                    ncset = 0;
1739
1.22k
                    break;
1740
1.22k
                }
1741
0
                ecode = code; /* can't be 1 */
1742
0
nce:
1743
0
                param_signal_error(plist, param_name, ecode);
1744
5.09k
            case 1:
1745
5.09k
                break;
1746
6.32k
        }
1747
6.32k
    }
1748
    /* Set the ICC output colors first */
1749
6.32k
    if ((code = param_read_string(plist, "ICCOutputColors", &icc_pro)) != 1) {
1750
1.22k
        if ((code = gx_default_put_icc_colorants(&icc_pro, dev)) < 0) {
1751
0
            ecode = code;
1752
0
            param_signal_error(plist, "ICCOutputColors", ecode);
1753
0
        }
1754
1.22k
    }
1755
6.32k
    if ((code = param_read_string(plist, "DeviceLinkProfile", &icc_pro)) != 1) {
1756
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsLINKPROFILE)) < 0) {
1757
0
            ecode = code;
1758
0
            param_signal_error(plist, "DeviceLinkProfile", ecode);
1759
0
        }
1760
1.22k
    }
1761
6.32k
    if ((code = param_read_string(plist, "PostRenderProfile", &icc_pro)) != 1) {
1762
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsPRPROFILE)) < 0) {
1763
0
            ecode = code;
1764
0
            param_signal_error(plist, "PostRenderProfile", ecode);
1765
0
        }
1766
1.22k
    }
1767
6.32k
    if ((code = param_read_string(plist, "OutputICCProfile", &icc_pro)) != 1) {
1768
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsDEFAULTPROFILE)) < 0) {
1769
0
            ecode = code;
1770
0
            param_signal_error(plist, "OutputICCProfile", ecode);
1771
0
        }
1772
1.22k
    }
1773
    /* Note, if a change is made to NUM_DEVICE_PROFILES we need to update
1774
       this with the name of the profile */
1775
6.32k
    if ((code = param_read_string(plist, "VectorICCProfile", &icc_pro)) != 1) {
1776
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsGRAPHICPROFILE)) < 0) {
1777
0
            ecode = code;
1778
0
            param_signal_error(plist, "VectorICCProfile", ecode);
1779
0
        }
1780
1.22k
    }
1781
6.32k
    if ((code = param_read_string(plist, "ImageICCProfile", &icc_pro)) != 1) {
1782
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsIMAGEPROFILE)) < 0) {
1783
0
            ecode = code;
1784
0
            param_signal_error(plist, "ImageICCProfile", ecode);
1785
0
        }
1786
1.22k
    }
1787
6.32k
    if ((code = param_read_string(plist, "TextICCProfile", &icc_pro)) != 1) {
1788
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsTEXTPROFILE)) < 0) {
1789
0
            ecode = code;
1790
0
            param_signal_error(plist, "TextICCProfile", ecode);
1791
0
        }
1792
1.22k
    }
1793
6.32k
    if ((code = param_read_string(plist, "ProofProfile", &icc_pro)) != 1) {
1794
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsPROOFPROFILE)) < 0) {
1795
0
            ecode = code;
1796
0
            param_signal_error(plist, "ProofProfile", ecode);
1797
0
        }
1798
1.22k
    }
1799
6.32k
    if ((code = param_read_string(plist, "BlendColorProfile", &icc_pro)) != 1) {
1800
1.22k
        if ((code = gx_default_put_icc(&icc_pro, dev, gsBLENDPROFILE)) < 0) {
1801
0
            ecode = code;
1802
0
            param_signal_error(plist, "BlendColorProfile", ecode);
1803
0
        }
1804
1.22k
    }
1805
6.32k
    if ((code = param_read_int(plist, (param_name = "RenderIntent"),
1806
6.32k
                                                    &(rend_intent[0]))) < 0) {
1807
0
        ecode = code;
1808
0
        param_signal_error(plist, param_name, ecode);
1809
0
    }
1810
6.32k
    if ((code = param_read_int(plist, (param_name = "VectorIntent"),
1811
6.32k
                                                    &(rend_intent[1]))) < 0) {
1812
0
        ecode = code;
1813
0
        param_signal_error(plist, param_name, ecode);
1814
0
    }
1815
6.32k
    if ((code = param_read_int(plist, (param_name = "ImageIntent"),
1816
6.32k
                                                    &(rend_intent[2]))) < 0) {
1817
0
        ecode = code;
1818
0
        param_signal_error(plist, param_name, ecode);
1819
0
    }
1820
6.32k
    if ((code = param_read_int(plist, (param_name = "TextIntent"),
1821
6.32k
                                                    &(rend_intent[3]))) < 0) {
1822
0
        ecode = code;
1823
0
        param_signal_error(plist, param_name, ecode);
1824
0
    }
1825
6.32k
    if ((code = param_read_int(plist, (param_name = "BlackPtComp"),
1826
6.32k
                                                    &(blackptcomp[0]))) < 0) {
1827
0
        ecode = code;
1828
0
        param_signal_error(plist, param_name, ecode);
1829
0
    }
1830
6.32k
    if ((code = param_read_int(plist, (param_name = "VectorBlackPt"),
1831
6.32k
                                                    &(blackptcomp[1]))) < 0) {
1832
0
        ecode = code;
1833
0
        param_signal_error(plist, param_name, ecode);
1834
0
    }
1835
6.32k
    if ((code = param_read_int(plist, (param_name = "ImageBlackPt"),
1836
6.32k
                                                    &(blackptcomp[2]))) < 0) {
1837
0
        ecode = code;
1838
0
        param_signal_error(plist, param_name, ecode);
1839
0
    }
1840
6.32k
    if ((code = param_read_int(plist, (param_name = "TextBlackPt"),
1841
6.32k
                                                    &(blackptcomp[3]))) < 0) {
1842
0
        ecode = code;
1843
0
        param_signal_error(plist, param_name, ecode);
1844
0
    }
1845
6.32k
    if ((code = param_read_int(plist, (param_name = "KPreserve"),
1846
6.32k
                                                    &(blackpreserve[0]))) < 0) {
1847
0
        ecode = code;
1848
0
        param_signal_error(plist, param_name, ecode);
1849
0
    }
1850
6.32k
    if ((code = param_read_int(plist, (param_name = "VectorKPreserve"),
1851
6.32k
                                                    &(blackpreserve[1]))) < 0) {
1852
0
        ecode = code;
1853
0
        param_signal_error(plist, param_name, ecode);
1854
0
    }
1855
6.32k
    if ((code = param_read_int(plist, (param_name = "ImageKPreserve"),
1856
6.32k
                                                    &(blackpreserve[2]))) < 0) {
1857
0
        ecode = code;
1858
0
        param_signal_error(plist, param_name, ecode);
1859
0
    }
1860
6.32k
    if ((code = param_read_int(plist, (param_name = "TextKPreserve"),
1861
6.32k
                                                    &(blackpreserve[3]))) < 0) {
1862
0
        ecode = code;
1863
0
        param_signal_error(plist, param_name, ecode);
1864
0
    }
1865
6.32k
    if ((code = param_read_int(plist, (param_name = "ColorAccuracy"),
1866
6.32k
                                                        &color_accuracy)) < 0) {
1867
0
        ecode = code;
1868
0
        param_signal_error(plist, param_name, ecode);
1869
0
    }
1870
6.32k
    if ((code = param_read_bool(plist, (param_name = "DeviceGrayToK"),
1871
6.32k
                                                        &devicegraytok)) < 0) {
1872
0
        ecode = code;
1873
0
        param_signal_error(plist, param_name, ecode);
1874
0
    }
1875
6.32k
    if ((code = param_read_bool(plist, (param_name = "GrayDetection"),
1876
6.32k
                                                        &graydetection)) < 0) {
1877
0
        ecode = code;
1878
0
        param_signal_error(plist, param_name, ecode);
1879
0
    }
1880
6.32k
    if ((code = param_read_bool(plist, (param_name = "UseFastColor"),
1881
6.32k
                                                        &usefastcolor)) < 0) {
1882
0
        ecode = code;
1883
0
        param_signal_error(plist, param_name, ecode);
1884
0
    }
1885
6.32k
    if ((code = param_read_bool(plist, (param_name = "BlackText"),
1886
6.32k
                                                        &blacktext)) < 0) {
1887
0
        ecode = code;
1888
0
        param_signal_error(plist, param_name, ecode);
1889
0
    }
1890
6.32k
    if ((code = param_read_bool(plist, (param_name = "BlackVector"),
1891
6.32k
                                                        &blackvector)) < 0) {
1892
0
        ecode = code;
1893
0
        param_signal_error(plist, param_name, ecode);
1894
0
    }
1895
6.32k
    if ((code = param_put_enum(plist, "Overprint",
1896
6.32k
                           (int*)&overprint_control, overprint_control_names, ecode)) < 0) {
1897
0
        ecode = code;
1898
0
        param_signal_error(plist, param_name, ecode);
1899
0
    }
1900
6.32k
    if ((code = param_read_bool(plist, (param_name = "PreBandThreshold"),
1901
6.32k
                                                        &prebandthreshold)) < 0) {
1902
0
        ecode = code;
1903
0
        param_signal_error(plist, param_name, ecode);
1904
0
    }
1905
6.32k
    if ((code = param_read_bool(plist, (param_name = "UseCIEColor"), &ucc)) < 0) {
1906
0
        ecode = code;
1907
0
        param_signal_error(plist, param_name, ecode);
1908
0
    }
1909
6.32k
    if ((code = param_anti_alias_bits(plist, "TextAlphaBits", &tab)) < 0)
1910
0
        ecode = code;
1911
6.32k
    if ((code = param_anti_alias_bits(plist, "GraphicsAlphaBits", &gab)) < 0)
1912
0
        ecode = code;
1913
6.32k
    if ((code = param_read_bool(plist, "AntidropoutDownscaler", &use_antidropout)) < 0)
1914
0
        ecode = code;
1915
6.32k
    if ((code = param_read_size_t(plist, "MaxPatternBitmap", &mpbm)) < 0)
1916
0
        ecode = code;
1917
6.32k
    if ((code = param_read_int(plist, "InterpolateControl", &ic)) < 0)
1918
0
        ecode = code;
1919
6.32k
    if ((code = param_read_bool(plist, (param_name = "PageUsesTransparency"),
1920
6.32k
                                &page_uses_transparency)) < 0) {
1921
0
        ecode = code;
1922
0
        param_signal_error(plist, param_name, ecode);
1923
0
    }
1924
6.32k
    if ((code = param_read_bool(plist, (param_name = "PageUsesOverprint"),
1925
6.32k
                                &page_uses_overprint)) < 0) {
1926
0
        ecode = code;
1927
0
        param_signal_error(plist, param_name, ecode);
1928
0
    }
1929
6.32k
    if ((code = param_read_size_t(plist, "MaxBitmap", &sp.MaxBitmap)) < 0)
1930
0
        ecode = code;
1931
1932
6.32k
#define CHECK_PARAM_CASES(member, bad, label)\
1933
6.32k
    case 0:\
1934
5.59k
        if ((sp.params_are_read_only ? sp.member != save_sp.member : bad))\
1935
0
            ecode = gs_error_rangecheck;\
1936
0
        else\
1937
5.59k
            break;\
1938
0
        goto label;\
1939
0
    default:\
1940
0
        ecode = code;\
1941
0
label:\
1942
0
        param_signal_error(plist, param_name, ecode);\
1943
19.7k
    case 1:\
1944
19.7k
        break
1945
1946
6.32k
    switch (code = param_read_size_t(plist, (param_name = "BufferSpace"), &sp.BufferSpace)) {
1947
6.32k
        CHECK_PARAM_CASES(BufferSpace, sp.BufferSpace < 10000, bse);
1948
6.32k
    }
1949
1950
6.32k
    switch (code = param_read_int(plist, (param_name = "BandWidth"), &sp.band.BandWidth)) {
1951
6.32k
        CHECK_PARAM_CASES(band.BandWidth, sp.band.BandWidth < 0, bwe);
1952
6.32k
    }
1953
1954
6.32k
    switch (code = param_read_int(plist, (param_name = "BandHeight"), &sp.band.BandHeight)) {
1955
6.32k
        CHECK_PARAM_CASES(band.BandHeight, sp.band.BandHeight < -1, bhe);
1956
6.32k
    }
1957
6.32k
    if (sp.band.BandHeight == -1)
1958
0
        sp.band.BandHeight = dev->height; /* 1 band for the page requested */
1959
1960
6.32k
    switch (code = param_read_size_t(plist, (param_name = "BandBufferSpace"), &sp.band.BandBufferSpace)) {
1961
6.32k
        CHECK_PARAM_CASES(band.BandBufferSpace, 0, bbse);
1962
6.32k
    }
1963
1964
1965
6.32k
    switch (code = param_read_bool(plist, (param_name = ".LockSafetyParams"), &locksafe)) {
1966
1.22k
        case 0:
1967
1.22k
            if (dev->LockSafetyParams && !locksafe)
1968
0
                code = gs_note_error(gs_error_invalidaccess);
1969
1.22k
            else
1970
1.22k
                break;
1971
0
        default:
1972
0
            ecode = code;
1973
0
            param_signal_error(plist, param_name, ecode);
1974
5.09k
        case 1:
1975
5.09k
            break;
1976
6.32k
    }
1977
    /* Ignore parameters that only have meaning for printers. */
1978
6.32k
#define IGNORE_INT_PARAM(pname)\
1979
25.3k
  { int igni;\
1980
25.3k
    switch ( code = param_read_int(plist, (param_name = pname), &igni) )\
1981
25.3k
      { default:\
1982
0
          ecode = code;\
1983
0
          param_signal_error(plist, param_name, ecode);\
1984
11.0k
        case 0:\
1985
25.3k
        case 1:\
1986
25.3k
          break;\
1987
25.3k
      }\
1988
25.3k
  }
1989
6.32k
    IGNORE_INT_PARAM("%MediaSource")
1990
6.32k
        IGNORE_INT_PARAM("%MediaDestination")
1991
6.32k
        switch (code = param_read_float_array(plist, (param_name = "ImagingBBox"), &ibba)) {
1992
0
        case 0:
1993
0
            if (ibba.size != 4 ||
1994
0
                ibba.data[2] < ibba.data[0] || ibba.data[3] < ibba.data[1]
1995
0
                )
1996
0
                ecode = gs_note_error(gs_error_rangecheck);
1997
0
            else
1998
0
                break;
1999
0
            goto ibbe;
2000
0
        default:
2001
0
            if ((code = param_read_null(plist, param_name)) == 0) {
2002
0
                ibbnull = true;
2003
0
                ibba.data = 0;
2004
0
                break;
2005
0
            }
2006
0
            ecode = code; /* can't be 1 */
2007
0
          ibbe:param_signal_error(plist, param_name, ecode);
2008
6.32k
        case 1:
2009
6.32k
            ibba.data = 0;
2010
6.32k
            break;
2011
6.32k
    }
2012
2013
    /* Separation, DeviceN Color, and ProcessColorModel related parameters. */
2014
6.32k
    {
2015
6.32k
        const char * pcms = get_process_color_model_name(dev);
2016
        /* the device should have set a process model name at this point */
2017
6.32k
        if ((code = param_check_string(plist, "ProcessColorModel", pcms, (pcms != NULL))) < 0)
2018
0
            ecode = code;
2019
6.32k
    }
2020
6.32k
    IGNORE_INT_PARAM("MaxSeparations")
2021
6.32k
    if ((code = param_check_bool(plist, "Separations", false, true)) < 0)
2022
0
        ecode = code;
2023
2024
7.55k
    BEGIN_ARRAY_PARAM(param_read_name_array, "SeparationColorNames", scna, scna.size, scne) {
2025
1.22k
        break;
2026
1.22k
    } END_ARRAY_PARAM(scna, scne);
2027
2028
    /* Now check nominally read-only parameters. */
2029
6.32k
    if ((code = param_check_string(plist, "OutputDevice", dev->dname, true)) < 0)
2030
0
        ecode = code;
2031
6.32k
    if ((code = param_check_string(plist, "Name", dev->dname, true)) < 0)
2032
0
        ecode = code;
2033
6.32k
    if ((code = param_check_int(plist, "Colors", colors, true)) < 0)
2034
0
        ecode = code;
2035
6.32k
    if ((code = param_check_int(plist, "BitsPerPixel", depth, true)) < 0)
2036
0
        ecode = code;
2037
6.32k
    if ((code = param_check_int(plist, "GrayValues", GrayValues, true)) < 0)
2038
0
        ecode = code;
2039
2040
    /* with saved-pages, PageCount can't be checked. No harm in letting it change */
2041
6.32k
    IGNORE_INT_PARAM("PageCount")
2042
2043
6.32k
    if ((code = param_check_int(plist, "RedValues", RGBValues, true)) < 0)
2044
0
        ecode = code;
2045
6.32k
    if ((code = param_check_int(plist, "GreenValues", RGBValues, true)) < 0)
2046
0
        ecode = code;
2047
6.32k
    if ((code = param_check_int(plist, "BlueValues", RGBValues, true)) < 0)
2048
0
        ecode = code;
2049
6.32k
    if ((code = param_check_long(plist, "ColorValues", ColorValues, true)) < 0)
2050
0
        ecode = code;
2051
6.32k
    if (param_read_string(plist, "HWColorMap", &cms) != 1) {
2052
0
        byte palette[3 << 8];
2053
2054
0
        if (param_HWColorMap(dev, palette))
2055
0
            code = param_check_bytes(plist, "HWColorMap", palette,
2056
0
                                     colors << depth, true);
2057
0
        else
2058
0
            code = param_check_bytes(plist, "HWColorMap", 0, 0, false);
2059
0
        if (code < 0)
2060
0
            ecode = code;
2061
0
    }
2062
2063
6.32k
    code = param_read_int(plist, "FirstPage", &dev->FirstPage);
2064
6.32k
    if (code < 0)
2065
0
        ecode = code;
2066
2067
6.32k
    code = param_read_int(plist,  "LastPage", &dev->LastPage);
2068
6.32k
    if (code < 0)
2069
0
        ecode = code;
2070
2071
6.32k
    code = param_read_bool(plist, "DisablePageHandler", &temp_bool);
2072
6.32k
    if (code < 0)
2073
0
        ecode = code;
2074
6.32k
    if (code == 0)
2075
1.22k
        dev->DisablePageHandler = temp_bool;
2076
2077
    /* If we have an NupControl subclass device (N-up) installed, this param will have  */
2078
    /* been handled there, so the check for different will be false, meaning that this  */
2079
    /* code won't end up doing anything. This will catch the first occurence and needs  */
2080
    /* to install the N-up subclass device.           */
2081
6.32k
    code = param_read_string(plist, "NupControl", &nuplist);
2082
6.32k
    if (code < 0)
2083
0
        ecode = code;
2084
6.32k
    if (code == 0) {
2085
1.22k
        if (dev->NupControl && (
2086
0
            nuplist.size == 0 ||
2087
0
            (strncmp(dev->NupControl->nupcontrol_str, (const char *)nuplist.data, nuplist.size) != 0))) {
2088
            /* There was a NupControl, but this one is different -- no longer use the old one */
2089
0
            rc_decrement(dev->NupControl, "default put_params NupControl");
2090
0
            dev->NupControl = NULL;
2091
0
        }
2092
1.22k
    }
2093
6.32k
    if (dev->NupControl == NULL && code == 0 && nuplist.size > 0) {
2094
0
        gx_device *next_dev;
2095
2096
0
        dev->NupControl = (gdev_nupcontrol *)gs_alloc_bytes(dev->memory->non_gc_memory,
2097
0
                                                          sizeof(gdev_nupcontrol), "structure to hold nupcontrol_str");
2098
0
        if (dev->NupControl == NULL)
2099
0
            return gs_note_error(gs_error_VMerror);
2100
0
        dev->NupControl->nupcontrol_str = (void *)gs_alloc_bytes(dev->memory->non_gc_memory,
2101
0
                                                                 nuplist.size + 1, "nupcontrol string");
2102
0
        if (dev->NupControl->nupcontrol_str == NULL){
2103
0
            gs_free(dev->memory->non_gc_memory, dev->NupControl, 1, sizeof(gdev_nupcontrol),
2104
0
                    "free structure to hold nupcontrol string");
2105
0
            dev->NupControl = 0;
2106
0
            return gs_note_error(gs_error_VMerror);
2107
0
        }
2108
0
        memset(dev->NupControl->nupcontrol_str, 0x00, nuplist.size + 1);
2109
0
        memcpy(dev->NupControl->nupcontrol_str, nuplist.data, nuplist.size);
2110
0
        rc_init_free(dev->NupControl, dev->memory->non_gc_memory, 1, rc_free_NupControl);
2111
2112
        /* Propagate the new NupControl struct to children */
2113
0
        next_dev = dev->child;
2114
0
        while (next_dev != NULL) {
2115
0
            if (next_dev->NupControl)
2116
0
                rc_decrement(next_dev->NupControl, "nup_put_params");
2117
0
            next_dev->NupControl = dev->NupControl;
2118
0
            rc_increment(dev->NupControl);
2119
0
            next_dev = next_dev->child;
2120
0
        }
2121
        /* Propagate the new NupControl struct to parents */
2122
0
        next_dev = dev->parent;
2123
0
        while (next_dev != NULL) {
2124
0
            if (next_dev->NupControl)
2125
0
                rc_decrement(next_dev->NupControl, "nup_put_params");
2126
0
            next_dev->NupControl = dev->NupControl;
2127
0
            rc_increment(dev->NupControl);
2128
0
            next_dev = next_dev->parent;
2129
0
        }
2130
0
    }
2131
2132
6.32k
    code = param_read_string(plist, "PageList", &pagelist);
2133
6.32k
    if (code < 0)
2134
0
        ecode = code;
2135
6.32k
    if (code == 0) {
2136
1.22k
        if (dev->PageList)
2137
1.22k
            rc_decrement(dev->PageList, "default put_params PageList");
2138
1.22k
        dev->PageList = NULL;
2139
1.22k
    }
2140
2141
6.32k
    if (code == 0 && pagelist.size > 0) {
2142
0
        dev->PageList = (gdev_pagelist *)gs_alloc_bytes(dev->memory->non_gc_memory, sizeof(gdev_pagelist), "structure to hold page list");
2143
0
        if (!dev->PageList)
2144
0
            return gs_note_error(gs_error_VMerror);
2145
0
        dev->PageList->Pages = (void *)gs_alloc_bytes(dev->memory->non_gc_memory, pagelist.size + 1, "String to hold page list");
2146
0
        if (!dev->PageList->Pages){
2147
0
            gs_free(dev->memory->non_gc_memory, dev->PageList, 1, sizeof(gdev_pagelist), "free structure to hold page list");
2148
0
            dev->PageList = 0;
2149
0
            return gs_note_error(gs_error_VMerror);
2150
0
        }
2151
0
        memset(dev->PageList->Pages, 0x00, pagelist.size + 1);
2152
0
        memcpy(dev->PageList->Pages, pagelist.data, pagelist.size);
2153
0
        dev->PageList->PagesSize = pagelist.size + 1;
2154
0
        rc_init_free(dev->PageList, dev->memory->non_gc_memory, 1, rc_free_pages_list);
2155
0
    }
2156
2157
6.32k
    code = param_read_bool(plist, "FILTERIMAGE", &temp_bool);
2158
6.32k
    if (code < 0)
2159
0
        ecode = code;
2160
6.32k
    if (code == 0) {
2161
1.22k
        if (temp_bool)
2162
0
            dev->ObjectFilter |= FILTERIMAGE;
2163
1.22k
        else
2164
1.22k
            dev->ObjectFilter &= ~FILTERIMAGE;
2165
1.22k
    }
2166
2167
6.32k
    code = param_read_bool(plist, "FILTERTEXT", &temp_bool);
2168
6.32k
    if (code < 0)
2169
0
        ecode = code;
2170
6.32k
    if (code == 0) {
2171
1.22k
        if (temp_bool)
2172
0
            dev->ObjectFilter |= FILTERTEXT;
2173
1.22k
        else
2174
1.22k
            dev->ObjectFilter &= ~FILTERTEXT;
2175
1.22k
    }
2176
2177
6.32k
    code = param_read_bool(plist, "FILTERVECTOR", &temp_bool);
2178
6.32k
    if (code < 0)
2179
0
        ecode = code;
2180
6.32k
    if (code == 0) {
2181
1.22k
        if (temp_bool)
2182
0
            dev->ObjectFilter |= FILTERVECTOR;
2183
1.22k
        else
2184
1.22k
            dev->ObjectFilter &= ~FILTERVECTOR;
2185
1.22k
    }
2186
2187
    /* We must 'commit', in order to detect unknown parameters, */
2188
    /* even if there were errors. */
2189
6.32k
    code = param_commit(plist);
2190
6.32k
    if (ecode < 0) {
2191
        /* restore_page_device (zdevice2.c) will turn off LockSafetyParams, and relies on putparams
2192
         * to put it back if we are restoring a device. The locksafe value is picked up above from the
2193
         * device we are restoring to, and we *must* make sure it is preserved, even if setting the
2194
         * params failed. Otherwise an attacker can use a failed grestore to reset LockSafetyParams.
2195
         * See bug #699687.
2196
         */
2197
0
        dev->LockSafetyParams = locksafe;
2198
0
        return ecode;
2199
0
    }
2200
6.32k
    if (code < 0) {
2201
1.23k
        dev->LockSafetyParams = locksafe;
2202
1.23k
        return code;
2203
1.23k
    }
2204
2205
    /*
2206
     * Now actually make the changes. Changing resolution, rotation
2207
     * (through LeadingEdge) or page size requires closing the device,
2208
     * but changing margins or ImagingBBox does not. In order not to
2209
     * close and reopen the device unnecessarily, we check for
2210
     * replacing the values with the same ones.
2211
     */
2212
2213
5.09k
    dev->color_info.use_antidropout_downscaler = use_antidropout;
2214
2215
5.09k
    if (hwra.data != 0 &&
2216
5.09k
        (dev->HWResolution[0] != hwra.data[0] ||
2217
1.91k
         dev->HWResolution[1] != hwra.data[1])
2218
5.09k
        ) {
2219
683
        if (dev->is_open)
2220
0
            gs_closedevice(dev);
2221
683
        gx_device_set_resolution(dev, hwra.data[0], hwra.data[1]);
2222
683
    }
2223
5.09k
    if ((leadingedge & LEADINGEDGE_MASK) !=
2224
5.09k
        (dev->LeadingEdge & LEADINGEDGE_MASK)) {
2225
        /* If the LeadingEdge_set flag changes but the value of LeadingEdge
2226
           itself does not, don't close device and recompute page size. */
2227
0
        dev->LeadingEdge = leadingedge;
2228
0
        if (dev->is_open)
2229
0
            gs_closedevice(dev);
2230
0
        gx_device_set_resolution(dev, dev->HWResolution[0], dev->HWResolution[1]);
2231
0
    }
2232
    /* clear leadingedge request, preserve "set" flag */
2233
5.09k
    dev->LeadingEdge &= LEADINGEDGE_MASK;
2234
5.09k
    dev->LeadingEdge |= (leadingedge & LEADINGEDGE_SET_MASK);
2235
2236
5.09k
    if (hwsa.data != 0 &&
2237
5.09k
        (dev->width != hwsa.data[0] ||
2238
1.22k
         dev->height != hwsa.data[1])
2239
5.09k
        ) {
2240
1.01k
        if (dev->is_open)
2241
0
            gs_closedevice(dev);
2242
1.01k
        gx_device_set_width_height(dev, hwsa.data[0], hwsa.data[1]);
2243
1.01k
    }
2244
5.09k
    if (msa.data != 0 &&
2245
5.09k
        (dev->MediaSize[0] != msa.data[0] ||
2246
3.68k
         dev->MediaSize[1] != msa.data[1])
2247
5.09k
        ) {
2248
1.01k
        if (dev->is_open)
2249
0
            gs_closedevice(dev);
2250
1.01k
        gx_device_set_page_size(dev, msa.data[0], msa.data[1]);
2251
1.01k
    }
2252
5.09k
    if (ma.data != 0) {
2253
1.22k
        dev->Margins[0] = ma.data[0];
2254
1.22k
        dev->Margins[1] = ma.data[1];
2255
1.22k
    }
2256
5.09k
    if (hwma.data != 0) {
2257
1.22k
        dev->HWMargins[0] = hwma.data[0];
2258
1.22k
        dev->HWMargins[1] = hwma.data[1];
2259
1.22k
        dev->HWMargins[2] = hwma.data[2];
2260
1.22k
        dev->HWMargins[3] = hwma.data[3];
2261
1.22k
    }
2262
5.09k
    dev->NumCopies = nci;
2263
5.09k
    dev->NumCopies_set = ncset;
2264
5.09k
    dev->IgnoreNumCopies = ignc;
2265
5.09k
    if (ibba.data != 0) {
2266
0
        dev->ImagingBBox[0] = ibba.data[0];
2267
0
        dev->ImagingBBox[1] = ibba.data[1];
2268
0
        dev->ImagingBBox[2] = ibba.data[2];
2269
0
        dev->ImagingBBox[3] = ibba.data[3];
2270
0
        dev->ImagingBBox_set = true;
2271
5.09k
    } else if (ibbnull) {
2272
0
        dev->ImagingBBox_set = false;
2273
0
    }
2274
5.09k
    dev->UseCIEColor = ucc;
2275
5.09k
        dev->color_info.anti_alias.text_bits =
2276
5.09k
                param_normalize_anti_alias_bits(max(dev->color_info.max_gray,
2277
5.09k
                        dev->color_info.max_color), tab);
2278
5.09k
        dev->color_info.anti_alias.graphics_bits =
2279
5.09k
                param_normalize_anti_alias_bits(max(dev->color_info.max_gray,
2280
5.09k
                        dev->color_info.max_color), gab);
2281
5.09k
    dev->LockSafetyParams = locksafe;
2282
5.09k
    dev->MaxPatternBitmap = mpbm;
2283
5.09k
    dev->interpolate_control = ic;
2284
5.09k
    dev->space_params = sp;
2285
5.09k
    dev->page_uses_transparency = page_uses_transparency;
2286
5.09k
    dev->page_uses_overprint = page_uses_overprint;
2287
5.09k
    gx_device_decache_colors(dev);
2288
2289
    /* Take care of the rendering intents and blackpts.  For those that
2290
       are not set special, the default provides an override */
2291
5.09k
    if (dev->icc_struct != NULL) {
2292
        /* Set the default object */
2293
5.09k
        code = gx_default_put_intent(rend_intent[0], dev, gsDEFAULTPROFILE);
2294
5.09k
        if (code < 0)
2295
0
            return code;
2296
5.09k
        code = gx_default_put_blackptcomp(blackptcomp[0], dev, gsDEFAULTPROFILE);
2297
5.09k
        if (code < 0)
2298
0
            return code;
2299
5.09k
        code = gx_default_put_blackpreserve(blackpreserve[0], dev, gsDEFAULTPROFILE);
2300
5.09k
        if (code < 0)
2301
0
            return code;
2302
        /* If the default was specified and not a specialized one (e.g. graphic
2303
           image or text) then the special one will get set to the default.  */
2304
20.3k
        for (k = 1; k < NUM_DEVICE_PROFILES; k++) {
2305
15.2k
            if (rend_intent[0] != gsRINOTSPECIFIED &&
2306
15.2k
                rend_intent[k] == gsRINOTSPECIFIED) {
2307
0
                code = gx_default_put_intent(rend_intent[0], dev, profile_types[k]);
2308
15.2k
            } else {
2309
15.2k
                code = gx_default_put_intent(rend_intent[k], dev, profile_types[k]);
2310
15.2k
            }
2311
15.2k
            if (code < 0)
2312
0
                return code;
2313
15.2k
            if (blackptcomp[0] != gsBPNOTSPECIFIED &&
2314
15.2k
                blackptcomp[k] == gsBPNOTSPECIFIED) {
2315
0
                code = gx_default_put_blackptcomp(blackptcomp[0], dev, profile_types[k]);
2316
15.2k
            } else {
2317
15.2k
                code = gx_default_put_blackptcomp(blackptcomp[k], dev, profile_types[k]);
2318
15.2k
            }
2319
15.2k
            if (code < 0)
2320
0
                return code;
2321
15.2k
            if (blackpreserve[0] != gsBKPRESNOTSPECIFIED &&
2322
15.2k
                blackpreserve[k] == gsBKPRESNOTSPECIFIED) {
2323
0
                code = gx_default_put_blackpreserve(blackpreserve[0], dev, profile_types[k]);
2324
15.2k
            } else {
2325
15.2k
                code = gx_default_put_blackpreserve(blackpreserve[k], dev, profile_types[k]);
2326
15.2k
            }
2327
15.2k
            if (code < 0)
2328
0
                return code;
2329
15.2k
        }
2330
5.09k
    }
2331
5.09k
    gsicc_setcoloraccuracy(dev->memory, color_accuracy);
2332
5.09k
    code = gx_default_put_graytok(devicegraytok, dev);
2333
5.09k
    if (code < 0)
2334
0
        return code;
2335
5.09k
    code = gx_default_put_usefastcolor(usefastcolor, dev);
2336
5.09k
    if (code < 0)
2337
0
        return code;
2338
5.09k
    code = gx_default_put_blacktext(blacktext, dev);
2339
5.09k
    if (code < 0)
2340
0
        return code;
2341
5.09k
    code = gx_default_put_blackvector(blackvector, dev);
2342
5.09k
    if (code < 0)
2343
0
        return code;
2344
5.09k
    code = gx_default_put_overprint_control(overprint_control, dev);
2345
5.09k
    if (code < 0)
2346
0
        return code;
2347
5.09k
    code = gx_default_put_graydetection(graydetection, dev);
2348
5.09k
    if (code < 0)
2349
0
        return code;
2350
5.09k
    return gx_default_put_prebandthreshold(prebandthreshold, dev);
2351
5.09k
}
2352
2353
void
2354
gx_device_request_leadingedge(gx_device *dev, int le_req)
2355
0
{
2356
0
    dev->LeadingEdge = (dev->LeadingEdge & ~LEADINGEDGE_REQ_VAL) |
2357
0
        ((le_req << LEADINGEDGE_REQ_VAL_SHIFT) & LEADINGEDGE_REQ_VAL) |
2358
0
        LEADINGEDGE_REQ_BIT;
2359
0
}
2360
2361
/* Limit the anti-alias bit values to the maximum legal value for the
2362
 * current color depth.
2363
 */
2364
static int
2365
param_normalize_anti_alias_bits( uint max_gray, int bits )
2366
10.1k
{
2367
10.1k
        int max_bits = ilog2( max_gray + 1);
2368
2369
10.1k
        return  (bits > max_bits ? max_bits : bits);
2370
10.1k
}
2371
2372
/* Read TextAlphaBits or GraphicsAlphaBits. */
2373
static int
2374
param_anti_alias_bits(gs_param_list * plist, gs_param_name param_name, int *pa)
2375
12.6k
{
2376
12.6k
    int code = param_read_int(plist, param_name, pa);
2377
2378
12.6k
    switch (code) {
2379
2.45k
    case 0:
2380
2.45k
        switch (*pa) {
2381
2.45k
        case 1: case 2: case 4:
2382
2.45k
            return 0;
2383
0
        default:
2384
0
            code = gs_error_rangecheck;
2385
2.45k
        }
2386
        /* fall through */
2387
0
    default:
2388
0
        param_signal_error(plist, param_name, code);
2389
10.1k
    case 1:
2390
10.1k
        ;
2391
12.6k
    }
2392
10.1k
    return code;
2393
12.6k
}
2394
2395
/* Read .MediaSize or, if supported as a synonym, PageSize. */
2396
static int
2397
param_MediaSize(gs_param_list * plist, gs_param_name pname,
2398
                const float *res, gs_param_float_array * pa)
2399
12.6k
{
2400
12.6k
    gs_param_name param_name;
2401
12.6k
    int ecode = 0;
2402
12.6k
    int code;
2403
2404
17.5k
    BEGIN_ARRAY_PARAM(param_read_float_array, pname, *pa, 2, mse) {
2405
4.91k
        float width_new = pa->data[0] * res[0] / 72;
2406
4.91k
        float height_new = pa->data[1] * res[1] / 72;
2407
2408
4.91k
        if (width_new < 0 || height_new < 0)
2409
0
            ecode = gs_note_error(gs_error_rangecheck);
2410
14.7k
#define max_coord (max_fixed / fixed_1)
2411
4.91k
#if max_coord < max_int
2412
4.91k
        else if (width_new > (long)max_coord || height_new > (long)max_coord)
2413
0
            ecode = gs_note_error(gs_error_limitcheck);
2414
4.91k
#endif
2415
4.91k
#undef max_coord
2416
4.91k
        else
2417
4.91k
            break;
2418
4.91k
    } END_ARRAY_PARAM(*pa, mse);
2419
12.6k
    return ecode;
2420
12.6k
}
2421
2422
/* Check that a nominally read-only parameter is being set to */
2423
/* its existing value. */
2424
static int
2425
param_check_bool(gs_param_list * plist, gs_param_name pname, bool value,
2426
                 bool is_defined)
2427
6.32k
{
2428
6.32k
    int code;
2429
6.32k
    bool new_value;
2430
2431
6.32k
    switch (code = param_read_bool(plist, pname, &new_value)) {
2432
1.22k
        case 0:
2433
1.22k
            if (is_defined && new_value == value)
2434
1.22k
                break;
2435
0
            code = gs_note_error(gs_error_rangecheck);
2436
0
            goto e;
2437
0
        default:
2438
0
            if (param_read_null(plist, pname) == 0)
2439
0
                return 1;
2440
0
          e:param_signal_error(plist, pname, code);
2441
5.09k
        case 1:
2442
5.09k
            ;
2443
6.32k
    }
2444
6.32k
    return code;
2445
6.32k
}
2446
static int
2447
param_check_long(gs_param_list * plist, gs_param_name pname, long value,
2448
                 bool is_defined)
2449
44.2k
{
2450
44.2k
    int code;
2451
44.2k
    long new_value;
2452
2453
44.2k
    switch (code = param_read_long(plist, pname, &new_value)) {
2454
0
        case 0:
2455
0
            if (is_defined && new_value == value)
2456
0
                break;
2457
0
            code = gs_note_error(gs_error_rangecheck);
2458
0
            goto e;
2459
0
        default:
2460
0
            if (param_read_null(plist, pname) == 0)
2461
0
                return 1;
2462
0
          e:param_signal_error(plist, pname, code);
2463
44.2k
        case 1:
2464
44.2k
            ;
2465
44.2k
    }
2466
44.2k
    return code;
2467
44.2k
}
2468
static int
2469
param_check_bytes(gs_param_list * plist, gs_param_name pname, const byte * str,
2470
                  uint size, bool is_defined)
2471
18.9k
{
2472
18.9k
    int code;
2473
18.9k
    gs_param_string new_value;
2474
2475
18.9k
    switch (code = param_read_string(plist, pname, &new_value)) {
2476
1.22k
        case 0:
2477
1.22k
            if (is_defined && new_value.size == size &&
2478
1.22k
                !memcmp((const char *)str, (const char *)new_value.data,
2479
1.22k
                        size)
2480
1.22k
                )
2481
1.22k
                break;
2482
0
            code = gs_note_error(gs_error_rangecheck);
2483
0
            goto e;
2484
0
        default:
2485
0
            if (param_read_null(plist, pname) == 0)
2486
0
                return 1;
2487
0
          e:param_signal_error(plist, pname, code);
2488
17.7k
        case 1:
2489
17.7k
            ;
2490
18.9k
    }
2491
18.9k
    return code;
2492
18.9k
}