home *** CD-ROM | disk | FTP | other *** search
/ PC World Komputer 1999 March B / SCO_CASTOR4RRT.iso / update701 / root.17 / usr / lib / lp / model / PS / PS
Encoding:
Text File  |  1998-08-18  |  17.8 KB  |  817 lines

  1. #!/usr/bin/sh
  2. #ident    "@(#)PS    1.3"
  3. #ident  "$Header: $"
  4.  
  5. ###########
  6. ##
  7. ##  PostScript interface program.
  8. ##
  9. ###########
  10. umask 0
  11.  
  12.  
  13. #####
  14. ##
  15. ##  Some logs.
  16. ##
  17. #####
  18. LOGFILE="/var/tmp/$$.log"
  19. ERRFILE="/var/tmp/$$.err"
  20.  
  21. /sbin/rm -f $LOGFILE $ERRFILE
  22.  
  23. #####
  24. #
  25. #  Special for debugging.
  26. #
  27. #####
  28. DEBUGFILE="/var/tmp/PS.debug"
  29. #echo "$LOGFILE" >$DEBUGFILE
  30. #echo "$ERRFILE" >>$DEBUGFILE
  31. #echo "$*" >>$DEBUGFILE
  32. #/usr/bin/env >>$DEBUGFILE
  33.  
  34. #####
  35. ##
  36. ##  Some tools.  Options will be added later.
  37. ##
  38. #####
  39. LPBIN="/usr/lib/lp/bin"
  40. PSBIN="/usr/lib/lp/postscript"
  41. PATH="/bin:/usr/bin:${LPBIN}"
  42.  
  43. LPCAT="$LPBIN/lp.cat"
  44. LPTELL="$LPBIN/lp.tell"
  45.  
  46. #####
  47. # ${DRAIN} is the name of a program that will wait
  48. # long enough for data sent to the printer to print.
  49. #####
  50. if [ -x "${LPBIN}/drain.output" ]
  51. then
  52.     DRAIN="${LPBIN}/drain.output 5"    # wait only five seconds
  53. else
  54.     DRAIN=
  55. fi
  56.  
  57. POSTPRINT="$PSBIN/postprint"
  58. DOWNLOAD="$PSBIN/download"
  59. POSTREVERSE="$PSBIN/postreverse"
  60. POSTIO="$PSBIN/postio"
  61. POSTIO_B="$LPCAT"
  62.  
  63. CAT=/usr/bin/cat
  64. MAILX=/usr/bin/mailx
  65.  
  66. #####
  67. #
  68. # Until we get to the point below where the printer port
  69. # and physical printer are initialized, we can't do much
  70. # except exit if the Spooler/Scheduler cancels us.
  71. #
  72. #####
  73. ExitCode=0
  74.  
  75. Exit ()
  76. {
  77.     if [ "$debug" = "yes" -a -n "$user_name" ]
  78.     then
  79.         if [ -s $LOGFILE ]
  80.         then
  81.             $MAILX -s "$request_id: LOG FILE" \
  82.                 $user_name <$LOGFILE
  83.         fi
  84.         if [ -s $ERRFILE ]
  85.         then
  86.             $MAILX -s "$request_id: ERROR FILE" \
  87.                 $user_name <$ERRFILE
  88.         fi
  89.         if [ -s $DEBUGFILE ]
  90.         then
  91.             $MAILX -s "$request_id: DEBUG FILE" \
  92.                 $user_name  <$DEBUGFILE
  93.         fi
  94.     fi
  95.     rm -f $ERRFILE $LOGFILE $DEBUGFILE
  96.     if [ -n "$1" ]
  97.     then
  98.         exit $1
  99.     else
  100.         exit $ExitCode
  101.     fi
  102. }
  103.  
  104. trap 'Exit 0' 15
  105.  
  106. #####
  107. #
  108. # We can be clever about getting a hangup or interrupt, though, at least
  109. # until the filter runs. Do this early, even though $LPTELL
  110. # isn't defined, so that we're covered.
  111. #
  112. #####
  113. catch_hangup ()
  114. {
  115.     echo \
  116. "The connection to the printer dropped; perhaps the printer went off-line?" \
  117.     >$ERRFILE
  118.     0<$ERRFILE ${LPTELL} ${printer}
  119.     $CAT $ERRFILE >>$LOGFILE
  120.     >$ERRFILE
  121.     return    0
  122. }
  123.  
  124. catch_interrupt ()
  125. {
  126.     echo \
  127. "Received an interrupt from the printer.  The reason is unknown,
  128. although a common cause is that the baud rate is too high." \
  129.     >$ERRFILE
  130.     0<$ERRFILE ${LPTELL} ${printer}
  131.     $CAT $ERRFILE >>$LOGFILE
  132.     >$ERRFILE
  133.     return    0
  134. }
  135. trap 'catch_hangup; Exit 129' 1
  136. trap 'catch_interrupt; Exit 129' 2 3
  137.  
  138. #####
  139. #
  140. # Most of the time we don't want the standard error to be captured
  141. # by the Spooler, mainly to avoid "Terminated" messages that the
  142. # shell puts out when we get a SIGTERM. We'll save the standard
  143. # error channel under another number, so we can use it when it
  144. # should be captured.
  145. #
  146. # Open another channel to the printer port, for use when the
  147. # regular standard output won't be directed there, such as in
  148. # command substitution (`cmd`).
  149. #####
  150. exec 5>&2 2>>$ERRFILE 3>&1
  151.  
  152. #####
  153. # Error message formatter:
  154. #
  155. # Invoke as
  156. #
  157. #    errmsg severity message-number problem help
  158. #
  159. # where severity is "ERROR" or "WARNING", message-number is
  160. # a unique identifier, problem is a short description of the
  161. # problem, and help is a short suggestion for fixing the problem.
  162. #####
  163.  
  164. LP_ERR_LABEL="UX:lp"
  165.  
  166. E_IP_ARGS=1
  167. E_IP_OPTS=2
  168. #E_IP_FILTER=3
  169. E_IP_STTY=4
  170. E_IP_UNKNOWN=5
  171. E_IP_BADFILE=6
  172. E_IP_BADCHARSET=7
  173. E_IP_BADCPI=8
  174. E_IP_BADLPI=9
  175. E_IP_BADWIDTH=10
  176. E_IP_BADLENGTH=11
  177. E_IP_ERRORS=12        # (in slow.filter)
  178.  
  179. errmsg ()
  180. {
  181.     case $1 in
  182.     ERROR )
  183.         sev="  ERROR";
  184.         ;;
  185.     WARNING )
  186.         sev="WARNING";
  187.         ;;
  188.     esac
  189.     echo "${LP_ERR_LABEL}: ${sev}: $3
  190.         TO FIX: $4" >&5
  191. }
  192.  
  193. #####
  194. #
  195. # This program is invoked as
  196. #
  197. # ${SPOOLDIR}/.../printer request-id user title copies options files...
  198. #
  199. # The first three arguments are simply reprinted on the banner page,
  200. # the fourth (copies) is used to control the number of copies to print,
  201. # the fifth (options) is a blank separated list (in a single argument)
  202. # of user or Spooler supplied options (without the -o prefix),
  203. # and the last arguments are the files to print.
  204. #####
  205.  
  206. if [ $# -lt 5 ]
  207. then
  208.     errmsg ERROR ${E_IP_ARGS} \
  209.         "wrong number of arguments to interface program" \
  210.         "consult your system administrator"
  211.     Exit 1
  212. fi
  213.  
  214. printer=`basename $0`
  215. request_id=$1
  216. user_name=$2
  217. title=$3
  218. copies=$4
  219. option_list=$5
  220.  
  221. shift 5
  222. files="$*"
  223.  
  224. nobanner="no"
  225. nofilebreak="no"
  226. debug="no"
  227. stty=
  228.  
  229. inlist=
  230. for i in ${option_list}
  231. do
  232.     case "${inlist}${i}" in
  233.  
  234.  
  235.     nobanner )
  236.         nobanner="yes"
  237.         ;;
  238.  
  239.     nofilebreak )
  240.         nofilebreak="yes"
  241.         ;;
  242.  
  243.     debug )
  244.         debug="yes"
  245.         ;;
  246.     copies=* )
  247.         ;;
  248.     length=* )
  249.         ;;
  250.     pages=* )
  251.         ;;
  252.  
  253.     #####
  254.     #
  255.     # If you want to add options that, like "stty",
  256.     # take a list (e.g. -o lopt='a b c'), identify
  257.     # them here and below (look for LOPT).
  258.     #####
  259.     stty=* | flist=* | lpd=* )
  260. #LOPT    stty=* | flist=* | lpd=* | lopt=* )
  261.  
  262.         inlist=`expr "${inlist}${i}" : "^\([^=]*=\)"`
  263.         case "${i}" in
  264.         ${inlist}\'*\' )
  265.             item=`expr "${i}" : "^[^=]*='*\(.*\)'\$"`
  266.             ;;
  267.         ${inlist}\' )
  268.             continue
  269.             ;;
  270.         ${inlist}\'* )
  271.             item=`expr "${i}" : "^[^=]*=''*\(.*\)\$"`
  272.             ;;
  273.         ${inlist}* )
  274.             item=`expr "${i}" : "^[^=]*=\(.*\)\$"`
  275.             ;;
  276.         *\' )
  277.             item=`expr "${i}" : "^\(.*\)'\$"`
  278.             ;;
  279.         * )
  280.             item="${i}"
  281.             ;;
  282.         esac
  283.  
  284.         #####
  285.         #
  286.         # We don't dare use "eval" because a clever user could
  287.         # put something in an option value that we'd end up
  288.         # exec'ing.
  289.         #####
  290.         case "${inlist}" in
  291.         stty= )
  292.             stty="${stty} ${item}"
  293.             ;;
  294.         flist= )
  295.             flist="${flist} ${item}"
  296.             ;;
  297.         lpd= )
  298.             lpd="${lpd} ${item}"
  299.             ;;
  300. #LOPT        lopt= )
  301. #LOPT            lopt="${lopt} ${item}"
  302. #LOPT            ;;
  303.         esac
  304.  
  305.         case "${i}" in
  306.         ${inlist}\'*\' )
  307.             inlist=
  308.             ;;
  309.         ${inlist}\'* )
  310.             ;;
  311.         *\' | ${inlist}* )
  312.             inlist=
  313.             ;;
  314.         esac
  315.         ;;
  316.  
  317.     * )
  318.         errmsg WARNING ${E_IP_OPTS} \
  319.             "unrecognized \"-o ${i}\" option" \
  320.             "check the option, resubmit if necessary
  321.         printing continues"
  322.         ;;
  323.     esac
  324. done
  325.  
  326. #####
  327. #
  328. # Additional ``parameters'' are passed via Shell environment
  329. # variables:
  330. #
  331. #    TERM    The printer type (used for Terminfo access)
  332. #    FILTER    The filter to run
  333. #####
  334.  
  335. if [ -z "$TERM" ]
  336. then
  337.     errmsg ERROR ${E_IP_ARGS} \
  338.         "Missing mandatory environment variable." \
  339.         "Consult your system administrator"
  340.     Exit 1
  341. fi
  342. if [ -z "$FILTER" ]
  343. then
  344.     FILTER="$LPCAT 0"
  345. fi
  346.  
  347. #####
  348. ##
  349. ##  Banner filter
  350. ##
  351. #####
  352.     #####
  353.     ##
  354.     ##  Where to find fonts (if appropriate).
  355.     ##
  356.     #####
  357.     DOWNLOAD="$DOWNLOAD -p$printer"
  358.  
  359.     POSTIO="$POSTIO 2>>$ERRFILE"
  360.  
  361.     #####
  362.     ##  Allow infinite delays on write.
  363.     #####
  364.     POSTIO_B="$POSTIO_B 0 2>>$ERRFILE"    
  365.  
  366.     case "${TERM}" in
  367.     "PS" | "PS-r" | "PSR")
  368.         BFILTER="$DOWNLOAD | $POSTIO"
  369.         ;;
  370.  
  371.     "PS-b" | "PS-br" )
  372.         BFILTER="$DOWNLOAD | $POSTIO_B"
  373.         ;;
  374.  
  375.     *)
  376.         errmsg ERROR ${E_IP_ARGS} \
  377.             "Bad mandatory environment variable." \
  378.             "Consult your system administrator."
  379.         Exit 1
  380.         ;;
  381.     esac
  382.  
  383. EndJob ()
  384. {
  385.     if [ "$TERM" = "PS-b" -o "$TERM" = "PS-br" ]
  386.     then
  387.         echo "\004\c"
  388.     fi
  389. }
  390.  
  391. ###########
  392. ##
  393. ## Initialize the printer port
  394. ##
  395. ###########
  396.  
  397. #####
  398. #
  399. # SERIAL PORTS:
  400. # Initialize everything.
  401. #
  402. # PARALLEL PORTS:
  403. # Don't initialize baud rate.
  404. #
  405. # It's not obvious how to tell if a port is parallel or serial.
  406. # However, by splitting the initialization into two steps and letting
  407. # the serial-only part fail nicely, it'll work.
  408. #
  409. # Another point: The output must be a ``tty'' device. If not, don't
  410. # bother with any of this.
  411. #####
  412. stty1= stty2=
  413. tty 0<&1 1>/dev/null 2>&1 && {
  414.  
  415.     #####
  416.     #
  417.     # First set the default parameters,
  418.     # then the requested parameters.
  419.     #####
  420.  
  421.     stty 9600 0<&1 2>/dev/null 1>&2
  422.  
  423.     stty cs8 -cstopb -parenb -parodd \
  424.         ixon -ixany \
  425.         opost -olcuc onlcr -ocrnl -onocr -onlret -ofill \
  426.         nl0 cr0 tab0 bs0 vt0 ff0 \
  427.             0<&1 2>/dev/null 1>&2
  428.  
  429.     if [ -n "${stty}" ]
  430.     then
  431.         if stty ${stty} 0<&1 1>/dev/null 2>&5
  432.         then
  433.             :
  434.         else
  435.             errmsg ERROR ${E_IP_STTY} \
  436.                 "stty option list failed" \
  437.                 "check the \"-o stty\" option you used,
  438.         or consult your system administrator"
  439.             Exit 1
  440.         fi
  441.     fi
  442.  
  443.  
  444.     ##########
  445.     #
  446.     # Find out if we have to turn off opost before initializing the
  447.     # printer and on after. Likewise, check clocal.
  448.     #
  449.     # Turning OFF opost (output postprocessing) keeps the UNIX system
  450.     # from changing what we try to send to the printer. Turning ON
  451.     # clocal keeps the UNIX system from dropping what we are trying to
  452.     # send if the printer drops DTR. An example of the former is the
  453.     # AT&T 479, which wants to send a linefeed (ASCII 10) when a page
  454.     # width of 10 is set; with opost on, this COULD BE turned into a
  455.     # carriage-return/linefeed pair. An example of the latter is the
  456.     # AT&T 455, which momentarily drops DTR when it gets the
  457.     # initialization string, is2; with clocal off, the UNIX system
  458.     # stops sending the rest of the initialization sequence at that
  459.     # point.
  460.     #
  461.     # THIS CODE MUST FOLLOW THE REST OF THE PORT INITIALIZATION CODE.
  462.     ##########
  463.     cur_stty=`stty -a 0<&3`
  464.     expr "${cur_stty}" : '.*-opost' 1>/dev/null 2>&1 \
  465.         || stty1="${stty1} -opost" stty2="${stty2} opost"
  466.     expr "${cur_stty}" : '.*-clocal' 1>/dev/null 2>&1 \
  467.         && stty1="${stty1} clocal" stty2="${stty2} -clocal"
  468.     expr "${cur_stty}" : '.* opost.*' 1>/dev/null 2>&1 \
  469.         || banner_filter=${FIX386BD}
  470.  
  471. }
  472.  
  473.  
  474.  
  475. #####
  476. #
  477. # Basic initialization. The ``else'' clause is equivalent,
  478. # but covers cases where old Terminal Information Utilities are present.
  479. #####
  480. [ -n "${stty1}" ] && stty ${stty1} 0<&1
  481. [ -n "${stty2}" ] && stty ${stty2} 0<&1
  482.  
  483.  
  484. #####
  485. #
  486. # Now that the printer is ready for printing, we're able
  487. # to record on paper a cancellation.
  488. #
  489. #####
  490.  
  491. cancel_page ()
  492. {
  493.     originator="$user_name"
  494.     if [ -n "$ALIAS_USERNAME" ]
  495.     then
  496.         user="$ALIAS_USERNAME"
  497.     fi
  498.     title="*** Cancelled ***"
  499.     $CAT $PSBIN/banner.ps
  500.     echo "(`LC_ALL=C LC_CTYPE=C LC_TIME=C date '+%a %H:%M %h %d, %Y'`)"
  501.     echo "($request_id)"
  502.     echo "($title)"
  503.     echo "($originator)"
  504.     echo "($user_name)"
  505.     echo "banner"
  506. }
  507.  
  508. cancel_job ()
  509. {
  510.     EndJob    #  if needed.
  511.     echo "##"                 >>$LOGFILE
  512.     echo "##  Printing cancel page."     >>$LOGFILE
  513.     echo "##  Banner filter: '$BFILTER'" >>$LOGFILE
  514.     echo "##"                 >>$LOGFILE
  515.     eval "cancel_page | $BFILTER"
  516.     ExitCode=$?
  517.     EndJob
  518.     if [ $ExitCode -ne 0 ]
  519.     then
  520.         $CAT $ERRFILE >>$LOGFILE
  521.         echo "##"                 >>$LOGFILE
  522.         echo "##  Cancel page failed."       >>$LOGFILE
  523.         echo "##  ExitCode: $ExitCode"       >>$LOGFILE
  524.         echo "##"                 >>$LOGFILE
  525.         0<$ERRFILE $LPTELL $printer
  526.         >$ERRFILE
  527.         Exit
  528.     else
  529.         $CAT $ERRFILE >>$LOGFILE
  530.         >$ERRFILE
  531.     fi
  532. }
  533. trap   'cancel_job; Exit 0' 15
  534.  
  535. ###########
  536. #
  537. # Print the banner page
  538. #
  539. ###########
  540.  
  541. #####
  542. #
  543. # You may want to change the following code to get a custom banner.
  544. #
  545. #####
  546.  
  547. banner_page ()
  548. {
  549.     originator="$user_name"
  550.     if [ -n "$ALIAS_USERNAME" ]
  551.     then
  552.         user="$ALIAS_USERNAME"
  553.     fi
  554.     if [ -z "${title}" ]
  555.     then
  556.         title="<untitled>"
  557.     fi
  558.     $CAT $PSBIN/banner.ps
  559.     echo "(`LC_ALL=C LC_CTYPE=C LC_TIME=C date '+%a %H:%M %h %d, %Y'`)"
  560.     echo "($request_id)"
  561.     echo "($title)"
  562.     echo "($originator)"
  563.     echo "($user_name)"
  564.     echo "banner"
  565. }
  566.  
  567.  
  568. #####
  569. #
  570. #  Generate banner page for non-reversed job.
  571. #
  572. #####
  573. if [ "no" = "${nobanner}" -a \( "${TERM}" = "PS" -o "$TERM" = "PS-b" \) ]
  574. then
  575.     echo "##"                 >>$LOGFILE
  576.     echo "##  Printing banner page."     >>$LOGFILE
  577.     echo "##  Banner filter: '$BFILTER'" >>$LOGFILE
  578.     echo "##"                 >>$LOGFILE
  579.     eval "banner_page | $BFILTER"
  580.     ExitCode=$?
  581.     EndJob
  582.     if [ $ExitCode -ne 0 ]
  583.     then
  584.         $CAT $ERRFILE >>$LOGFILE
  585.         echo "##"                 >>$LOGFILE
  586.         echo "##  Banner page failed."       >>$LOGFILE
  587.         echo "##  ExitCode: $ExitCode"       >>$LOGFILE
  588.         echo "##"                 >>$LOGFILE
  589.         0<$ERRFILE $LPTELL $printer
  590.         >$ERRFILE
  591.         Exit
  592.     else
  593.         $CAT $ERRFILE >>$LOGFILE
  594.         >$ERRFILE
  595.     fi
  596. fi
  597.  
  598. ###########
  599. ##
  600. ## Print some copies of the file(s)
  601. ##
  602. ###########
  603.  
  604. #####
  605. #
  606. # The protocol between the interface program and the Spooler
  607. # is fairly simple:
  608. #
  609. #    All standard error output is assumed to indicate a
  610. #    fault WITH THE REQUEST. The output is mailed to the
  611. #    user who submitted the print request and the print
  612. #    request is finished.
  613. #
  614. #    If the interface program sets a zero exit code,
  615. #    it is assumed that the file printed correctly.
  616. #    If the interface program sets a non-zero exit code
  617. #    less than 128, it is assumed that the file did not
  618. #    print correctly, and the user will be notified.
  619. #    In either case the print request is finished.
  620. #
  621. #    If the interface program sets an exit code greater
  622. #    than 128, it is assumed that the file did not print
  623. #    because of a printer fault. If an alert isn't already
  624. #    active (see below) one will be activated. (Exit code
  625. #    128 should not be used at all. The shell, which executes
  626. #    this program, turns SIGTERM, used to kill this program
  627. #    for a cancellation or disabling, into exit 128. The
  628. #    Spooler thus interpretes 128 as SIGTERM.)
  629. #
  630. #    A message sent to the standard input of the ${LPTELL}
  631. #    program is assumed to describe a fault WITH THE PRINTER.
  632. #    The output is used in an alert (if alerts are defined).
  633. #    If the fault recovery is "wait" or "begin", the printer
  634. #    is disabled (killing the interface program if need be),
  635. #    and the print request is left on the queue.
  636. #    If the fault recovery is "continue", the interface program
  637. #    is allowed to wait for the printer fault to be cleared so
  638. #    it can resume printing.
  639. #
  640. # This interface program relies on filters to detect printer faults.
  641. # In absence of a filter provided by the customer, it uses a simple
  642. # filter (${LPCAT}) to detect the class of faults that cause DCD
  643. # (``carrier'') drop. The protocol between the interface program and
  644. # the filter:
  645. #
  646. #    The filter should exit with zero if printing was
  647. #    successful and non-zero if printing failed because
  648. #    of a printer fault. This interface program turns a
  649. #    non-zero exit of the filter into an "exit 129" from
  650. #    itself, thus telling the Spooler that a printer fault
  651. #    (still) exists.
  652. #
  653. #    The filter should report printer faults via a message
  654. #    to its standard error. This interface program takes all
  655. #    standard error output from the filter and feeds it as
  656. #    standard input to the ${LPTELL} program.
  657. #
  658. #    The filter should wait for a printer fault to clear,
  659. #    and should resume printing when the fault clears.
  660. #    Preferably it should resume at the top of the page
  661. #    that was being printed when the fault occurred.
  662. #    If it waits and finishes printing, it should exit
  663. #    with a 0 exit code. If it can't wait, it should exit
  664. #    with a non-zero exit code.
  665. #
  666. #    The interface program expects that ANY message on the
  667. #    standard error from the filter indicates a printer fault.
  668. #    Therefore, a filter should not put user (input) error
  669. #    messages on the standard error, but on the standard output
  670. #    (where the user can read them when he or she examines
  671. #    the print-out).
  672. #
  673. #####
  674.  
  675. badfileyet=
  676. i=1
  677. while [ $i -le $copies ]
  678. do
  679.     for file in ${files}
  680.     do
  681.  
  682.         if [ -r "${file}" ]
  683.         then
  684.  
  685.             #####
  686.             #
  687.             # Here's where we set up the $LPTELL program to
  688.             # capture fault messages, and...
  689.             #
  690.             # Here's where we print the file.
  691.             #
  692.             # We set up a pipeline to $LPTELL, but play a trick
  693.             # to get the filter's standard ERROR piped instead of
  694.             # its standard OUTPUT: Divert the standard error (#2) to
  695.             # the standard output (#1) IN THE PIPELINE. The shell
  696.             # will have changed #1 to be the pipe, not the
  697.             # printer, so diverting #2 connects it to the pipe.
  698.             # We then change the filter's #1 to a copy of the real
  699.             # standard output (the printer port) made earlier,
  700.             # so that is connected back to the printer again.
  701.             #
  702.             # We do all this inside a parenthesized expression
  703.             # so that we can get the exit code; this is necessary
  704.             # because the exit code of a pipeline is the exit
  705.             # code of the right-most command, which isn't the
  706.             # filter.
  707.             #
  708.             # These two tricks could be avoided by using a named
  709.             # pipe to connect the standard error to $LPTELL. In
  710.             # fact an early prototype of this script did just
  711.             # that; however, the named pipe introduced a timing
  712.             # problem. The processes that open a named pipe hang
  713.             # until both ends of the pipe are opened. Cancelling
  714.             # a request or disabling the printer often killed one
  715.             # of the processes, causing the other process to hang
  716.             # forever waiting for the other end of the pipe to
  717.             # be opened.
  718.             #####
  719.  
  720.             trap '' 1    # Let the filter handle a hangup
  721.             trap '' 2 3    # and interrupts
  722.  
  723.             #####
  724.             #  Put the 0<${file} before the "eval" to keep
  725.             #  clever users from giving a file name that
  726.             #  evaluates as something to execute.
  727.             #####
  728.             echo "##"                 >>$LOGFILE
  729.             echo "##  Printing file: '$file'"    >>$LOGFILE
  730.             echo "##"                 >>$LOGFILE
  731.             0<${file} eval ${FILTER} 2>&1 1>&3
  732.             ExitCode=$?
  733.             EndJob
  734.  
  735.             trap 'catch_hangup; exit 129' 1
  736.             trap 'catch_interrupt; exit 129' 2 3
  737.  
  738.             if [ "${ExitCode}" -ne 0 ]
  739.             then
  740.                 $CAT $ERRFILE >>$LOGFILE
  741.                 echo "##"                      >>$LOGFILE
  742.                 echo "##  Job failed."         >>$LOGFILE
  743.                 echo "##  ExitCode: $ExitCode" >>$LOGFILE
  744.                 echo "##"                      >>$LOGFILE
  745.                 trap '' 15  # Avoid dying from disable
  746.                 0<$ERRFILE $LPTELL $printer
  747.                 >$ERRFILE
  748.                 sleep 4        # Give $LPTELL a chance to tell
  749.                 Exit 129
  750.             else
  751.                 $CAT $ERRFILE >>$LOGFILE
  752.                 >$ERRFILE
  753.             fi
  754.         else
  755.             #####
  756.             #
  757.             # Don't complain about not being able to read
  758.             # a file on second and subsequent copies, unless
  759.             # we've not complained yet. This removes repeated
  760.             # messages about the same file yet reduces the
  761.             # chance that the user can remove a file and not
  762.             # know that we had trouble finding it.
  763.             #
  764.             #####
  765.             if [ "${i}" -le 1 -o -z "${badfileyet}" ]
  766.             then
  767.                 errmsg WARNING ${E_IP_BADFILE} \
  768.                     "cannot read file \"${file}\"" \
  769.                     "see if the file still exists and is readable,
  770.         or consult your system administrator;
  771.         printing continues"
  772.                 badfileyet=yes
  773.             fi
  774.  
  775.         fi
  776.  
  777.     done
  778.     i=`expr $i + 1`
  779.  
  780. done
  781.  
  782. #####
  783. #
  784. #  Banner page for reversed job.
  785. #
  786. #####
  787. if [ "no" = "${nobanner}" -a \
  788.     \( "${TERM}" = "PS-r" -o "$TERM" = "PS-br" -o "$TERM" = "PSR" \) ]
  789. then
  790.     echo "##"                 >>$LOGFILE
  791.     echo "##  Printing banner page."     >>$LOGFILE
  792.     echo "##  Banner filter: '$BFILTER'" >>$LOGFILE
  793.     echo "##"                 >>$LOGFILE
  794.     eval "banner_page | $BFILTER"
  795.     ExitCode=$?
  796.     EndJob
  797.     if [ $ExitCode -ne 0 ]
  798.     then
  799.         $CAT $ERRFILE >>$LOGFILE
  800.         echo "##"                 >>$LOGFILE
  801.         echo "##  Banner page failed."       >>$LOGFILE
  802.         echo "##  ExitCode: $ExitCode"       >>$LOGFILE
  803.         echo "##"                 >>$LOGFILE
  804.         0<$ERRFILE $LPTELL $printer
  805.         >$ERRFILE
  806.         Exit
  807.     else
  808.         $CAT $ERRFILE >>$LOGFILE
  809.         >$ERRFILE
  810.     fi
  811. fi
  812.  
  813.  
  814. ${DRAIN}
  815.  
  816. Exit ${ExitCode}
  817.