]> git.ipfire.org Git - thirdparty/cups.git/blame - cups/ipp-support.c
More tweaks for IPP Everywhere support in web interface.
[thirdparty/cups.git] / cups / ipp-support.c
CommitLineData
ef416fc2 1/*
d21dc0ed 2 * Internet Printing Protocol support functions for CUPS.
ef416fc2 3 *
1f717210
MS
4 * Copyright © 2007-2018 by Apple Inc.
5 * Copyright © 1997-2007 by Easy Software Products, all rights reserved.
ef416fc2 6 *
d21dc0ed
MS
7 * These coded instructions, statements, and computer programs are the
8 * property of Apple Inc. and are protected by Federal copyright
9 * law. Distribution and use rights are outlined in the file "LICENSE.txt"
10 * which should have been included with this file. If this file is
57b7b66b 11 * missing or damaged, see the license at "http://www.cups.org/".
ef416fc2 12 *
d21dc0ed 13 * This file is subject to the Apple OS-Developed Software exception.
ef416fc2 14 */
15
16/*
17 * Include necessary headers...
18 */
19
71e16022 20#include "cups-private.h"
ef416fc2 21
22
23/*
24 * Local globals...
25 */
26
d21dc0ed
MS
27static const char * const ipp_states[] =
28 {
29 "IPP_STATE_ERROR",
30 "IPP_STATE_IDLE",
31 "IPP_STATE_HEADER",
32 "IPP_STATE_ATTRIBUTE",
33 "IPP_STATE_DATA"
34 };
ef416fc2 35static const char * const ipp_status_oks[] = /* "OK" status codes */
a2326b5b 36 { /* (name) = abandoned standard value */
ef416fc2 37 "successful-ok",
38 "successful-ok-ignored-or-substituted-attributes",
39 "successful-ok-conflicting-attributes",
40 "successful-ok-ignored-subscriptions",
a2326b5b 41 "(successful-ok-ignored-notifications)",
ef416fc2 42 "successful-ok-too-many-events",
a2326b5b 43 "(successful-ok-but-cancel-subscription)",
bd7854cb 44 "successful-ok-events-complete"
ef416fc2 45 },
46 * const ipp_status_400s[] = /* Client errors */
a2326b5b 47 { /* (name) = abandoned standard value */
ef416fc2 48 "client-error-bad-request",
49 "client-error-forbidden",
50 "client-error-not-authenticated",
51 "client-error-not-authorized",
52 "client-error-not-possible",
53 "client-error-timeout",
54 "client-error-not-found",
55 "client-error-gone",
56 "client-error-request-entity-too-large",
57 "client-error-request-value-too-long",
58 "client-error-document-format-not-supported",
59 "client-error-attributes-or-values-not-supported",
60 "client-error-uri-scheme-not-supported",
61 "client-error-charset-not-supported",
62 "client-error-conflicting-attributes",
63 "client-error-compression-not-supported",
64 "client-error-compression-error",
65 "client-error-document-format-error",
66 "client-error-document-access-error",
67 "client-error-attributes-not-settable",
68 "client-error-ignored-all-subscriptions",
69 "client-error-too-many-subscriptions",
a2326b5b 70 "(client-error-ignored-all-notifications)",
82cc1f9a
MS
71 "(client-error-client-print-support-file-not-found)",
72 "client-error-document-password-error",
73 "client-error-document-permission-error",
74 "client-error-document-security-error",
6b13fa61
MS
75 "client-error-document-unprintable-error",
76 "client-error-account-info-needed",
77 "client-error-account-closed",
78 "client-error-account-limit-reached",
c47d4869
MS
79 "client-error-account-authorization-failed",
80 "client-error-not-fetchable"
ef416fc2 81 },
a469f8a5
MS
82 * const ipp_status_480s[] = /* Vendor client errors */
83 {
84 /* 0x0480 - 0x048F */
85 "0x0480",
86 "0x0481",
87 "0x0482",
88 "0x0483",
89 "0x0484",
90 "0x0485",
91 "0x0486",
92 "0x0487",
93 "0x0488",
94 "0x0489",
95 "0x048A",
96 "0x048B",
97 "0x048C",
98 "0x048D",
99 "0x048E",
100 "0x048F",
101 /* 0x0490 - 0x049F */
102 "0x0490",
103 "0x0491",
104 "0x0492",
105 "0x0493",
106 "0x0494",
107 "0x0495",
108 "0x0496",
109 "0x0497",
110 "0x0498",
111 "0x0499",
112 "0x049A",
113 "0x049B",
114 "cups-error-account-info-needed",
115 "cups-error-account-closed",
116 "cups-error-account-limit-reached",
117 "cups-error-account-authorization-failed"
118 },
ef416fc2 119 * const ipp_status_500s[] = /* Server errors */
120 {
121 "server-error-internal-error",
122 "server-error-operation-not-supported",
123 "server-error-service-unavailable",
124 "server-error-version-not-supported",
125 "server-error-device-error",
126 "server-error-temporary-error",
127 "server-error-not-accepting-jobs",
128 "server-error-busy",
129 "server-error-job-canceled",
130 "server-error-multiple-document-jobs-not-supported",
a2326b5b
MS
131 "server-error-printer-is-deactivated",
132 "server-error-too-many-jobs",
133 "server-error-too-many-documents"
7cf5915e
MS
134 },
135 * const ipp_status_1000s[] = /* CUPS internal */
136 {
a469f8a5 137 "cups-authentication-canceled",
7cf5915e
MS
138 "cups-pki-error",
139 "cups-upgrade-required"
ef416fc2 140 };
a2326b5b 141static const char * const ipp_std_ops[] =
ef416fc2 142 {
143 /* 0x0000 - 0x000f */
db8b865d
MS
144 "0x0000",
145 "0x0001",
aaf19ab0
MS
146 "Print-Job",
147 "Print-URI",
148 "Validate-Job",
149 "Create-Job",
150 "Send-Document",
151 "Send-URI",
152 "Cancel-Job",
153 "Get-Job-Attributes",
154 "Get-Jobs",
155 "Get-Printer-Attributes",
156 "Hold-Job",
157 "Release-Job",
158 "Restart-Job",
db8b865d 159 "0x000f",
ef416fc2 160
161 /* 0x0010 - 0x001f */
aaf19ab0
MS
162 "Pause-Printer",
163 "Resume-Printer",
164 "Purge-Jobs",
165 "Set-Printer-Attributes",
ef416fc2 166 "Set-Job-Attributes",
167 "Get-Printer-Supported-Values",
42404685
MS
168 "Create-Printer-Subscriptions",
169 "Create-Job-Subscriptions",
ef416fc2 170 "Get-Subscription-Attributes",
aaf19ab0
MS
171 "Get-Subscriptions",
172 "Renew-Subscription",
173 "Cancel-Subscription",
174 "Get-Notifications",
a2326b5b
MS
175 "(Send-Notifications)",
176 "(Get-Resource-Attributes)",
177 "(Get-Resource-Data)",
ef416fc2 178
179 /* 0x0020 - 0x002f */
a2326b5b
MS
180 "(Get-Resources)",
181 "(Get-Printer-Support-Files)",
ef416fc2 182 "Enable-Printer",
183 "Disable-Printer",
184 "Pause-Printer-After-Current-Job",
185 "Hold-New-Jobs",
186 "Release-Held-New-Jobs",
187 "Deactivate-Printer",
188 "Activate-Printer",
189 "Restart-Printer",
190 "Shutdown-Printer",
191 "Startup-Printer",
192 "Reprocess-Job",
193 "Cancel-Current-Job",
194 "Suspend-Current-Job",
195 "Resume-Job",
196
9b4bd602 197 /* 0x0030 - 0x003f */
ef416fc2 198 "Promote-Job",
aaf19ab0 199 "Schedule-Job-After",
db8b865d 200 "0x0032",
aaf19ab0
MS
201 "Cancel-Document",
202 "Get-Document-Attributes",
203 "Get-Documents",
204 "Delete-Document",
205 "Set-Document-Attributes",
206 "Cancel-Jobs",
207 "Cancel-My-Jobs",
208 "Resubmit-Job",
771bd8cb 209 "Close-Job",
82cc1f9a 210 "Identify-Printer",
9475ec92 211 "Validate-Document",
e06e4eb5 212 "Add-Document-Images",
9b4bd602
MS
213 "Acknowledge-Document",
214
215 /* 0x0040 - 0x004a */
216 "Acknowledge-Identify-Printer",
217 "Acknowledge-Job",
218 "Fetch-Document",
219 "Fetch-Job",
220 "Get-Output-Device-Attributes",
221 "Update-Active-Jobs",
222 "Deregister-Output-Device",
223 "Update-Document-Status",
224 "Update-Job-Status",
225 "Update-Output-Device-Attributes",
226 "Get-Next-Document-Data"
ef416fc2 227 },
228 * const ipp_cups_ops[] =
229 {
230 "CUPS-Get-Default",
231 "CUPS-Get-Printers",
480ef0fe 232 "CUPS-Add-Modify-Printer",
ef416fc2 233 "CUPS-Delete-Printer",
234 "CUPS-Get-Classes",
480ef0fe 235 "CUPS-Add-Modify-Class",
ef416fc2 236 "CUPS-Delete-Class",
237 "CUPS-Accept-Jobs",
238 "CUPS-Reject-Jobs",
239 "CUPS-Set-Default",
240 "CUPS-Get-Devices",
241 "CUPS-Get-PPDs",
242 "CUPS-Move-Job",
b94498cf 243 "CUPS-Authenticate-Job",
244 "CUPS-Get-PPD"
2e4ff8af
MS
245 },
246 * const ipp_cups_ops2[] =
247 {
95ece0cb
MS
248 "CUPS-Get-Document",
249 "CUPS-Create-Local-Printer"
1ff0402e
MS
250 },
251 * const ipp_tag_names[] =
252 { /* Value/group tag names */
253 "zero", /* 0x00 */
254 "operation-attributes-tag",
255 /* 0x01 */
256 "job-attributes-tag", /* 0x02 */
257 "end-of-attributes-tag",
258 /* 0x03 */
259 "printer-attributes-tag",
260 /* 0x04 */
261 "unsupported-attributes-tag",
262 /* 0x05 */
263 "subscription-attributes-tag",
264 /* 0x06 */
265 "event-notification-attributes-tag",
266 /* 0x07 */
a2326b5b
MS
267 "(resource-attributes-tag)",
268 /* 0x08 */
d7225fc2
MS
269 "document-attributes-tag",
270 /* 0x09 */
271 "0x0a", /* 0x0a */
272 "0x0b", /* 0x0b */
273 "0x0c", /* 0x0c */
274 "0x0d", /* 0x0d */
275 "0x0e", /* 0x0e */
276 "0x0f", /* 0x0f */
1ff0402e
MS
277 "unsupported", /* 0x10 */
278 "default", /* 0x11 */
279 "unknown", /* 0x12 */
280 "no-value", /* 0x13 */
d7225fc2 281 "0x14", /* 0x14 */
1ff0402e
MS
282 "not-settable", /* 0x15 */
283 "delete-attribute", /* 0x16 */
284 "admin-define", /* 0x17 */
d7225fc2
MS
285 "0x18", /* 0x18 */
286 "0x19", /* 0x19 */
287 "0x1a", /* 0x1a */
288 "0x1b", /* 0x1b */
289 "0x1c", /* 0x1c */
290 "0x1d", /* 0x1d */
291 "0x1e", /* 0x1e */
292 "0x1f", /* 0x1f */
293 "0x20", /* 0x20 */
1ff0402e
MS
294 "integer", /* 0x21 */
295 "boolean", /* 0x22 */
296 "enum", /* 0x23 */
d7225fc2
MS
297 "0x24", /* 0x24 */
298 "0x25", /* 0x25 */
299 "0x26", /* 0x26 */
300 "0x27", /* 0x27 */
301 "0x28", /* 0x28 */
302 "0x29", /* 0x29 */
303 "0x2a", /* 0x2a */
304 "0x2b", /* 0x2b */
305 "0x2c", /* 0x2c */
306 "0x2d", /* 0x2d */
307 "0x2e", /* 0x2e */
308 "0x2f", /* 0x2f */
1ff0402e
MS
309 "octetString", /* 0x30 */
310 "dateTime", /* 0x31 */
311 "resolution", /* 0x32 */
312 "rangeOfInteger", /* 0x33 */
f8b3a85b 313 "collection", /* 0x34 */
1ff0402e
MS
314 "textWithLanguage", /* 0x35 */
315 "nameWithLanguage", /* 0x36 */
316 "endCollection", /* 0x37 */
d7225fc2
MS
317 "0x38", /* 0x38 */
318 "0x39", /* 0x39 */
319 "0x3a", /* 0x3a */
320 "0x3b", /* 0x3b */
321 "0x3c", /* 0x3c */
322 "0x3d", /* 0x3d */
323 "0x3e", /* 0x3e */
324 "0x3f", /* 0x3f */
325 "0x40", /* 0x40 */
1ff0402e
MS
326 "textWithoutLanguage",/* 0x41 */
327 "nameWithoutLanguage",/* 0x42 */
d7225fc2 328 "0x43", /* 0x43 */
1ff0402e
MS
329 "keyword", /* 0x44 */
330 "uri", /* 0x45 */
331 "uriScheme", /* 0x46 */
332 "charset", /* 0x47 */
333 "naturalLanguage", /* 0x48 */
334 "mimeMediaType", /* 0x49 */
335 "memberAttrName" /* 0x4a */
ef416fc2 336 };
a2326b5b
MS
337static const char * const ipp_document_states[] =
338 { /* document-state-enums */
339 "pending",
340 "4",
341 "processing",
cd3614ae 342 "processing-stopped", /* IPPSIX */
a2326b5b
MS
343 "canceled",
344 "aborted",
345 "completed"
346 },
347 * const ipp_finishings[] =
348 { /* finishings enums */
349 "none",
350 "staple",
351 "punch",
352 "cover",
353 "bind",
354 "saddle-stitch",
355 "edge-stitch",
356 "fold",
357 "trim",
358 "bale",
359 "booklet-maker",
360 "jog-offset",
cd3614ae
MS
361 "coat", /* Finishings 2.0 */
362 "laminate", /* Finishings 2.0 */
a2326b5b
MS
363 "17",
364 "18",
365 "19",
366 "staple-top-left",
367 "staple-bottom-left",
368 "staple-top-right",
369 "staple-bottom-right",
370 "edge-stitch-left",
371 "edge-stitch-top",
372 "edge-stitch-right",
373 "edge-stitch-bottom",
374 "staple-dual-left",
375 "staple-dual-top",
376 "staple-dual-right",
377 "staple-dual-bottom",
cd3614ae
MS
378 "staple-triple-left", /* Finishings 2.0 */
379 "staple-triple-top", /* Finishings 2.0 */
380 "staple-triple-right",/* Finishings 2.0 */
381 "staple-triple-bottom",/* Finishings 2.0 */
a2326b5b
MS
382 "36",
383 "37",
384 "38",
385 "39",
386 "40",
387 "41",
388 "42",
389 "43",
390 "44",
391 "45",
392 "46",
393 "47",
394 "48",
395 "49",
396 "bind-left",
397 "bind-top",
398 "bind-right",
399 "bind-bottom",
400 "54",
401 "55",
402 "56",
403 "57",
404 "58",
405 "59",
406 "trim-after-pages",
407 "trim-after-documents",
408 "trim-after-copies",
9475ec92
MS
409 "trim-after-job",
410 "64",
411 "65",
412 "66",
413 "67",
414 "68",
415 "69",
cd3614ae
MS
416 "punch-top-left", /* Finishings 2.0 */
417 "punch-bottom-left", /* Finishings 2.0 */
418 "punch-top-right", /* Finishings 2.0 */
419 "punch-bottom-right", /* Finishings 2.0 */
420 "punch-dual-left", /* Finishings 2.0 */
421 "punch-dual-top", /* Finishings 2.0 */
422 "punch-dual-right", /* Finishings 2.0 */
423 "punch-dual-bottom", /* Finishings 2.0 */
424 "punch-triple-left", /* Finishings 2.0 */
425 "punch-triple-top", /* Finishings 2.0 */
426 "punch-triple-right", /* Finishings 2.0 */
427 "punch-triple-bottom",/* Finishings 2.0 */
428 "punch-quad-left", /* Finishings 2.0 */
429 "punch-quad-top", /* Finishings 2.0 */
430 "punch-quad-right", /* Finishings 2.0 */
431 "punch-quad-bottom", /* Finishings 2.0 */
2a8afc20
MS
432 "punch-multiple-left",/* Finishings 2.1/Canon */
433 "punch-multiple-top", /* Finishings 2.1/Canon */
434 "punch-multiple-right",/* Finishings 2.1/Canon */
435 "punch-multiple-bottom",/* Finishings 2.1/Canon */
cd3614ae
MS
436 "fold-accordian", /* Finishings 2.0 */
437 "fold-double-gate", /* Finishings 2.0 */
438 "fold-gate", /* Finishings 2.0 */
439 "fold-half", /* Finishings 2.0 */
440 "fold-half-z", /* Finishings 2.0 */
441 "fold-left-gate", /* Finishings 2.0 */
442 "fold-letter", /* Finishings 2.0 */
443 "fold-parallel", /* Finishings 2.0 */
444 "fold-poster", /* Finishings 2.0 */
445 "fold-right-gate", /* Finishings 2.0 */
2a8afc20
MS
446 "fold-z", /* Finishings 2.0 */
447 "fold-engineering-z" /* Finishings 2.1 */
a2326b5b 448 },
a469f8a5
MS
449 * const ipp_finishings_vendor[] =
450 {
451 /* 0x40000000 to 0x4000000F */
452 "0x40000000",
453 "0x40000001",
454 "0x40000002",
455 "0x40000003",
456 "0x40000004",
457 "0x40000005",
458 "0x40000006",
459 "0x40000007",
460 "0x40000008",
461 "0x40000009",
462 "0x4000000A",
463 "0x4000000B",
464 "0x4000000C",
465 "0x4000000D",
466 "0x4000000E",
467 "0x4000000F",
468 /* 0x40000010 to 0x4000001F */
469 "0x40000010",
470 "0x40000011",
471 "0x40000012",
472 "0x40000013",
473 "0x40000014",
474 "0x40000015",
475 "0x40000016",
476 "0x40000017",
477 "0x40000018",
478 "0x40000019",
479 "0x4000001A",
480 "0x4000001B",
481 "0x4000001C",
482 "0x4000001D",
483 "0x4000001E",
484 "0x4000001F",
485 /* 0x40000020 to 0x4000002F */
486 "0x40000020",
487 "0x40000021",
488 "0x40000022",
489 "0x40000023",
490 "0x40000024",
491 "0x40000025",
492 "0x40000026",
493 "0x40000027",
494 "0x40000028",
495 "0x40000029",
496 "0x4000002A",
497 "0x4000002B",
498 "0x4000002C",
499 "0x4000002D",
500 "0x4000002E",
501 "0x4000002F",
502 /* 0x40000030 to 0x4000003F */
503 "0x40000030",
504 "0x40000031",
505 "0x40000032",
506 "0x40000033",
507 "0x40000034",
508 "0x40000035",
509 "0x40000036",
510 "0x40000037",
511 "0x40000038",
512 "0x40000039",
513 "0x4000003A",
514 "0x4000003B",
515 "0x4000003C",
516 "0x4000003D",
517 "0x4000003E",
518 "0x4000003F",
519 /* 0x40000040 - 0x4000004F */
520 "0x40000040",
521 "0x40000041",
522 "0x40000042",
523 "0x40000043",
524 "0x40000044",
525 "0x40000045",
9475ec92
MS
526 "cups-punch-top-left",
527 "cups-punch-bottom-left",
528 "cups-punch-top-right",
529 "cups-punch-bottom-right",
530 "cups-punch-dual-left",
531 "cups-punch-dual-top",
532 "cups-punch-dual-right",
533 "cups-punch-dual-bottom",
534 "cups-punch-triple-left",
535 "cups-punch-triple-top",
6961465f 536 /* 0x40000050 - 0x4000005F */
9475ec92
MS
537 "cups-punch-triple-right",
538 "cups-punch-triple-bottom",
539 "cups-punch-quad-left",
540 "cups-punch-quad-top",
541 "cups-punch-quad-right",
542 "cups-punch-quad-bottom",
6961465f
MS
543 "0x40000056",
544 "0x40000057",
545 "0x40000058",
546 "0x40000059",
9475ec92
MS
547 "cups-fold-accordian",
548 "cups-fold-double-gate",
549 "cups-fold-gate",
550 "cups-fold-half",
551 "cups-fold-half-z",
552 "cups-fold-left-gate",
6961465f 553 /* 0x40000060 - 0x40000064 */
9475ec92
MS
554 "cups-fold-letter",
555 "cups-fold-parallel",
556 "cups-fold-poster",
557 "cups-fold-right-gate",
558 "cups-fold-z"
a469f8a5 559 },
a2326b5b
MS
560 * const ipp_job_collation_types[] =
561 { /* job-collation-type enums */
562 "uncollated-sheets",
563 "collated-documents",
564 "uncollated-documents"
565 },
566 * const ipp_job_states[] =
567 { /* job-state enums */
568 "pending",
569 "pending-held",
570 "processing",
571 "processing-stopped",
572 "canceled",
573 "aborted",
574 "completed"
575 },
576 * const ipp_orientation_requesteds[] =
577 { /* orientation-requested enums */
578 "portrait",
579 "landscape",
580 "reverse-landscape",
8f787fca
MS
581 "reverse-portrait",
582 "none"
a2326b5b
MS
583 },
584 * const ipp_print_qualities[] =
585 { /* print-quality enums */
586 "draft",
587 "normal",
588 "high"
589 },
590 * const ipp_printer_states[] =
591 { /* printer-state enums */
592 "idle",
593 "processing",
594 "stopped",
595 };
aaf19ab0
MS
596
597
598/*
599 * Local functions...
600 */
601
602static size_t ipp_col_string(ipp_t *col, char *buffer, size_t bufsize);
603
604
605/*
a2326b5b 606 * 'ippAttributeString()' - Convert the attribute's value to a string.
aaf19ab0
MS
607 *
608 * Returns the number of bytes that would be written, not including the
609 * trailing nul. The buffer pointer can be NULL to get the required length,
610 * just like (v)snprintf.
a2326b5b 611 *
8072030b 612 * @since CUPS 1.6/macOS 10.8@
aaf19ab0
MS
613 */
614
615size_t /* O - Number of bytes less nul */
a2326b5b
MS
616ippAttributeString(
617 ipp_attribute_t *attr, /* I - Attribute */
618 char *buffer, /* I - String buffer or NULL */
619 size_t bufsize) /* I - Size of string buffer */
aaf19ab0
MS
620{
621 int i; /* Looping var */
622 char *bufptr, /* Pointer into buffer */
623 *bufend, /* End of buffer */
624 temp[256]; /* Temporary string */
db8b865d
MS
625 const char *ptr, /* Pointer into string */
626 *end; /* Pointer to end of string */
a2326b5b 627 _ipp_value_t *val; /* Current value */
aaf19ab0
MS
628
629
630 if (!attr || !attr->name)
631 {
632 if (buffer)
633 *buffer = '\0';
634
635 return (0);
636 }
637
638 bufptr = buffer;
639 if (buffer)
640 bufend = buffer + bufsize - 1;
641 else
642 bufend = NULL;
643
644 for (i = attr->num_values, val = attr->values; i > 0; i --, val ++)
645 {
646 if (val > attr->values)
647 {
7cf5915e 648 if (buffer && bufptr < bufend)
aaf19ab0
MS
649 *bufptr++ = ',';
650 else
651 bufptr ++;
652 }
653
cb7f98ee 654 switch (attr->value_tag & ~IPP_TAG_CUPS_CONST)
aaf19ab0
MS
655 {
656 case IPP_TAG_ENUM :
a2326b5b 657 ptr = ippEnumString(attr->name, val->integer);
aaf19ab0 658
a2326b5b 659 if (buffer && bufptr < bufend)
07623986 660 strlcpy(bufptr, ptr, (size_t)(bufend - bufptr + 1));
9b66acc5 661
a2326b5b
MS
662 bufptr += strlen(ptr);
663 break;
aaf19ab0
MS
664
665 case IPP_TAG_INTEGER :
7cf5915e 666 if (buffer && bufptr < bufend)
07623986 667 bufptr += snprintf(bufptr, (size_t)(bufend - bufptr + 1), "%d", val->integer);
aaf19ab0
MS
668 else
669 bufptr += snprintf(temp, sizeof(temp), "%d", val->integer);
670 break;
671
672 case IPP_TAG_BOOLEAN :
7cf5915e 673 if (buffer && bufptr < bufend)
07623986 674 strlcpy(bufptr, val->boolean ? "true" : "false", (size_t)(bufend - bufptr + 1));
aaf19ab0
MS
675
676 bufptr += val->boolean ? 4 : 5;
677 break;
678
679 case IPP_TAG_RANGE :
7cf5915e 680 if (buffer && bufptr < bufend)
07623986 681 bufptr += snprintf(bufptr, (size_t)(bufend - bufptr + 1), "%d-%d", val->range.lower, val->range.upper);
aaf19ab0 682 else
07623986 683 bufptr += snprintf(temp, sizeof(temp), "%d-%d", val->range.lower, val->range.upper);
aaf19ab0
MS
684 break;
685
686 case IPP_TAG_RESOLUTION :
4a838088
MS
687 if (val->resolution.xres == val->resolution.yres)
688 {
689 if (buffer && bufptr < bufend)
690 bufptr += snprintf(bufptr, (size_t)(bufend - bufptr + 1), "%d%s", val->resolution.xres, val->resolution.units == IPP_RES_PER_INCH ? "dpi" : "dpcm");
691 else
692 bufptr += snprintf(temp, sizeof(temp), "%d%s", val->resolution.xres, val->resolution.units == IPP_RES_PER_INCH ? "dpi" : "dpcm");
693 }
694 else if (buffer && bufptr < bufend)
07623986 695 bufptr += snprintf(bufptr, (size_t)(bufend - bufptr + 1), "%dx%d%s", val->resolution.xres, val->resolution.yres, val->resolution.units == IPP_RES_PER_INCH ? "dpi" : "dpcm");
aaf19ab0 696 else
07623986 697 bufptr += snprintf(temp, sizeof(temp), "%dx%d%s", val->resolution.xres, val->resolution.yres, val->resolution.units == IPP_RES_PER_INCH ? "dpi" : "dpcm");
aaf19ab0
MS
698 break;
699
700 case IPP_TAG_DATE :
701 {
702 unsigned year; /* Year */
703
7e86f2f6 704 year = ((unsigned)val->date[0] << 8) + (unsigned)val->date[1];
aaf19ab0
MS
705
706 if (val->date[9] == 0 && val->date[10] == 0)
707 snprintf(temp, sizeof(temp), "%04u-%02u-%02uT%02u:%02u:%02uZ",
708 year, val->date[2], val->date[3], val->date[4],
709 val->date[5], val->date[6]);
710 else
711 snprintf(temp, sizeof(temp),
712 "%04u-%02u-%02uT%02u:%02u:%02u%c%02u%02u",
713 year, val->date[2], val->date[3], val->date[4],
714 val->date[5], val->date[6], val->date[8], val->date[9],
715 val->date[10]);
716
7cf5915e 717 if (buffer && bufptr < bufend)
07623986 718 strlcpy(bufptr, temp, (size_t)(bufend - bufptr + 1));
aaf19ab0
MS
719
720 bufptr += strlen(temp);
721 }
722 break;
723
724 case IPP_TAG_TEXT :
725 case IPP_TAG_NAME :
726 case IPP_TAG_KEYWORD :
727 case IPP_TAG_CHARSET :
728 case IPP_TAG_URI :
d7225fc2 729 case IPP_TAG_URISCHEME :
aaf19ab0
MS
730 case IPP_TAG_MIMETYPE :
731 case IPP_TAG_LANGUAGE :
732 case IPP_TAG_TEXTLANG :
733 case IPP_TAG_NAMELANG :
7cf5915e
MS
734 if (!val->string.text)
735 break;
736
aaf19ab0
MS
737 for (ptr = val->string.text; *ptr; ptr ++)
738 {
a2326b5b 739 if (*ptr == '\\' || *ptr == '\"' || *ptr == '[')
aaf19ab0 740 {
7cf5915e 741 if (buffer && bufptr < bufend)
aaf19ab0
MS
742 *bufptr = '\\';
743 bufptr ++;
744 }
745
7cf5915e 746 if (buffer && bufptr < bufend)
aaf19ab0
MS
747 *bufptr = *ptr;
748 bufptr ++;
749 }
a2326b5b
MS
750
751 if (val->string.language)
752 {
753 /*
754 * Add "[language]" to end of string...
755 */
756
757 if (buffer && bufptr < bufend)
758 *bufptr = '[';
759 bufptr ++;
760
761 if (buffer && bufptr < bufend)
07623986 762 strlcpy(bufptr, val->string.language, (size_t)(bufend - bufptr));
a2326b5b
MS
763 bufptr += strlen(val->string.language);
764
765 if (buffer && bufptr < bufend)
766 *bufptr = ']';
767 bufptr ++;
768 }
aaf19ab0
MS
769 break;
770
771 case IPP_TAG_BEGIN_COLLECTION :
7cf5915e 772 if (buffer && bufptr < bufend)
7e86f2f6 773 bufptr += ipp_col_string(val->collection, bufptr, (size_t)(bufend - bufptr + 1));
aaf19ab0
MS
774 else
775 bufptr += ipp_col_string(val->collection, NULL, 0);
776 break;
777
778 case IPP_TAG_STRING :
db8b865d
MS
779 for (ptr = val->unknown.data, end = ptr + val->unknown.length;
780 ptr < end; ptr ++)
aaf19ab0 781 {
7cf5915e 782 if (*ptr == '\\' || _cups_isspace(*ptr))
aaf19ab0 783 {
7cf5915e 784 if (buffer && bufptr < bufend)
aaf19ab0
MS
785 *bufptr = '\\';
786 bufptr ++;
787
7cf5915e 788 if (buffer && bufptr < bufend)
aaf19ab0
MS
789 *bufptr = *ptr;
790 bufptr ++;
791 }
792 else if (!isprint(*ptr & 255))
793 {
7cf5915e 794 if (buffer && bufptr < bufend)
07623986 795 bufptr += snprintf(bufptr, (size_t)(bufend - bufptr + 1), "\\%03o", *ptr & 255);
aaf19ab0 796 else
07623986 797 bufptr += snprintf(temp, sizeof(temp), "\\%03o", *ptr & 255);
aaf19ab0
MS
798 }
799 else
800 {
7cf5915e 801 if (buffer && bufptr < bufend)
aaf19ab0
MS
802 *bufptr = *ptr;
803 bufptr ++;
804 }
805 }
806 break;
807
808 default :
809 ptr = ippTagString(attr->value_tag);
7cf5915e 810 if (buffer && bufptr < bufend)
07623986 811 strlcpy(bufptr, ptr, (size_t)(bufend - bufptr + 1));
aaf19ab0
MS
812 bufptr += strlen(ptr);
813 break;
814 }
815 }
816
7cf5915e 817 if (buffer && bufptr < bufend)
aaf19ab0
MS
818 *bufptr = '\0';
819 else if (bufend)
820 *bufend = '\0';
821
7e86f2f6 822 return ((size_t)(bufptr - buffer));
aaf19ab0 823}
ef416fc2 824
825
db8b865d
MS
826/*
827 * 'ippCreateRequestedArray()' - Create a CUPS array of attribute names from the
828 * given requested-attributes attribute.
829 *
830 * This function creates a (sorted) CUPS array of attribute names matching the
831 * list of "requested-attribute" values supplied in an IPP request. All IANA-
832 * registered values are supported in addition to the CUPS IPP extension
833 * attributes.
834 *
835 * The @code request@ parameter specifies the request message that was read from
836 * the client.
837 *
838 * @code NULL@ is returned if all attributes should be returned. Otherwise, the
839 * result is a sorted array of attribute names, where @code cupsArrayFind(array,
840 * "attribute-name")@ will return a non-NULL pointer. The array must be freed
841 * using the @code cupsArrayDelete@ function.
842 *
8072030b 843 * @since CUPS 1.7/macOS 10.9@
db8b865d
MS
844 */
845
846cups_array_t * /* O - CUPS array or @code NULL@ if all */
847ippCreateRequestedArray(ipp_t *request) /* I - IPP request */
848{
849 int i, j, /* Looping vars */
850 count, /* Number of values */
851 added; /* Was name added? */
852 ipp_attribute_t *requested; /* requested-attributes attribute */
853 cups_array_t *ra; /* Requested attributes array */
854 const char *value; /* Current value */
855 /* The following lists come from the current IANA IPP registry of attributes */
856 static const char * const document_description[] =
857 { /* document-description group */
858 "compression",
859 "copies-actual",
860 "cover-back-actual",
861 "cover-front-actual",
862 "current-page-order",
863 "date-time-at-completed",
864 "date-time-at-creation",
865 "date-time-at-processing",
866 "detailed-status-messages",
867 "document-access-errors",
868 "document-charset",
869 "document-digital-signature",
870 "document-format",
871 "document-format-details",
872 "document-format-detected",
873 "document-format-version",
874 "document-format-version-detected",
875 "document-job-id",
876 "document-job-uri",
877 "document-message",
878 "document-metadata",
879 "document-name",
880 "document-natural-language",
881 "document-number",
882 "document-printer-uri",
883 "document-state",
884 "document-state-message",
885 "document-state-reasons",
886 "document-uri",
887 "document-uuid",
888 "errors-count",
889 "finishings-actual",
890 "finishings-col-actual",
891 "force-front-side-actual",
892 "imposition-template-actual",
893 "impressions",
894 "impressions-completed",
895 "impressions-completed-current-copy",
896 "insert-sheet-actual",
897 "k-octets",
898 "k-octets-processed",
899 "last-document",
87e9bb55 900 "materials-col-actual", /* IPP 3D */
db8b865d
MS
901 "media-actual",
902 "media-col-actual",
903 "media-input-tray-check-actual",
904 "media-sheets",
905 "media-sheets-completed",
906 "more-info",
87e9bb55 907 "multiple-object-handling-actual", /* IPP 3D */
db8b865d
MS
908 "number-up-actual",
909 "orientation-requested-actual",
910 "output-bin-actual",
911 "output-device-assigned",
912 "overrides-actual",
913 "page-delivery-actual",
914 "page-order-received-actual",
915 "page-ranges-actual",
916 "pages",
917 "pages-completed",
918 "pages-completed-current-copy",
87e9bb55 919 "platform-temperature-actual", /* IPP 3D */
db8b865d 920 "presentation-direction-number-up-actual",
87e9bb55
MS
921 "print-accuracy-actual", /* IPP 3D */
922 "print-base-actual", /* IPP 3D */
db8b865d
MS
923 "print-color-mode-actual",
924 "print-content-optimize-actual",
87e9bb55 925 "print-objects-actual", /* IPP 3D */
db8b865d
MS
926 "print-quality-actual",
927 "print-rendering-intent-actual",
6961465f 928 "print-scaling-actual", /* IPP Paid Printing */
87e9bb55 929 "print-supports-actual", /* IPP 3D */
db8b865d
MS
930 "printer-resolution-actual",
931 "printer-up-time",
932 "separator-sheets-actual",
933 "sheet-completed-copy-number",
934 "sides-actual",
935 "time-at-completed",
936 "time-at-creation",
937 "time-at-processing",
938 "x-image-position-actual",
939 "x-image-shift-actual",
940 "x-side1-image-shift-actual",
941 "x-side2-image-shift-actual",
942 "y-image-position-actual",
943 "y-image-shift-actual",
944 "y-side1-image-shift-actual",
945 "y-side2-image-shift-actual"
946 };
947 static const char * const document_template[] =
948 { /* document-template group */
949 "copies",
950 "copies-default",
951 "copies-supported",
952 "cover-back",
953 "cover-back-default",
954 "cover-back-supported",
955 "cover-front",
956 "cover-front-default",
957 "cover-front-supported",
958 "feed-orientation",
959 "feed-orientation-default",
960 "feed-orientation-supported",
961 "finishings",
962 "finishings-col",
1f717210 963 "finishings-col-database",
db8b865d 964 "finishings-col-default",
1f717210 965 "finishings-col-ready",
db8b865d
MS
966 "finishings-col-supported",
967 "finishings-default",
1f717210 968 "finishings-ready",
db8b865d
MS
969 "finishings-supported",
970 "font-name-requested",
971 "font-name-requested-default",
972 "font-name-requested-supported",
973 "font-size-requested",
974 "font-size-requested-default",
975 "font-size-requested-supported",
976 "force-front-side",
977 "force-front-side-default",
978 "force-front-side-supported",
979 "imposition-template",
980 "imposition-template-default",
981 "imposition-template-supported",
982 "insert-after-page-number-supported",
983 "insert-count-supported",
984 "insert-sheet",
985 "insert-sheet-default",
986 "insert-sheet-supported",
87e9bb55
MS
987 "material-amount-units-supported", /* IPP 3D */
988 "material-diameter-supported", /* IPP 3D */
989 "material-purpose-supported", /* IPP 3D */
990 "material-rate-supported", /* IPP 3D */
991 "material-rate-units-supported", /* IPP 3D */
992 "material-shell-thickness-supported",/* IPP 3D */
993 "material-temperature-supported", /* IPP 3D */
994 "material-type-supported", /* IPP 3D */
995 "materials-col", /* IPP 3D */
996 "materials-col-database", /* IPP 3D */
997 "materials-col-default", /* IPP 3D */
998 "materials-col-ready", /* IPP 3D */
999 "materials-col-supported", /* IPP 3D */
1000 "max-materials-col-supported", /* IPP 3D */
db8b865d
MS
1001 "max-stitching-locations-supported",
1002 "media",
1003 "media-back-coating-supported",
1004 "media-bottom-margin-supported",
1005 "media-col",
1006 "media-col-default",
1f717210 1007 "media-col-ready",
db8b865d
MS
1008 "media-col-supported",
1009 "media-color-supported",
1010 "media-default",
1011 "media-front-coating-supported",
1012 "media-grain-supported",
1013 "media-hole-count-supported",
1014 "media-info-supported",
1015 "media-input-tray-check",
1016 "media-input-tray-check-default",
1017 "media-input-tray-check-supported",
1018 "media-key-supported",
1019 "media-left-margin-supported",
1020 "media-order-count-supported",
1021 "media-pre-printed-supported",
1f717210 1022 "media-ready",
db8b865d
MS
1023 "media-recycled-supported",
1024 "media-right-margin-supported",
1025 "media-size-supported",
1026 "media-source-supported",
1027 "media-supported",
1028 "media-thickness-supported",
1029 "media-top-margin-supported",
1030 "media-type-supported",
1031 "media-weight-metric-supported",
1032 "multiple-document-handling",
1033 "multiple-document-handling-default",
1034 "multiple-document-handling-supported",
87e9bb55
MS
1035 "multiple-object-handling", /* IPP 3D */
1036 "multiple-object-handling-default", /* IPP 3D */
1037 "multiple-object-handling-supported",/* IPP 3D */
db8b865d
MS
1038 "number-up",
1039 "number-up-default",
1040 "number-up-supported",
1041 "orientation-requested",
1042 "orientation-requested-default",
1043 "orientation-requested-supported",
6961465f
MS
1044 "output-mode", /* CUPS extension */
1045 "output-mode-default", /* CUPS extension */
1046 "output-mode-supported", /* CUPS extension */
db8b865d
MS
1047 "overrides",
1048 "overrides-supported",
1049 "page-delivery",
1050 "page-delivery-default",
1051 "page-delivery-supported",
1052 "page-order-received",
1053 "page-order-received-default",
1054 "page-order-received-supported",
1055 "page-ranges",
1056 "page-ranges-supported",
1057 "pages-per-subset",
1058 "pages-per-subset-supported",
1059 "pdl-init-file",
1060 "pdl-init-file-default",
1061 "pdl-init-file-entry-supported",
1062 "pdl-init-file-location-supported",
1063 "pdl-init-file-name-subdirectory-supported",
1064 "pdl-init-file-name-supported",
1065 "pdl-init-file-supported",
87e9bb55
MS
1066 "platform-temperature", /* IPP 3D */
1067 "platform-temperature-default", /* IPP 3D */
1068 "platform-temperature-supported", /* IPP 3D */
db8b865d
MS
1069 "presentation-direction-number-up",
1070 "presentation-direction-number-up-default",
1071 "presentation-direction-number-up-supported",
87e9bb55
MS
1072 "print-accuracy", /* IPP 3D */
1073 "print-accuracy-default", /* IPP 3D */
1074 "print-accuracy-supported", /* IPP 3D */
1075 "print-base", /* IPP 3D */
1076 "print-base-default", /* IPP 3D */
1077 "print-base-supported", /* IPP 3D */
db8b865d
MS
1078 "print-color-mode",
1079 "print-color-mode-default",
1080 "print-color-mode-supported",
1081 "print-content-optimize",
1082 "print-content-optimize-default",
1083 "print-content-optimize-supported",
87e9bb55
MS
1084 "print-objects", /* IPP 3D */
1085 "print-objects-default", /* IPP 3D */
1086 "print-objects-supported", /* IPP 3D */
db8b865d
MS
1087 "print-quality",
1088 "print-quality-default",
1089 "print-quality-supported",
1090 "print-rendering-intent",
1091 "print-rendering-intent-default",
1092 "print-rendering-intent-supported",
6961465f
MS
1093 "print-scaling", /* IPP Paid Printing */
1094 "print-scaling-default", /* IPP Paid Printing */
1095 "print-scaling-supported", /* IPP Paid Printing */
87e9bb55
MS
1096 "print-supports", /* IPP 3D */
1097 "print-supports-default", /* IPP 3D */
1098 "print-supports-supported", /* IPP 3D */
db8b865d
MS
1099 "printer-resolution",
1100 "printer-resolution-default",
1101 "printer-resolution-supported",
1102 "separator-sheets",
1103 "separator-sheets-default",
1104 "separator-sheets-supported",
1105 "sheet-collate",
1106 "sheet-collate-default",
1107 "sheet-collate-supported",
1108 "sides",
1109 "sides-default",
1110 "sides-supported",
1111 "stitching-locations-supported",
1112 "stitching-offset-supported",
1113 "x-image-position",
1114 "x-image-position-default",
1115 "x-image-position-supported",
1116 "x-image-shift",
1117 "x-image-shift-default",
1118 "x-image-shift-supported",
1119 "x-side1-image-shift",
1120 "x-side1-image-shift-default",
1121 "x-side1-image-shift-supported",
1122 "x-side2-image-shift",
1123 "x-side2-image-shift-default",
1124 "x-side2-image-shift-supported",
1125 "y-image-position",
1126 "y-image-position-default",
1127 "y-image-position-supported",
1128 "y-image-shift",
1129 "y-image-shift-default",
1130 "y-image-shift-supported",
1131 "y-side1-image-shift",
1132 "y-side1-image-shift-default",
1133 "y-side1-image-shift-supported",
1134 "y-side2-image-shift",
1135 "y-side2-image-shift-default",
1136 "y-side2-image-shift-supported"
1137 };
1138 static const char * const job_description[] =
1139 { /* job-description group */
1140 "compression-supplied",
1141 "copies-actual",
1142 "cover-back-actual",
1143 "cover-front-actual",
1144 "current-page-order",
1145 "date-time-at-completed",
1146 "date-time-at-creation",
1147 "date-time-at-processing",
1148 "destination-statuses",
1149 "document-charset-supplied",
1150 "document-digital-signature-supplied",
1151 "document-format-details-supplied",
1152 "document-format-supplied",
1153 "document-message-supplied",
1154 "document-metadata",
1155 "document-name-supplied",
1156 "document-natural-language-supplied",
1157 "document-overrides-actual",
1158 "errors-count",
1159 "finishings-actual",
1160 "finishings-col-actual",
1161 "force-front-side-actual",
1162 "imposition-template-actual",
1163 "impressions-completed-current-copy",
1164 "insert-sheet-actual",
1165 "job-account-id-actual",
1166 "job-accounting-sheets-actual",
1167 "job-accounting-user-id-actual",
1168 "job-attribute-fidelity",
1169 "job-charge-info", /* CUPS extension */
1170 "job-collation-type",
1171 "job-collation-type-actual",
1172 "job-copies-actual",
1173 "job-cover-back-actual",
1174 "job-cover-front-actual",
1175 "job-detailed-status-message",
1176 "job-document-access-errors",
1177 "job-error-sheet-actual",
1178 "job-finishings-actual",
1179 "job-finishings-col-actual",
1180 "job-hold-until-actual",
1181 "job-id",
1182 "job-impressions",
1183 "job-impressions-completed",
1184 "job-k-octets",
1185 "job-k-octets-processed",
1186 "job-mandatory-attributes",
1187 "job-media-progress", /* CUPS extension */
1188 "job-media-sheets",
1189 "job-media-sheets-completed",
1190 "job-message-from-operator",
1191 "job-more-info",
1192 "job-name",
1193 "job-originating-host-name", /* CUPS extension */
1194 "job-originating-user-name",
1195 "job-originating-user-uri",
1196 "job-pages",
1197 "job-pages-completed",
1198 "job-pages-completed-current-copy",
1199 "job-printer-state-message", /* CUPS extension */
1200 "job-printer-state-reasons", /* CUPS extension */
1201 "job-printer-up-time",
1202 "job-printer-uri",
1203 "job-priority-actual",
1204 "job-save-printer-make-and-model",
1205 "job-sheet-message-actual",
1206 "job-sheets-actual",
1207 "job-sheets-col-actual",
1208 "job-state",
1209 "job-state-message",
1210 "job-state-reasons",
1211 "job-uri",
1212 "job-uuid",
87e9bb55 1213 "materials-col-actual", /* IPP 3D */
db8b865d
MS
1214 "media-actual",
1215 "media-col-actual",
1216 "media-check-input-tray-actual",
1217 "multiple-document-handling-actual",
87e9bb55 1218 "multiple-object-handling-actual", /* IPP 3D */
db8b865d
MS
1219 "number-of-documents",
1220 "number-of-intervening-jobs",
1221 "number-up-actual",
1222 "orientation-requested-actual",
1223 "original-requesting-user-name",
1224 "output-bin-actual",
1225 "output-device-assigned",
1226 "overrides-actual",
1227 "page-delivery-actual",
1228 "page-order-received-actual",
1229 "page-ranges-actual",
87e9bb55 1230 "platform-temperature-actual", /* IPP 3D */
db8b865d 1231 "presentation-direction-number-up-actual",
87e9bb55
MS
1232 "print-accuracy-actual", /* IPP 3D */
1233 "print-base-actual", /* IPP 3D */
db8b865d
MS
1234 "print-color-mode-actual",
1235 "print-content-optimize-actual",
87e9bb55 1236 "print-objects-actual", /* IPP 3D */
db8b865d
MS
1237 "print-quality-actual",
1238 "print-rendering-intent-actual",
6961465f 1239 "print-scaling-actual", /* IPP Paid Printing */
87e9bb55 1240 "print-supports-actual", /* IPP 3D */
db8b865d
MS
1241 "printer-resolution-actual",
1242 "separator-sheets-actual",
1243 "sheet-collate-actual",
1244 "sheet-completed-copy-number",
1245 "sheet-completed-document-number",
1246 "sides-actual",
1247 "time-at-completed",
1248 "time-at-creation",
1249 "time-at-processing",
1250 "warnings-count",
1251 "x-image-position-actual",
1252 "x-image-shift-actual",
1253 "x-side1-image-shift-actual",
1254 "x-side2-image-shift-actual",
1255 "y-image-position-actual",
1256 "y-image-shift-actual",
1257 "y-side1-image-shift-actual",
1258 "y-side2-image-shift-actual"
1259 };
1260 static const char * const job_template[] =
1261 { /* job-template group */
87e9bb55 1262 "accuracy-units-supported", /* IPP 3D */
db8b865d
MS
1263 "confirmation-sheet-print", /* IPP FaxOut */
1264 "confirmation-sheet-print-default",
1265 "copies",
1266 "copies-default",
1267 "copies-supported",
1268 "cover-back",
1269 "cover-back-default",
1270 "cover-back-supported",
1271 "cover-front",
1272 "cover-front-default",
1273 "cover-front-supported",
1274 "cover-sheet-info", /* IPP FaxOut */
1275 "cover-sheet-info-default",
1276 "cover-sheet-info-supported",
1277 "destination-uri-schemes-supported",/* IPP FaxOut */
1278 "destination-uris", /* IPP FaxOut */
1279 "destination-uris-supported",
1280 "feed-orientation",
1281 "feed-orientation-default",
1282 "feed-orientation-supported",
1283 "finishings",
1284 "finishings-col",
1f717210 1285 "finishings-col-database",
db8b865d 1286 "finishings-col-default",
1f717210 1287 "finishings-col-ready",
db8b865d
MS
1288 "finishings-col-supported",
1289 "finishings-default",
1f717210 1290 "finishings-ready",
db8b865d
MS
1291 "finishings-supported",
1292 "font-name-requested",
1293 "font-name-requested-default",
1294 "font-name-requested-supported",
1295 "font-size-requested",
1296 "font-size-requested-default",
1297 "font-size-requested-supported",
1298 "force-front-side",
1299 "force-front-side-default",
1300 "force-front-side-supported",
1301 "imposition-template",
1302 "imposition-template-default",
1303 "imposition-template-supported",
1304 "insert-after-page-number-supported",
1305 "insert-count-supported",
1306 "insert-sheet",
1307 "insert-sheet-default",
1308 "insert-sheet-supported",
1309 "job-account-id",
1310 "job-account-id-default",
1311 "job-account-id-supported",
1312 "job-accounting-sheets"
1313 "job-accounting-sheets-default"
1314 "job-accounting-sheets-supported"
1315 "job-accounting-user-id",
1316 "job-accounting-user-id-default",
1317 "job-accounting-user-id-supported",
1318 "job-copies",
1319 "job-copies-default",
1320 "job-copies-supported",
1321 "job-cover-back",
1322 "job-cover-back-default",
1323 "job-cover-back-supported",
1324 "job-cover-front",
1325 "job-cover-front-default",
1326 "job-cover-front-supported",
1327 "job-delay-output-until",
1328 "job-delay-output-until-default",
1329 "job-delay-output-until-supported",
1330 "job-delay-output-until-time",
1331 "job-delay-output-until-time-default",
1332 "job-delay-output-until-time-supported",
1333 "job-error-action",
1334 "job-error-action-default",
1335 "job-error-action-supported",
1336 "job-error-sheet",
1337 "job-error-sheet-default",
1338 "job-error-sheet-supported",
1339 "job-finishings",
1340 "job-finishings-col",
1341 "job-finishings-col-default",
1342 "job-finishings-col-supported",
1343 "job-finishings-default",
1344 "job-finishings-supported",
1345 "job-hold-until",
1346 "job-hold-until-default",
1347 "job-hold-until-supported",
1348 "job-hold-until-time",
1349 "job-hold-until-time-default",
1350 "job-hold-until-time-supported",
1351 "job-message-to-operator",
1352 "job-message-to-operator-default",
1353 "job-message-to-operator-supported",
1354 "job-phone-number",
1355 "job-phone-number-default",
1356 "job-phone-number-supported",
1357 "job-priority",
1358 "job-priority-default",
1359 "job-priority-supported",
1360 "job-recipient-name",
1361 "job-recipient-name-default",
1362 "job-recipient-name-supported",
1363 "job-save-disposition",
1364 "job-save-disposition-default",
1365 "job-save-disposition-supported",
1366 "job-sheets",
1367 "job-sheets-col",
1368 "job-sheets-col-default",
1369 "job-sheets-col-supported",
1370 "job-sheets-default",
1371 "job-sheets-supported",
1372 "logo-uri-schemes-supported",
87e9bb55
MS
1373 "material-amount-units-supported", /* IPP 3D */
1374 "material-diameter-supported", /* IPP 3D */
1375 "material-purpose-supported", /* IPP 3D */
1376 "material-rate-supported", /* IPP 3D */
1377 "material-rate-units-supported", /* IPP 3D */
1378 "material-shell-thickness-supported",/* IPP 3D */
1379 "material-temperature-supported", /* IPP 3D */
1380 "material-type-supported", /* IPP 3D */
1381 "materials-col", /* IPP 3D */
1382 "materials-col-database", /* IPP 3D */
1383 "materials-col-default", /* IPP 3D */
1384 "materials-col-ready", /* IPP 3D */
1385 "materials-col-supported", /* IPP 3D */
1386 "max-materials-col-supported", /* IPP 3D */
db8b865d
MS
1387 "max-save-info-supported",
1388 "max-stitching-locations-supported",
1389 "media",
1390 "media-back-coating-supported",
1391 "media-bottom-margin-supported",
1392 "media-col",
1393 "media-col-default",
1f717210 1394 "media-col-ready",
db8b865d
MS
1395 "media-col-supported",
1396 "media-color-supported",
1397 "media-default",
1398 "media-front-coating-supported",
1399 "media-grain-supported",
1400 "media-hole-count-supported",
1401 "media-info-supported",
1402 "media-input-tray-check",
1403 "media-input-tray-check-default",
1404 "media-input-tray-check-supported",
1405 "media-key-supported",
1406 "media-left-margin-supported",
1407 "media-order-count-supported",
1408 "media-pre-printed-supported",
1f717210 1409 "media-ready",
db8b865d
MS
1410 "media-recycled-supported",
1411 "media-right-margin-supported",
1412 "media-size-supported",
1413 "media-source-supported",
1414 "media-supported",
1415 "media-thickness-supported",
1416 "media-top-margin-supported",
1417 "media-type-supported",
1418 "media-weight-metric-supported",
1419 "multiple-document-handling",
1420 "multiple-document-handling-default",
1421 "multiple-document-handling-supported",
87e9bb55
MS
1422 "multiple-object-handling", /* IPP 3D */
1423 "multiple-object-handling-default", /* IPP 3D */
1424 "multiple-object-handling-supported",/* IPP 3D */
db8b865d
MS
1425 "number-of-retries", /* IPP FaxOut */
1426 "number-of-retries-default",
1427 "number-of-retries-supported",
1428 "number-up",
1429 "number-up-default",
1430 "number-up-supported",
1431 "orientation-requested",
1432 "orientation-requested-default",
1433 "orientation-requested-supported",
1434 "output-bin",
1435 "output-bin-default",
1436 "output-bin-supported",
1437 "output-device",
1438 "output-device-default",
1439 "output-device-supported",
6961465f
MS
1440 "output-mode", /* CUPS extension */
1441 "output-mode-default", /* CUPS extension */
1442 "output-mode-supported", /* CUPS extension */
db8b865d
MS
1443 "overrides",
1444 "overrides-supported",
1445 "page-delivery",
1446 "page-delivery-default",
1447 "page-delivery-supported",
1448 "page-order-received",
1449 "page-order-received-default",
1450 "page-order-received-supported",
1451 "page-ranges",
1452 "page-ranges-supported",
1453 "pages-per-subset",
1454 "pages-per-subset-supported",
1455 "pdl-init-file",
1456 "pdl-init-file-default",
1457 "pdl-init-file-entry-supported",
1458 "pdl-init-file-location-supported",
1459 "pdl-init-file-name-subdirectory-supported",
1460 "pdl-init-file-name-supported",
1461 "pdl-init-file-supported",
87e9bb55
MS
1462 "platform-temperature", /* IPP 3D */
1463 "platform-temperature-default", /* IPP 3D */
1464 "platform-temperature-supported", /* IPP 3D */
db8b865d
MS
1465 "presentation-direction-number-up",
1466 "presentation-direction-number-up-default",
1467 "presentation-direction-number-up-supported",
87e9bb55
MS
1468 "print-accuracy", /* IPP 3D */
1469 "print-accuracy-default", /* IPP 3D */
1470 "print-accuracy-supported", /* IPP 3D */
1471 "print-base", /* IPP 3D */
1472 "print-base-default", /* IPP 3D */
1473 "print-base-supported", /* IPP 3D */
db8b865d
MS
1474 "print-color-mode",
1475 "print-color-mode-default",
1476 "print-color-mode-supported",
1477 "print-content-optimize",
1478 "print-content-optimize-default",
1479 "print-content-optimize-supported",
87e9bb55
MS
1480 "print-objects", /* IPP 3D */
1481 "print-objects-default", /* IPP 3D */
1482 "print-objects-supported", /* IPP 3D */
db8b865d
MS
1483 "print-quality",
1484 "print-quality-default",
1485 "print-quality-supported",
1486 "print-rendering-intent",
1487 "print-rendering-intent-default",
1488 "print-rendering-intent-supported",
6961465f
MS
1489 "print-scaling", /* IPP Paid Printing */
1490 "print-scaling-default", /* IPP Paid Printing */
1491 "print-scaling-supported", /* IPP Paid Printing */
87e9bb55
MS
1492 "print-supports", /* IPP 3D */
1493 "print-supports-default", /* IPP 3D */
1494 "print-supports-supported", /* IPP 3D */
db8b865d
MS
1495 "printer-resolution",
1496 "printer-resolution-default",
1497 "printer-resolution-supported",
1498 "proof-print",
1499 "proof-print-default",
1500 "proof-print-supported",
1501 "retry-interval", /* IPP FaxOut */
1502 "retry-interval-default",
1503 "retry-interval-supported",
1504 "retry-timeout", /* IPP FaxOut */
1505 "retry-timeout-default",
1506 "retry-timeout-supported",
1507 "save-disposition-supported",
1508 "save-document-format-default",
1509 "save-document-format-supported",
1510 "save-location-default",
1511 "save-location-supported",
1512 "save-name-subdirectory-supported",
1513 "save-name-supported",
1514 "separator-sheets",
1515 "separator-sheets-default",
1516 "separator-sheets-supported",
1517 "sheet-collate",
1518 "sheet-collate-default",
1519 "sheet-collate-supported",
1520 "sides",
1521 "sides-default",
1522 "sides-supported",
1523 "stitching-locations-supported",
1524 "stitching-offset-supported",
1525 "x-image-position",
1526 "x-image-position-default",
1527 "x-image-position-supported",
1528 "x-image-shift",
1529 "x-image-shift-default",
1530 "x-image-shift-supported",
1531 "x-side1-image-shift",
1532 "x-side1-image-shift-default",
1533 "x-side1-image-shift-supported",
1534 "x-side2-image-shift",
1535 "x-side2-image-shift-default",
1536 "x-side2-image-shift-supported",
1537 "y-image-position",
1538 "y-image-position-default",
1539 "y-image-position-supported",
1540 "y-image-shift",
1541 "y-image-shift-default",
1542 "y-image-shift-supported",
1543 "y-side1-image-shift",
1544 "y-side1-image-shift-default",
1545 "y-side1-image-shift-supported",
1546 "y-side2-image-shift",
1547 "y-side2-image-shift-default",
1548 "y-side2-image-shift-supported"
1549 };
1550 static const char * const printer_description[] =
1551 { /* printer-description group */
1552 "auth-info-required", /* CUPS extension */
1553 "charset-configured",
1554 "charset-supported",
1555 "color-supported",
1556 "compression-supported",
1557 "device-service-count",
1558 "device-uri", /* CUPS extension */
1559 "device-uuid",
1560 "document-charset-default",
1561 "document-charset-supported",
1562 "document-creation-attributes-supported",
1563 "document-digital-signature-default",
1564 "document-digital-signature-supported",
1565 "document-format-default",
1566 "document-format-details-default",
1567 "document-format-details-supported",
1568 "document-format-supported",
1569 "document-format-varying-attributes",
1570 "document-format-version-default",
1571 "document-format-version-supported",
1572 "document-natural-language-default",
1573 "document-natural-language-supported",
1574 "document-password-supported",
1575 "generated-natural-language-supported",
1576 "identify-actions-default",
1577 "identify-actions-supported",
1578 "input-source-supported",
1579 "ipp-features-supported",
1580 "ipp-versions-supported",
1581 "ippget-event-life",
1582 "job-authorization-uri-supported", /* CUPS extension */
1583 "job-constraints-supported",
1584 "job-creation-attributes-supported",
1585 "job-finishings-col-ready",
1586 "job-finishings-ready",
1587 "job-ids-supported",
1588 "job-impressions-supported",
1589 "job-k-limit", /* CUPS extension */
1590 "job-k-octets-supported",
1591 "job-media-sheets-supported",
1592 "job-page-limit", /* CUPS extension */
1593 "job-password-encryption-supported",
1594 "job-password-supported",
1f717210 1595 "job-presets-supported", /* IPP Presets */
db8b865d
MS
1596 "job-quota-period", /* CUPS extension */
1597 "job-resolvers-supported",
1598 "job-settable-attributes-supported",
1599 "job-spooling-supported",
1f717210 1600 "job-triggers-supported", /* IPP Presets */
c5b24bfa
MS
1601 "jpeg-k-octets-supported", /* CUPS extension */
1602 "jpeg-x-dimension-supported", /* CUPS extension */
1603 "jpeg-y-dimension-supported", /* CUPS extension */
1604 "landscape-orientation-requested-preferred",
1605 /* CUPS extension */
db8b865d
MS
1606 "marker-change-time", /* CUPS extension */
1607 "marker-colors", /* CUPS extension */
1608 "marker-high-levels", /* CUPS extension */
1609 "marker-levels", /* CUPS extension */
1610 "marker-low-levels", /* CUPS extension */
1611 "marker-message", /* CUPS extension */
1612 "marker-names", /* CUPS extension */
1613 "marker-types", /* CUPS extension */
db8b865d
MS
1614 "member-names", /* CUPS extension */
1615 "member-uris", /* CUPS extension */
1616 "multiple-destination-uris-supported",/* IPP FaxOut */
1617 "multiple-document-jobs-supported",
1618 "multiple-operation-time-out",
1619 "multiple-operation-time-out-action",
1620 "natural-language-configured",
1621 "operations-supported",
1622 "pages-per-minute",
1623 "pages-per-minute-color",
c5b24bfa 1624 "pdf-k-octets-supported", /* CUPS extension */
87e9bb55 1625 "pdf-features-supported", /* IPP 3D */
c5b24bfa 1626 "pdf-versions-supported", /* CUPS extension */
db8b865d
MS
1627 "pdl-override-supported",
1628 "port-monitor", /* CUPS extension */
1629 "port-monitor-supported", /* CUPS extension */
1630 "preferred-attributes-supported",
1631 "printer-alert",
1632 "printer-alert-description",
1633 "printer-charge-info",
1634 "printer-charge-info-uri",
1635 "printer-commands", /* CUPS extension */
1f717210
MS
1636 "printer-config-change-date-time",
1637 "printer-config-change-time",
db8b865d
MS
1638 "printer-current-time",
1639 "printer-detailed-status-messages",
1640 "printer-device-id",
1641 "printer-dns-sd-name", /* CUPS extension */
1642 "printer-driver-installer",
1643 "printer-fax-log-uri", /* IPP FaxOut */
1644 "printer-fax-modem-info", /* IPP FaxOut */
1645 "printer-fax-modem-name", /* IPP FaxOut */
1646 "printer-fax-modem-number", /* IPP FaxOut */
8f787fca
MS
1647 "printer-firmware-name", /* PWG 5110.1 */
1648 "printer-firmware-patches", /* PWG 5110.1 */
1649 "printer-firmware-string-version", /* PWG 5110.1 */
1650 "printer-firmware-version", /* PWG 5110.1 */
db8b865d
MS
1651 "printer-geo-location",
1652 "printer-get-attributes-supported",
1653 "printer-icc-profiles",
1654 "printer-icons",
cd3a0368 1655 "printer-id", /* CUPS extension */
db8b865d 1656 "printer-info",
8f787fca 1657 "printer-input-tray", /* IPP JPS3 */
db8b865d 1658 "printer-is-accepting-jobs",
6961465f 1659 "printer-is-shared", /* CUPS extension */
7ae00c35 1660 "printer-is-temporary", /* CUPS extension */
6961465f 1661 "printer-kind", /* IPP Paid Printing */
db8b865d
MS
1662 "printer-location",
1663 "printer-make-and-model",
1664 "printer-mandatory-job-attributes",
1665 "printer-message-date-time",
1666 "printer-message-from-operator",
1667 "printer-message-time",
1668 "printer-more-info",
1669 "printer-more-info-manufacturer",
1670 "printer-name",
6961465f 1671 "printer-native-formats",
db8b865d
MS
1672 "printer-organization",
1673 "printer-organizational-unit",
8f787fca 1674 "printer-output-tray", /* IPP JPS3 */
34a63bd9 1675 "printer-queue-id", /* CUPS extension */
db8b865d
MS
1676 "printer-settable-attributes-supported",
1677 "printer-state",
1678 "printer-state-change-date-time",
1679 "printer-state-change-time",
1680 "printer-state-message",
1681 "printer-state-reasons",
1682 "printer-supply",
1683 "printer-supply-description",
1684 "printer-supply-info-uri",
1685 "printer-type", /* CUPS extension */
1686 "printer-up-time",
1687 "printer-uri-supported",
1688 "printer-uuid",
1689 "printer-xri-supported",
1690 "pwg-raster-document-resolution-supported",
1691 "pwg-raster-document-sheet-back",
1692 "pwg-raster-document-type-supported",
1693 "queued-job-count",
1694 "reference-uri-schemes-supported",
1695 "repertoire-supported",
1696 "requesting-user-name-allowed", /* CUPS extension */
1697 "requesting-user-name-denied", /* CUPS extension */
1698 "requesting-user-uri-supported",
1699 "subordinate-printers-supported",
6961465f 1700 "urf-supported", /* CUPS extension */
db8b865d
MS
1701 "uri-authentication-supported",
1702 "uri-security-supported",
1703 "user-defined-value-supported",
1704 "which-jobs-supported",
1705 "xri-authentication-supported",
1706 "xri-security-supported",
1707 "xri-uri-scheme-supported"
1708 };
1709 static const char * const subscription_description[] =
1710 { /* subscription-description group */
1711 "notify-job-id",
1712 "notify-lease-expiration-time",
1713 "notify-printer-up-time",
1714 "notify-printer-uri",
1715 "notify-sequence-number",
1716 "notify-subscriber-user-name",
1717 "notify-subscriber-user-uri",
1718 "notify-subscription-id",
1719 "subscriptions-uuid"
1720 };
1721 static const char * const subscription_template[] =
1722 { /* subscription-template group */
1723 "notify-attributes",
1724 "notify-attributes-supported",
1725 "notify-charset",
1726 "notify-events",
1727 "notify-events-default",
1728 "notify-events-supported",
1729 "notify-lease-duration",
1730 "notify-lease-duration-default",
1731 "notify-lease-duration-supported",
1732 "notify-max-events-supported",
1733 "notify-natural-language",
1734 "notify-pull-method",
1735 "notify-pull-method-supported",
1736 "notify-recipient-uri",
1737 "notify-schemes-supported",
1738 "notify-time-interval",
1739 "notify-user-data"
1740 };
1741
1742
1743 /*
1744 * Get the requested-attributes attribute...
1745 */
1746
1747 if ((requested = ippFindAttribute(request, "requested-attributes",
1748 IPP_TAG_KEYWORD)) == NULL)
1749 {
1750 /*
1751 * The Get-Jobs operation defaults to "job-id" and "job-uri", all others
1752 * default to "all"...
1753 */
1754
cb7f98ee 1755 if (ippGetOperation(request) == IPP_OP_GET_JOBS)
db8b865d
MS
1756 {
1757 ra = cupsArrayNew((cups_array_func_t)strcmp, NULL);
1758 cupsArrayAdd(ra, "job-id");
1759 cupsArrayAdd(ra, "job-uri");
1760
1761 return (ra);
1762 }
1763 else
1764 return (NULL);
1765 }
1766
1767 /*
1768 * If the attribute contains a single "all" keyword, return NULL...
1769 */
1770
1771 count = ippGetCount(requested);
1772 if (count == 1 && !strcmp(ippGetString(requested, 0, NULL), "all"))
1773 return (NULL);
1774
1775 /*
1776 * Create an array using "strcmp" as the comparison function...
1777 */
1778
1779 ra = cupsArrayNew((cups_array_func_t)strcmp, NULL);
1780
1781 for (i = 0; i < count; i ++)
1782 {
1783 added = 0;
1784 value = ippGetString(requested, i, NULL);
1785
1786 if (!strcmp(value, "document-description") || !strcmp(value, "all"))
1787 {
1788 for (j = 0;
1789 j < (int)(sizeof(document_description) /
1790 sizeof(document_description[0]));
1791 j ++)
1792 cupsArrayAdd(ra, (void *)document_description[j]);
1793
1794 added = 1;
1795 }
1796
1797 if (!strcmp(value, "document-template") || !strcmp(value, "all"))
1798 {
1799 for (j = 0;
1800 j < (int)(sizeof(document_template) / sizeof(document_template[0]));
1801 j ++)
1802 cupsArrayAdd(ra, (void *)document_template[j]);
1803
1804 added = 1;
1805 }
1806
1807 if (!strcmp(value, "job-description") || !strcmp(value, "all"))
1808 {
1809 for (j = 0;
1810 j < (int)(sizeof(job_description) / sizeof(job_description[0]));
1811 j ++)
1812 cupsArrayAdd(ra, (void *)job_description[j]);
1813
1814 added = 1;
1815 }
1816
1817 if (!strcmp(value, "job-template") || !strcmp(value, "all"))
1818 {
1819 for (j = 0;
1820 j < (int)(sizeof(job_template) / sizeof(job_template[0]));
1821 j ++)
1822 cupsArrayAdd(ra, (void *)job_template[j]);
1823
1824 added = 1;
1825 }
1826
1827 if (!strcmp(value, "printer-description") || !strcmp(value, "all"))
1828 {
1829 for (j = 0;
1830 j < (int)(sizeof(printer_description) /
1831 sizeof(printer_description[0]));
1832 j ++)
1833 cupsArrayAdd(ra, (void *)printer_description[j]);
1834
1835 added = 1;
1836 }
1837
1838 if (!strcmp(value, "subscription-description") || !strcmp(value, "all"))
1839 {
1840 for (j = 0;
1841 j < (int)(sizeof(subscription_description) /
1842 sizeof(subscription_description[0]));
1843 j ++)
1844 cupsArrayAdd(ra, (void *)subscription_description[j]);
1845
1846 added = 1;
1847 }
1848
1849 if (!strcmp(value, "subscription-template") || !strcmp(value, "all"))
1850 {
1851 for (j = 0;
1852 j < (int)(sizeof(subscription_template) /
1853 sizeof(subscription_template[0]));
1854 j ++)
1855 cupsArrayAdd(ra, (void *)subscription_template[j]);
1856
1857 added = 1;
1858 }
1859
1860 if (!added)
1861 cupsArrayAdd(ra, (void *)value);
1862 }
1863
1864 return (ra);
1865}
1866
1867
a2326b5b
MS
1868/*
1869 * 'ippEnumString()' - Return a string corresponding to the enum value.
1870 */
1871
1872const char * /* O - Enum string */
1873ippEnumString(const char *attrname, /* I - Attribute name */
1874 int enumvalue) /* I - Enum value */
1875{
1876 _cups_globals_t *cg = _cupsGlobals(); /* Pointer to library globals */
1877
1878
1879 /*
1880 * Check for standard enum values...
1881 */
1882
1883 if (!strcmp(attrname, "document-state") &&
1884 enumvalue >= 3 &&
0fa6c7fa
MS
1885 enumvalue < (3 + (int)(sizeof(ipp_document_states) /
1886 sizeof(ipp_document_states[0]))))
a2326b5b 1887 return (ipp_document_states[enumvalue - 3]);
a469f8a5
MS
1888 else if (!strcmp(attrname, "finishings") ||
1889 !strcmp(attrname, "finishings-actual") ||
1890 !strcmp(attrname, "finishings-default") ||
1891 !strcmp(attrname, "finishings-ready") ||
6961465f
MS
1892 !strcmp(attrname, "finishings-supported") ||
1893 !strcmp(attrname, "job-finishings") ||
1894 !strcmp(attrname, "job-finishings-default") ||
1895 !strcmp(attrname, "job-finishings-supported"))
a469f8a5
MS
1896 {
1897 if (enumvalue >= 3 &&
0fa6c7fa
MS
1898 enumvalue < (3 + (int)(sizeof(ipp_finishings) /
1899 sizeof(ipp_finishings[0]))))
a469f8a5
MS
1900 return (ipp_finishings[enumvalue - 3]);
1901 else if (enumvalue >= 0x40000000 &&
1902 enumvalue <= (0x40000000 + (int)(sizeof(ipp_finishings_vendor) /
1903 sizeof(ipp_finishings_vendor[0]))))
1904 return (ipp_finishings_vendor[enumvalue - 0x40000000]);
1905 }
a2326b5b
MS
1906 else if ((!strcmp(attrname, "job-collation-type") ||
1907 !strcmp(attrname, "job-collation-type-actual")) &&
1908 enumvalue >= 3 &&
0fa6c7fa
MS
1909 enumvalue < (3 + (int)(sizeof(ipp_job_collation_types) /
1910 sizeof(ipp_job_collation_types[0]))))
a2326b5b
MS
1911 return (ipp_job_collation_types[enumvalue - 3]);
1912 else if (!strcmp(attrname, "job-state") &&
cb7f98ee
MS
1913 enumvalue >= IPP_JSTATE_PENDING && enumvalue <= IPP_JSTATE_COMPLETED)
1914 return (ipp_job_states[enumvalue - IPP_JSTATE_PENDING]);
a2326b5b
MS
1915 else if (!strcmp(attrname, "operations-supported"))
1916 return (ippOpString((ipp_op_t)enumvalue));
1917 else if ((!strcmp(attrname, "orientation-requested") ||
1918 !strcmp(attrname, "orientation-requested-actual") ||
1919 !strcmp(attrname, "orientation-requested-default") ||
1920 !strcmp(attrname, "orientation-requested-supported")) &&
1921 enumvalue >= 3 &&
0fa6c7fa
MS
1922 enumvalue < (3 + (int)(sizeof(ipp_orientation_requesteds) /
1923 sizeof(ipp_orientation_requesteds[0]))))
a2326b5b
MS
1924 return (ipp_orientation_requesteds[enumvalue - 3]);
1925 else if ((!strcmp(attrname, "print-quality") ||
1926 !strcmp(attrname, "print-quality-actual") ||
1927 !strcmp(attrname, "print-quality-default") ||
1928 !strcmp(attrname, "print-quality-supported")) &&
1929 enumvalue >= 3 &&
0fa6c7fa
MS
1930 enumvalue < (3 + (int)(sizeof(ipp_print_qualities) /
1931 sizeof(ipp_print_qualities[0]))))
a2326b5b
MS
1932 return (ipp_print_qualities[enumvalue - 3]);
1933 else if (!strcmp(attrname, "printer-state") &&
cb7f98ee
MS
1934 enumvalue >= IPP_PSTATE_IDLE && enumvalue <= IPP_PSTATE_STOPPED)
1935 return (ipp_printer_states[enumvalue - IPP_PSTATE_IDLE]);
a2326b5b
MS
1936
1937 /*
1938 * Not a standard enum value, just return the decimal equivalent...
1939 */
1940
1941 snprintf(cg->ipp_unknown, sizeof(cg->ipp_unknown), "%d", enumvalue);
1942 return (cg->ipp_unknown);
1943}
1944
1945
1946/*
1947 * 'ippEnumValue()' - Return the value associated with a given enum string.
1948 */
1949
1950int /* O - Enum value or -1 if unknown */
1951ippEnumValue(const char *attrname, /* I - Attribute name */
1952 const char *enumstring) /* I - Enum string */
1953{
1954 int i, /* Looping var */
1955 num_strings; /* Number of strings to compare */
1956 const char * const *strings; /* Strings to compare */
1957
1958
1959 /*
1960 * If the string is just a number, return it...
1961 */
1962
1963 if (isdigit(*enumstring & 255))
7e86f2f6 1964 return ((int)strtol(enumstring, NULL, 0));
a2326b5b
MS
1965
1966 /*
1967 * Otherwise look up the string...
1968 */
1969
1970 if (!strcmp(attrname, "document-state"))
1971 {
1972 num_strings = (int)(sizeof(ipp_document_states) / sizeof(ipp_document_states[0]));
1973 strings = ipp_document_states;
1974 }
1975 else if (!strcmp(attrname, "finishings") ||
1976 !strcmp(attrname, "finishings-actual") ||
1977 !strcmp(attrname, "finishings-default") ||
1978 !strcmp(attrname, "finishings-ready") ||
1979 !strcmp(attrname, "finishings-supported"))
1980 {
a469f8a5
MS
1981 for (i = 0;
1982 i < (int)(sizeof(ipp_finishings_vendor) /
1983 sizeof(ipp_finishings_vendor[0]));
1984 i ++)
1985 if (!strcmp(enumstring, ipp_finishings_vendor[i]))
1986 return (i + 0x40000000);
1987
a2326b5b
MS
1988 num_strings = (int)(sizeof(ipp_finishings) / sizeof(ipp_finishings[0]));
1989 strings = ipp_finishings;
1990 }
1991 else if (!strcmp(attrname, "job-collation-type") ||
1992 !strcmp(attrname, "job-collation-type-actual"))
1993 {
1994 num_strings = (int)(sizeof(ipp_job_collation_types) /
1995 sizeof(ipp_job_collation_types[0]));
1996 strings = ipp_job_collation_types;
1997 }
1998 else if (!strcmp(attrname, "job-state"))
1999 {
2000 num_strings = (int)(sizeof(ipp_job_states) / sizeof(ipp_job_states[0]));
2001 strings = ipp_job_states;
2002 }
2003 else if (!strcmp(attrname, "operations-supported"))
2004 return (ippOpValue(enumstring));
2005 else if (!strcmp(attrname, "orientation-requested") ||
2006 !strcmp(attrname, "orientation-requested-actual") ||
2007 !strcmp(attrname, "orientation-requested-default") ||
2008 !strcmp(attrname, "orientation-requested-supported"))
2009 {
2010 num_strings = (int)(sizeof(ipp_orientation_requesteds) /
2011 sizeof(ipp_orientation_requesteds[0]));
2012 strings = ipp_orientation_requesteds;
2013 }
2014 else if (!strcmp(attrname, "print-quality") ||
2015 !strcmp(attrname, "print-quality-actual") ||
2016 !strcmp(attrname, "print-quality-default") ||
2017 !strcmp(attrname, "print-quality-supported"))
2018 {
2019 num_strings = (int)(sizeof(ipp_print_qualities) / sizeof(ipp_print_qualities[0]));
2020 strings = ipp_print_qualities;
2021 }
2022 else if (!strcmp(attrname, "printer-state"))
2023 {
2024 num_strings = (int)(sizeof(ipp_printer_states) / sizeof(ipp_printer_states[0]));
2025 strings = ipp_printer_states;
2026 }
2027 else
2028 return (-1);
2029
2030 for (i = 0; i < num_strings; i ++)
2031 if (!strcmp(enumstring, strings[i]))
2032 return (i + 3);
2033
2034 return (-1);
2035}
2036
2037
ef416fc2 2038/*
2039 * 'ippErrorString()' - Return a name for the given status code.
2040 */
2041
2042const char * /* O - Text string */
2043ippErrorString(ipp_status_t error) /* I - Error status */
2044{
2045 _cups_globals_t *cg = _cupsGlobals(); /* Pointer to library globals */
2046
2047
2048 /*
2049 * See if the error code is a known value...
2050 */
2051
a469f8a5 2052 if (error >= IPP_STATUS_OK && error <= IPP_STATUS_OK_EVENTS_COMPLETE)
ef416fc2 2053 return (ipp_status_oks[error]);
a469f8a5 2054 else if (error == IPP_STATUS_REDIRECTION_OTHER_SITE)
ef416fc2 2055 return ("redirection-other-site");
a469f8a5 2056 else if (error == IPP_STATUS_CUPS_SEE_OTHER)
b94498cf 2057 return ("cups-see-other");
a469f8a5 2058 else if (error >= IPP_STATUS_ERROR_BAD_REQUEST &&
6b13fa61 2059 error <= IPP_STATUS_ERROR_ACCOUNT_AUTHORIZATION_FAILED)
a469f8a5
MS
2060 return (ipp_status_400s[error - IPP_STATUS_ERROR_BAD_REQUEST]);
2061 else if (error >= 0x480 &&
2062 error <= IPP_STATUS_ERROR_CUPS_ACCOUNT_AUTHORIZATION_FAILED)
2063 return (ipp_status_480s[error - 0x0480]);
2064 else if (error >= IPP_STATUS_ERROR_INTERNAL &&
2065 error <= IPP_STATUS_ERROR_TOO_MANY_DOCUMENTS)
2066 return (ipp_status_500s[error - IPP_STATUS_ERROR_INTERNAL]);
2067 else if (error >= IPP_STATUS_ERROR_CUPS_AUTHENTICATION_CANCELED &&
2068 error <= IPP_STATUS_ERROR_CUPS_UPGRADE_REQUIRED)
2069 return (ipp_status_1000s[error -
2070 IPP_STATUS_ERROR_CUPS_AUTHENTICATION_CANCELED]);
ef416fc2 2071
2072 /*
d7225fc2 2073 * No, build an "0xxxxx" error string...
ef416fc2 2074 */
2075
d7225fc2 2076 sprintf(cg->ipp_unknown, "0x%04x", error);
ef416fc2 2077
2078 return (cg->ipp_unknown);
2079}
2080
2081
2082/*
2083 * 'ippErrorValue()' - Return a status code for the given name.
2084 *
8072030b 2085 * @since CUPS 1.2/macOS 10.5@
ef416fc2 2086 */
2087
2088ipp_status_t /* O - IPP status code */
2089ippErrorValue(const char *name) /* I - Name */
2090{
7e86f2f6 2091 size_t i; /* Looping var */
ef416fc2 2092
2093
2094 for (i = 0; i < (sizeof(ipp_status_oks) / sizeof(ipp_status_oks[0])); i ++)
88f9aafc 2095 if (!_cups_strcasecmp(name, ipp_status_oks[i]))
ef416fc2 2096 return ((ipp_status_t)i);
2097
88f9aafc 2098 if (!_cups_strcasecmp(name, "redirection-other-site"))
a469f8a5 2099 return (IPP_STATUS_REDIRECTION_OTHER_SITE);
ef416fc2 2100
88f9aafc 2101 if (!_cups_strcasecmp(name, "cups-see-other"))
a469f8a5 2102 return (IPP_STATUS_CUPS_SEE_OTHER);
b94498cf 2103
ef416fc2 2104 for (i = 0; i < (sizeof(ipp_status_400s) / sizeof(ipp_status_400s[0])); i ++)
88f9aafc 2105 if (!_cups_strcasecmp(name, ipp_status_400s[i]))
ef416fc2 2106 return ((ipp_status_t)(i + 0x400));
2107
a469f8a5
MS
2108 for (i = 0; i < (sizeof(ipp_status_480s) / sizeof(ipp_status_480s[0])); i ++)
2109 if (!_cups_strcasecmp(name, ipp_status_480s[i]))
2110 return ((ipp_status_t)(i + 0x480));
2111
ef416fc2 2112 for (i = 0; i < (sizeof(ipp_status_500s) / sizeof(ipp_status_500s[0])); i ++)
88f9aafc 2113 if (!_cups_strcasecmp(name, ipp_status_500s[i]))
ef416fc2 2114 return ((ipp_status_t)(i + 0x500));
2115
7cf5915e 2116 for (i = 0; i < (sizeof(ipp_status_1000s) / sizeof(ipp_status_1000s[0])); i ++)
88f9aafc 2117 if (!_cups_strcasecmp(name, ipp_status_1000s[i]))
7cf5915e
MS
2118 return ((ipp_status_t)(i + 0x1000));
2119
ef416fc2 2120 return ((ipp_status_t)-1);
2121}
2122
2123
2124/*
2125 * 'ippOpString()' - Return a name for the given operation id.
2126 *
8072030b 2127 * @since CUPS 1.2/macOS 10.5@
ef416fc2 2128 */
2129
2130const char * /* O - Name */
2131ippOpString(ipp_op_t op) /* I - Operation ID */
2132{
2133 _cups_globals_t *cg = _cupsGlobals(); /* Pointer to library globals */
2134
2135
2136 /*
2137 * See if the operation ID is a known value...
2138 */
2139
4888dff9 2140 if (op >= IPP_OP_PRINT_JOB && op < (ipp_op_t)(sizeof(ipp_std_ops) / sizeof(ipp_std_ops[0])))
ef416fc2 2141 return (ipp_std_ops[op]);
a469f8a5 2142 else if (op == IPP_OP_PRIVATE)
ef416fc2 2143 return ("windows-ext");
a469f8a5 2144 else if (op >= IPP_OP_CUPS_GET_DEFAULT && op <= IPP_OP_CUPS_GET_PPD)
cb7f98ee 2145 return (ipp_cups_ops[op - IPP_OP_CUPS_GET_DEFAULT]);
c585706d
MS
2146 else if (op >= IPP_OP_CUPS_GET_DOCUMENT && op <= IPP_OP_CUPS_CREATE_LOCAL_PRINTER)
2147 return (ipp_cups_ops2[op - IPP_OP_CUPS_GET_DOCUMENT]);
ef416fc2 2148
2149 /*
d7225fc2 2150 * No, build an "0xxxxx" operation string...
ef416fc2 2151 */
2152
9b66acc5 2153 sprintf(cg->ipp_unknown, "0x%04x", op);
ef416fc2 2154
2155 return (cg->ipp_unknown);
2156}
2157
2158
2159/*
2160 * 'ippOpValue()' - Return an operation id for the given name.
2161 *
8072030b 2162 * @since CUPS 1.2/macOS 10.5@
ef416fc2 2163 */
2164
2165ipp_op_t /* O - Operation ID */
2166ippOpValue(const char *name) /* I - Textual name */
2167{
7e86f2f6 2168 size_t i; /* Looping var */
ef416fc2 2169
2170
9b66acc5
MS
2171 if (!strncmp(name, "0x", 2))
2172 return ((ipp_op_t)strtol(name + 2, NULL, 16));
2173
ef416fc2 2174 for (i = 0; i < (sizeof(ipp_std_ops) / sizeof(ipp_std_ops[0])); i ++)
88f9aafc 2175 if (!_cups_strcasecmp(name, ipp_std_ops[i]))
ef416fc2 2176 return ((ipp_op_t)i);
2177
88f9aafc 2178 if (!_cups_strcasecmp(name, "windows-ext"))
a469f8a5 2179 return (IPP_OP_PRIVATE);
ef416fc2 2180
2181 for (i = 0; i < (sizeof(ipp_cups_ops) / sizeof(ipp_cups_ops[0])); i ++)
88f9aafc 2182 if (!_cups_strcasecmp(name, ipp_cups_ops[i]))
ef416fc2 2183 return ((ipp_op_t)(i + 0x4001));
2184
2e4ff8af 2185 for (i = 0; i < (sizeof(ipp_cups_ops2) / sizeof(ipp_cups_ops2[0])); i ++)
88f9aafc 2186 if (!_cups_strcasecmp(name, ipp_cups_ops2[i]))
2e4ff8af
MS
2187 return ((ipp_op_t)(i + 0x4027));
2188
42404685
MS
2189 if (!_cups_strcasecmp(name, "Create-Job-Subscription"))
2190 return (IPP_OP_CREATE_JOB_SUBSCRIPTIONS);
2191
2192 if (!_cups_strcasecmp(name, "Create-Printer-Subscription"))
2193 return (IPP_OP_CREATE_PRINTER_SUBSCRIPTIONS);
2194
88f9aafc 2195 if (!_cups_strcasecmp(name, "CUPS-Add-Class"))
a469f8a5 2196 return (IPP_OP_CUPS_ADD_MODIFY_CLASS);
480ef0fe 2197
88f9aafc 2198 if (!_cups_strcasecmp(name, "CUPS-Add-Printer"))
a469f8a5 2199 return (IPP_OP_CUPS_ADD_MODIFY_PRINTER);
480ef0fe 2200
a469f8a5 2201 return (IPP_OP_CUPS_INVALID);
ef416fc2 2202}
2203
2204
2205/*
2206 * 'ippPort()' - Return the default IPP port number.
2207 */
2208
2209int /* O - Port number */
2210ippPort(void)
2211{
ef416fc2 2212 _cups_globals_t *cg = _cupsGlobals(); /* Pointer to library globals */
2213
2214
d09495fa 2215 DEBUG_puts("ippPort()");
2216
2217 if (!cg->ipp_port)
e07d4801 2218 _cupsSetDefaults();
d09495fa 2219
e07d4801 2220 DEBUG_printf(("1ippPort: Returning %d...", cg->ipp_port));
d09495fa 2221
ef416fc2 2222 return (cg->ipp_port);
2223}
2224
2225
2226/*
2227 * 'ippSetPort()' - Set the default port number.
2228 */
2229
2230void
2231ippSetPort(int p) /* I - Port number to use */
2232{
e07d4801 2233 DEBUG_printf(("ippSetPort(p=%d)", p));
d09495fa 2234
ef416fc2 2235 _cupsGlobals()->ipp_port = p;
2236}
2237
2238
d21dc0ed
MS
2239/*
2240 * 'ippStateString()' - Return the name corresponding to a state value.
2241 *
e1f19878 2242 * @since CUPS 2.0/OS 10.10@
d21dc0ed
MS
2243 */
2244
2245const char * /* O - State name */
2246ippStateString(ipp_state_t state) /* I - State value */
2247{
2248 if (state >= IPP_STATE_ERROR && state <= IPP_STATE_DATA)
2249 return (ipp_states[state - IPP_STATE_ERROR]);
2250 else
2251 return ("UNKNOWN");
2252}
2253
2254
ef416fc2 2255/*
1ff0402e
MS
2256 * 'ippTagString()' - Return the tag name corresponding to a tag value.
2257 *
65bebeac 2258 * The returned names are defined in RFC 8011 and the IANA IPP Registry.
1ff0402e 2259 *
8072030b 2260 * @since CUPS 1.4/macOS 10.6@
1ff0402e
MS
2261 */
2262
2263const char * /* O - Tag name */
2264ippTagString(ipp_tag_t tag) /* I - Tag value */
2265{
cb7f98ee 2266 tag &= IPP_TAG_CUPS_MASK;
ed6e7faf 2267
1ff0402e
MS
2268 if (tag < (ipp_tag_t)(sizeof(ipp_tag_names) / sizeof(ipp_tag_names[0])))
2269 return (ipp_tag_names[tag]);
2270 else
2271 return ("UNKNOWN");
2272}
2273
2274
2275/*
2276 * 'ippTagValue()' - Return the tag value corresponding to a tag name.
2277 *
65bebeac 2278 * The tag names are defined in RFC 8011 and the IANA IPP Registry.
1ff0402e 2279 *
8072030b 2280 * @since CUPS 1.4/macOS 10.6@
1ff0402e
MS
2281 */
2282
2283ipp_tag_t /* O - Tag value */
2284ippTagValue(const char *name) /* I - Tag name */
2285{
7e86f2f6 2286 size_t i; /* Looping var */
1ff0402e
MS
2287
2288
2289 for (i = 0; i < (sizeof(ipp_tag_names) / sizeof(ipp_tag_names[0])); i ++)
88f9aafc 2290 if (!_cups_strcasecmp(name, ipp_tag_names[i]))
1ff0402e
MS
2291 return ((ipp_tag_t)i);
2292
88f9aafc 2293 if (!_cups_strcasecmp(name, "operation"))
1ff0402e 2294 return (IPP_TAG_OPERATION);
88f9aafc 2295 else if (!_cups_strcasecmp(name, "job"))
1ff0402e 2296 return (IPP_TAG_JOB);
88f9aafc 2297 else if (!_cups_strcasecmp(name, "printer"))
1ff0402e 2298 return (IPP_TAG_PRINTER);
88f9aafc 2299 else if (!_cups_strcasecmp(name, "unsupported"))
5a6b583a 2300 return (IPP_TAG_UNSUPPORTED_GROUP);
88f9aafc 2301 else if (!_cups_strcasecmp(name, "subscription"))
1ff0402e 2302 return (IPP_TAG_SUBSCRIPTION);
88f9aafc 2303 else if (!_cups_strcasecmp(name, "event"))
5a6b583a 2304 return (IPP_TAG_EVENT_NOTIFICATION);
88f9aafc 2305 else if (!_cups_strcasecmp(name, "language"))
1ff0402e 2306 return (IPP_TAG_LANGUAGE);
88f9aafc 2307 else if (!_cups_strcasecmp(name, "mimetype"))
1ff0402e 2308 return (IPP_TAG_MIMETYPE);
88f9aafc 2309 else if (!_cups_strcasecmp(name, "name"))
1ff0402e 2310 return (IPP_TAG_NAME);
88f9aafc 2311 else if (!_cups_strcasecmp(name, "text"))
1ff0402e 2312 return (IPP_TAG_TEXT);
88f9aafc 2313 else if (!_cups_strcasecmp(name, "begCollection"))
5a6b583a 2314 return (IPP_TAG_BEGIN_COLLECTION);
1ff0402e
MS
2315 else
2316 return (IPP_TAG_ZERO);
2317}
2318
2319
2320/*
1106b00e
MS
2321 * 'ipp_col_string()' - Convert a collection to a string.
2322 */
2323
2324static size_t /* O - Number of bytes */
2325ipp_col_string(ipp_t *col, /* I - Collection attribute */
2326 char *buffer, /* I - Buffer or NULL */
2327 size_t bufsize) /* I - Size of buffer */
2328{
2329 char *bufptr, /* Position in buffer */
2330 *bufend, /* End of buffer */
9c80ffa2 2331 prefix = '{', /* Prefix character */
1106b00e
MS
2332 temp[256]; /* Temporary string */
2333 ipp_attribute_t *attr; /* Current member attribute */
2334
2335
2c69d462
MS
2336 if (!col)
2337 {
2338 if (buffer)
2339 *buffer = '\0';
2340
2341 return (0);
2342 }
2343
1106b00e
MS
2344 bufptr = buffer;
2345 bufend = buffer + bufsize - 1;
2346
1106b00e
MS
2347 for (attr = col->attrs; attr; attr = attr->next)
2348 {
2349 if (!attr->name)
2350 continue;
2351
9c80ffa2
MS
2352 if (buffer && bufptr < bufend)
2353 *bufptr = prefix;
2354 bufptr ++;
2355 prefix = ' ';
2356
1106b00e 2357 if (buffer && bufptr < bufend)
07623986 2358 bufptr += snprintf(bufptr, (size_t)(bufend - bufptr + 1), "%s=", attr->name);
1106b00e
MS
2359 else
2360 bufptr += strlen(attr->name) + 1;
2361
2362 if (buffer && bufptr < bufend)
7e86f2f6 2363 bufptr += ippAttributeString(attr, bufptr, (size_t)(bufend - bufptr + 1));
1106b00e 2364 else
a2326b5b 2365 bufptr += ippAttributeString(attr, temp, sizeof(temp));
1106b00e
MS
2366 }
2367
9c80ffa2
MS
2368 if (prefix == '{')
2369 {
2370 if (buffer && bufptr < bufend)
2371 *bufptr = prefix;
2372 bufptr ++;
2373 }
2374
1106b00e
MS
2375 if (buffer && bufptr < bufend)
2376 *bufptr = '}';
2377 bufptr ++;
2378
7e86f2f6 2379 return ((size_t)(bufptr - buffer));
1106b00e 2380}