diff options
-rw-r--r-- | docs/docbook/devdoc/printing.sgml | 129 |
1 files changed, 124 insertions, 5 deletions
diff --git a/docs/docbook/devdoc/printing.sgml b/docs/docbook/devdoc/printing.sgml index 1d4085bb88..2e9d429439 100644 --- a/docs/docbook/devdoc/printing.sgml +++ b/docs/docbook/devdoc/printing.sgml @@ -1,6 +1,6 @@ != != Samba Printing Internals -!= +!= != Author : Gerald Carter <jerry@samba.org> != !=================================================================== @@ -9,18 +9,137 @@ The purpose of this document is to provide some insight into Samba's printing functionality and also to describe the semantics of certain features of Windows client printing. + +Printing Interface to Various Backends +-------------------------------------- + +Samba uses a table of function pointers to seven functions. The +function prototypes are defined in the printif structure declared +in printing.h. + + * retrieve the contents of a print queue + * pause the print queue + * resume a paused print queue + * delete a job from the queue + * pause a job in the print queue + * result a paused print job in the queue + * submit a jobn to the print queue + +Currently there are only two printing backend implementations +defined. + + * a generic set of functions for working with standard UNIX + printing subsystems + * a set of CUPS specific functions (this is only enabled if + the CUPS libraries were located at compile time). + + + Print Queue TDB's ------------------ -* matching lanman jobids, spoolss jobids, & lpd jobids -* why ? -* caching time +Samba provides periodic caching of the output from the "lpq command" +for performance reasons. This cache time is configurable in seconds. +Obviously the longer the cache time the less often smbd will be +required to exec a copy of lpq. However, the accuracy of the print +queue contents displayed to clients will be diminished as well. + +The list of currently opened print queue TDB's can eb found +be examining the list of tdb_print_db structures ( see print_db_head +in printing.c ). A queue TDB is opened using the wrapper function +printing.c:get_print_db_byname(). The function ensures that smbd +does not open more than MAX_PRINT_DBS_OPEN in an effort to prevent +a large print server from exhausting all available file descriptors. +If the number of open queue TDB's exceeds the MAX_PRINT_DBS_OPEN +limit, smbd falls back to a most recently used algorithm for maintaining +a list of open TDB's. + +There are two ways in which a a print job can be entered into +a print queue's TDB. The first is to submit the job from a Windows +client which will insert the job information directly into the TDB. +The second method is to have the print job picked up by executing the +"lpq command". + +/* included from printing.h */ +struct printjob { + pid_t pid; /* which process launched the job */ + int sysjob; /* the system (lp) job number */ + int fd; /* file descriptor of open file if open */ + time_t starttime; /* when the job started spooling */ + int status; /* the status of this job */ + size_t size; /* the size of the job so far */ + int page_count; /* then number of pages so far */ + BOOL spooled; /* has it been sent to the spooler yet? */ + BOOL smbjob; /* set if the job is a SMB job */ + fstring filename; /* the filename used to spool the file */ + fstring jobname; /* the job name given to us by the client */ + fstring user; /* the user who started the job */ + fstring queuename; /* service number of printer for this job */ + NT_DEVICEMODE *nt_devmode; +}; + +The current manifestation of the printjob structure contains a field +for the UNIX job id returned from the "lpq command" and a Windows job +ID (32-bit bounded by PRINT_MAX_JOBID). When a print job is returned +by the "lpq command" that does not match an existing job in th queue's +TDB, a 32-bit job ID above the is generating by adding UNIX_JOB_START to +the id reported by lpq. + +In order to match a 32-bit Windows jobid onto a 16-bit lanman print job +id, smbd uses an in memory TDB to match the former to a number approriate +for old lanman clients. + +When updating a print queue, smbd will performs the following +steps ( refer to print.c:print_queue_update() ): + + 1) Check to see if another sbmd is currently in the process of + updating the queue contents by checking the pid stored in + "LOCK/<printer_name>". If so, then do not update the TDB. + 2) Lock the mutex entry in the TDB and store our own pid. + Check that this succeeded, else fail. + 3) Store the updated time stamp for the new cache listing + 4) Retrieve the queue listing via "lpq command" + 5) foreach job in the queue + { + if the job is a UNIX job, create a new entry; + if the job has a Windows based jobid, then + { + Lookup the record by the jobid; + if the lookup failed, then + treat it as a UNIX job; + else + update the job status only + } + } + 6) Delete any jobs in the TDB that are not in the in the lpq + listing + 7) Store the print queue status in the TDB + 8) update the cache time stamp again + +Note that it is the contents of this TDB that is returned to Windows +clients and not the actual listing from the "lpq command". + +The NT_DEVICEMODE stored as part of the printjob structure is used to +store a pointer to a non-default DeviceMode associated with the print +job. The pointer will be non-null when the client included a Device +Mode in the OpePrinterEx() call and subsequently submitted a job for +printing on that sam handle. If the client did not include a Device +Mode in the OpenPrinterEx() request, the nt_devmode field is NULL +and the job has the printer's device mode associated with it by default. + +Only non-default Device Mode are stored with print jobs in the print +queue TDB. Otherwise, the Device Mode is obtained from the printer +object when the client issues a GetJob(level == 2) request. + + + + ChangeID & Client Caching of Printer Information ------------------------------------------------ -[To be filled in later] + [To be filled in later] Windows NT/2K Printer Change Notify |