/*
- * "$Id$"
- *
* Printer routines for the CUPS scheduler.
*
- * Copyright 2007-2014 by Apple Inc.
- * Copyright 1997-2007 by Easy Software Products, all rights reserved.
+ * Copyright © 2007-2019 by Apple Inc.
+ * Copyright © 1997-2007 by Easy Software Products, all rights reserved.
*
- * These coded instructions, statements, and computer programs are the
- * property of Apple Inc. and are protected by Federal copyright
- * law. Distribution and use rights are outlined in the file "LICENSE.txt"
- * which should have been included with this file. If this file is
- * file is missing or damaged, see the license at "http://www.cups.org/".
+ * Licensed under Apache License v2.0. See the file "LICENSE" for more
+ * information.
*/
/*
static void delete_printer_filters(cupsd_printer_t *p);
static void dirty_printer(cupsd_printer_t *p);
static void load_ppd(cupsd_printer_t *p);
-static void log_ipp_conformance(cupsd_printer_t *p, const char *reason);
-static ipp_t *new_media_col(_pwg_size_t *size, const char *source,
- const char *type);
+static ipp_t *new_media_col(pwg_size_t *size);
static void write_xml_string(cups_file_t *fp, const char *s);
return (NULL);
}
+ _cupsRWInit(&p->lock);
+
cupsdSetString(&p->name, name);
cupsdSetString(&p->info, name);
cupsdSetString(&p->hostname, ServerName);
uuid, sizeof(uuid)));
cupsdSetDeviceURI(p, "file:///dev/null");
- p->state = IPP_PRINTER_STOPPED;
- p->state_time = time(NULL);
- p->accepting = 0;
- p->shared = DefaultShared;
- p->filetype = mimeAddType(MimeDatabase, "printer", name);
+ p->config_time = time(NULL);
+ p->state = IPP_PRINTER_STOPPED;
+ p->state_time = time(NULL);
+ p->accepting = 0;
+ p->shared = DefaultShared;
+ p->filetype = mimeAddType(MimeDatabase, "printer", name);
cupsdSetString(&p->job_sheets[0], "none");
cupsdSetString(&p->job_sheets[1], "none");
struct statfs spoolinfo; /* FS info for spool directory */
double spoolsize; /* FS size */
#endif /* HAVE_STATVFS */
- static const int nups[] = /* number-up-supported values */
+ static const char * const page_delivery[] =
+ { /* page-delivery-supported values */
+ "reverse-order",
+ "same-order"
+ };
+ static const char * const print_scaling[] =
+ { /* print-scaling-supported values */
+ "auto",
+ "auto-fit",
+ "fill",
+ "fit",
+ "none"
+ };
+ static const int number_up[] = /* number-up-supported values */
{ 1, 2, 4, 6, 9, 16 };
+ static const char * const number_up_layout[] =
+ { /* number-up-layout-supported values */
+ "btlr",
+ "btrl",
+ "lrbt",
+ "lrtb",
+ "rlbt",
+ "rltb",
+ "tblr",
+ "tbrl"
+ };
static const int orients[4] =/* orientation-requested-supported values */
{
IPP_PORTRAIT,
"third-shift",
"weekend"
};
+ static const char * const features[] =/* ipp-features-supported values */
+ {
+ "subscription-object"
+ };
static const char * const versions[] =/* ipp-versions-supported values */
{
"1.0",
};
static const int ops[] = /* operations-supported values */
{
- IPP_PRINT_JOB,
- IPP_VALIDATE_JOB,
- IPP_CREATE_JOB,
- IPP_SEND_DOCUMENT,
- IPP_CANCEL_JOB,
- IPP_GET_JOB_ATTRIBUTES,
- IPP_GET_JOBS,
- IPP_GET_PRINTER_ATTRIBUTES,
- IPP_HOLD_JOB,
- IPP_RELEASE_JOB,
- IPP_RESTART_JOB,
- IPP_PAUSE_PRINTER,
- IPP_RESUME_PRINTER,
- IPP_PURGE_JOBS,
- IPP_SET_PRINTER_ATTRIBUTES,
- IPP_SET_JOB_ATTRIBUTES,
- IPP_GET_PRINTER_SUPPORTED_VALUES,
- IPP_CREATE_PRINTER_SUBSCRIPTION,
- IPP_CREATE_JOB_SUBSCRIPTION,
- IPP_GET_SUBSCRIPTION_ATTRIBUTES,
- IPP_GET_SUBSCRIPTIONS,
- IPP_RENEW_SUBSCRIPTION,
- IPP_CANCEL_SUBSCRIPTION,
- IPP_GET_NOTIFICATIONS,
- IPP_ENABLE_PRINTER,
- IPP_DISABLE_PRINTER,
- IPP_HOLD_NEW_JOBS,
- IPP_RELEASE_HELD_NEW_JOBS,
- IPP_CANCEL_JOBS,
- IPP_CANCEL_MY_JOBS,
- IPP_CLOSE_JOB,
- CUPS_GET_DEFAULT,
- CUPS_GET_PRINTERS,
- CUPS_ADD_PRINTER,
- CUPS_DELETE_PRINTER,
- CUPS_GET_CLASSES,
- CUPS_ADD_CLASS,
- CUPS_DELETE_CLASS,
- CUPS_ACCEPT_JOBS,
- CUPS_REJECT_JOBS,
- CUPS_SET_DEFAULT,
- CUPS_GET_DEVICES,
- CUPS_GET_PPDS,
- CUPS_MOVE_JOB,
- CUPS_AUTHENTICATE_JOB,
- CUPS_GET_PPD,
- CUPS_GET_DOCUMENT,
- IPP_RESTART_JOB
+ IPP_OP_PRINT_JOB,
+ IPP_OP_VALIDATE_JOB,
+ IPP_OP_CREATE_JOB,
+ IPP_OP_SEND_DOCUMENT,
+ IPP_OP_CANCEL_JOB,
+ IPP_OP_GET_JOB_ATTRIBUTES,
+ IPP_OP_GET_JOBS,
+ IPP_OP_GET_PRINTER_ATTRIBUTES,
+ IPP_OP_HOLD_JOB,
+ IPP_OP_RELEASE_JOB,
+ IPP_OP_PAUSE_PRINTER,
+ IPP_OP_RESUME_PRINTER,
+ IPP_OP_PURGE_JOBS,
+ IPP_OP_SET_PRINTER_ATTRIBUTES,
+ IPP_OP_SET_JOB_ATTRIBUTES,
+ IPP_OP_GET_PRINTER_SUPPORTED_VALUES,
+ IPP_OP_CREATE_PRINTER_SUBSCRIPTIONS,
+ IPP_OP_CREATE_JOB_SUBSCRIPTIONS,
+ IPP_OP_GET_SUBSCRIPTION_ATTRIBUTES,
+ IPP_OP_GET_SUBSCRIPTIONS,
+ IPP_OP_RENEW_SUBSCRIPTION,
+ IPP_OP_CANCEL_SUBSCRIPTION,
+ IPP_OP_GET_NOTIFICATIONS,
+ IPP_OP_ENABLE_PRINTER,
+ IPP_OP_DISABLE_PRINTER,
+ IPP_OP_HOLD_NEW_JOBS,
+ IPP_OP_RELEASE_HELD_NEW_JOBS,
+ IPP_OP_CANCEL_JOBS,
+ IPP_OP_CANCEL_MY_JOBS,
+ IPP_OP_CLOSE_JOB,
+ IPP_OP_CUPS_GET_DEFAULT,
+ IPP_OP_CUPS_GET_PRINTERS,
+ IPP_OP_CUPS_ADD_MODIFY_PRINTER,
+ IPP_OP_CUPS_DELETE_PRINTER,
+ IPP_OP_CUPS_GET_CLASSES,
+ IPP_OP_CUPS_ADD_MODIFY_CLASS,
+ IPP_OP_CUPS_DELETE_CLASS,
+ IPP_OP_CUPS_ACCEPT_JOBS,
+ IPP_OP_CUPS_REJECT_JOBS,
+ IPP_OP_CUPS_SET_DEFAULT,
+ IPP_OP_CUPS_GET_DEVICES,
+ IPP_OP_CUPS_GET_PPDS,
+ IPP_OP_CUPS_MOVE_JOB,
+ IPP_OP_CUPS_AUTHENTICATE_JOB,
+ IPP_OP_CUPS_GET_PPD,
+ IPP_OP_CUPS_GET_DOCUMENT,
+ IPP_OP_RESTART_JOB
};
static const char * const charsets[] =/* charset-supported values */
{
{ /* job-creation-attributes-supported */
"copies",
"finishings",
+ "finishings-col",
"ipp-attribute-fidelity",
"job-hold-until",
"job-name",
"media-col",
"multiple-document-handling",
"number-up",
- "output-bin",
+ "number-up-layout",
"orientation-requested",
+ "output-bin",
+ "page-delivery",
"page-ranges",
"print-color-mode",
"print-quality",
+ "print-scaling",
"printer-resolution",
"sides"
};
};
static const char * const printer_settable[] =
{ /* printer-settable-attributes-supported */
+ "printer-geo-location",
"printer-info",
- "printer-location"
+ "printer-location",
+ "printer-organization",
+ "printer-organizational-unit"
};
static const char * const which_jobs[] =
{ /* which-jobs-supported values */
ippAddString(CommonData, IPP_TAG_PRINTER, IPP_TAG_LANGUAGE,
"generated-natural-language-supported", NULL, DefaultLanguage);
+ /* ipp-features-supported */
+ ippAddStrings(CommonData, IPP_TAG_PRINTER, IPP_CONST_TAG(IPP_TAG_KEYWORD), "ipp-features-supported", sizeof(features) / sizeof(features[0]), NULL, features);
+
/* ipp-versions-supported */
ippAddStrings(CommonData, IPP_TAG_PRINTER, IPP_TAG_KEYWORD | IPP_TAG_COPY,
"ipp-versions-supported", sizeof(versions) / sizeof(versions[0]),
ippAddInteger(CommonData, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
"multiple-operation-time-out", MultipleOperationTimeout);
+ /* multiple-operation-time-out-action */
+ ippAddString(CommonData, IPP_TAG_PRINTER, IPP_CONST_TAG(IPP_TAG_KEYWORD), "multiple-operation-time-out-action", NULL, "process-job");
+
/* natural-language-configured (no IPP_TAG_COPY) */
ippAddString(CommonData, IPP_TAG_PRINTER, IPP_TAG_LANGUAGE,
"natural-language-configured", NULL, DefaultLanguage);
/* number-up-supported */
ippAddIntegers(CommonData, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "number-up-supported", sizeof(nups) / sizeof(nups[0]), nups);
+ "number-up-supported", sizeof(number_up) / sizeof(number_up[0]), number_up);
+
+ /* number-up-layout-supported */
+ ippAddStrings(CommonData, IPP_TAG_PRINTER, IPP_CONST_TAG(IPP_TAG_KEYWORD), "number-up-layout-supported", sizeof(number_up_layout) / sizeof(number_up_layout[0]), NULL, number_up_layout);
/* operations-supported */
ippAddIntegers(CommonData, IPP_TAG_PRINTER, IPP_TAG_ENUM,
ippAddIntegers(CommonData, IPP_TAG_PRINTER, IPP_TAG_ENUM,
"orientation-requested-supported", 4, orients);
+ /* page-delivery-supported */
+ ippAddStrings(CommonData, IPP_TAG_PRINTER, IPP_CONST_TAG(IPP_TAG_KEYWORD), "page-delivery-supported", sizeof(page_delivery) / sizeof(page_delivery[0]), NULL, page_delivery);
+
/* page-ranges-supported */
ippAddBoolean(CommonData, IPP_TAG_PRINTER, "page-ranges-supported", 1);
ippAddString(CommonData, IPP_TAG_PRINTER, IPP_TAG_KEYWORD | IPP_TAG_COPY,
"pdl-override-supported", NULL, "attempted");
+ /* print-scaling-supported */
+ ippAddStrings(CommonData, IPP_TAG_PRINTER, IPP_CONST_TAG(IPP_TAG_KEYWORD), "print-scaling-supported", sizeof(print_scaling) / sizeof(print_scaling[0]), NULL, print_scaling);
+
+ /* printer-get-attributes-supported */
+ ippAddString(CommonData, IPP_TAG_PRINTER, IPP_CONST_TAG(IPP_TAG_KEYWORD), "printer-get-attributes-supported", NULL, "document-format");
+
/* printer-op-policy-supported */
attr = ippAddStrings(CommonData, IPP_TAG_PRINTER, IPP_TAG_NAME | IPP_TAG_COPY,
"printer-op-policy-supported", cupsArrayCount(Policies),
cupsdDeregisterPrinter(p, 1);
+ /*
+ * Remove support files if this is a temporary queue and deregister color
+ * profiles...
+ */
+
+ if (p->temporary)
+ {
+ char filename[1024]; /* Script/PPD filename */
+
+ /*
+ * Remove any old PPD or script files...
+ */
+
+ snprintf(filename, sizeof(filename), "%s/ppd/%s.ppd", ServerRoot, p->name);
+ unlink(filename);
+ snprintf(filename, sizeof(filename), "%s/ppd/%s.ppd.O", ServerRoot, p->name);
+ unlink(filename);
+
+ snprintf(filename, sizeof(filename), "%s/%s.png", CacheDir, p->name);
+ unlink(filename);
+
+ snprintf(filename, sizeof(filename), "%s/%s.data", CacheDir, p->name);
+ unlink(filename);
+
+ /*
+ * Unregister color profiles...
+ */
+
+ cupsdUnregisterColor(p);
+ }
+
/*
* Free all memory used by the printer...
*/
cupsdClearString(&p->hostname);
cupsdClearString(&p->name);
cupsdClearString(&p->location);
+ cupsdClearString(&p->geo_location);
cupsdClearString(&p->make_model);
cupsdClearString(&p->info);
cupsdClearString(&p->job_sheets[0]);
cupsdClearString(&p->port_monitor);
cupsdClearString(&p->op_policy);
cupsdClearString(&p->error_policy);
+ cupsdClearString(&p->strings);
cupsdClearString(&p->alert);
cupsdClearString(&p->alert_description);
}
+/*
+ * 'cupsdDeleteTemporaryPrinters()' - Delete unneeded temporary printers.
+ */
+
+void
+cupsdDeleteTemporaryPrinters(int force) /* I - Force deletion instead of auto? */
+{
+ cupsd_printer_t *p; /* Current printer */
+ time_t unused_time; /* Last time for printer state change */
+
+
+ /*
+ * Allow temporary printers to stick around for 60 seconds after the last job
+ * completes.
+ */
+
+ unused_time = time(NULL) - 60;
+
+ for (p = (cupsd_printer_t *)cupsArrayFirst(Printers); p; p = (cupsd_printer_t *)cupsArrayNext(Printers))
+ {
+ if (p->temporary && (force || p->state_time < unused_time))
+ cupsdDeletePrinter(p, 0);
+ }
+}
+
+
/*
* 'cupsdFindDest()' - Find a destination in the list.
*/
* Decode the directive...
*/
- if (!_cups_strcasecmp(line, "<Printer") ||
- !_cups_strcasecmp(line, "<DefaultPrinter"))
+ if (!_cups_strcasecmp(line, "NextPrinterId"))
+ {
+ if (value && (i = atoi(value)) > 0)
+ NextPrinterId = i;
+ else
+ cupsdLogMessage(CUPSD_LOG_ERROR, "Syntax error on line %d of printers.conf.", linenum);
+ }
+ else if (!_cups_strcasecmp(line, "<Printer") || !_cups_strcasecmp(line, "<DefaultPrinter"))
{
/*
* <Printer name> or <DefaultPrinter name>
cupsdLogMessage(CUPSD_LOG_ERROR,
"Syntax error on line %d of printers.conf.", linenum);
}
- else if (!_cups_strcasecmp(line, "</Printer>"))
+ else if (!_cups_strcasecmp(line, "</Printer>") || !_cups_strcasecmp(line, "</DefaultPrinter>"))
{
if (p != NULL)
{
* Close out the current printer...
*/
+ if (!p->printer_id)
+ {
+ p->printer_id = NextPrinterId ++;
+ cupsdMarkDirty(CUPSD_DIRTY_PRINTERS);
+ }
+
cupsdSetPrinterAttrs(p);
- if (strncmp(p->device_uri, "file:", 5) &&
- p->state != IPP_PRINTER_STOPPED)
+ if (strncmp(p->device_uri, "file:", 5) && p->state != IPP_PRINTER_STOPPED)
{
/*
* See if the backend exists...
*/
- snprintf(line, sizeof(line), "%s/backend/%s", ServerBin,
- p->device_uri);
+ snprintf(line, sizeof(line), "%s/backend/%s", ServerBin, p->device_uri);
if ((valueptr = strchr(line + strlen(ServerBin), ':')) != NULL)
*valueptr = '\0'; /* Chop everything but URI scheme */
*/
p->state = IPP_PRINTER_STOPPED;
- snprintf(p->state_message, sizeof(p->state_message),
- "Backend %s does not exist!", line);
+ snprintf(p->state_message, sizeof(p->state_message), "Backend %s does not exist!", line);
}
}
cupsdLogMessage(CUPSD_LOG_ERROR,
"Syntax error on line %d of printers.conf.", linenum);
}
+ else if (!_cups_strcasecmp(line, "PrinterId"))
+ {
+ if (value && (i = atoi(value)) > 0)
+ p->printer_id = i;
+ else
+ cupsdLogMessage(CUPSD_LOG_ERROR, "Bad PrinterId on line %d of printers.conf.", linenum);
+ }
else if (!_cups_strcasecmp(line, "UUID"))
{
if (value && !strncmp(value, "urn:uuid:", 9))
if (value)
cupsdSetString(&p->location, value);
}
+ else if (!_cups_strcasecmp(line, "GeoLocation"))
+ {
+ if (value)
+ cupsdSetString(&p->geo_location, value);
+ }
+ else if (!_cups_strcasecmp(line, "Organization"))
+ {
+ if (value)
+ cupsdSetString(&p->organization, value);
+ }
+ else if (!_cups_strcasecmp(line, "OrganizationalUnit"))
+ {
+ if (value)
+ cupsdSetString(&p->organizational_unit, value);
+ }
else if (!_cups_strcasecmp(line, "DeviceURI"))
{
if (value)
if (value)
p->state_time = atoi(value);
}
+ else if (!_cups_strcasecmp(line, "ConfigTime"))
+ {
+ /*
+ * Set the config time...
+ */
+
+ if (value)
+ p->config_time = atoi(value);
+ }
else if (!_cups_strcasecmp(line, "Accepting"))
{
/*
else if (!_cups_strcasecmp(line, "ErrorPolicy"))
{
if (value)
- cupsdSetString(&p->error_policy, value);
+ {
+ if (strcmp(value, "retry-current-job") &&
+ strcmp(value, "abort-job") &&
+ strcmp(value, "retry-job") &&
+ strcmp(value, "stop-printer"))
+ cupsdLogMessage(CUPSD_LOG_ALERT, "Invalid ErrorPolicy \"%s\" on line %d or printers.conf.", ErrorPolicy, linenum);
+ else
+ cupsdSetString(&p->error_policy, value);
+ }
else
- cupsdLogMessage(CUPSD_LOG_ERROR,
- "Syntax error on line %d of printers.conf.", linenum);
+ cupsdLogMessage(CUPSD_LOG_ERROR, "Syntax error on line %d of printers.conf.", linenum);
}
else if (!_cups_strcasecmp(line, "Attribute") && value)
{
cupsFilePrintf(fp, "# Written by cupsd on %s\n", temp);
cupsFilePuts(fp, "# DO NOT EDIT THIS FILE WHEN CUPSD IS RUNNING\n");
+ cupsFilePrintf(fp, "NextPrinterId %d\n", NextPrinterId);
+
/*
* Write each local printer known to the system...
*/
printer = (cupsd_printer_t *)cupsArrayNext(Printers))
{
/*
- * Skip printer classes...
+ * Skip printer classes and temporary queues...
*/
- if (printer->type & CUPS_PRINTER_CLASS)
+ if ((printer->type & CUPS_PRINTER_CLASS) || printer->temporary)
continue;
/*
else
cupsFilePrintf(fp, "<Printer %s>\n", printer->name);
+ if (printer->printer_id)
+ cupsFilePrintf(fp, "PrinterId %d\n", printer->printer_id);
+
cupsFilePrintf(fp, "UUID %s\n", printer->uuid);
if (printer->num_auth_info_required > 0)
if (printer->location)
cupsFilePutConf(fp, "Location", printer->location);
+ if (printer->geo_location)
+ cupsFilePutConf(fp, "GeoLocation", printer->geo_location);
+
if (printer->make_model)
cupsFilePutConf(fp, "MakeModel", printer->make_model);
+ if (printer->organization)
+ cupsFilePutConf(fp, "Organization", printer->organization);
+
+ if (printer->organizational_unit)
+ cupsFilePutConf(fp, "OrganizationalUnit", printer->organizational_unit);
+
cupsFilePutConf(fp, "DeviceURI", printer->device_uri);
if (printer->port_monitor)
{
cupsFilePuts(fp, "State Stopped\n");
- if (printer->state_message)
+ if (printer->state_message[0])
cupsFilePutConf(fp, "StateMessage", printer->state_message);
}
else
cupsFilePuts(fp, "State Idle\n");
cupsFilePrintf(fp, "StateTime %d\n", (int)printer->state_time);
+ cupsFilePrintf(fp, "ConfigTime %d\n", (int)printer->config_time);
for (i = 0; i < printer->num_reasons; i ++)
if (strcmp(printer->reasons[i], "connecting-to-device") &&
if (i)
*ptr++ = ',';
- strlcpy(ptr, marker->values[i].string.text,
- value + sizeof(value) - ptr);
+ strlcpy(ptr, marker->values[i].string.text, (size_t)(value + sizeof(value) - ptr));
ptr += strlen(ptr);
}
if (i)
*ptr++ = ',';
- strlcpy(ptr, marker->values[i].string.text,
- value + sizeof(value) - ptr);
+ strlcpy(ptr, marker->values[i].string.text, (size_t)(value + sizeof(value) - ptr));
ptr += strlen(ptr);
}
if (i)
*ptr++ = ',';
- strlcpy(ptr, marker->values[i].string.text,
- value + sizeof(value) - ptr);
+ strlcpy(ptr, marker->values[i].string.text, (size_t)(value + sizeof(value) - ptr));
ptr += strlen(ptr);
}
cupsFilePrintf(fp, "Attribute marker-change-time %ld\n",
(long)printer->marker_time);
- cupsFilePuts(fp, "</Printer>\n");
+ if (printer == DefaultPrinter)
+ cupsFilePuts(fp, "</DefaultPrinter>\n");
+ else
+ cupsFilePuts(fp, "</Printer>\n");
}
cupsdCloseCreatedConfFile(fp, filename);
}
free(temp);
+
+ /*
+ * Update the printer-supply and printer-supply-description, as needed...
+ */
+
+ if (!strcmp(name, "marker-names"))
+ {
+ ipp_attribute_t *supply_desc = ippFindAttribute(p->attrs, "printer-supply-description", IPP_TAG_TEXT);
+ /* printer-supply-description attribute */
+
+ if (supply_desc != NULL)
+ ippDeleteAttribute(p->attrs, supply_desc);
+
+ supply_desc = ippCopyAttribute(p->attrs, attr, 0);
+ ippSetName(p->attrs, &supply_desc, "printer-supply-description");
+ ippSetValueTag(p->attrs, &supply_desc, IPP_TAG_TEXT);
+ }
+ else if (!strcmp(name, "marker-colors") || !strcmp(name, "marker-levels") || !strcmp(name, "marker-types"))
+ {
+ char buffer[256], /* printer-supply values */
+ pstype[64], /* printer-supply type value */
+ *psptr; /* Pointer into type */
+ const char *color, /* marker-colors value */
+ *type; /* marker-types value */
+ int level; /* marker-levels value */
+ ipp_attribute_t *colors = ippFindAttribute(p->attrs, "marker-colors", IPP_TAG_NAME);
+ /* marker-colors attribute */
+ ipp_attribute_t *levels = ippFindAttribute(p->attrs, "marker-levels", IPP_TAG_INTEGER);
+ /* marker-levels attribute */
+ ipp_attribute_t *types = ippFindAttribute(p->attrs, "marker-types", IPP_TAG_KEYWORD);
+ /* marker-types attribute */
+ ipp_attribute_t *supply = ippFindAttribute(p->attrs, "printer-supply", IPP_TAG_STRING);
+ /* printer-supply attribute */
+
+ if (supply != NULL)
+ {
+ ippDeleteAttribute(p->attrs, supply);
+ supply = NULL;
+ }
+
+ if (!colors || !levels || !types)
+ return;
+
+ count = ippGetCount(colors);
+ if (count != ippGetCount(levels) || count != ippGetCount(types))
+ return;
+
+ for (i = 0; i < count; i ++)
+ {
+ color = ippGetString(colors, i, NULL);
+ level = ippGetInteger(levels, i);
+ type = ippGetString(types, i, NULL);
+
+ for (psptr = pstype; *type && psptr < (pstype + sizeof(pstype) - 1); type ++)
+ if (*type == '-')
+ {
+ type ++;
+ *psptr++ = (char)toupper(*type & 255);
+ }
+ else
+ *psptr++ = *type;
+ *psptr = '\0';
+
+ snprintf(buffer, sizeof(buffer), "index=%d;class=%s;type=%s;unit=percent;maxcapacity=100;level=%d;colorantname=%s;", i + 1, strncmp(pstype, "waste", 5) ? "supplyThatIsConsumed" : "receptacleThatIsFilled", pstype, level, color);
+
+ if (!i)
+ supply = ippAddOctetString(p->attrs, IPP_TAG_PRINTER, "printer-supply", buffer, (int)strlen(buffer));
+ else
+ ippSetOctetString(p->attrs, &supply, i, buffer, (int)strlen(buffer));
+ }
+ }
}
*filter; /* Current filter */
- DEBUG_printf(("cupsdSetPrinterAttrs: entering name = %s, type = %x\n", p->name,
- p->type));
-
/*
* Make sure that we have the common attributes defined...
*/
if (!CommonData)
cupsdCreateCommonData();
+ _cupsRWLockWrite(&p->lock);
+
/*
* Clear out old filters, if any...
*/
if ((auth_type = auth->type) == CUPSD_AUTH_DEFAULT)
auth_type = cupsdDefaultAuthType();
- if (auth_type == CUPSD_AUTH_BASIC || auth_type == CUPSD_AUTH_BASICDIGEST)
+ if (auth_type == CUPSD_AUTH_BASIC)
auth_supported = "basic";
- else if (auth_type == CUPSD_AUTH_DIGEST)
- auth_supported = "digest";
#ifdef HAVE_GSSAPI
else if (auth_type == CUPSD_AUTH_NEGOTIATE)
auth_supported = "negotiate";
"uri-authentication-supported", NULL, auth_supported);
ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD,
"uri-security-supported", NULL, "none");
+ if (p->printer_id)
+ ippAddInteger(p->attrs, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "printer-id", p->printer_id);
ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_NAME, "printer-name", NULL,
p->name);
ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT, "printer-location",
NULL, p->location ? p->location : "");
+ if (p->geo_location)
+ ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_URI, "printer-geo-location", NULL, p->geo_location);
+ else
+ ippAddOutOfBand(p->attrs, IPP_TAG_PRINTER, IPP_TAG_UNKNOWN, "printer-geo-location");
ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT, "printer-info",
NULL, p->info ? p->info : "");
- ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_URI, "printer-uuid", NULL,
- p->uuid);
+ ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT, "printer-organization", NULL, p->organization ? p->organization : "");
+ ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT, "printer-organizational-unit", NULL, p->organizational_unit ? p->organizational_unit : "");
+ ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_URI, "printer-uuid", NULL, p->uuid);
if (cupsArrayCount(p->users) > 0)
{
}
else if (!(p->type & CUPS_PRINTER_REMOTE))
{
- char interface[1024]; /* Interface script */
-
-
- snprintf(interface, sizeof(interface), "%s/interfaces/%s", ServerRoot,
- p->name);
- if (!access(interface, X_OK))
- {
- /*
- * Yes, we have a System V style interface script; use it!
- */
-
- snprintf(interface, sizeof(interface), "*/* 0 %s/interfaces/%s",
- ServerRoot, p->name);
- add_printer_filter(p, p->filetype, interface);
- }
- else
- {
- /*
- * Add a filter from application/vnd.cups-raw to printer/name to
- * handle "raw" printing by users.
- */
+ /*
+ * Add a filter from application/vnd.cups-raw to printer/name to
+ * handle "raw" printing by users.
+ */
- add_printer_filter(p, p->filetype, "application/vnd.cups-raw 0 -");
+ add_printer_filter(p, p->filetype, "application/vnd.cups-raw 0 -");
- /*
- * Add a PostScript filter, since this is still possibly PS printer.
- */
+ /*
+ * Add a PostScript filter, since this is still possibly PS printer.
+ */
- add_printer_filter(p, p->filetype,
- "application/vnd.cups-postscript 0 -");
- }
+ add_printer_filter(p, p->filetype,
+ "application/vnd.cups-postscript 0 -");
}
if (p->pc && p->pc->prefilters)
add_printer_formats(p);
- DEBUG_printf(("cupsdSetPrinterAttrs: leaving name = %s, type = %x\n", p->name,
- p->type));
-
/*
* Add name-default attributes...
*/
add_printer_defaults(p);
+ _cupsRWUnlock(&p->lock);
+
/*
* Let the browse protocols reflect the change
*/
if (i >= p->num_reasons)
{
- if (!strncmp(reason, "cups-ipp-missing-", 17) ||
- !strncmp(reason, "cups-ipp-wrong-", 15))
- log_ipp_conformance(p, reason);
-
if (i >= (int)(sizeof(p->reasons) / sizeof(p->reasons[0])))
{
cupsdLogMessage(CUPSD_LOG_ALERT,
int port; /* Port portion of URI */
- DEBUG_printf(("cupsdValidateDest(uri=\"%s\", dtype=%p, printer=%p)\n", uri,
- dtype, printer));
-
/*
* Initialize return values...
*/
}
}
- DEBUG_printf(("localized hostname is \"%s\"...\n", localname));
-
/*
* Find a matching printer or class...
*/
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("document-format-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("finishings-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("job-account-id-default"));
- cupsArrayAdd(CommonDefaults,
- _cupsStrAlloc("job-accounting-user-id-default"));
+ cupsArrayAdd(CommonDefaults, _cupsStrAlloc("job-accounting-user-id-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("job-cancel-after-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("job-hold-until-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("job-priority-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("job-sheets-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("media-col-default"));
+ cupsArrayAdd(CommonDefaults, _cupsStrAlloc("notify-lease-duration-default"));
+ cupsArrayAdd(CommonDefaults, _cupsStrAlloc("notify-events-default"));
cupsArrayAdd(CommonDefaults, _cupsStrAlloc("number-up-default"));
- cupsArrayAdd(CommonDefaults,
- _cupsStrAlloc("orientation-requested-default"));
+ cupsArrayAdd(CommonDefaults, _cupsStrAlloc("orientation-requested-default"));
+ cupsArrayAdd(CommonDefaults, _cupsStrAlloc("print-quality-default"));
}
/*
"document-format-default", NULL, "application/octet-stream");
if (!cupsGetOption("job-cancel-after", p->num_options, p->options))
- ippAddInteger(p->attrs, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
+ ippAddInteger(p->attrs, IPP_TAG_PRINTER, MaxJobTime > 0 ? IPP_TAG_INTEGER : IPP_TAG_NOVALUE,
"job-cancel-after-default", MaxJobTime);
if (!cupsGetOption("job-hold-until", p->num_options, p->options))
filter;
filter = (mime_filter_t *)cupsArrayNext(MimeDatabase->filters))
{
- if (filter->dst == p->filetype && filter->filter &&
- strstr(filter->filter, "PrintJobMgr"))
+ if (filter->dst == p->filetype && strstr(filter->filter, "PrintJobMgr"))
break;
}
static void
load_ppd(cupsd_printer_t *p) /* I - Printer */
{
- int i, j, k; /* Looping vars */
+ int i, j; /* Looping vars */
char cache_name[1024]; /* Cache filename */
struct stat cache_info; /* Cache file info */
ppd_file_t *ppd; /* PPD file */
char ppd_name[1024]; /* PPD filename */
struct stat ppd_info; /* PPD file info */
- int num_media; /* Number of media options */
+ char strings_name[1024]; /* Strings filename */
+ int num_media; /* Number of media values */
ppd_size_t *size; /* Current PPD size */
ppd_option_t *duplex, /* Duplex option */
*output_bin, /* OutputBin option */
*output_mode, /* OutputMode option */
*resolution; /* (Set|JCL|)Resolution option */
- ppd_choice_t *choice, /* Current PPD choice */
- *input_slot, /* Current input slot */
- *media_type; /* Current media type */
+ ppd_choice_t *choice; /* Current PPD choice */
ppd_attr_t *ppd_attr; /* PPD attribute */
int xdpi, /* Horizontal resolution */
ydpi; /* Vertical resolution */
const char *resptr; /* Pointer into resolution keyword */
- _pwg_size_t *pwgsize; /* Current PWG size */
- _pwg_map_t *pwgsource, /* Current PWG source */
+ pwg_size_t *pwgsize; /* Current PWG size */
+ pwg_map_t *pwgsource, /* Current PWG source */
*pwgtype; /* Current PWG type */
ipp_attribute_t *attr; /* Attribute data */
_ipp_value_t *val; /* Attribute value */
int num_finishings, /* Number of finishings */
- finishings[5]; /* finishings-supported values */
+ finishings[100]; /* finishings-supported values */
int num_qualities, /* Number of print-quality values */
qualities[3]; /* print-quality values */
int num_margins, /* Number of media-*-margin-supported values */
margins[16]; /* media-*-margin-supported values */
const char *filter, /* Current filter */
*mandatory; /* Current mandatory attribute */
+ static const char * const pwg_raster_document_types[] =
+ {
+ "black_1",
+ "sgray_8",
+ "srgb_8"
+ };
static const char * const sides[3] = /* sides-supported values */
{
"one-sided",
if (stat(ppd_name, &ppd_info))
ppd_info.st_mtime = 1;
+ snprintf(strings_name, sizeof(strings_name), "%s/%s.strings", CacheDir, p->name);
+
ippDelete(p->ppd_attrs);
p->ppd_attrs = NULL;
cupsdLogMessage(CUPSD_LOG_DEBUG, "load_ppd: Loading %s...", ppd_name);
+ cupsdClearString(&(p->make_model));
+
p->type &= (cups_ptype_t)~CUPS_PRINTER_OPTIONS;
p->type |= CUPS_PRINTER_BW;
"pages-per-minute-color", 1);
}
+ if ((ppd_attr = ppdFindAttr(ppd, "1284DeviceId", NULL)) != NULL)
+ ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT, "printer-device-id", NULL, ppd_attr->value);
+
num_qualities = 0;
if ((output_mode = ppdFindOption(ppd, "OutputMode")) != NULL)
ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT,
"printer-make-and-model", NULL, p->make_model);
+ if (p->pc && p->pc->strings)
+ _cupsMessageSave(strings_name, _CUPS_MESSAGE_STRINGS, p->pc->strings);
+
+ if (!access(strings_name, R_OK))
+ cupsdSetString(&p->strings, strings_name);
+ else
+ cupsdClearString(&p->strings);
+
/*
* Add media options from the PPD file...
*/
if (ppd->num_sizes == 0 || !p->pc)
{
- if (!ppdFindAttr(ppd, "APScannerOnly", NULL))
+ if (!ppdFindAttr(ppd, "APScannerOnly", NULL) && !ppdFindAttr(ppd, "cups3D", NULL))
cupsdLogMessage(CUPSD_LOG_CRIT,
"The PPD file for printer %s contains no media "
- "options and is therefore invalid!", p->name);
+ "options and is therefore invalid.", p->name);
ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD,
"media-default", NULL, "unknown");
{
ipp_t *col; /* Collection value */
- input_slot = ppdFindMarkedChoice(ppd, "InputSlot");
- media_type = ppdFindMarkedChoice(ppd, "MediaType");
- col = new_media_col(pwgsize,
- input_slot ?
- _ppdCacheGetSource(p->pc,
- input_slot->choice) :
- NULL,
- media_type ?
- _ppdCacheGetType(p->pc,
- media_type->choice) :
- NULL);
-
- ippAddCollection(p->ppd_attrs, IPP_TAG_PRINTER, "media-col-default",
- col);
+ col = new_media_col(pwgsize);
+ ippAddCollection(p->ppd_attrs, IPP_TAG_PRINTER, "media-col-default", col);
ippDelete(col);
}
* media-col-database
*/
- num_media = p->pc->num_sizes;
- if (p->pc->num_sources)
+ if ((attr = ippAddCollections(p->ppd_attrs, IPP_TAG_PRINTER, "media-col-database", p->pc->num_sizes, NULL)) != NULL)
{
- if (p->pc->num_types > 0)
- num_media += p->pc->num_sizes * p->pc->num_sources *
- p->pc->num_types;
- else
- num_media += p->pc->num_sizes * p->pc->num_sources;
- }
- else if (p->pc->num_types)
- num_media += p->pc->num_sizes * p->pc->num_types;
+ /*
+ * Add each page size without source or type...
+ */
- if ((attr = ippAddCollections(p->ppd_attrs, IPP_TAG_PRINTER,
- "media-col-database", num_media,
- NULL)) != NULL)
- {
- for (i = p->pc->num_sizes, pwgsize = p->pc->sizes, val = attr->values;
- i > 0;
- i --, pwgsize ++)
+ for (i = 0, pwgsize = p->pc->sizes; i < p->pc->num_sizes; i ++, pwgsize ++)
{
- /*
- * Start by adding the page size without source or type...
- */
-
- ppdMarkOption(ppd, "PageSize", pwgsize->map.ppd);
+ ipp_t *col = new_media_col(pwgsize);
- val->collection = new_media_col(pwgsize, NULL, NULL);
- val ++;
-
- /*
- * Then add the specific, supported combinations of size, source, and
- * type...
- */
-
- if (p->pc->num_sources > 0)
- {
- for (j = p->pc->num_sources, pwgsource = p->pc->sources;
- j > 0;
- j --, pwgsource ++)
- {
- ppdMarkOption(ppd, "InputSlot", pwgsource->ppd);
-
- if (p->pc->num_types > 0)
- {
- for (k = p->pc->num_types, pwgtype = p->pc->types;
- k > 0;
- k --, pwgtype ++)
- {
- if (!ppdMarkOption(ppd, "MediaType", pwgtype->ppd))
- {
- val->collection = new_media_col(pwgsize, pwgsource->pwg,
- pwgtype->pwg);
- val ++;
- }
- }
- }
- else if (!ppdConflicts(ppd))
- {
- val->collection = new_media_col(pwgsize, pwgsource->pwg, NULL);
- val ++;
- }
- }
- }
- else if (p->pc->num_types > 0)
- {
- for (j = p->pc->num_types, pwgtype = p->pc->types;
- j > 0;
- j --, pwgtype ++)
- {
- if (!ppdMarkOption(ppd, "MediaType", pwgtype->ppd))
- {
- val->collection = new_media_col(pwgsize, NULL, pwgtype->pwg);
- val ++;
- }
- }
- }
+ ippSetCollection(p->ppd_attrs, &attr, i, col);
+ ippDelete(col);
}
-
- /*
- * Update the number of media-col-database values...
- */
-
- attr->num_values = val - attr->values;
}
}
"print-color-mode-supported", 2, NULL, color_modes);
ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD,
"print-color-mode-default", NULL, "color");
+ ippAddStrings(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD, "pwg-raster-document-type-supported", 3, NULL, pwg_raster_document_types);
}
else
{
"print-color-mode-supported", NULL, "monochrome");
ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD,
"print-color-mode-default", NULL, "monochrome");
+ ippAddStrings(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD, "pwg-raster-document-type-supported", 2, NULL, pwg_raster_document_types);
}
/*
* Report all supported resolutions...
*/
- attr = ippAddResolutions(p->ppd_attrs, IPP_TAG_PRINTER,
- "printer-resolution-supported",
- resolution->num_choices, IPP_RES_PER_INCH,
- NULL, NULL);
+ attr = ippAddResolutions(p->ppd_attrs, IPP_TAG_PRINTER, "printer-resolution-supported", resolution->num_choices, IPP_RES_PER_INCH, NULL, NULL);
for (i = 0, choice = resolution->choices;
i < resolution->num_choices;
attr->values[i].resolution.units = IPP_RES_PER_INCH;
if (choice->marked)
- ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER,
- "printer-resolution-default", IPP_RES_PER_INCH,
- xdpi, ydpi);
+ ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER, "printer-resolution-default", IPP_RES_PER_INCH, xdpi, ydpi);
+
+ if (i == 0)
+ ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER, "pwg-raster-document-resolution-supported", IPP_RES_PER_INCH, xdpi, ydpi);
}
}
else if ((ppd_attr = ppdFindAttr(ppd, "DefaultResolution", NULL)) != NULL &&
ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER,
"printer-resolution-supported", IPP_RES_PER_INCH,
xdpi, ydpi);
+ ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER, "pwg-raster-document-resolution-supported", IPP_RES_PER_INCH, xdpi, ydpi);
}
else
{
ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER,
"printer-resolution-supported", IPP_RES_PER_INCH,
300, 300);
+ ippAddResolution(p->ppd_attrs, IPP_TAG_PRINTER, "pwg-raster-document-resolution-supported", IPP_RES_PER_INCH, 300, 300);
}
/*
{
p->type |= CUPS_PRINTER_DUPLEX;
+ ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD, "pwg-raster-document-sheet-back", NULL, "normal");
+
ippAddStrings(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_KEYWORD,
"sides-supported", 3, NULL, sides);
if (ppdFindOption(ppd, "Collate") != NULL)
p->type |= CUPS_PRINTER_COLLATE;
- if (ppdFindOption(ppd, "StapleLocation") != NULL)
+ if (p->pc && p->pc->finishings)
{
- p->type |= CUPS_PRINTER_STAPLE;
- finishings[num_finishings++] = IPP_FINISHINGS_STAPLE;
+ _pwg_finishings_t *fin; /* Current finishing value */
+
+ for (fin = (_pwg_finishings_t *)cupsArrayFirst(p->pc->finishings); fin; fin = (_pwg_finishings_t *)cupsArrayNext(p->pc->finishings))
+ {
+ if (num_finishings < (int)(sizeof(finishings) / sizeof(finishings[0])))
+ finishings[num_finishings++] = fin->value;
+
+ switch (fin->value)
+ {
+ case IPP_FINISHINGS_BIND :
+ case IPP_FINISHINGS_BIND_LEFT :
+ case IPP_FINISHINGS_BIND_TOP :
+ case IPP_FINISHINGS_BIND_RIGHT :
+ case IPP_FINISHINGS_BIND_BOTTOM :
+ case IPP_FINISHINGS_EDGE_STITCH :
+ case IPP_FINISHINGS_EDGE_STITCH_LEFT :
+ case IPP_FINISHINGS_EDGE_STITCH_TOP :
+ case IPP_FINISHINGS_EDGE_STITCH_RIGHT :
+ case IPP_FINISHINGS_EDGE_STITCH_BOTTOM :
+ p->type |= CUPS_PRINTER_BIND;
+ break;
+
+ case IPP_FINISHINGS_COVER :
+ p->type |= CUPS_PRINTER_COVER;
+ break;
+
+ case IPP_FINISHINGS_PUNCH :
+ case IPP_FINISHINGS_PUNCH_TOP_LEFT :
+ case IPP_FINISHINGS_PUNCH_BOTTOM_LEFT :
+ case IPP_FINISHINGS_PUNCH_TOP_RIGHT :
+ case IPP_FINISHINGS_PUNCH_BOTTOM_RIGHT :
+ case IPP_FINISHINGS_PUNCH_DUAL_LEFT :
+ case IPP_FINISHINGS_PUNCH_DUAL_TOP :
+ case IPP_FINISHINGS_PUNCH_DUAL_RIGHT :
+ case IPP_FINISHINGS_PUNCH_DUAL_BOTTOM :
+ case IPP_FINISHINGS_PUNCH_TRIPLE_LEFT :
+ case IPP_FINISHINGS_PUNCH_TRIPLE_TOP :
+ case IPP_FINISHINGS_PUNCH_TRIPLE_RIGHT :
+ case IPP_FINISHINGS_PUNCH_TRIPLE_BOTTOM :
+ case IPP_FINISHINGS_PUNCH_QUAD_LEFT :
+ case IPP_FINISHINGS_PUNCH_QUAD_TOP :
+ case IPP_FINISHINGS_PUNCH_QUAD_RIGHT :
+ case IPP_FINISHINGS_PUNCH_QUAD_BOTTOM :
+ p->type |= CUPS_PRINTER_PUNCH;
+ break;
+
+ case IPP_FINISHINGS_STAPLE :
+ case IPP_FINISHINGS_STAPLE_TOP_LEFT :
+ case IPP_FINISHINGS_STAPLE_BOTTOM_LEFT :
+ case IPP_FINISHINGS_STAPLE_TOP_RIGHT :
+ case IPP_FINISHINGS_STAPLE_BOTTOM_RIGHT :
+ case IPP_FINISHINGS_STAPLE_DUAL_LEFT :
+ case IPP_FINISHINGS_STAPLE_DUAL_TOP :
+ case IPP_FINISHINGS_STAPLE_DUAL_RIGHT :
+ case IPP_FINISHINGS_STAPLE_DUAL_BOTTOM :
+ case IPP_FINISHINGS_STAPLE_TRIPLE_LEFT :
+ case IPP_FINISHINGS_STAPLE_TRIPLE_TOP :
+ case IPP_FINISHINGS_STAPLE_TRIPLE_RIGHT :
+ case IPP_FINISHINGS_STAPLE_TRIPLE_BOTTOM :
+ p->type |= CUPS_PRINTER_STAPLE;
+ break;
+
+ default :
+ break;
+ }
+ }
}
- if (ppdFindOption(ppd, "BindEdge") != NULL)
+ if (p->pc && p->pc->templates)
{
- p->type |= CUPS_PRINTER_BIND;
- finishings[num_finishings++] = IPP_FINISHINGS_BIND;
+ const char *template; /* Finishing template */
+ ipp_attribute_t *fin_col_db; /* finishings-col-database attribute */
+ ipp_t *fin_col; /* finishings-col value */
+
+ fin_col_db = ippAddCollections(p->ppd_attrs, IPP_TAG_PRINTER, "finishings-col-database", cupsArrayCount(p->pc->templates), NULL);
+ for (i = 0, template = (const char *)cupsArrayFirst(p->pc->templates); template; i ++, template = (const char *)cupsArrayNext(p->pc->templates))
+ {
+ fin_col = ippNew();
+ ippAddString(fin_col, IPP_TAG_PRINTER, IPP_TAG_KEYWORD, "finishing-template", NULL, template);
+ ippSetCollection(p->ppd_attrs, &fin_col_db, i, fin_col);
+ ippDelete(fin_col);
+ }
}
for (i = 0; i < ppd->num_sizes; i ++)
pstatus = ppdLastError(&pline);
- cupsdLogMessage(CUPSD_LOG_ERROR, "PPD file for %s cannot be loaded!",
- p->name);
+ cupsdLogMessage(CUPSD_LOG_ERROR, "PPD file for %s cannot be loaded.", p->name);
if (pstatus <= PPD_ALLOC_ERROR)
- cupsdLogMessage(CUPSD_LOG_ERROR, "%s", strerror(errno));
+ cupsdLogMessage(CUPSD_LOG_ERROR, "%s: %s", ppd_name, strerror(errno));
else
- cupsdLogMessage(CUPSD_LOG_ERROR, "%s on line %d.",
- ppdErrorString(pstatus), pline);
+ cupsdLogMessage(CUPSD_LOG_ERROR, "%s on line %d of %s.", ppdErrorString(pstatus), pline, ppd_name);
cupsdLogMessage(CUPSD_LOG_INFO,
"Hint: Run \"cupstestppd %s\" and fix any errors.",
}
else
{
- /*
- * If we have an interface script, add a filter entry for it...
- */
-
- char interface[1024]; /* Interface script */
-
-
- snprintf(interface, sizeof(interface), "%s/interfaces/%s", ServerRoot,
- p->name);
- if (!access(interface, X_OK))
- {
- /*
- * Yes, we have a System V style interface script; use it!
- */
-
- ippAddString(p->ppd_attrs, IPP_TAG_PRINTER, IPP_TAG_TEXT,
- "printer-make-and-model", NULL,
- "Local System V Printer");
- }
- else if (((!strncmp(p->device_uri, "ipp://", 6) ||
- !strncmp(p->device_uri, "ipps://", 7)) &&
- (strstr(p->device_uri, "/printers/") != NULL ||
- strstr(p->device_uri, "/classes/") != NULL)) ||
- ((strstr(p->device_uri, "._ipp.") != NULL ||
- strstr(p->device_uri, "._ipps.") != NULL) &&
- !strcmp(p->device_uri + strlen(p->device_uri) - 5, "/cups")))
+ if (((!strncmp(p->device_uri, "ipp://", 6) ||
+ !strncmp(p->device_uri, "ipps://", 7)) &&
+ (strstr(p->device_uri, "/printers/") != NULL ||
+ strstr(p->device_uri, "/classes/") != NULL)) ||
+ ((strstr(p->device_uri, "._ipp.") != NULL ||
+ strstr(p->device_uri, "._ipps.") != NULL) &&
+ !strcmp(p->device_uri + strlen(p->device_uri) - 5, "/cups")))
{
/*
* Tell the client this is really a hard-wired remote printer.
p->type |= CUPS_PRINTER_REMOTE;
- /*
- * Point the printer-uri-supported attribute to the
- * remote printer...
- */
-
- if (strchr(p->device_uri, '?'))
- {
- /*
- * Strip trailing "?options" from URI...
- */
-
- char resource[HTTP_MAX_URI], /* New URI */
- *ptr; /* Pointer into URI */
-
- strlcpy(resource, p->device_uri, sizeof(resource));
- if ((ptr = strchr(resource, '?')) != NULL)
- *ptr = '\0';
-
- ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_URI,
- "printer-uri-supported", NULL, resource);
- }
- else
- ippAddString(p->attrs, IPP_TAG_PRINTER, IPP_TAG_URI,
- "printer-uri-supported", NULL, p->device_uri);
-
/*
* Then set the make-and-model accordingly...
*/
}
-/*
- * 'log_ipp_conformance()' - Log an IPP conformance issue with a printer.
- */
-
-static void
-log_ipp_conformance(
- cupsd_printer_t *p, /* I - Printer */
- const char *reason) /* I - Printer state reason */
-{
- const char *message; /* Message to log */
-#ifdef __APPLE__
- aslmsg aslm; /* Apple System Log message */
-#endif /* __APPLE__ */
-
-
- /*
- * Strip the leading "cups-ipp-" from the reason and create a log message for
- * it...
- */
-
- reason += 9;
- if (!strcmp(reason, "missing-cancel-job"))
- message = "Printer does not support REQUIRED Cancel-Job operation.";
- else if (!strcmp(reason, "missing-get-job-attributes"))
- message = "Printer does not support REQUIRED Get-Job-Attributes operation.";
- else if (!strcmp(reason, "missing-print-job"))
- message = "Printer does not support REQUIRED Print-Job operation.";
- else if (!strcmp(reason, "missing-validate-job"))
- message = "Printer does not support REQUIRED Validate-Job operation.";
- else if (!strcmp(reason, "missing-get-printer-attributes"))
- message = "Printer does not support REQUIRED Get-Printer-Attributes operation.";
- else if (!strcmp(reason, "missing-send-document"))
- message = "Printer supports Create-Job but not Send-Document operation.";
- else if (!strcmp(reason, "missing-job-history"))
- message = "Printer does not provide REQUIRED job history.";
- else if (!strcmp(reason, "missing-job-id"))
- message = "Printer does not provide REQUIRED job-id attribute.";
- else if (!strcmp(reason, "missing-job-state"))
- message = "Printer does not provide REQUIRED job-state attribute.";
- else if (!strcmp(reason, "missing-operations-supported"))
- message = "Printer does not provide REQUIRED operations-supported "
- "attribute.";
- else if (!strcmp(reason, "missing-printer-is-accepting-jobs"))
- message = "Printer does not provide REQUIRED printer-is-accepting-jobs "
- "attribute.";
- else if (!strcmp(reason, "missing-printer-state-reasons"))
- message = "Printer does not provide REQUIRED printer-state-reasons "
- "attribute.";
- else if (!strcmp(reason, "wrong-http-version"))
- message = "Printer does not use REQUIRED HTTP/1.1 transport.";
- else
- message = "Unknown IPP conformance failure.";
-
- cupsdLogMessage(CUPSD_LOG_WARN, "%s: %s", p->name, message);
-
-#ifdef __APPLE__
- /*
- * Report the failure information to Apple if the user opts into providing
- * feedback to Apple...
- */
-
- aslm = asl_new(ASL_TYPE_MSG);
- if (aslm)
- {
- asl_set(aslm, "com.apple.message.domain", "com.apple.printing.ipp.conformance");
- asl_set(aslm, "com.apple.message.domain_scope", "com.apple.printing.ipp.conformance");
- asl_set(aslm, "com.apple.message.signature", reason);
- asl_set(aslm, "com.apple.message.signature2",
- p->make_model ? p->make_model : "Unknown");
- asl_log(NULL, aslm, ASL_LEVEL_NOTICE, "%s: %s",
- p->make_model ? p->make_model : "Unknown", message);
- asl_free(aslm);
- }
-#endif /* __APPLE__ */
-}
-
-
/*
* 'new_media_col()' - Create a media-col collection value.
*/
static ipp_t * /* O - Collection value */
-new_media_col(_pwg_size_t *size, /* I - media-size/margin values */
- const char *source, /* I - media-source value */
- const char *type) /* I - media-type value */
+new_media_col(pwg_size_t *size) /* I - media-size/margin values */
{
ipp_t *media_col, /* Collection value */
*media_size; /* media-size value */
media_col = ippNew();
media_size = ippNew();
- ippAddInteger(media_size, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "x-dimension", size->width);
- ippAddInteger(media_size, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "y-dimension", size->length);
+ ippAddInteger(media_size, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "x-dimension", size->width);
+ ippAddInteger(media_size, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "y-dimension", size->length);
ippAddCollection(media_col, IPP_TAG_PRINTER, "media-size", media_size);
ippDelete(media_size);
- ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "media-bottom-margin", size->bottom);
- ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "media-left-margin", size->left);
- ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "media-right-margin", size->right);
- ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER,
- "media-top-margin", size->top);
-
- if (source)
- ippAddString(media_col, IPP_TAG_PRINTER, IPP_TAG_KEYWORD, "media-source",
- NULL, source);
-
- if (type)
- ippAddString(media_col, IPP_TAG_PRINTER, IPP_TAG_KEYWORD, "media-type",
- NULL, type);
+ ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "media-bottom-margin", size->bottom);
+ ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "media-left-margin", size->left);
+ ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "media-right-margin", size->right);
+ ippAddInteger(media_col, IPP_TAG_PRINTER, IPP_TAG_INTEGER, "media-top-margin", size->top);
return (media_col);
}
if (s > start)
cupsFilePuts(fp, start);
}
-
-
-/*
- * End of "$Id$".
- */