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 /* 23 * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */ 28 /* All Rights Reserved */ 29 30 31 #pragma ident "%Z%%M% %I% %E% SMI" 32 33 #include "stdio.h" 34 #include "sys/types.h" 35 #include "memory.h" 36 #include "string.h" 37 #include "pwd.h" 38 #include "fcntl.h" 39 #include "errno.h" 40 #include "signal.h" 41 #include "unistd.h" 42 #include "stdlib.h" 43 44 #include "lp.h" 45 #include "access.h" 46 #include "form.h" 47 #include "requests.h" 48 #include "filters.h" 49 #include "printers.h" 50 #include "class.h" 51 #include "users.h" 52 #include "secure.h" 53 #include "msgs.h" 54 55 #include "nodes.h" 56 57 /** 58 ** Defines: 59 **/ 60 61 /* 62 * These are the fields in the PSTATUS and CSTATUS files, 63 * found in the SYSTEM directory. 64 */ 65 66 #define PST_MAX 8 67 # define PST_BRK 0 68 # define PST_NAME 1 69 # define PST_STATUS 2 70 # define PST_DATE 3 71 # define PST_DISREAS 4 72 # define PST_REJREAS 5 73 # define PST_PWHEEL 6 74 # define PST_FORM 7 75 76 #define CST_MAX 5 77 # define CST_BRK 0 78 # define CST_NAME 1 79 # define CST_STATUS 2 80 # define CST_DATE 3 81 # define CST_REJREAS 4 82 83 /* 84 * Exit codes from child processes: 85 * 86 * 0 <= exit <= 0177 (127) are reserved for ``normal'' exits. 87 * 0200 <= exit <= 0377 (255) are reserved for special failures. 88 * 89 * If bit 0200 is set, then we have three sets of special error 90 * codes available, with 32 values in each set (except the first): 91 * 92 * 0201 - 0237 Printer faults 93 * 0240 - 0277 Dial problems 94 * 0300 - 0337 Port problems 95 * 0340 - 0377 Exec problems 96 * 97 * 0200 Interface received SIGTERM 98 */ 99 #define EXEC_EXIT_OKAY 0 /* success */ 100 #define EXEC_EXIT_USER 0177 /* user exit codes, 7 bits */ 101 #define EXEC_EXIT_NMASK 0340 /* mask to uncover reason bits */ 102 #define EXEC_EXIT_FAULT 0201 /* printer fault */ 103 #define EXEC_EXIT_HUP 0202 /* got hangup early in exec */ 104 #define EXEC_EXIT_INTR 0203 /* got interrupt early in exec */ 105 #define EXEC_EXIT_PIPE 0204 /* got close of FIFO early in exec */ 106 #define EXEC_EXIT_EXIT 0237 /* interface used reserved exit code */ 107 #define EXEC_EXIT_NDIAL 0240 /* can't dial, low 5 bits abs(dial()) */ 108 #define EXEC_EXIT_NPORT 0300 /* can't open port */ 109 #define EXEC_EXIT_TMOUT 0301 /* can't open port in N seconds */ 110 #define EXEC_EXIT_NOPEN 0340 /* can't open input/output file */ 111 #define EXEC_EXIT_NEXEC 0341 /* can't exec */ 112 #define EXEC_EXIT_NOMEM 0342 /* malloc failed */ 113 #define EXEC_EXIT_NFORK 0343 /* fork failed, must try again */ 114 #define EXEC_EXIT_NPUSH 0344 /* could not push streams module(s) */ 115 116 #define EXIT_RETRY 129 /* interface failed, try again */ 117 118 /* 119 * If killed, return signal, else 0. 120 */ 121 #define KILLED(x) (!(x & 0xFF00)? (x & 0x7F) : 0) 122 123 /* 124 * If exited, return exit code, else -1. 125 */ 126 #define EXITED(x) (!(x & 0xFF)? ((x >> 8) & 0xFF) : -1) 127 128 /* 129 * Events that can be scheduled: 130 */ 131 #define EV_SLOWF 1 132 #define EV_INTERF 2 133 #define EV_NOTIFY 3 134 #define EV_LATER 4 135 #define EV_ALARM 5 136 #define EV_MESSAGE 6 137 #define EV_ENABLE 7 138 #define EV_FORM_MESSAGE 8 139 140 /* 141 * How long to wait before retrying an event: 142 * (For best results, make CLOCK_TICK a factor of 60.) 143 */ 144 #define CLOCK_TICK 10 /* no. seconds between alarms */ 145 #define MINUTE (60/CLOCK_TICK) /* number of ticks per minute */ 146 #define WHEN_FORK (MINUTE) /* retry forking child process */ 147 #define WHEN_PRINTER (1*MINUTE) /* retry faulted printer */ 148 149 /* 150 * Alert types: 151 */ 152 #define A_PRINTER 1 153 #define A_PWHEEL 2 154 #define A_FORM 3 155 156 /* 157 * How to handle active requests when disabling a printer: 158 */ 159 #define DISABLE_STOP 0 160 #define DISABLE_FINISH 1 161 #define DISABLE_CANCEL 2 162 163 /* 164 * validate_request() - VERIFY REQUEST CAN BE PRINTED 165 * evaluate_request() - TRY REQUEST ON A PARTICULAR PRINTER 166 * reevaluate_request() - TRY TO MOVE REQUEST TO ANOTHER PRINTER 167 */ 168 169 #define validate_request(PRS,PREFIXP,MOVING) \ 170 _validate((PRS), (PSTATUS *)0, (PSTATUS *)0, (PREFIXP), (MOVING)) 171 172 #define evaluate_request(PRS,PPS,MOVING) \ 173 _validate((PRS), (PPS), (PSTATUS *)0, (char **)0, (MOVING)) 174 175 #define reevaluate_request(PRS,PPS) \ 176 _validate((PRS), (PSTATUS *)0, (PPS), (char **)0, 0) 177 178 /* 179 * Request is ready to be slow-filtered: 180 */ 181 #define NEEDS_FILTERING(PRS) \ 182 ((PRS)->slow && !((PRS)->request->outcome & RS_FILTERED)) 183 184 /* 185 * Misc: 186 */ 187 188 #define isadmin(ID) (!(ID) || (ID) == Lp_Uid) 189 190 #define makereqerr(PRS) \ 191 makepath( \ 192 Lp_Temp, \ 193 getreqno((PRS)->secure->req_id), \ 194 (char *)0 \ 195 ) 196 197 #define EVER ;; 198 199 #define DEFAULT_SHELL "/bin/sh" 200 201 #define BINMAIL "/bin/mail" 202 #define BINWRITE "/bin/write" 203 204 #define RMCMD "/usr/bin/rm -f" 205 206 207 #if defined(MLISTENDEL_WORKS) 208 #define DROP_MD(MD) if (MD) { \ 209 mlistendel (MD); \ 210 mdisconnect (MD); \ 211 MD = 0; \ 212 } else /*EMPTY*/ 213 #else 214 #define DROP_MD(MD) if (MD) { \ 215 Close ((MD)->readfd); \ 216 if ((MD)->writefd == (MD)->readfd) \ 217 (MD)->writefd = -1; \ 218 (MD)->readfd = -1; \ 219 MD = 0; \ 220 } else /*EMPTY*/ 221 #endif 222 223 /** 224 ** External routines: 225 **/ 226 227 typedef int (*qchk_fnc_type)( RSTATUS * ); 228 229 CLASS * Getclass ( char * ); 230 231 extern void GetRequestFiles(REQUEST *req, char *buffer, int length); 232 233 234 PRINTER * Getprinter ( char * ); 235 236 PWHEEL * Getpwheel ( char * ); 237 238 239 REQUEST * Getrequest ( char * ); 240 241 RSTATUS * request_by_id ( char * ); 242 RSTATUS * request_by_id_num ( long ); 243 RSTATUS * request_by_jobid ( char * , char * ); 244 245 SECURE * Getsecure ( char * ); 246 247 USER * Getuser ( char * ); 248 249 _FORM * Getform ( char * ); 250 251 char * _alloc_files ( int , char * , uid_t , gid_t); 252 char * dispatchName(int); 253 char * statusName(int); 254 char * getreqno ( char * ); 255 256 int Loadfilters ( char * ); 257 int Putsecure(char *, SECURE *); 258 int cancel ( RSTATUS * , int ); 259 int disable ( PSTATUS * , char * , int ); 260 int enable ( PSTATUS * ); 261 int exec ( int , ... ); 262 int one_printer_with_charsets ( RSTATUS * ); 263 int open_dialup ( char * , PRINTER * ); 264 int open_direct ( char * , PRINTER * ); 265 int qchk_filter ( RSTATUS * ); 266 int qchk_form ( RSTATUS * ); 267 int qchk_pwheel ( RSTATUS * ); 268 int qchk_waiting ( RSTATUS * ); 269 int queue_repel ( PSTATUS * , int , int (*)( RSTATUS * ) ); 270 int rsort ( RSTATUS ** , RSTATUS ** ); 271 272 long getkey ( void ); 273 long _alloc_req_id ( void ); 274 275 off_t chfiles ( char ** , uid_t , gid_t ); 276 277 short _validate ( RSTATUS * , PSTATUS * , PSTATUS * , char ** , int ); 278 279 void add_flt_act ( MESG * , ... ); 280 void alert ( int , ... ); 281 void cancel_alert ( int , ... ); 282 void check_children ( void ); 283 void check_form_alert ( FSTATUS * , _FORM * ); 284 void check_pwheel_alert ( PWSTATUS * , PWHEEL * ); 285 void check_request ( RSTATUS * ); 286 void del_flt_act ( MESG * , ... ); 287 void dial_problem ( PSTATUS * , RSTATUS * , int ); 288 void dispatch ( int , char * , MESG * ); 289 void dowait ( void ); 290 void dump_cstatus ( void ); 291 void dump_fault_status(PSTATUS *); 292 void dump_pstatus ( void ); 293 void dump_status ( void ); 294 void execlog ( char * , ... ); 295 void fail ( char * , ... ); 296 void free_form ( _FORM * ); 297 void freerstatus ( register RSTATUS * ); 298 void init_memory ( void ); 299 void init_messages ( void ); 300 void insertr ( RSTATUS * ); 301 void load_sdn ( char ** , SCALED ); 302 void load_status ( void ); 303 void load_str ( char ** , char * ); 304 void lp_endpwent ( void ); 305 void lp_setpwent ( void ); 306 void lpfsck ( void ); 307 void lpshut ( int ); 308 void mallocfail ( void ); 309 void maybe_schedule ( RSTATUS * ); 310 void note ( char * , ... ); 311 void notify ( RSTATUS * , char * , int , int , int ); 312 void printer_fault ( PSTATUS * , RSTATUS * , char * , int ); 313 void clear_printer_fault ( PSTATUS * , char * ); 314 void putjobfiles ( RSTATUS * ); 315 void queue_attract ( PSTATUS * , int (*)( RSTATUS * ) , int ); 316 void queue_check ( int (*)( RSTATUS * ) ); 317 void queue_form ( RSTATUS * , FSTATUS * ); 318 void queue_pwheel ( RSTATUS * , char * ); 319 void remount_form(register PSTATUS *, FSTATUS *, short); 320 void remover ( RSTATUS * ); 321 void rmfiles ( RSTATUS * , int ); 322 void rmreq ( RSTATUS * ); 323 void schedule ( int , ... ); 324 void take_message ( void ); 325 void terminate ( EXEC * ); 326 void unload_list ( char *** ); 327 void unload_str ( char ** ); 328 void unqueue_form ( RSTATUS * ); 329 void unqueue_pwheel ( RSTATUS * ); 330 void update_req ( char * , long ); 331 int isFormMountedOnPrinter ( PSTATUS *, FSTATUS * ); 332 int isFormUsableOnPrinter ( PSTATUS *, FSTATUS * ); 333 char *allTraysWithForm ( PSTATUS *, FSTATUS * ); 334 extern int list_append(void ***, void *); 335 extern void list_remove(void ***, void *); 336 337 extern RSTATUS *new_rstatus(REQUEST *, SECURE *); 338 extern PSTATUS *new_pstatus(PRINTER *); 339 extern CSTATUS *new_cstatus(CLASS *); 340 extern FSTATUS *new_fstatus(_FORM *f); 341 extern PWSTATUS *new_pwstatus(PWHEEL *p); 342 extern ALERT *new_alert(char *fmt, int i); 343 extern EXEC *new_exec(int type, void *ex); 344 345 extern void pstatus_add_printer(PSTATUS *, PRINTER *); 346 347 extern void free_exec(EXEC *); 348 extern void free_alert(ALERT *); 349 extern void free_pwstatus(PWSTATUS *); 350 extern void free_fstatus(FSTATUS *); 351 extern void free_cstatus(CSTATUS *); 352 extern void free_pstatus(PSTATUS *); 353 extern void free_rstatus(RSTATUS *); 354 355 extern CSTATUS *search_cstatus ( char * ); 356 extern FSTATUS *search_fptable(register char *); 357 extern FSTATUS *search_fstatus ( char * ); 358 extern PSTATUS *search_pstatus ( char * ); 359 extern PWSTATUS *search_pwstatus ( char * ); 360 361 /* 362 * Things that can't be passed as parameters: 363 */ 364 365 extern FSTATUS *form_in_question; 366 367 extern char *pwheel_in_question; 368 369 /** 370 ** External tables, lists: 371 **/ 372 373 extern CSTATUS **CStatus; /* Status of classes */ 374 extern PSTATUS **PStatus; /* Status of printers */ 375 extern FSTATUS **FStatus; /* Status of forms */ 376 extern PWSTATUS **PWStatus; /* Status of print wheels */ 377 378 extern EXEC **Exec_Table; /* Running processes */ 379 extern EXEC **Exec_Slow, /* First slow filter exec */ 380 **Exec_Notify; /* First notification exec */ 381 382 extern RSTATUS *Request_List; /* Queue of print requests */ 383 extern RSTATUS *NewRequest; /* Not in Request_List yet */ 384 385 extern int ET_SlowSize, /* Number of filter execs */ 386 ET_NotifySize; /* Number of notify execs */ 387 388 #if defined(DEBUG) 389 #define DB_ABORT 0x00000008 390 #define DB_SDB 0x00000020 391 #define DB_ALL 0xFFFFFFFF 392 393 extern unsigned long debug; 394 #endif 395 396 extern char *Local_System, /* Node name of local system */ 397 *SHELL; /* value of $SHELL, or default */ 398 399 extern int lock_fd; 400 401 extern uid_t Lp_Uid; 402 403 extern gid_t Lp_Gid; 404 405 extern int Starting, 406 OpenMax, 407 Sig_Alrm, 408 DoneChildren, 409 am_in_background, 410 Shutdown; 411 412 extern unsigned long chkprinter_result; 413 414 #if defined(MDL) 415 #include "mdl.h" 416 #endif 417 # define CLOSE_ON_EXEC(fd) (void) Fcntl(fd, F_SETFD, 1) 418