]>
git.ipfire.org Git - thirdparty/cups.git/blob - cups/testipp.c
2 * "$Id: testipp.c 6649 2007-07-11 21:46:42Z mike $"
4 * IPP test program for CUPS.
6 * Copyright 2007-2010 by Apple Inc.
7 * Copyright 1997-2005 by Easy Software Products.
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/".
15 * This file is subject to the Apple OS-Developed Software exception.
19 * main() - Main entry.
20 * hex_dump() - Produce a hex dump of a buffer.
21 * print_attributes() - Print the attributes in a request...
22 * read_cb() - Read data from a buffer.
23 * write_cb() - Write data into a buffer.
27 * Include necessary headers...
31 #include <cups/file.h>
32 #include "string-private.h"
33 #include "ipp-private.h"
46 int rpos
; /* Current position in buffer */
47 ipp_uchar_t wbuffer
[8192]; /* Write buffer */
48 int wused
; /* Number of bytes in buffer */
49 ipp_uchar_t collection
[] = /* Collection buffer */
51 0x01, 0x01, /* IPP version */
52 0x00, 0x02, /* Print-Job operation */
53 0x00, 0x00, 0x00, 0x01, /* Request ID */
58 0x00, 0x12, /* Name length + name */
59 'a','t','t','r','i','b','u','t','e','s','-',
60 'c','h','a','r','s','e','t',
61 0x00, 0x05, /* Value length + value */
65 0x00, 0x1b, /* Name length + name */
66 'a','t','t','r','i','b','u','t','e','s','-',
67 'n','a','t','u','r','a','l','-','l','a','n',
69 0x00, 0x02, /* Value length + value */
73 0x00, 0x0b, /* Name length + name */
74 'p','r','i','n','t','e','r','-','u','r','i',
75 0x00, 0x1c, /* Value length + value */
76 'i','p','p',':','/','/','l','o','c','a','l',
77 'h','o','s','t','/','p','r','i','n','t','e',
78 'r','s','/','f','o','o',
80 IPP_TAG_JOB
, /* job group tag */
82 IPP_TAG_BEGIN_COLLECTION
, /* begCollection tag */
83 0x00, 0x09, /* Name length + name */
84 'm', 'e', 'd', 'i', 'a', '-', 'c', 'o', 'l',
85 0x00, 0x00, /* No value */
86 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
87 0x00, 0x00, /* No name */
88 0x00, 0x0a, /* Value length + value */
89 'm', 'e', 'd', 'i', 'a', '-', 's', 'i', 'z', 'e',
90 IPP_TAG_BEGIN_COLLECTION
, /* begCollection tag */
91 0x00, 0x00, /* Name length + name */
92 0x00, 0x00, /* No value */
93 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
94 0x00, 0x00, /* No name */
95 0x00, 0x0b, /* Value length + value */
96 'x', '-', 'd', 'i', 'm', 'e', 'n', 's', 'i', 'o', 'n',
97 IPP_TAG_INTEGER
, /* integer tag */
98 0x00, 0x00, /* No name */
99 0x00, 0x04, /* Value length + value */
100 0x00, 0x00, 0x54, 0x56,
101 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
102 0x00, 0x00, /* No name */
103 0x00, 0x0b, /* Value length + value */
104 'y', '-', 'd', 'i', 'm', 'e', 'n', 's', 'i', 'o', 'n',
105 IPP_TAG_INTEGER
, /* integer tag */
106 0x00, 0x00, /* No name */
107 0x00, 0x04, /* Value length + value */
108 0x00, 0x00, 0x6d, 0x24,
109 IPP_TAG_END_COLLECTION
, /* endCollection tag */
110 0x00, 0x00, /* No name */
111 0x00, 0x00, /* No value */
112 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
113 0x00, 0x00, /* No name */
114 0x00, 0x0b, /* Value length + value */
115 'm', 'e', 'd', 'i', 'a', '-', 'c', 'o', 'l', 'o', 'r',
116 IPP_TAG_KEYWORD
, /* keyword tag */
117 0x00, 0x00, /* No name */
118 0x00, 0x04, /* Value length + value */
121 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
122 0x00, 0x00, /* No name */
123 0x00, 0x0a, /* Value length + value */
124 'm', 'e', 'd', 'i', 'a', '-', 't', 'y', 'p', 'e',
125 IPP_TAG_KEYWORD
, /* keyword tag */
126 0x00, 0x00, /* No name */
127 0x00, 0x05, /* Value length + value */
128 'p', 'l', 'a', 'i', 'n',
129 IPP_TAG_END_COLLECTION
, /* endCollection tag */
130 0x00, 0x00, /* No name */
131 0x00, 0x00, /* No value */
133 IPP_TAG_BEGIN_COLLECTION
, /* begCollection tag */
134 0x00, 0x00, /* No name */
135 0x00, 0x00, /* No value */
136 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
137 0x00, 0x00, /* No name */
138 0x00, 0x0a, /* Value length + value */
139 'm', 'e', 'd', 'i', 'a', '-', 's', 'i', 'z', 'e',
140 IPP_TAG_BEGIN_COLLECTION
, /* begCollection tag */
141 0x00, 0x00, /* Name length + name */
142 0x00, 0x00, /* No value */
143 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
144 0x00, 0x00, /* No name */
145 0x00, 0x0b, /* Value length + value */
146 'x', '-', 'd', 'i', 'm', 'e', 'n', 's', 'i', 'o', 'n',
147 IPP_TAG_INTEGER
, /* integer tag */
148 0x00, 0x00, /* No name */
149 0x00, 0x04, /* Value length + value */
150 0x00, 0x00, 0x52, 0x08,
151 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
152 0x00, 0x00, /* No name */
153 0x00, 0x0b, /* Value length + value */
154 'y', '-', 'd', 'i', 'm', 'e', 'n', 's', 'i', 'o', 'n',
155 IPP_TAG_INTEGER
, /* integer tag */
156 0x00, 0x00, /* No name */
157 0x00, 0x04, /* Value length + value */
158 0x00, 0x00, 0x74, 0x04,
159 IPP_TAG_END_COLLECTION
, /* endCollection tag */
160 0x00, 0x00, /* No name */
161 0x00, 0x00, /* No value */
162 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
163 0x00, 0x00, /* No name */
164 0x00, 0x0b, /* Value length + value */
165 'm', 'e', 'd', 'i', 'a', '-', 'c', 'o', 'l', 'o', 'r',
166 IPP_TAG_KEYWORD
, /* keyword tag */
167 0x00, 0x00, /* No name */
168 0x00, 0x05, /* Value length + value */
169 'p', 'l', 'a', 'i', 'd',
171 IPP_TAG_MEMBERNAME
, /* memberAttrName tag */
172 0x00, 0x00, /* No name */
173 0x00, 0x0a, /* Value length + value */
174 'm', 'e', 'd', 'i', 'a', '-', 't', 'y', 'p', 'e',
175 IPP_TAG_KEYWORD
, /* keyword tag */
176 0x00, 0x00, /* No name */
177 0x00, 0x06, /* Value length + value */
178 'g', 'l', 'o', 's', 's', 'y',
179 IPP_TAG_END_COLLECTION
, /* endCollection tag */
180 0x00, 0x00, /* No name */
181 0x00, 0x00, /* No value */
183 IPP_TAG_END
/* end tag */
191 void hex_dump(const char *title
, ipp_uchar_t
*buffer
, int bytes
);
192 void print_attributes(ipp_t
*ipp
, int indent
);
193 ssize_t
read_cb(void *data
, ipp_uchar_t
*buffer
, size_t bytes
);
194 ssize_t
write_cb(void *data
, ipp_uchar_t
*buffer
, size_t bytes
);
198 * 'main()' - Main entry.
201 int /* O - Exit status */
202 main(int argc
, /* I - Number of command-line arguments */
203 char *argv
[]) /* I - Command-line arguments */
205 ipp_t
*cols
[2], /* Collections */
206 *size
; /* media-size collection */
207 ipp_t
*request
; /* Request */
208 ipp_attribute_t
*media_col
, /* media-col attribute */
209 *media_size
, /* media-size attribute */
210 *attr
; /* Other attribute */
211 ipp_state_t state
; /* State */
212 int length
; /* Length of data */
213 cups_file_t
*fp
; /* File pointer */
214 int i
; /* Looping var */
215 int status
; /* Status of tests (0 = success, 1 = fail) */
223 * Test request generation code...
226 printf("Create Sample Request: ");
229 request
->request
.op
.version
[0] = 0x01;
230 request
->request
.op
.version
[1] = 0x01;
231 request
->request
.op
.operation_id
= IPP_PRINT_JOB
;
232 request
->request
.op
.request_id
= 1;
234 ippAddString(request
, IPP_TAG_OPERATION
, IPP_TAG_CHARSET
,
235 "attributes-charset", NULL
, "utf-8");
236 ippAddString(request
, IPP_TAG_OPERATION
, IPP_TAG_LANGUAGE
,
237 "attributes-natural-language", NULL
, "en");
238 ippAddString(request
, IPP_TAG_OPERATION
, IPP_TAG_URI
,
239 "printer-uri", NULL
, "ipp://localhost/printers/foo");
243 ippAddInteger(size
, IPP_TAG_ZERO
, IPP_TAG_INTEGER
, "x-dimension", 21590);
244 ippAddInteger(size
, IPP_TAG_ZERO
, IPP_TAG_INTEGER
, "y-dimension", 27940);
245 ippAddCollection(cols
[0], IPP_TAG_JOB
, "media-size", size
);
247 ippAddString(cols
[0], IPP_TAG_JOB
, IPP_TAG_KEYWORD
, "media-color", NULL
,
249 ippAddString(cols
[0], IPP_TAG_JOB
, IPP_TAG_KEYWORD
, "media-type", NULL
,
254 ippAddInteger(size
, IPP_TAG_ZERO
, IPP_TAG_INTEGER
, "x-dimension", 21000);
255 ippAddInteger(size
, IPP_TAG_ZERO
, IPP_TAG_INTEGER
, "y-dimension", 29700);
256 ippAddCollection(cols
[1], IPP_TAG_JOB
, "media-size", size
);
258 ippAddString(cols
[1], IPP_TAG_JOB
, IPP_TAG_KEYWORD
, "media-color", NULL
,
260 ippAddString(cols
[1], IPP_TAG_JOB
, IPP_TAG_KEYWORD
, "media-type", NULL
,
263 ippAddCollections(request
, IPP_TAG_JOB
, "media-col", 2,
264 (const ipp_t
**)cols
);
268 length
= ippLength(request
);
269 if (length
!= sizeof(collection
))
271 printf("FAIL - wrong ippLength(), %d instead of %d bytes!\n",
272 length
, (int)sizeof(collection
));
282 printf("Write Sample to Memory: ");
285 while ((state
= ippWriteIO(wbuffer
, write_cb
, 1, NULL
,
286 request
)) != IPP_DATA
)
287 if (state
== IPP_ERROR
)
290 if (state
!= IPP_DATA
)
292 printf("FAIL - %d bytes written.\n", wused
);
295 else if (wused
!= sizeof(collection
))
297 printf("FAIL - wrote %d bytes, expected %d bytes!\n", wused
,
298 (int)sizeof(collection
));
299 hex_dump("Bytes Written", wbuffer
, wused
);
300 hex_dump("Baseline", collection
, sizeof(collection
));
303 else if (memcmp(wbuffer
, collection
, wused
))
305 for (i
= 0; i
< wused
; i
++)
306 if (wbuffer
[i
] != collection
[i
])
309 printf("FAIL - output does not match baseline at 0x%04x!\n", i
);
310 hex_dump("Bytes Written", wbuffer
, wused
);
311 hex_dump("Baseline", collection
, sizeof(collection
));
320 * Read the data back in and confirm...
323 printf("Read Sample from Memory: ");
328 while ((state
= ippReadIO(wbuffer
, read_cb
, 1, NULL
, request
)) != IPP_DATA
)
329 if (state
== IPP_ERROR
)
332 length
= ippLength(request
);
334 if (state
!= IPP_DATA
)
336 printf("FAIL - %d bytes read.\n", rpos
);
339 else if (rpos
!= wused
)
341 printf("FAIL - read %d bytes, expected %d bytes!\n", rpos
, wused
);
342 print_attributes(request
, 8);
345 else if (length
!= sizeof(collection
))
347 printf("FAIL - wrong ippLength(), %d instead of %d bytes!\n",
348 length
, (int)sizeof(collection
));
349 print_attributes(request
, 8);
355 fputs("ippFindAttribute(media-col): ", stdout
);
356 if ((media_col
= ippFindAttribute(request
, "media-col",
357 IPP_TAG_BEGIN_COLLECTION
)) == NULL
)
359 if ((media_col
= ippFindAttribute(request
, "media-col",
360 IPP_TAG_ZERO
)) == NULL
)
361 puts("FAIL (not found)");
363 printf("FAIL (wrong type - %s)\n", ippTagString(media_col
->value_tag
));
367 else if (media_col
->num_values
!= 2)
369 printf("FAIL (wrong count - %d)\n", media_col
->num_values
);
377 fputs("ippFindAttribute(media-size 1): ", stdout
);
378 if ((media_size
= ippFindAttribute(media_col
->values
[0].collection
,
380 IPP_TAG_BEGIN_COLLECTION
)) == NULL
)
382 if ((media_size
= ippFindAttribute(media_col
->values
[0].collection
,
384 IPP_TAG_ZERO
)) == NULL
)
385 puts("FAIL (not found)");
387 printf("FAIL (wrong type - %s)\n",
388 ippTagString(media_size
->value_tag
));
394 if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
395 "x-dimension", IPP_TAG_INTEGER
)) == NULL
)
397 if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
398 "x-dimension", IPP_TAG_ZERO
)) == NULL
)
399 puts("FAIL (missing x-dimension)");
401 printf("FAIL (wrong type for x-dimension - %s)\n",
402 ippTagString(attr
->value_tag
));
406 else if (attr
->values
[0].integer
!= 21590)
408 printf("FAIL (wrong value for x-dimension - %d)\n",
409 attr
->values
[0].integer
);
412 else if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
414 IPP_TAG_INTEGER
)) == NULL
)
416 if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
417 "y-dimension", IPP_TAG_ZERO
)) == NULL
)
418 puts("FAIL (missing y-dimension)");
420 printf("FAIL (wrong type for y-dimension - %s)\n",
421 ippTagString(attr
->value_tag
));
425 else if (attr
->values
[0].integer
!= 27940)
427 printf("FAIL (wrong value for y-dimension - %d)\n",
428 attr
->values
[0].integer
);
435 fputs("ippFindAttribute(media-size 2): ", stdout
);
436 if ((media_size
= ippFindAttribute(media_col
->values
[1].collection
,
438 IPP_TAG_BEGIN_COLLECTION
)) == NULL
)
440 if ((media_size
= ippFindAttribute(media_col
->values
[1].collection
,
442 IPP_TAG_ZERO
)) == NULL
)
443 puts("FAIL (not found)");
445 printf("FAIL (wrong type - %s)\n",
446 ippTagString(media_size
->value_tag
));
452 if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
454 IPP_TAG_INTEGER
)) == NULL
)
456 if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
457 "x-dimension", IPP_TAG_ZERO
)) == NULL
)
458 puts("FAIL (missing x-dimension)");
460 printf("FAIL (wrong type for x-dimension - %s)\n",
461 ippTagString(attr
->value_tag
));
465 else if (attr
->values
[0].integer
!= 21000)
467 printf("FAIL (wrong value for x-dimension - %d)\n",
468 attr
->values
[0].integer
);
471 else if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
473 IPP_TAG_INTEGER
)) == NULL
)
475 if ((attr
= ippFindAttribute(media_size
->values
[0].collection
,
476 "y-dimension", IPP_TAG_ZERO
)) == NULL
)
477 puts("FAIL (missing y-dimension)");
479 printf("FAIL (wrong type for y-dimension - %s)\n",
480 ippTagString(attr
->value_tag
));
484 else if (attr
->values
[0].integer
!= 29700)
486 printf("FAIL (wrong value for y-dimension - %d)\n",
487 attr
->values
[0].integer
);
498 * Test _ippFindOption() private API...
501 fputs("_ippFindOption(printer-type): ", stdout
);
502 if (_ippFindOption("printer-type"))
517 puts("Core IPP tests failed.");
519 puts("Core IPP tests passed.");
527 for (i
= 1; i
< argc
; i
++)
529 if ((fp
= cupsFileOpen(argv
[i
], "r")) == NULL
)
531 printf("Unable to open \"%s\" - %s\n", argv
[i
], strerror(errno
));
537 while ((state
= ippReadIO(fp
, (ipp_iocb_t
)cupsFileRead
, 1, NULL
,
538 request
)) == IPP_ATTRIBUTE
);
540 if (state
!= IPP_DATA
)
542 printf("Error reading IPP message from \"%s\"!\n", argv
[i
]);
547 printf("\n%s:\n", argv
[i
]);
548 print_attributes(request
, 4);
561 * 'hex_dump()' - Produce a hex dump of a buffer.
565 hex_dump(const char *title
, /* I - Title */
566 ipp_uchar_t
*buffer
, /* I - Buffer to dump */
567 int bytes
) /* I - Number of bytes */
569 int i
, j
; /* Looping vars */
570 int ch
; /* Current ASCII char */
574 * Show lines of 16 bytes at a time...
577 printf(" %s:\n", title
);
579 for (i
= 0; i
< bytes
; i
+= 16)
588 * Then up to 16 bytes in hex...
591 for (j
= 0; j
< 16; j
++)
593 printf(" %02x", buffer
[i
+ j
]);
598 * Then the ASCII representation of the bytes...
604 for (j
= 0; j
< 16 && (i
+ j
) < bytes
; j
++)
606 ch
= buffer
[i
+ j
] & 127;
608 if (ch
< ' ' || ch
== 127)
620 * 'print_attributes()' - Print the attributes in a request...
624 print_attributes(ipp_t
*ipp
, /* I - IPP request */
625 int indent
) /* I - Indentation */
627 int i
; /* Looping var */
628 ipp_tag_t group
; /* Current group */
629 ipp_attribute_t
*attr
; /* Current attribute */
630 ipp_value_t
*val
; /* Current value */
631 static const char * const tags
[] = /* Value/group tag strings */
634 "operation-attributes-tag",
635 "job-attributes-tag",
636 "end-of-attributes-tag",
637 "printer-attributes-tag",
638 "unsupported-attributes-tag",
639 "subscription-attributes-tag",
640 "event-attributes-tag",
698 "textWithoutLanguage",
699 "nameWithoutLanguage",
711 for (group
= IPP_TAG_ZERO
, attr
= ipp
->attrs
; attr
; attr
= attr
->next
)
713 if (!attr
->name
&& indent
== 4)
715 group
= IPP_TAG_ZERO
;
720 if (group
!= attr
->group_tag
)
722 group
= attr
->group_tag
;
724 printf("\n%*s%s:\n\n", indent
- 4, "", tags
[group
]);
727 printf("%*s%s (", indent
, "", attr
->name
? attr
->name
: "(null)");
728 if (attr
->num_values
> 1)
730 printf("%s):", tags
[attr
->value_tag
]);
732 switch (attr
->value_tag
)
735 case IPP_TAG_INTEGER
:
736 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
737 printf(" %d", val
->integer
);
741 case IPP_TAG_BOOLEAN
:
742 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
743 printf(" %s", val
->boolean
? "true" : "false");
748 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
749 printf(" %d-%d", val
->range
.lower
, val
->range
.upper
);
755 time_t vtime
; /* Date/Time value */
756 struct tm
*vdate
; /* Date info */
757 char vstring
[256]; /* Formatted time */
759 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
761 vtime
= ippDateToTime(val
->date
);
762 vdate
= localtime(&vtime
);
763 strftime(vstring
, sizeof(vstring
), "%c", vdate
);
764 printf(" (%s)", vstring
);
770 case IPP_TAG_RESOLUTION
:
771 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
772 printf(" %dx%d%s", val
->resolution
.xres
, val
->resolution
.yres
,
773 val
->resolution
.units
== IPP_RES_PER_INCH
? "dpi" : "dpc");
777 case IPP_TAG_STRING
:
778 case IPP_TAG_TEXTLANG
:
779 case IPP_TAG_NAMELANG
:
782 case IPP_TAG_KEYWORD
:
784 case IPP_TAG_URISCHEME
:
785 case IPP_TAG_CHARSET
:
786 case IPP_TAG_LANGUAGE
:
787 case IPP_TAG_MIMETYPE
:
788 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
789 printf(" \"%s\"", val
->string
.text
);
793 case IPP_TAG_BEGIN_COLLECTION
:
796 for (i
= 0, val
= attr
->values
; i
< attr
->num_values
; i
++, val
++)
800 print_attributes(val
->collection
, indent
+ 4);
805 printf("UNKNOWN (%d values)\n", attr
->num_values
);
813 * 'read_cb()' - Read data from a buffer.
816 ssize_t
/* O - Number of bytes read */
817 read_cb(void *data
, /* I - Data */
818 ipp_uchar_t
*buffer
, /* O - Buffer to read */
819 size_t bytes
) /* I - Number of bytes to read */
821 int count
; /* Number of bytes */
825 * Copy bytes from the data buffer to the read buffer...
828 for (count
= bytes
; count
> 0 && rpos
< wused
; count
--, rpos
++)
829 *buffer
++ = wbuffer
[rpos
];
832 * Return the number of bytes read...
835 return (bytes
- count
);
840 * 'write_cb()' - Write data into a buffer.
843 ssize_t
/* O - Number of bytes written */
844 write_cb(void *data
, /* I - Data */
845 ipp_uchar_t
*buffer
, /* I - Buffer to write */
846 size_t bytes
) /* I - Number of bytes to write */
848 int count
; /* Number of bytes */
852 * Loop until all bytes are written...
855 for (count
= bytes
; count
> 0 && wused
< sizeof(wbuffer
); count
--, wused
++)
856 wbuffer
[wused
] = *buffer
++;
859 * Return the number of bytes written...
862 return (bytes
- count
);
867 * End of "$Id: testipp.c 6649 2007-07-11 21:46:42Z mike $".