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, Version 1.0 only 6 * (the "License"). You may not use this file except in compliance 7 * with the License. 8 * 9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10 * or http://www.opensolaris.org/os/licensing. 11 * See the License for the specific language governing permissions 12 * and limitations under the License. 13 * 14 * When distributing Covered Code, include this CDDL HEADER in each 15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16 * If applicable, add the following below this CDDL HEADER, with the 17 * fields enclosed by brackets "[]" replaced with your own identifying 18 * information: Portions Copyright [yyyy] [name of copyright owner] 19 * 20 * CDDL HEADER END 21 */ 22 /* 23 * Copyright 2001 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" /* SVr4.0 1.9.1.11 */ 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 "systems.h" 53 #include "secure.h" 54 #include "msgs.h" 55 56 #include "nodes.h" 57 58 /** 59 ** Defines: 60 **/ 61 62 /* 63 * These are the fields in the PSTATUS and CSTATUS files, 64 * found in the SYSTEM directory. 65 */ 66 67 #define PST_MAX 8 68 # define PST_BRK 0 69 # define PST_NAME 1 70 # define PST_STATUS 2 71 # define PST_DATE 3 72 # define PST_DISREAS 4 73 # define PST_REJREAS 5 74 # define PST_PWHEEL 6 75 # define PST_FORM 7 76 77 #define CST_MAX 5 78 # define CST_BRK 0 79 # define CST_NAME 1 80 # define CST_STATUS 2 81 # define CST_DATE 3 82 # define CST_REJREAS 4 83 84 /* 85 * Exit codes from child processes: 86 * 87 * 0 <= exit <= 0177 (127) are reserved for ``normal'' exits. 88 * 0200 <= exit <= 0377 (255) are reserved for special failures. 89 * 90 * If bit 0200 is set, then we have three sets of special error 91 * codes available, with 32 values in each set (except the first): 92 * 93 * 0201 - 0237 Printer faults 94 * 0240 - 0277 Dial problems 95 * 0300 - 0337 Port problems 96 * 0340 - 0377 Exec problems 97 * 98 * 0200 Interface received SIGTERM 99 */ 100 #define EXEC_EXIT_OKAY 0 /* success */ 101 #define EXEC_EXIT_USER 0177 /* user exit codes, 7 bits */ 102 #define EXEC_EXIT_NMASK 0340 /* mask to uncover reason bits */ 103 #define EXEC_EXIT_FAULT 0201 /* printer fault */ 104 #define EXEC_EXIT_HUP 0202 /* got hangup early in exec */ 105 #define EXEC_EXIT_INTR 0203 /* got interrupt early in exec */ 106 #define EXEC_EXIT_PIPE 0204 /* got close of FIFO early in exec */ 107 #define EXEC_EXIT_EXIT 0237 /* interface used reserved exit code */ 108 #define EXEC_EXIT_NDIAL 0240 /* can't dial, low 5 bits abs(dial()) */ 109 #define EXEC_EXIT_NPORT 0300 /* can't open port */ 110 #define EXEC_EXIT_TMOUT 0301 /* can't open port in N seconds */ 111 #define EXEC_EXIT_NOPEN 0340 /* can't open input/output file */ 112 #define EXEC_EXIT_NEXEC 0341 /* can't exec */ 113 #define EXEC_EXIT_NOMEM 0342 /* malloc failed */ 114 #define EXEC_EXIT_NFORK 0343 /* fork failed, must try again */ 115 #define EXEC_EXIT_NPUSH 0344 /* could not push streams module(s) */ 116 117 #define EXIT_RETRY 129 /* interface failed, try again */ 118 119 /* 120 * If killed, return signal, else 0. 121 */ 122 #define KILLED(x) (!(x & 0xFF00)? (x & 0x7F) : 0) 123 124 /* 125 * If exited, return exit code, else -1. 126 */ 127 #define EXITED(x) (!(x & 0xFF)? ((x >> 8) & 0xFF) : -1) 128 129 /* 130 * Events that can be scheduled: 131 */ 132 #define EV_SLOWF 1 133 #define EV_INTERF 2 134 #define EV_NOTIFY 3 135 #define EV_LATER 4 136 #define EV_ALARM 5 137 #define EV_MESSAGE 6 138 #define EV_CHECKCHILD 7 139 #define EV_SYSTEM 8 140 #define EV_ENABLE 9 141 #define EV_POLLBSDSYSTEMS 10 142 #define EV_FORM_MESSAGE 11 143 #define EV_STATUS 12 144 145 /* 146 * How long to wait before retrying an event: 147 * (For best results, make CLOCK_TICK a factor of 60.) 148 */ 149 #define CLOCK_TICK 10 /* no. seconds between alarms */ 150 #define MINUTE (60/CLOCK_TICK) /* number of ticks per minute */ 151 #define WHEN_FORK (MINUTE) /* retry forking child process */ 152 #define WHEN_PRINTER (1*MINUTE) /* retry faulted printer */ 153 154 /* 155 * Alert types: 156 */ 157 #define A_PRINTER 1 158 #define A_PWHEEL 2 159 #define A_FORM 3 160 161 /* 162 * How to handle active requests when disabling a printer: 163 */ 164 #define DISABLE_STOP 0 165 #define DISABLE_FINISH 1 166 #define DISABLE_CANCEL 2 167 168 /* 169 * validate_request() - VERIFY REQUEST CAN BE PRINTED 170 * evaluate_request() - TRY REQUEST ON A PARTICULAR PRINTER 171 * reevaluate_request() - TRY TO MOVE REQUEST TO ANOTHER PRINTER 172 */ 173 174 #define validate_request(PRS,PREFIXP,MOVING) \ 175 _validate((PRS), (PSTATUS *)0, (PSTATUS *)0, (PREFIXP), (MOVING)) 176 177 #define evaluate_request(PRS,PPS,MOVING) \ 178 _validate((PRS), (PPS), (PSTATUS *)0, (char **)0, (MOVING)) 179 180 #define reevaluate_request(PRS,PPS) \ 181 _validate((PRS), (PSTATUS *)0, (PPS), (char **)0, 0) 182 183 /* 184 * Request is ready to be slow-filtered: 185 */ 186 #define NEEDS_FILTERING(PRS) \ 187 ((PRS)->slow && !((PRS)->request->outcome & RS_FILTERED)) 188 189 /* 190 * Where requests are handled: 191 */ 192 193 #define PRINTING_AT(PRS,PSS) \ 194 ((PRS)->printer->system == (PSS)) 195 196 #define ORIGINATING_AT(PRS,PSS) \ 197 STREQU((PRS)->secure->system, (PSS)->system->name) 198 199 /* 200 * Misc: 201 */ 202 203 #define isadmin(ID) (!(ID) || (ID) == Lp_Uid) 204 205 #define makereqerr(PRS) \ 206 makepath( \ 207 Lp_Tmp, \ 208 (PRS)->secure->system, \ 209 getreqno((PRS)->secure->req_id), \ 210 (char *)0 \ 211 ) 212 213 #define EVER ;; 214 215 #define DEFAULT_SHELL "/bin/sh" 216 217 #define BINMAIL "/bin/mail" 218 #define BINWRITE "/bin/write" 219 220 #define RMCMD "/usr/bin/rm -f" 221 222 223 #if defined(MLISTENDEL_WORKS) 224 #define DROP_MD(MD) if (MD) { \ 225 mlistendel (MD); \ 226 mdisconnect (MD); \ 227 } else /*EMPTY*/ 228 #else 229 #define DROP_MD(MD) if (MD) { \ 230 Close ((MD)->readfd); \ 231 if ((MD)->writefd == (MD)->readfd) \ 232 (MD)->writefd = -1; \ 233 (MD)->readfd = -1; \ 234 } else /*EMPTY*/ 235 #endif 236 237 /** 238 ** External routines: 239 **/ 240 241 typedef int (*qchk_fnc_type)( RSTATUS * ); 242 243 CLASS * Getclass ( char * ); 244 245 CSTATUS * search_ctable ( char * ); 246 CSTATUS * walk_ctable ( int ); 247 248 249 FSTATUS * search_fptable(register char *); 250 FSTATUS * search_ftable ( char * ); 251 FSTATUS * walk_ftable ( int ); 252 253 extern void GetRequestFiles(REQUEST *req, char *buffer, int length); 254 255 256 PRINTER * Getprinter ( char * ); 257 258 PSTATUS * search_ptable ( char * ); 259 PSTATUS * walk_ptable ( int ); 260 261 PWHEEL * Getpwheel ( char * ); 262 263 PWSTATUS * search_pwtable ( char * ); 264 PWSTATUS * walk_pwtable ( int ); 265 266 REQUEST * Getrequest ( char * ); 267 268 RSTATUS * allocr ( void ); 269 RSTATUS * request_by_id ( char * ); 270 RSTATUS * request_by_id_num ( long ); 271 RSTATUS * request_by_jobid ( char * , char * ); 272 RSTATUS * walk_req_by_dest ( RSTATUS ** , char * ); 273 RSTATUS * walk_req_by_form ( RSTATUS ** , FSTATUS * ); 274 RSTATUS * walk_req_by_printer ( RSTATUS ** , PSTATUS * ); 275 RSTATUS * walk_req_by_pwheel ( RSTATUS ** , char * ); 276 277 SECURE * Getsecure ( char * ); 278 279 USER * Getuser ( char * ); 280 281 _FORM * Getform ( char * ); 282 283 char * _alloc_files ( int , char * , uid_t , gid_t, char * ); 284 char * dispatchName(int); 285 char * statusName(int); 286 char * getreqno ( char * ); 287 288 int Loadfilters ( char * ); 289 int Putsecure(char *, SECURE *); 290 int cancel ( RSTATUS * , int ); 291 int disable ( PSTATUS * , char * , int ); 292 int enable ( PSTATUS * ); 293 int exec ( int , ... ); 294 int one_printer_with_charsets ( RSTATUS * ); 295 int open_dialup ( char * , PRINTER * ); 296 int open_direct ( char * , PRINTER * ); 297 int qchk_filter ( RSTATUS * ); 298 int qchk_form ( RSTATUS * ); 299 int qchk_pwheel ( RSTATUS * ); 300 int qchk_waiting ( RSTATUS * ); 301 int queue_repel ( PSTATUS * , int , int (*)( RSTATUS * ) ); 302 int rsort ( RSTATUS ** , RSTATUS ** ); 303 304 long getkey ( void ); 305 long _alloc_req_id ( void ); 306 307 off_t chfiles ( char ** , uid_t , gid_t ); 308 309 short _validate ( RSTATUS * , PSTATUS * , PSTATUS * , char ** , int ); 310 311 void add_flt_act ( MESG * , ... ); 312 void alert ( int , ... ); 313 void cancel_alert ( int , ... ); 314 void check_children ( void ); 315 void check_form_alert ( FSTATUS * , _FORM * ); 316 void check_pwheel_alert ( PWSTATUS * , PWHEEL * ); 317 void check_request ( RSTATUS * ); 318 void del_flt_act ( MESG * , ... ); 319 void dial_problem ( PSTATUS * , RSTATUS * , int ); 320 void dispatch ( int , char * , MESG * ); 321 void dowait ( void ); 322 void dump_cstatus ( void ); 323 void dump_fault_status(PSTATUS *); 324 void dump_pstatus ( void ); 325 void dump_status ( void ); 326 void execlog ( char * , ... ); 327 void fail ( char * , ... ); 328 void free_form ( _FORM * ); 329 void freerstatus ( register RSTATUS * ); 330 void init_memory ( void ); 331 void init_messages ( void ); 332 void insertr ( RSTATUS * ); 333 void load_sdn ( char ** , SCALED ); 334 void load_status ( void ); 335 void load_str ( char ** , char * ); 336 void lp_endpwent ( void ); 337 void lp_setpwent ( void ); 338 void lpfsck ( void ); 339 void lpshut ( int ); 340 void mallocfail ( void ); 341 void maybe_schedule ( RSTATUS * ); 342 void note ( char * , ... ); 343 void notify ( RSTATUS * , char * , int , int , int ); 344 void printer_fault ( PSTATUS * , RSTATUS * , char * , int ); 345 void clear_printer_fault ( PSTATUS * , char * ); 346 void putjobfiles ( RSTATUS * ); 347 void queue_attract ( PSTATUS * , int (*)( RSTATUS * ) , int ); 348 void queue_check ( int (*)( RSTATUS * ) ); 349 void queue_form ( RSTATUS * , FSTATUS * ); 350 void queue_pwheel ( RSTATUS * , char * ); 351 void remount_form(register PSTATUS *, FSTATUS *, short); 352 void remover ( RSTATUS * ); 353 void rmfiles ( RSTATUS * , int ); 354 void rmreq ( RSTATUS * ); 355 void schedule ( int , ... ); 356 void take_message ( void ); 357 void terminate ( EXEC * ); 358 void unload_list ( char *** ); 359 void unload_str ( char ** ); 360 void unqueue_form ( RSTATUS * ); 361 void unqueue_pwheel ( RSTATUS * ); 362 void update_req ( char * , long ); 363 int isFormMountedOnPrinter ( PSTATUS *, FSTATUS * ); 364 int isFormUsableOnPrinter ( PSTATUS *, FSTATUS * ); 365 char *allTraysWithForm ( PSTATUS *, FSTATUS * ); 366 367 /* 368 * Things that can't be passed as parameters: 369 */ 370 371 extern FSTATUS *form_in_question; 372 373 extern char *pwheel_in_question; 374 375 /** 376 ** External tables, lists: 377 **/ 378 379 extern CSTATUS *CStatus; /* Status of classes */ 380 381 extern EXEC *Exec_Table; /* Running processes */ 382 383 extern FSTATUS *FStatus; /* Status of forms */ 384 385 extern PSTATUS *PStatus; /* Status of printers */ 386 387 extern PWSTATUS *PWStatus; /* Status of print wheels */ 388 389 extern RSTATUS *Request_List; /* Queue of print requests */ 390 extern RSTATUS *Status_List; /* Queue of fake requests */ 391 extern RSTATUS *NewRequest; /* Not in Request_List yet */ 392 393 extern EXEC *Exec_Slow, /* First slow filter exec */ 394 *Exec_Notify; /* First notification exec */ 395 396 extern int CT_Size, /* Size of class table */ 397 ET_Size, /* Size of exec table */ 398 ET_SlowSize, /* Number of filter execs */ 399 ET_NotifySize, /* Number of notify execs */ 400 FT_Size, /* Size of form table */ 401 PT_Size, /* Size of printer table */ 402 PWT_Size, /* Size of print wheel table */ 403 ST_Size, /* Size of system status table */ 404 ST_Count; /* No. active entries in above */ 405 406 #if defined(DEBUG) 407 #define DB_EXEC 0x00000001 408 #define DB_DONE 0x00000002 409 #define DB_INIT 0x00000004 410 #define DB_ABORT 0x00000008 411 #define DB_SCHEDLOG 0x00000010 412 #define DB_SDB 0x00000020 413 #define DB_MESSAGES 0x00000040 414 #define DB_MALLOC 0x00000080 415 #define DB_ALL 0xFFFFFFFF 416 417 extern unsigned long debug; 418 #endif 419 420 extern char *Local_System, /* Node name of local system */ 421 *SHELL; /* value of $SHELL, or default */ 422 423 extern int lock_fd; 424 425 extern uid_t Lp_Uid; 426 427 extern gid_t Lp_Gid; 428 429 extern int Starting, 430 OpenMax, 431 Sig_Alrm, 432 DoneChildren, 433 am_in_background, 434 Shutdown; 435 436 extern unsigned long chkprinter_result; 437 438 #if defined(MDL) 439 #include "mdl.h" 440 #endif 441 # define CLOSE_ON_EXEC(fd) (void) Fcntl(fd, F_SETFD, 1) 442