]> git.ipfire.org Git - thirdparty/cups.git/blob - cups/testppd.c
Merge changes from CUPS 1.5svn-r9567
[thirdparty/cups.git] / cups / testppd.c
1 /*
2 * "$Id: testppd.c 7897 2008-09-02 19:33:19Z mike $"
3 *
4 * PPD test program for CUPS.
5 *
6 * Copyright 2007-2010 by Apple Inc.
7 * Copyright 1997-2006 by Easy Software Products.
8 *
9 * These coded instructions, statements, and computer programs are the
10 * property of Apple Inc. and are protected by Federal copyright
11 * law. Distribution and use rights are outlined in the file "LICENSE.txt"
12 * which should have been included with this file. If this file is
13 * file is missing or damaged, see the license at "http://www.cups.org/".
14 *
15 * This file is subject to the Apple OS-Developed Software exception.
16 *
17 * Contents:
18 *
19 * main() - Main entry.
20 */
21
22 /*
23 * Include necessary headers...
24 */
25
26 #include "cups-private.h"
27 #include <sys/stat.h>
28 #ifdef WIN32
29 # include <io.h>
30 #else
31 # include <unistd.h>
32 # include <fcntl.h>
33 #endif /* WIN32 */
34
35
36 /*
37 * Test data...
38 */
39
40 static const char *default_code =
41 "[{\n"
42 "%%BeginFeature: *InstalledDuplexer False\n"
43 "%%EndFeature\n"
44 "} stopped cleartomark\n"
45 "[{\n"
46 "%%BeginFeature: *PageRegion Letter\n"
47 "PageRegion=Letter\n"
48 "%%EndFeature\n"
49 "} stopped cleartomark\n"
50 "[{\n"
51 "%%BeginFeature: *InputSlot Tray\n"
52 "InputSlot=Tray\n"
53 "%%EndFeature\n"
54 "} stopped cleartomark\n"
55 "[{\n"
56 "%%BeginFeature: *MediaType Plain\n"
57 "MediaType=Plain\n"
58 "%%EndFeature\n"
59 "} stopped cleartomark\n"
60 "[{\n"
61 "%%BeginFeature: *IntOption None\n"
62 "%%EndFeature\n"
63 "} stopped cleartomark\n"
64 "[{\n"
65 "%%BeginFeature: *StringOption None\n"
66 "%%EndFeature\n"
67 "} stopped cleartomark\n";
68
69 static const char *custom_code =
70 "[{\n"
71 "%%BeginFeature: *InstalledDuplexer False\n"
72 "%%EndFeature\n"
73 "} stopped cleartomark\n"
74 "[{\n"
75 "%%BeginFeature: *InputSlot Tray\n"
76 "InputSlot=Tray\n"
77 "%%EndFeature\n"
78 "} stopped cleartomark\n"
79 "[{\n"
80 "%%BeginFeature: *MediaType Plain\n"
81 "MediaType=Plain\n"
82 "%%EndFeature\n"
83 "} stopped cleartomark\n"
84 "[{\n"
85 "%%BeginFeature: *IntOption None\n"
86 "%%EndFeature\n"
87 "} stopped cleartomark\n"
88 "[{\n"
89 "%%BeginFeature: *CustomStringOption True\n"
90 "(value\\0502\\051)\n"
91 "(value 1)\n"
92 "StringOption=Custom\n"
93 "%%EndFeature\n"
94 "} stopped cleartomark\n"
95 "[{\n"
96 "%%BeginFeature: *CustomPageSize True\n"
97 "400\n"
98 "500\n"
99 "0\n"
100 "0\n"
101 "0\n"
102 "PageSize=Custom\n"
103 "%%EndFeature\n"
104 "} stopped cleartomark\n";
105
106 static const char *default2_code =
107 "[{\n"
108 "%%BeginFeature: *InstalledDuplexer False\n"
109 "%%EndFeature\n"
110 "} stopped cleartomark\n"
111 "[{\n"
112 "%%BeginFeature: *InputSlot Tray\n"
113 "InputSlot=Tray\n"
114 "%%EndFeature\n"
115 "} stopped cleartomark\n"
116 "[{\n"
117 "%%BeginFeature: *Quality Normal\n"
118 "Quality=Normal\n"
119 "%%EndFeature\n"
120 "} stopped cleartomark\n"
121 "[{\n"
122 "%%BeginFeature: *IntOption None\n"
123 "%%EndFeature\n"
124 "} stopped cleartomark\n"
125 "[{\n"
126 "%%BeginFeature: *StringOption None\n"
127 "%%EndFeature\n"
128 "} stopped cleartomark\n";
129
130
131 /*
132 * 'main()' - Main entry.
133 */
134
135 int /* O - Exit status */
136 main(int argc, /* I - Number of command-line arguments */
137 char *argv[]) /* I - Command-line arguments */
138 {
139 int i; /* Looping var */
140 ppd_file_t *ppd; /* PPD file loaded from disk */
141 int status; /* Status of tests (0 = success, 1 = fail) */
142 int conflicts; /* Number of conflicts */
143 char *s; /* String */
144 char buffer[8192]; /* String buffer */
145 const char *text, /* Localized text */
146 *val; /* Option value */
147 int num_options; /* Number of options */
148 cups_option_t *options; /* Options */
149 ppd_size_t minsize, /* Minimum size */
150 maxsize, /* Maximum size */
151 *size; /* Current size */
152 ppd_attr_t *attr; /* Current attribute */
153
154
155 status = 0;
156
157 if (argc == 1)
158 {
159 /*
160 * Setup directories for locale stuff...
161 */
162
163 if (access("locale", 0))
164 {
165 mkdir("locale", 0777);
166 mkdir("locale/fr", 0777);
167 symlink("../../../locale/cups_fr.po", "locale/fr/cups_fr.po");
168 mkdir("locale/zh_TW", 0777);
169 symlink("../../../locale/cups_zh_TW.po", "locale/zh_TW/cups_zh_TW.po");
170 }
171
172 putenv("LOCALEDIR=locale");
173 putenv("SOFTWARE=CUPS");
174
175 /*
176 * Do tests with test.ppd...
177 */
178
179 fputs("ppdOpenFile(test.ppd): ", stdout);
180
181 if ((ppd = ppdOpenFile("test.ppd")) != NULL)
182 puts("PASS");
183 else
184 {
185 ppd_status_t err; /* Last error in file */
186 int line; /* Line number in file */
187
188
189 status ++;
190 err = ppdLastError(&line);
191
192 printf("FAIL (%s on line %d)\n", ppdErrorString(err), line);
193 }
194
195 fputs("ppdFindAttr(wildcard): ", stdout);
196 if ((attr = ppdFindAttr(ppd, "cupsTest", NULL)) == NULL)
197 {
198 status ++;
199 puts("FAIL (not found)");
200 }
201 else if (strcmp(attr->name, "cupsTest") || strcmp(attr->spec, "Foo"))
202 {
203 status ++;
204 printf("FAIL (got \"%s %s\")\n", attr->name, attr->spec);
205 }
206 else
207 puts("PASS");
208
209 fputs("ppdFindNextAttr(wildcard): ", stdout);
210 if ((attr = ppdFindNextAttr(ppd, "cupsTest", NULL)) == NULL)
211 {
212 status ++;
213 puts("FAIL (not found)");
214 }
215 else if (strcmp(attr->name, "cupsTest") || strcmp(attr->spec, "Bar"))
216 {
217 status ++;
218 printf("FAIL (got \"%s %s\")\n", attr->name, attr->spec);
219 }
220 else
221 puts("PASS");
222
223 fputs("ppdFindAttr(Foo): ", stdout);
224 if ((attr = ppdFindAttr(ppd, "cupsTest", "Foo")) == NULL)
225 {
226 status ++;
227 puts("FAIL (not found)");
228 }
229 else if (strcmp(attr->name, "cupsTest") || strcmp(attr->spec, "Foo"))
230 {
231 status ++;
232 printf("FAIL (got \"%s %s\")\n", attr->name, attr->spec);
233 }
234 else
235 puts("PASS");
236
237 fputs("ppdFindNextAttr(Foo): ", stdout);
238 if ((attr = ppdFindNextAttr(ppd, "cupsTest", "Foo")) != NULL)
239 {
240 status ++;
241 printf("FAIL (got \"%s %s\")\n", attr->name, attr->spec);
242 }
243 else
244 puts("PASS");
245
246 fputs("ppdMarkDefaults: ", stdout);
247 ppdMarkDefaults(ppd);
248
249 if ((conflicts = ppdConflicts(ppd)) == 0)
250 puts("PASS");
251 else
252 {
253 status ++;
254 printf("FAIL (%d conflicts)\n", conflicts);
255 }
256
257 fputs("ppdEmitString (defaults): ", stdout);
258 if ((s = ppdEmitString(ppd, PPD_ORDER_ANY, 0.0)) != NULL &&
259 !strcmp(s, default_code))
260 puts("PASS");
261 else
262 {
263 status ++;
264 printf("FAIL (%d bytes instead of %d)\n", s ? (int)strlen(s) : 0,
265 (int)strlen(default_code));
266
267 if (s)
268 puts(s);
269 }
270
271 if (s)
272 free(s);
273
274 fputs("ppdEmitString (custom size and string): ", stdout);
275 ppdMarkOption(ppd, "PageSize", "Custom.400x500");
276 ppdMarkOption(ppd, "StringOption", "{String1=\"value 1\" String2=value(2)}");
277
278 if ((s = ppdEmitString(ppd, PPD_ORDER_ANY, 0.0)) != NULL &&
279 !strcmp(s, custom_code))
280 puts("PASS");
281 else
282 {
283 status ++;
284 printf("FAIL (%d bytes instead of %d)\n", s ? (int)strlen(s) : 0,
285 (int)strlen(custom_code));
286
287 if (s)
288 puts(s);
289 }
290
291 if (s)
292 free(s);
293
294 /*
295 * Test constraints...
296 */
297
298 fputs("cupsGetConflicts(InputSlot=Envelope): ", stdout);
299 ppdMarkOption(ppd, "PageSize", "Letter");
300
301 num_options = cupsGetConflicts(ppd, "InputSlot", "Envelope", &options);
302 if (num_options != 2 ||
303 (val = cupsGetOption("PageRegion", num_options, options)) == NULL ||
304 strcasecmp(val, "Letter") ||
305 (val = cupsGetOption("PageSize", num_options, options)) == NULL ||
306 strcasecmp(val, "Letter"))
307 {
308 printf("FAIL (%d options:", num_options);
309 for (i = 0; i < num_options; i ++)
310 printf(" %s=%s", options[i].name, options[i].value);
311 puts(")");
312 status ++;
313 }
314 else
315 puts("PASS");
316
317 fputs("ppdConflicts(): ", stdout);
318 ppdMarkOption(ppd, "InputSlot", "Envelope");
319
320 if ((conflicts = ppdConflicts(ppd)) == 2)
321 puts("PASS (2)");
322 else
323 {
324 printf("FAIL (%d)\n", conflicts);
325 status ++;
326 }
327
328 fputs("cupsResolveConflicts(InputSlot=Envelope): ", stdout);
329 num_options = 0;
330 options = NULL;
331 if (!cupsResolveConflicts(ppd, "InputSlot", "Envelope", &num_options,
332 &options))
333 {
334 puts("FAIL (Unable to resolve)");
335 status ++;
336 }
337 else if (num_options != 2 ||
338 !cupsGetOption("PageSize", num_options, options))
339 {
340 printf("FAIL (%d options:", num_options);
341 for (i = 0; i < num_options; i ++)
342 printf(" %s=%s", options[i].name, options[i].value);
343 puts(")");
344 status ++;
345 }
346 else
347 puts("PASS (Resolved by changing PageSize)");
348
349 cupsFreeOptions(num_options, options);
350
351 fputs("cupsResolveConflicts(No option/choice): ", stdout);
352 num_options = 0;
353 options = NULL;
354 if (cupsResolveConflicts(ppd, NULL, NULL, &num_options, &options) &&
355 num_options == 1 && !strcasecmp(options[0].name, "InputSlot") &&
356 !strcasecmp(options[0].value, "Tray"))
357 puts("PASS (Resolved by changing InputSlot)");
358 else if (num_options > 0)
359 {
360 printf("FAIL (%d options:", num_options);
361 for (i = 0; i < num_options; i ++)
362 printf(" %s=%s", options[i].name, options[i].value);
363 puts(")");
364 status ++;
365 }
366 else
367 {
368 puts("FAIL (Unable to resolve)");
369 status ++;
370 }
371 cupsFreeOptions(num_options, options);
372
373 fputs("ppdInstallableConflict(): ", stdout);
374 if (ppdInstallableConflict(ppd, "Duplex", "DuplexNoTumble") &&
375 !ppdInstallableConflict(ppd, "Duplex", "None"))
376 puts("PASS");
377 else if (!ppdInstallableConflict(ppd, "Duplex", "DuplexNoTumble"))
378 {
379 puts("FAIL (Duplex=DuplexNoTumble did not conflict)");
380 status ++;
381 }
382 else
383 {
384 puts("FAIL (Duplex=None conflicted)");
385 status ++;
386 }
387
388 /*
389 * ppdPageSizeLimits
390 */
391
392 fputs("ppdPageSizeLimits: ", stdout);
393 if (ppdPageSizeLimits(ppd, &minsize, &maxsize))
394 {
395 if (minsize.width != 36 || minsize.length != 36 ||
396 maxsize.width != 1080 || maxsize.length != 86400)
397 {
398 printf("FAIL (got min=%.0fx%.0f, max=%.0fx%.0f, "
399 "expected min=36x36, max=1080x86400)\n", minsize.width,
400 minsize.length, maxsize.width, maxsize.length);
401 status ++;
402 }
403 else
404 puts("PASS");
405 }
406 else
407 {
408 puts("FAIL (returned 0)");
409 status ++;
410 }
411
412 /*
413 * cupsMarkOptions with PWG and IPP size names.
414 */
415
416 fputs("cupsMarkOptions(media=iso-a4): ", stdout);
417 num_options = cupsAddOption("media", "iso-a4", 0, &options);
418 cupsMarkOptions(ppd, num_options, options);
419 cupsFreeOptions(num_options, options);
420
421 size = ppdPageSize(ppd, NULL);
422 if (!size || strcmp(size->name, "A4"))
423 {
424 printf("FAIL (%s)\n", size ? size->name : "unknown");
425 status ++;
426 }
427 else
428 puts("PASS");
429
430 fputs("cupsMarkOptions(media=na_letter_8.5x11in): ", stdout);
431 num_options = cupsAddOption("media", "na_letter_8.5x11in", 0, &options);
432 cupsMarkOptions(ppd, num_options, options);
433 cupsFreeOptions(num_options, options);
434
435 size = ppdPageSize(ppd, NULL);
436 if (!size || strcmp(size->name, "Letter"))
437 {
438 printf("FAIL (%s)\n", size ? size->name : "unknown");
439 status ++;
440 }
441 else
442 puts("PASS");
443
444 fputs("cupsMarkOptions(media=A4): ", stdout);
445 num_options = cupsAddOption("media", "A4", 0, &options);
446 cupsMarkOptions(ppd, num_options, options);
447 cupsFreeOptions(num_options, options);
448
449 size = ppdPageSize(ppd, NULL);
450 if (!size || strcmp(size->name, "A4"))
451 {
452 printf("FAIL (%s)\n", size ? size->name : "unknown");
453 status ++;
454 }
455 else
456 puts("PASS");
457
458 /*
459 * Test localization...
460 */
461
462 fputs("ppdLocalizeIPPReason(text): ", stdout);
463 if (ppdLocalizeIPPReason(ppd, "foo", NULL, buffer, sizeof(buffer)) &&
464 !strcmp(buffer, "Foo Reason"))
465 puts("PASS");
466 else
467 {
468 status ++;
469 printf("FAIL (\"%s\" instead of \"Foo Reason\")\n", buffer);
470 }
471
472 fputs("ppdLocalizeIPPReason(http): ", stdout);
473 if (ppdLocalizeIPPReason(ppd, "foo", "http", buffer, sizeof(buffer)) &&
474 !strcmp(buffer, "http://foo/bar.html"))
475 puts("PASS");
476 else
477 {
478 status ++;
479 printf("FAIL (\"%s\" instead of \"http://foo/bar.html\")\n", buffer);
480 }
481
482 fputs("ppdLocalizeIPPReason(help): ", stdout);
483 if (ppdLocalizeIPPReason(ppd, "foo", "help", buffer, sizeof(buffer)) &&
484 !strcmp(buffer, "help:anchor='foo'%20bookID=Vendor%20Help"))
485 puts("PASS");
486 else
487 {
488 status ++;
489 printf("FAIL (\"%s\" instead of \"help:anchor='foo'%%20bookID=Vendor%%20Help\")\n", buffer);
490 }
491
492 fputs("ppdLocalizeIPPReason(file): ", stdout);
493 if (ppdLocalizeIPPReason(ppd, "foo", "file", buffer, sizeof(buffer)) &&
494 !strcmp(buffer, "/help/foo/bar.html"))
495 puts("PASS");
496 else
497 {
498 status ++;
499 printf("FAIL (\"%s\" instead of \"/help/foo/bar.html\")\n", buffer);
500 }
501
502 putenv("LANG=fr");
503 putenv("LC_ALL=fr");
504 putenv("LC_CTYPE=fr");
505 putenv("LC_MESSAGES=fr");
506
507 fputs("ppdLocalizeIPPReason(fr text): ", stdout);
508 if (ppdLocalizeIPPReason(ppd, "foo", NULL, buffer, sizeof(buffer)) &&
509 !strcmp(buffer, "La Long Foo Reason"))
510 puts("PASS");
511 else
512 {
513 status ++;
514 printf("FAIL (\"%s\" instead of \"La Long Foo Reason\")\n", buffer);
515 }
516
517 putenv("LANG=zh_TW");
518 putenv("LC_ALL=zh_TW");
519 putenv("LC_CTYPE=zh_TW");
520 putenv("LC_MESSAGES=zh_TW");
521
522 fputs("ppdLocalizeIPPReason(zh_TW text): ", stdout);
523 if (ppdLocalizeIPPReason(ppd, "foo", NULL, buffer, sizeof(buffer)) &&
524 !strcmp(buffer, "Number 1 Foo Reason"))
525 puts("PASS");
526 else
527 {
528 status ++;
529 printf("FAIL (\"%s\" instead of \"Number 1 Foo Reason\")\n", buffer);
530 }
531
532 /*
533 * cupsMarkerName localization...
534 */
535
536 putenv("LANG=en");
537 putenv("LC_ALL=en");
538 putenv("LC_CTYPE=en");
539 putenv("LC_MESSAGES=en");
540
541 fputs("ppdLocalizeMarkerName(bogus): ", stdout);
542
543 if ((text = ppdLocalizeMarkerName(ppd, "bogus")) != NULL)
544 {
545 status ++;
546 printf("FAIL (\"%s\" instead of NULL)\n", text);
547 }
548 else
549 puts("PASS");
550
551 fputs("ppdLocalizeMarkerName(cyan): ", stdout);
552
553 if ((text = ppdLocalizeMarkerName(ppd, "cyan")) != NULL &&
554 !strcmp(text, "Cyan Toner"))
555 puts("PASS");
556 else
557 {
558 status ++;
559 printf("FAIL (\"%s\" instead of \"Cyan Toner\")\n",
560 text ? text : "(null)");
561 }
562
563 putenv("LANG=fr");
564 putenv("LC_ALL=fr");
565 putenv("LC_CTYPE=fr");
566 putenv("LC_MESSAGES=fr");
567
568 fputs("ppdLocalizeMarkerName(fr cyan): ", stdout);
569 if ((text = ppdLocalizeMarkerName(ppd, "cyan")) != NULL &&
570 !strcmp(text, "La Toner Cyan"))
571 puts("PASS");
572 else
573 {
574 status ++;
575 printf("FAIL (\"%s\" instead of \"La Toner Cyan\")\n",
576 text ? text : "(null)");
577 }
578
579 putenv("LANG=zh_TW");
580 putenv("LC_ALL=zh_TW");
581 putenv("LC_CTYPE=zh_TW");
582 putenv("LC_MESSAGES=zh_TW");
583
584 fputs("ppdLocalizeMarkerName(zh_TW cyan): ", stdout);
585 if ((text = ppdLocalizeMarkerName(ppd, "cyan")) != NULL &&
586 !strcmp(text, "Number 1 Cyan Toner"))
587 puts("PASS");
588 else
589 {
590 status ++;
591 printf("FAIL (\"%s\" instead of \"Number 1 Cyan Toner\")\n",
592 text ? text : "(null)");
593 }
594
595 ppdClose(ppd);
596
597 /*
598 * Test new constraints...
599 */
600
601 fputs("ppdOpenFile(test2.ppd): ", stdout);
602
603 if ((ppd = ppdOpenFile("test2.ppd")) != NULL)
604 puts("PASS");
605 else
606 {
607 ppd_status_t err; /* Last error in file */
608 int line; /* Line number in file */
609
610
611 status ++;
612 err = ppdLastError(&line);
613
614 printf("FAIL (%s on line %d)\n", ppdErrorString(err), line);
615 }
616
617 fputs("ppdMarkDefaults: ", stdout);
618 ppdMarkDefaults(ppd);
619
620 if ((conflicts = ppdConflicts(ppd)) == 0)
621 puts("PASS");
622 else
623 {
624 status ++;
625 printf("FAIL (%d conflicts)\n", conflicts);
626 }
627
628 fputs("ppdEmitString (defaults): ", stdout);
629 if ((s = ppdEmitString(ppd, PPD_ORDER_ANY, 0.0)) != NULL &&
630 !strcmp(s, default2_code))
631 puts("PASS");
632 else
633 {
634 status ++;
635 printf("FAIL (%d bytes instead of %d)\n", s ? (int)strlen(s) : 0,
636 (int)strlen(default2_code));
637
638 if (s)
639 puts(s);
640 }
641
642 if (s)
643 free(s);
644
645 fputs("ppdConflicts(): ", stdout);
646 ppdMarkOption(ppd, "PageSize", "Env10");
647 ppdMarkOption(ppd, "InputSlot", "Envelope");
648 ppdMarkOption(ppd, "Quality", "Photo");
649
650 if ((conflicts = ppdConflicts(ppd)) == 1)
651 puts("PASS (1)");
652 else
653 {
654 printf("FAIL (%d)\n", conflicts);
655 status ++;
656 }
657
658 fputs("cupsResolveConflicts(Quality=Photo): ", stdout);
659 num_options = 0;
660 options = NULL;
661 if (cupsResolveConflicts(ppd, "Quality", "Photo", &num_options,
662 &options))
663 {
664 printf("FAIL (%d options:", num_options);
665 for (i = 0; i < num_options; i ++)
666 printf(" %s=%s", options[i].name, options[i].value);
667 puts(")");
668 status ++;
669 }
670 else
671 puts("PASS (Unable to resolve)");
672 cupsFreeOptions(num_options, options);
673
674 fputs("cupsResolveConflicts(No option/choice): ", stdout);
675 num_options = 0;
676 options = NULL;
677 if (cupsResolveConflicts(ppd, NULL, NULL, &num_options, &options) &&
678 num_options == 1 && !strcasecmp(options->name, "Quality") &&
679 !strcasecmp(options->value, "Normal"))
680 puts("PASS");
681 else if (num_options > 0)
682 {
683 printf("FAIL (%d options:", num_options);
684 for (i = 0; i < num_options; i ++)
685 printf(" %s=%s", options[i].name, options[i].value);
686 puts(")");
687 status ++;
688 }
689 else
690 {
691 puts("FAIL (Unable to resolve!)");
692 status ++;
693 }
694 cupsFreeOptions(num_options, options);
695
696 fputs("cupsResolveConflicts(loop test): ", stdout);
697 ppdMarkOption(ppd, "PageSize", "A4");
698 ppdMarkOption(ppd, "InputSlot", "Tray");
699 ppdMarkOption(ppd, "Quality", "Photo");
700 num_options = 0;
701 options = NULL;
702 if (!cupsResolveConflicts(ppd, NULL, NULL, &num_options, &options))
703 puts("PASS");
704 else if (num_options > 0)
705 {
706 printf("FAIL (%d options:", num_options);
707 for (i = 0; i < num_options; i ++)
708 printf(" %s=%s", options[i].name, options[i].value);
709 puts(")");
710 }
711 else
712 puts("FAIL (No conflicts!)");
713
714 fputs("ppdInstallableConflict(): ", stdout);
715 if (ppdInstallableConflict(ppd, "Duplex", "DuplexNoTumble") &&
716 !ppdInstallableConflict(ppd, "Duplex", "None"))
717 puts("PASS");
718 else if (!ppdInstallableConflict(ppd, "Duplex", "DuplexNoTumble"))
719 {
720 puts("FAIL (Duplex=DuplexNoTumble did not conflict)");
721 status ++;
722 }
723 else
724 {
725 puts("FAIL (Duplex=None conflicted)");
726 status ++;
727 }
728
729 /*
730 * ppdPageSizeLimits
731 */
732
733 ppdMarkDefaults(ppd);
734
735 fputs("ppdPageSizeLimits(default): ", stdout);
736 if (ppdPageSizeLimits(ppd, &minsize, &maxsize))
737 {
738 if (minsize.width != 36 || minsize.length != 36 ||
739 maxsize.width != 1080 || maxsize.length != 86400)
740 {
741 printf("FAIL (got min=%.0fx%.0f, max=%.0fx%.0f, "
742 "expected min=36x36, max=1080x86400)\n", minsize.width,
743 minsize.length, maxsize.width, maxsize.length);
744 status ++;
745 }
746 else
747 puts("PASS");
748 }
749 else
750 {
751 puts("FAIL (returned 0)");
752 status ++;
753 }
754
755 ppdMarkOption(ppd, "InputSlot", "Manual");
756
757 fputs("ppdPageSizeLimits(InputSlot=Manual): ", stdout);
758 if (ppdPageSizeLimits(ppd, &minsize, &maxsize))
759 {
760 if (minsize.width != 100 || minsize.length != 100 ||
761 maxsize.width != 1000 || maxsize.length != 1000)
762 {
763 printf("FAIL (got min=%.0fx%.0f, max=%.0fx%.0f, "
764 "expected min=100x100, max=1000x1000)\n", minsize.width,
765 minsize.length, maxsize.width, maxsize.length);
766 status ++;
767 }
768 else
769 puts("PASS");
770 }
771 else
772 {
773 puts("FAIL (returned 0)");
774 status ++;
775 }
776
777 ppdMarkOption(ppd, "Quality", "Photo");
778
779 fputs("ppdPageSizeLimits(Quality=Photo): ", stdout);
780 if (ppdPageSizeLimits(ppd, &minsize, &maxsize))
781 {
782 if (minsize.width != 200 || minsize.length != 200 ||
783 maxsize.width != 1000 || maxsize.length != 1000)
784 {
785 printf("FAIL (got min=%.0fx%.0f, max=%.0fx%.0f, "
786 "expected min=200x200, max=1000x1000)\n", minsize.width,
787 minsize.length, maxsize.width, maxsize.length);
788 status ++;
789 }
790 else
791 puts("PASS");
792 }
793 else
794 {
795 puts("FAIL (returned 0)");
796 status ++;
797 }
798
799 ppdMarkOption(ppd, "InputSlot", "Tray");
800
801 fputs("ppdPageSizeLimits(Quality=Photo): ", stdout);
802 if (ppdPageSizeLimits(ppd, &minsize, &maxsize))
803 {
804 if (minsize.width != 300 || minsize.length != 300 ||
805 maxsize.width != 1080 || maxsize.length != 86400)
806 {
807 printf("FAIL (got min=%.0fx%.0f, max=%.0fx%.0f, "
808 "expected min=300x300, max=1080x86400)\n", minsize.width,
809 minsize.length, maxsize.width, maxsize.length);
810 status ++;
811 }
812 else
813 puts("PASS");
814 }
815 else
816 {
817 puts("FAIL (returned 0)");
818 status ++;
819 }
820 }
821 else
822 {
823 const char *filename; /* PPD filename */
824 struct stat fileinfo; /* File information */
825
826
827 if (!strncmp(argv[1], "-d", 2))
828 {
829 const char *printer; /* Printer name */
830
831 if (argv[1][2])
832 printer = argv[1] + 2;
833 else if (argv[2])
834 printer = argv[2];
835 else
836 {
837 puts("Usage: ./testppd -d printer");
838 return (1);
839 }
840
841 filename = cupsGetPPD(printer);
842
843 if (!filename)
844 {
845 printf("%s: %s\n", printer, cupsLastErrorString());
846 return (1);
847 }
848 }
849 else
850 filename = argv[1];
851
852 if (lstat(filename, &fileinfo))
853 {
854 printf("%s: %s\n", filename, strerror(errno));
855 return (1);
856 }
857
858 if (S_ISLNK(fileinfo.st_mode))
859 {
860 char realfile[1024]; /* Real file path */
861 ssize_t realsize; /* Size of real file path */
862
863
864 if ((realsize = readlink(filename, realfile, sizeof(realfile) - 1)) < 0)
865 strcpy(realfile, "Unknown");
866 else
867 realfile[realsize] = '\0';
868
869 if (stat(realfile, &fileinfo))
870 printf("%s: symlink to \"%s\", %s\n", filename, realfile,
871 strerror(errno));
872 else
873 printf("%s: symlink to \"%s\", %ld bytes\n", filename, realfile,
874 (long)fileinfo.st_size);
875 }
876 else
877 printf("%s: regular file, %ld bytes\n", filename, (long)fileinfo.st_size);
878
879 if ((ppd = ppdOpenFile(filename)) == NULL)
880 {
881 ppd_status_t err; /* Last error in file */
882 int line; /* Line number in file */
883
884
885 status ++;
886 err = ppdLastError(&line);
887
888 printf("%s: %s on line %d\n", argv[1], ppdErrorString(err), line);
889 }
890 else
891 {
892 int j, k; /* Looping vars */
893 ppd_group_t *group; /* Option group */
894 ppd_option_t *option; /* Option */
895 ppd_coption_t *coption; /* Custom option */
896 ppd_cparam_t *cparam; /* Custom parameter */
897 ppd_const_t *c; /* UIConstraints */
898 char lang[255], /* LANG environment variable */
899 lc_all[255], /* LC_ALL environment variable */
900 lc_ctype[255], /* LC_CTYPE environment variable */
901 lc_messages[255];/* LC_MESSAGES environment variable */
902
903
904 if (argc > 2)
905 {
906 snprintf(lang, sizeof(lang), "LANG=%s", argv[2]);
907 putenv(lang);
908 snprintf(lc_all, sizeof(lc_all), "LC_ALL=%s", argv[2]);
909 putenv(lc_all);
910 snprintf(lc_ctype, sizeof(lc_ctype), "LC_CTYPE=%s", argv[2]);
911 putenv(lc_ctype);
912 snprintf(lc_messages, sizeof(lc_messages), "LC_MESSAGES=%s", argv[2]);
913 putenv(lc_messages);
914 }
915
916 ppdLocalize(ppd);
917 ppdMarkDefaults(ppd);
918
919 if (argc > 3)
920 {
921 text = ppdLocalizeIPPReason(ppd, argv[3], NULL, buffer, sizeof(buffer));
922 printf("ppdLocalizeIPPReason(%s)=%s\n", argv[3],
923 text ? text : "(null)");
924 return (text == NULL);
925 }
926
927 for (i = ppd->num_groups, group = ppd->groups;
928 i > 0;
929 i --, group ++)
930 {
931 printf("%s (%s):\n", group->name, group->text);
932
933 for (j = group->num_options, option = group->options;
934 j > 0;
935 j --, option ++)
936 {
937 printf(" %s (%s):\n", option->keyword, option->text);
938
939 for (k = 0; k < option->num_choices; k ++)
940 printf(" - %s%s (%s)\n",
941 option->choices[k].marked ? "*" : "",
942 option->choices[k].choice, option->choices[k].text);
943
944 if ((coption = ppdFindCustomOption(ppd, option->keyword)) != NULL)
945 {
946 for (cparam = (ppd_cparam_t *)cupsArrayFirst(coption->params);
947 cparam;
948 cparam = (ppd_cparam_t *)cupsArrayNext(coption->params))
949 {
950 switch (cparam->type)
951 {
952 case PPD_CUSTOM_CURVE :
953 printf(" %s(%s): PPD_CUSTOM_CURVE (%g to %g)\n",
954 cparam->name, cparam->text,
955 cparam->minimum.custom_curve,
956 cparam->maximum.custom_curve);
957 break;
958
959 case PPD_CUSTOM_INT :
960 printf(" %s(%s): PPD_CUSTOM_INT (%d to %d)\n",
961 cparam->name, cparam->text,
962 cparam->minimum.custom_int,
963 cparam->maximum.custom_int);
964 break;
965
966 case PPD_CUSTOM_INVCURVE :
967 printf(" %s(%s): PPD_CUSTOM_INVCURVE (%g to %g)\n",
968 cparam->name, cparam->text,
969 cparam->minimum.custom_invcurve,
970 cparam->maximum.custom_invcurve);
971 break;
972
973 case PPD_CUSTOM_PASSCODE :
974 printf(" %s(%s): PPD_CUSTOM_PASSCODE (%d to %d)\n",
975 cparam->name, cparam->text,
976 cparam->minimum.custom_passcode,
977 cparam->maximum.custom_passcode);
978 break;
979
980 case PPD_CUSTOM_PASSWORD :
981 printf(" %s(%s): PPD_CUSTOM_PASSWORD (%d to %d)\n",
982 cparam->name, cparam->text,
983 cparam->minimum.custom_password,
984 cparam->maximum.custom_password);
985 break;
986
987 case PPD_CUSTOM_POINTS :
988 printf(" %s(%s): PPD_CUSTOM_POINTS (%g to %g)\n",
989 cparam->name, cparam->text,
990 cparam->minimum.custom_points,
991 cparam->maximum.custom_points);
992 break;
993
994 case PPD_CUSTOM_REAL :
995 printf(" %s(%s): PPD_CUSTOM_REAL (%g to %g)\n",
996 cparam->name, cparam->text,
997 cparam->minimum.custom_real,
998 cparam->maximum.custom_real);
999 break;
1000
1001 case PPD_CUSTOM_STRING :
1002 printf(" %s(%s): PPD_CUSTOM_STRING (%d to %d)\n",
1003 cparam->name, cparam->text,
1004 cparam->minimum.custom_string,
1005 cparam->maximum.custom_string);
1006 break;
1007 }
1008 }
1009 }
1010 }
1011 }
1012
1013 puts("\nSizes:");
1014 for (i = ppd->num_sizes, size = ppd->sizes; i > 0; i --, size ++)
1015 printf(" %s = %gx%g, [%g %g %g %g]\n", size->name, size->width,
1016 size->length, size->left, size->bottom, size->right, size->top);
1017
1018 puts("\nConstraints:");
1019
1020 for (i = ppd->num_consts, c = ppd->consts; i > 0; i --, c ++)
1021 printf(" *UIConstraints: *%s %s *%s %s\n", c->option1, c->choice1,
1022 c->option2, c->choice2);
1023 if (ppd->num_consts == 0)
1024 puts(" NO CONSTRAINTS");
1025
1026 puts("\nFilters:");
1027
1028 for (i = 0; i < ppd->num_filters; i ++)
1029 printf(" %s\n", ppd->filters[i]);
1030
1031 if (ppd->num_filters == 0)
1032 puts(" NO FILTERS");
1033
1034 puts("\nAttributes:");
1035
1036 for (attr = (ppd_attr_t *)cupsArrayFirst(ppd->sorted_attrs);
1037 attr;
1038 attr = (ppd_attr_t *)cupsArrayNext(ppd->sorted_attrs))
1039 printf(" *%s %s/%s: \"%s\"\n", attr->name, attr->spec,
1040 attr->text, attr->value ? attr->value : "");
1041 }
1042
1043 if (!strncmp(argv[1], "-d", 2))
1044 unlink(filename);
1045 }
1046
1047 #ifdef __APPLE__
1048 if (getenv("MallocStackLogging") && getenv("MallocStackLoggingNoCompact"))
1049 {
1050 char command[1024]; /* malloc_history command */
1051
1052 snprintf(command, sizeof(command), "malloc_history %d -all_by_size",
1053 getpid());
1054 fflush(stdout);
1055 system(command);
1056 }
1057 #endif /* __APPLE__ */
1058
1059 ppdClose(ppd);
1060
1061 return (status);
1062 }
1063
1064
1065 /*
1066 * End of "$Id: testppd.c 7897 2008-09-02 19:33:19Z mike $".
1067 */