From 8f4595eb11c549ac51b453d118d55c636e6e229e Mon Sep 17 00:00:00 2001 From: mike Date: Mon, 24 Mar 2003 21:30:08 +0000 Subject: [PATCH] Mirror 1.1.x changes. git-svn-id: svn+ssh://src.apple.com/svn/cups/cups.org/branches/branch-1.2@3519 7a7537e8-13f0-0310-91df-b6672ffda945 --- CHANGES-1.1.txt | 2 + backend/ipp.c | 202 +++++++++++++++++++++++++++++++----------------- scheduler/job.c | 28 +++---- 3 files changed, 148 insertions(+), 84 deletions(-) diff --git a/CHANGES-1.1.txt b/CHANGES-1.1.txt index 051b20d54..c7f99d1ed 100644 --- a/CHANGES-1.1.txt +++ b/CHANGES-1.1.txt @@ -3,6 +3,8 @@ CHANGES-1.1.txt CHANGES IN CUPS V1.1.19 + - Filters and backends may now report the total number + of pages ("PAGE: total NNN") to the scheduler. - The LPD backend now supports timeout and sanitize_title options (default to 300 and yes, respectively) and has some additional changes to diff --git a/backend/ipp.c b/backend/ipp.c index 2df94e8d8..ea12713e9 100644 --- a/backend/ipp.c +++ b/backend/ipp.c @@ -1,5 +1,5 @@ /* - * "$Id: ipp.c,v 1.38.2.24 2003/02/20 03:50:33 mike Exp $" + * "$Id: ipp.c,v 1.38.2.25 2003/03/24 21:30:07 mike Exp $" * * IPP backend for the Common UNIX Printing System (CUPS). * @@ -29,6 +29,9 @@ * password_cb() - Disable the password prompt for * cupsDoFileRequest(). * report_printer_state() - Report the printer state. + * run_pictwps_filter() - Convert PICT files to PostScript when printing + * remotely. + * sigterm_handler() - Handle 'terminate' signals that stop the backend. */ /* @@ -47,6 +50,13 @@ #include +/* + * Globals... + */ + +static char tmpfilename[1024] = ""; /* Temporary spool file name */ + + /* * Some OS's don't have hstrerror(), most notably Solaris... */ @@ -85,6 +95,7 @@ int report_printer_state(ipp_t *ipp); #ifdef __APPLE__ int run_pictwps_filter(char **argv, char *filename, int length); #endif /* __APPLE__ */ +static void sigterm_handler(int sig); /* @@ -112,8 +123,8 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ char method[255], /* Method in URI */ hostname[1024], /* Hostname */ username[255], /* Username info */ - resource[1024], /* Resource info (printer name) */ - filename[1024]; /* File to print */ + resource[1024]; /* Resource info (printer name) */ + const char *filename; /* File to print */ int port; /* Port number (not used) */ char uri[HTTP_MAX_URI];/* Updated URI without user/pass */ ipp_status_t ipp_status; /* Status of IPP request */ @@ -123,6 +134,7 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ *supported; /* get-printer-attributes response */ ipp_attribute_t *job_id_attr; /* job-id attribute */ int job_id; /* job-id value */ + ipp_attribute_t *job_sheets; /* job-media-sheets-completed attribute */ ipp_attribute_t *job_state; /* job-state attribute */ ipp_attribute_t *copies_sup; /* copies-supported attribute */ ipp_attribute_t *charset_sup; /* charset-supported attribute */ @@ -140,6 +152,20 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ #endif /* HAVE_SIGACTION && !HAVE_SIGSET */ int version; /* IPP version */ int reasons; /* Number of printer-state-reasons shown */ + static const char * const pattrs[] = + { /* Printer attributes we want */ + "copies-supported", + "charset-supported", + "document-format-supported", + "printer-is-accepting-jobs", + "printer-state", + "printer-state-reasons", + }; + static const char * const jattrs[] = + { /* Job attributes we want */ + "job-media-sheets-completed", + "job-state" + }; /* @@ -149,17 +175,24 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ setbuf(stderr, NULL); /* - * Ignore SIGPIPE signals... + * Ignore SIGPIPE and catch SIGTERM signals... */ #ifdef HAVE_SIGSET sigset(SIGPIPE, SIG_IGN); + sigset(SIGTERM, sigterm_handler); #elif defined(HAVE_SIGACTION) memset(&action, 0, sizeof(action)); action.sa_handler = SIG_IGN; sigaction(SIGPIPE, &action, NULL); + + sigemptyset(&action.sa_mask); + sigaddset(&action.sa_mask, SIGTERM); + action.sa_handler = sigterm_handler; + sigaction(SIGTERM, &action, NULL); #else signal(SIGPIPE, SIG_IGN); + signal(SIGTERM, sigterm_handler); #endif /* HAVE_SIGSET */ /* @@ -214,7 +247,7 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ int bytes; /* Number of bytes read */ - if ((fd = cupsTempFd(filename, sizeof(filename))) < 0) + if ((fd = cupsTempFd(tmpfilename, sizeof(tmpfilename))) < 0) { perror("ERROR: unable to create temporary file"); return (1); @@ -225,14 +258,15 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ { perror("ERROR: unable to write to temporary file"); close(fd); - unlink(filename); + unlink(tmpfilename); return (1); } close(fd); + filename = tmpfilename; } else - strlcpy(filename, argv[6], sizeof(filename)); + filename = argv[6]; /* * Extract the hostname and printer name from the URI... @@ -354,6 +388,10 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_URI, "printer-uri", NULL, uri); + ippAddStrings(request, IPP_TAG_OPERATION, IPP_TAG_KEYWORD, + "requested-attributes", sizeof(pattrs) / sizeof(pattrs[0]), + NULL, pattrs); + /* * Do the request... */ @@ -479,28 +517,6 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ } } - /* - * Now that we are "connected" to the port, ignore SIGTERM so that we - * can finish out any page data the driver sends (e.g. to eject the - * current page... Only ignore SIGTERM if we are printing data from - * stdin (otherwise you can't cancel raw jobs...) - */ - - if (argc < 7) - { -#ifdef HAVE_SIGSET /* Use System V signals over POSIX to avoid bugs */ - sigset(SIGTERM, SIG_IGN); -#elif defined(HAVE_SIGACTION) - memset(&action, 0, sizeof(action)); - - sigemptyset(&action.sa_mask); - action.sa_handler = SIG_IGN; - sigaction(SIGTERM, &action, NULL); -#else - signal(SIGTERM, SIG_IGN); -#endif /* HAVE_SIGSET */ - } - /* * See if the printer supports multiple copies... */ @@ -747,8 +763,9 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_NAME, "requesting-user-name", NULL, argv[2]); - ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_KEYWORD, - "requested-attributes", NULL, "job-state"); + ippAddStrings(request, IPP_TAG_OPERATION, IPP_TAG_KEYWORD, + "requested-attributes", sizeof(jattrs) / sizeof(jattrs[0]), + NULL, jattrs); /* * Do the request... @@ -787,17 +804,26 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ break; } } - else if ((job_state = ippFindAttribute(response, "job-state", IPP_TAG_ENUM)) != NULL) + + if (response != NULL) { - /* - * Stop polling if the job is finished or pending-held... - */ + if ((job_sheets = ippFindAttribute(response, "job-media-sheets-completed", + IPP_TAG_INTEGER)) != NULL) + fprintf(stderr, "PAGE: total %d\n", job_sheets->values[0].integer); - if (job_state->values[0].integer > IPP_JOB_PROCESSING || - job_state->values[0].integer == IPP_JOB_HELD) + if ((job_state = ippFindAttribute(response, "job-state", + IPP_TAG_ENUM)) != NULL) { - ippDelete(response); - break; + /* + * Stop polling if the job is finished or pending-held... + */ + + if (job_state->values[0].integer > IPP_JOB_PROCESSING || + job_state->values[0].integer == IPP_JOB_HELD) + { + ippDelete(response); + break; + } } } @@ -861,11 +887,11 @@ main(int argc, /* I - Number of command-line arguments (6 or 7) */ ippDelete(supported); /* - * Close and remove the temporary file if necessary... + * Remove the temporary file if necessary... */ - if (argc == 6 || strcmp(filename, argv[6])) - unlink(filename); + if (tmpfilename[6]) + unlink(tmpfilename); /* * Return the queue status... @@ -901,74 +927,86 @@ report_printer_state(ipp_t *ipp) /* I - IPP response */ int i; /* Looping var */ int count; /* Count of reasons shown... */ ipp_attribute_t *reasons; /* printer-state-reasons */ + const char *reason; /* Current reason */ const char *message; /* Message to show */ char unknown[1024]; /* Unknown message string */ + const char *prefix; /* Prefix for STATE: line */ + char state[1024]; /* State string */ if ((reasons = ippFindAttribute(ipp, "printer-state-reasons", IPP_TAG_KEYWORD)) == NULL) return (0); + state[0] = '\0'; + prefix = "STATE: "; + for (i = 0, count = 0; i < reasons->num_values; i ++) { + reason = reasons->values[i].string.text; + + strlcat(state, prefix, sizeof(state)); + strlcat(state, reason, sizeof(state)); + + prefix = ","; message = NULL; - if (strncmp(reasons->values[i].string.text, "media-needed", 12) == 0) + if (strncmp(reason, "media-needed", 12) == 0) message = "Media tray needs to be filled."; - else if (strncmp(reasons->values[i].string.text, "media-jam", 9) == 0) + else if (strncmp(reason, "media-jam", 9) == 0) message = "Media jam!"; - else if (strncmp(reasons->values[i].string.text, "moving-to-paused", 16) == 0 || - strncmp(reasons->values[i].string.text, "paused", 6) == 0 || - strncmp(reasons->values[i].string.text, "shutdown", 8) == 0) + else if (strncmp(reason, "moving-to-paused", 16) == 0 || + strncmp(reason, "paused", 6) == 0 || + strncmp(reason, "shutdown", 8) == 0) message = "Printer off-line."; - else if (strncmp(reasons->values[i].string.text, "toner-low", 9) == 0) + else if (strncmp(reason, "toner-low", 9) == 0) message = "Toner low."; - else if (strncmp(reasons->values[i].string.text, "toner-empty", 11) == 0) + else if (strncmp(reason, "toner-empty", 11) == 0) message = "Out of toner!"; - else if (strncmp(reasons->values[i].string.text, "cover-open", 10) == 0) + else if (strncmp(reason, "cover-open", 10) == 0) message = "Cover open."; - else if (strncmp(reasons->values[i].string.text, "interlock-open", 14) == 0) + else if (strncmp(reason, "interlock-open", 14) == 0) message = "Interlock open."; - else if (strncmp(reasons->values[i].string.text, "door-open", 9) == 0) + else if (strncmp(reason, "door-open", 9) == 0) message = "Door open."; - else if (strncmp(reasons->values[i].string.text, "input-tray-missing", 18) == 0) + else if (strncmp(reason, "input-tray-missing", 18) == 0) message = "Media tray missing!"; - else if (strncmp(reasons->values[i].string.text, "media-low", 9) == 0) + else if (strncmp(reason, "media-low", 9) == 0) message = "Media tray almost empty."; - else if (strncmp(reasons->values[i].string.text, "media-empty", 11) == 0) + else if (strncmp(reason, "media-empty", 11) == 0) message = "Media tray empty!"; - else if (strncmp(reasons->values[i].string.text, "output-tray-missing", 19) == 0) + else if (strncmp(reason, "output-tray-missing", 19) == 0) message = "Output tray missing!"; - else if (strncmp(reasons->values[i].string.text, "output-area-almost-full", 23) == 0) + else if (strncmp(reason, "output-area-almost-full", 23) == 0) message = "Output bin almost full."; - else if (strncmp(reasons->values[i].string.text, "output-area-full", 16) == 0) + else if (strncmp(reason, "output-area-full", 16) == 0) message = "Output bin full!"; - else if (strncmp(reasons->values[i].string.text, "marker-supply-low", 17) == 0) + else if (strncmp(reason, "marker-supply-low", 17) == 0) message = "Ink/toner almost empty."; - else if (strncmp(reasons->values[i].string.text, "marker-supply-empty", 19) == 0) + else if (strncmp(reason, "marker-supply-empty", 19) == 0) message = "Ink/toner empty!"; - else if (strncmp(reasons->values[i].string.text, "marker-waste-almost-full", 24) == 0) + else if (strncmp(reason, "marker-waste-almost-full", 24) == 0) message = "Ink/toner waste bin almost full."; - else if (strncmp(reasons->values[i].string.text, "marker-waste-full", 17) == 0) + else if (strncmp(reason, "marker-waste-full", 17) == 0) message = "Ink/toner waste bin full!"; - else if (strncmp(reasons->values[i].string.text, "fuser-over-temp", 15) == 0) + else if (strncmp(reason, "fuser-over-temp", 15) == 0) message = "Fuser temperature high!"; - else if (strncmp(reasons->values[i].string.text, "fuser-under-temp", 16) == 0) + else if (strncmp(reason, "fuser-under-temp", 16) == 0) message = "Fuser temperature low!"; - else if (strncmp(reasons->values[i].string.text, "opc-near-eol", 12) == 0) + else if (strncmp(reason, "opc-near-eol", 12) == 0) message = "OPC almost at end-of-life."; - else if (strncmp(reasons->values[i].string.text, "opc-life-over", 13) == 0) + else if (strncmp(reason, "opc-life-over", 13) == 0) message = "OPC at end-of-life!"; - else if (strncmp(reasons->values[i].string.text, "developer-low", 13) == 0) + else if (strncmp(reason, "developer-low", 13) == 0) message = "Developer almost empty."; - else if (strncmp(reasons->values[i].string.text, "developer-empty", 15) == 0) + else if (strncmp(reason, "developer-empty", 15) == 0) message = "Developer empty!"; - else if (strstr(reasons->values[i].string.text, "error") != NULL) + else if (strstr(reason, "error") != NULL) { message = unknown; snprintf(unknown, sizeof(unknown), "Unknown printer error (%s)!", - reasons->values[i].string.text); + reason); } if (message) @@ -983,6 +1021,8 @@ report_printer_state(ipp_t *ipp) /* I - IPP response */ } } + fprintf(stderr, "%s\n", state); + return (count); } @@ -1149,5 +1189,25 @@ run_pictwps_filter(char **argv, /* I - Command-line arguments */ /* - * End of "$Id: ipp.c,v 1.38.2.24 2003/02/20 03:50:33 mike Exp $". + * 'sigterm_handler()' - Handle 'terminate' signals that stop the backend. + */ + +static void +sigterm_handler(int sig) /* I - Signal */ +{ + (void)sig; /* remove compiler warnings... */ + + /* + * Remove the temporary file if necessary... + */ + + if (tmpfilename[0]) + unlink(tmpfilename); + + exit(1); +} + + +/* + * End of "$Id: ipp.c,v 1.38.2.25 2003/03/24 21:30:07 mike Exp $". */ diff --git a/scheduler/job.c b/scheduler/job.c index a4f82da14..712a24e9a 100644 --- a/scheduler/job.c +++ b/scheduler/job.c @@ -1,5 +1,5 @@ /* - * "$Id: job.c,v 1.124.2.57 2003/03/21 18:10:02 mike Exp $" + * "$Id: job.c,v 1.124.2.58 2003/03/24 21:30:08 mike Exp $" * * Job management routines for the Common UNIX Printing System (CUPS). * @@ -2200,20 +2200,22 @@ UpdateJob(job_t *job) /* I - Job to check */ if (job->sheets != NULL) { - if (!sscanf(message, "%*d%d", &copies)) + if (!strncasecmp(message, "total ", 6)) { - job->sheets->values[0].integer ++; + /* + * Got a total count of pages from a backend or filter... + */ - if (job->printer->page_limit) - UpdateQuota(job->printer, job->username, 1, 0); - } - else - { - job->sheets->values[0].integer += copies; + copies = atoi(message + 6); + copies -= job->sheets->values[0].integer; /* Just track the delta */ + } + else if (!sscanf(message, "%*d%d", &copies)) + copies = 1; + + job->sheets->values[0].integer += copies; - if (job->printer->page_limit) - UpdateQuota(job->printer, job->username, copies, 0); - } + if (job->printer->page_limit) + UpdateQuota(job->printer, job->username, copies, 0); } LogPage(job, message); @@ -2631,5 +2633,5 @@ start_process(const char *command, /* I - Full path to command */ /* - * End of "$Id: job.c,v 1.124.2.57 2003/03/21 18:10:02 mike Exp $". + * End of "$Id: job.c,v 1.124.2.58 2003/03/24 21:30:08 mike Exp $". */ -- 2.39.5