Till Kamppeter
2013-02-19 15:47:28 UTC
Hi,
to allow driverless printiung on network-connected printers, especially
from mobile devices I want to poll capability information from the
printer, where I want to support IPP printers with known PDLs, like
PostScript, PCL, IPP Everywhere, ... The program should then
automatically generate a PPD file or at least select the most suitable
generic one, depending on how much info the printer provides.
Using ipptool of CUPS I have no problem to poll info from IPP printers,
running
ipptool -X <IPP URI of the printer> cap.ipptool
cap.ipptool contains:
----------
IGNORE-ERRORS yes
{
NAME "Get printer attributes using Get-Printer-Attributes"
OPERATION Get-Printer-Attributes
GROUP operation-attributes-tag
ATTR charset attributes-charset utf-8
ATTR language attributes-natural-language en
ATTR uri printer-uri $uri
ATTR keyword requested-attributes
job-template,printer-description,printer-resolution-supported,print-color-mode-supported,print-quality-supported,media-supported,media-default,media-ready,output-bin-supported,finishings-supported,color-supported,sides-supported,number-up-supported,page-ranges-supported,all,media-col-database
}
----------
Now I want to poll with my own C program. It contains:
----------
char *uri;
http_t *http;
ipp_t *request, *response;
int i;
char scheme[10], userpass[1024], host_name[1024], resource[1024];
static const char * const requested_attrs[] =
{
"printer-description",
"document-format-supported",
"color-supported",
"pages-per-minute",
"pages-per-minute-color",
"media-supported",
"media-ready",
"media-default",
"media-type-supported",
"media-source-supported",
"media-col-database",
"sides-supported",
"sides-default",
"output-bin-supported",
"output-bin-default",
"finishings-supported",
"finishings-default",
"print-color-mode-supported",
"print-color-mode-default",
"output-mode-supported",
"output-mode-default",
"print-quality-supported",
"print-quality-default",
"printer-resolution-supported",
"printer-resolution-default",
"copies-supported",
"copies-default",
"all"
};
uri_status = httpSeparateURI(HTTP_URI_CODING_ALL, uri,
scheme, sizeof(scheme),
userpass, sizeof(userpass),
host_name, sizeof(host_name),
&(port),
resource, sizeof(resource));
if (uri_status != HTTP_URI_OK)
goto fail;
if ((http = httpConnect(host_name, port)) ==
NULL) {
goto fail;
}
request = ippNewRequest(IPP_GET_PRINTER_ATTRIBUTES);
/*ippSetRequestId(request, (CUPS_RAND() % 1000) * 137 + 1);*/
/*ippAddSeparator(request);*/
/*ippSetVersion(request, 1, 1);*/
/*ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_CHARSET,
"attributes-charset", NULL, "utf-8");*/
/*ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_LANGUAGE,
"attributes-natural-language", NULL, "en");*/
ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_URI,
"printer-uri", NULL, p->uri);
/*ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_NAME,
"requesting-user-name", NULL, cupsUser());*/
ippAddStrings(request, IPP_TAG_OPERATION, IPP_TAG_NAME,
"requested-attributes",
sizeof(requested_attrs) / sizeof(requested_attrs[0]),
NULL, requested_attrs);
/*int status = cupsSendRequest(http, request, resource,
ippLength(request));
response = cupsGetResponse(http, resource);*/
response = cupsDoRequest(http, request, resource);
if (response == NULL) {
httpClose(http);
goto fail;
}
printf("cups-browsed: Remote printer %s: %s (%s)\n",
p->uri, ippErrorString(cupsLastError()),
cupsLastErrorString());
ipp_attribute_t *attr;
attr = ippFirstAttribute(response);
while (attr) {
printf("Attr: %s\n",
ippGetName(attr));
for (i = 0; i < ippGetCount(attr); i ++)
printf("Value: %s\n",
ippGetString(attr, i, NULL));
attr = ippNextAttribute(response);
}
attr = ippFindAttribute(response,
"document-format-supported",
IPP_TAG_ZERO);
if (attr)
for (i = 0; i < ippGetCount(attr); i ++)
printf("Format: %s\n",
ippGetString(attr, i, NULL));
else
printf("Not found.\n");
/* Clean up */
ippDelete(response);
httpClose(http);
fail:
----------
With this I always get client-error-bad-request, independent whwther I
run it as shown here or whatever combination of lines which are
currently commented out I activated. I tried with several HP printers
(HP Color LaserJet CM3530 MFP, HP LaserJet P3005, HP OfficeJet Pro 8500
A910) and the Canon iR-ADV C5000s-B1, all with the same result, and all
work with ipptool. I also tried to remove and re-add items from the list
of requested attributes.
Note: I am using this code only for directly talking with network
printers, not for remote CUPS queues.
Any idea what I am doing wrong?
Till
to allow driverless printiung on network-connected printers, especially
from mobile devices I want to poll capability information from the
printer, where I want to support IPP printers with known PDLs, like
PostScript, PCL, IPP Everywhere, ... The program should then
automatically generate a PPD file or at least select the most suitable
generic one, depending on how much info the printer provides.
Using ipptool of CUPS I have no problem to poll info from IPP printers,
running
ipptool -X <IPP URI of the printer> cap.ipptool
cap.ipptool contains:
----------
IGNORE-ERRORS yes
{
NAME "Get printer attributes using Get-Printer-Attributes"
OPERATION Get-Printer-Attributes
GROUP operation-attributes-tag
ATTR charset attributes-charset utf-8
ATTR language attributes-natural-language en
ATTR uri printer-uri $uri
ATTR keyword requested-attributes
job-template,printer-description,printer-resolution-supported,print-color-mode-supported,print-quality-supported,media-supported,media-default,media-ready,output-bin-supported,finishings-supported,color-supported,sides-supported,number-up-supported,page-ranges-supported,all,media-col-database
}
----------
Now I want to poll with my own C program. It contains:
----------
char *uri;
http_t *http;
ipp_t *request, *response;
int i;
char scheme[10], userpass[1024], host_name[1024], resource[1024];
static const char * const requested_attrs[] =
{
"printer-description",
"document-format-supported",
"color-supported",
"pages-per-minute",
"pages-per-minute-color",
"media-supported",
"media-ready",
"media-default",
"media-type-supported",
"media-source-supported",
"media-col-database",
"sides-supported",
"sides-default",
"output-bin-supported",
"output-bin-default",
"finishings-supported",
"finishings-default",
"print-color-mode-supported",
"print-color-mode-default",
"output-mode-supported",
"output-mode-default",
"print-quality-supported",
"print-quality-default",
"printer-resolution-supported",
"printer-resolution-default",
"copies-supported",
"copies-default",
"all"
};
uri_status = httpSeparateURI(HTTP_URI_CODING_ALL, uri,
scheme, sizeof(scheme),
userpass, sizeof(userpass),
host_name, sizeof(host_name),
&(port),
resource, sizeof(resource));
if (uri_status != HTTP_URI_OK)
goto fail;
if ((http = httpConnect(host_name, port)) ==
NULL) {
goto fail;
}
request = ippNewRequest(IPP_GET_PRINTER_ATTRIBUTES);
/*ippSetRequestId(request, (CUPS_RAND() % 1000) * 137 + 1);*/
/*ippAddSeparator(request);*/
/*ippSetVersion(request, 1, 1);*/
/*ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_CHARSET,
"attributes-charset", NULL, "utf-8");*/
/*ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_LANGUAGE,
"attributes-natural-language", NULL, "en");*/
ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_URI,
"printer-uri", NULL, p->uri);
/*ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_NAME,
"requesting-user-name", NULL, cupsUser());*/
ippAddStrings(request, IPP_TAG_OPERATION, IPP_TAG_NAME,
"requested-attributes",
sizeof(requested_attrs) / sizeof(requested_attrs[0]),
NULL, requested_attrs);
/*int status = cupsSendRequest(http, request, resource,
ippLength(request));
response = cupsGetResponse(http, resource);*/
response = cupsDoRequest(http, request, resource);
if (response == NULL) {
httpClose(http);
goto fail;
}
printf("cups-browsed: Remote printer %s: %s (%s)\n",
p->uri, ippErrorString(cupsLastError()),
cupsLastErrorString());
ipp_attribute_t *attr;
attr = ippFirstAttribute(response);
while (attr) {
printf("Attr: %s\n",
ippGetName(attr));
for (i = 0; i < ippGetCount(attr); i ++)
printf("Value: %s\n",
ippGetString(attr, i, NULL));
attr = ippNextAttribute(response);
}
attr = ippFindAttribute(response,
"document-format-supported",
IPP_TAG_ZERO);
if (attr)
for (i = 0; i < ippGetCount(attr); i ++)
printf("Format: %s\n",
ippGetString(attr, i, NULL));
else
printf("Not found.\n");
/* Clean up */
ippDelete(response);
httpClose(http);
fail:
----------
With this I always get client-error-bad-request, independent whwther I
run it as shown here or whatever combination of lines which are
currently commented out I activated. I tried with several HP printers
(HP Color LaserJet CM3530 MFP, HP LaserJet P3005, HP OfficeJet Pro 8500
A910) and the Canon iR-ADV C5000s-B1, all with the same result, and all
work with ipptool. I also tried to remove and re-add items from the list
of requested attributes.
Note: I am using this code only for directly talking with network
printers, not for remote CUPS queues.
Any idea what I am doing wrong?
Till