1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */ 27 /* All Rights Reserved */ 28 29 #include "lpsched.h" 30 31 static char *N_Msg[] = { 32 "Subject: Status of lp request %s\n\nYour request %s destined for %s%s\n", 33 "has completed successfully on printer %s.\n", 34 "was canceled by the lpsched daemon%s\n", /* bugfix 1100252 */ 35 "encountered an error during filtering.\n", 36 "encountered an error while printing on printer %s.\n", 37 "Filtering stopped with an exit code of %d.\n", 38 "Printing stopped with an exit code of %d.\n", 39 "Filtering was interrupted with a signal %d.\n", 40 "Printing was interrupted with a signal %d.\n", 41 "\nReason for failure:\n\n%s\n", 42 "\nReason for being canceled:\n\n%s\n", 43 }; 44 45 static struct reason { 46 short reason; 47 char *msg; 48 } N_Reason[] = { 49 { 50 MNODEST, 51 "The requested print destination has been removed." 52 }, { 53 MERRDEST, 54 "All candidate destinations are rejecting further requests." 55 }, { 56 MDENYDEST, 57 "You are no longer allowed to use any printer suitable for\nthe request." 58 }, { 59 MDENYDEST, 60 "No candidate printer can handle these characteristics:" 61 }, { 62 MNOMEDIA, 63 "The form you requested no longer exists." 64 }, { 65 MDENYMEDIA, 66 "You are no longer allowed to use the form you requested." 67 }, { 68 MDENYMEDIA, 69 "The form you wanted now requires a different character set." 70 }, { 71 MNOFILTER, 72 "There is no longer a filter that will convert your file for printing." 73 }, { 74 MNOMOUNT, 75 "The form or print wheel you requested is not allowed on any\nprinter otherwise suitable for the request." 76 }, { 77 MNOSPACE, 78 "Memory allocation problem." 79 }, { 80 -1, 81 "" 82 } 83 }; 84 85 86 static void print_reason(int, int); 87 88 89 /** 90 ** notify() - NOTIFY USER OF FINISHED REQUEST 91 **/ 92 93 void 94 notify(register RSTATUS *prs, char *errbuf, int k, int e, int slow) 95 { 96 register char *cp; 97 char *file; 98 int fd; 99 100 101 /* 102 * Screen out cases where no notification is needed. 103 */ 104 if (!(prs->request->outcome & RS_NOTIFY)) 105 return; 106 if ( 107 !(prs->request->actions & (ACT_MAIL|ACT_WRITE|ACT_NOTIFY)) 108 && !prs->request->alert 109 && !(prs->request->outcome & RS_CANCELLED) 110 && !e && !k && !errbuf /* exited normally */ 111 ) 112 return; 113 114 /* 115 * Create the notification message to the user. 116 */ 117 file = makereqerr(prs); 118 if ((fd = open_locked(file, "w", MODE_NOREAD)) >= 0) { 119 fdprintf(fd, N_Msg[0], prs->secure->req_id, prs->secure->req_id, 120 prs->request->destination, 121 STREQU(prs->request->destination, NAME_ANY)? " printer" 122 : ""); 123 124 if (prs->request) { 125 char file[BUFSIZ]; 126 127 GetRequestFiles(prs->request, file, sizeof(file)); 128 fdprintf(fd, "\nThe job title was:\t%s\n", file); 129 fdprintf(fd, " submitted by:\t%s\n", 130 prs->request->user); 131 fdprintf(fd, " at:\t%s\n", 132 ctime(&prs->secure->date)); 133 } 134 135 if (prs->request->outcome & RS_PRINTED) 136 fdprintf(fd, N_Msg[1], prs->printer->printer->name); 137 138 if (prs->request->outcome & RS_CANCELLED) 139 fdprintf(fd, N_Msg[2], 140 (prs->request->outcome & RS_FAILED)? ", and" 141 : "."); 142 143 144 if (prs->request->outcome & RS_FAILED) { 145 if (slow) 146 fdprintf(fd, N_Msg[3]); 147 else 148 fdprintf(fd, N_Msg[4], 149 prs->printer->printer->name); 150 151 if (e > 0) 152 fdprintf(fd, N_Msg[slow? 5 : 6], e); 153 else if (k) 154 fdprintf(fd, N_Msg[slow? 7 : 8], k); 155 } 156 157 if (errbuf) { 158 for (cp = errbuf; *cp && *cp == '\n'; cp++) 159 ; 160 fdprintf(fd, N_Msg[9], cp); 161 if (prs->request->outcome & RS_CANCELLED) 162 fdprintf(fd, "\n"); 163 } 164 165 /* start fix for bugid 1100252 */ 166 if (prs->request->outcome & RS_CANCELLED) { 167 print_reason (fd, prs->reason); 168 } 169 170 close(fd); 171 schedule (EV_NOTIFY, prs); 172 173 } 174 if (file) 175 Free (file); 176 177 return; 178 } 179 180 /** 181 ** print_reason() - PRINT REASON FOR AUTOMATIC CANCEL 182 **/ 183 184 static void 185 print_reason(int fd, int reason) 186 { 187 register int i; 188 189 190 #define P(BIT,MSG) if (chkprinter_result & BIT) fdprintf(fd, MSG) 191 192 for (i = 0; N_Reason[i].reason != -1; i++) 193 if (N_Reason[i].reason == reason) { 194 if (reason == MDENYDEST && chkprinter_result) 195 i++; 196 if (reason == MDENYMEDIA && chkprinter_result) 197 i++; 198 fdprintf(fd, N_Msg[10], N_Reason[i].msg); 199 if (reason == MDENYDEST && chkprinter_result) { 200 P (PCK_TYPE, "\tprinter type\n"); 201 P (PCK_CHARSET, "\tcharacter set\n"); 202 P (PCK_CPI, "\tcharacter pitch\n"); 203 P (PCK_LPI, "\tline pitch\n"); 204 P (PCK_WIDTH, "\tpage width\n"); 205 P (PCK_LENGTH, "\tpage length\n"); 206 P (PCK_BANNER, "\tno banner\n"); 207 } 208 break; 209 } 210 211 return; 212 } 213