s3-printing: fix broken print_job_get_name() return
[ddiss/samba.git] / source3 / printing / printing.c
1 /*
2    Unix SMB/Netbios implementation.
3    Version 3.0
4    printing backend routines
5    Copyright (C) Andrew Tridgell 1992-2000
6    Copyright (C) Jeremy Allison 2002
7
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 3 of the License, or
11    (at your option) any later version.
12
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program.  If not, see <http://www.gnu.org/licenses/>.
20 */
21
22 #include "includes.h"
23 #include "system/syslog.h"
24 #include "system/filesys.h"
25 #include "printing.h"
26 #include "../librpc/gen_ndr/ndr_spoolss.h"
27 #include "nt_printing.h"
28 #include "../librpc/gen_ndr/netlogon.h"
29 #include "printing/notify.h"
30 #include "printing/pcap.h"
31 #include "serverid.h"
32 #include "smbd/smbd.h"
33 #include "auth.h"
34 #include "messages.h"
35 #include "util_tdb.h"
36
37 extern struct current_user current_user;
38 extern userdom_struct current_user_info;
39
40 /* Current printer interface */
41 static bool remove_from_jobs_added(const char* sharename, uint32 jobid);
42
43 /*
44    the printing backend revolves around a tdb database that stores the
45    SMB view of the print queue
46
47    The key for this database is a jobid - a internally generated number that
48    uniquely identifies a print job
49
50    reading the print queue involves two steps:
51      - possibly running lpq and updating the internal database from that
52      - reading entries from the database
53
54    jobids are assigned when a job starts spooling.
55 */
56
57 static TDB_CONTEXT *rap_tdb;
58 static uint16 next_rap_jobid;
59 struct rap_jobid_key {
60         fstring sharename;
61         uint32  jobid;
62 };
63
64 /***************************************************************************
65  Nightmare. LANMAN jobid's are 16 bit numbers..... We must map them to 32
66  bit RPC jobids.... JRA.
67 ***************************************************************************/
68
69 uint16 pjobid_to_rap(const char* sharename, uint32 jobid)
70 {
71         uint16 rap_jobid;
72         TDB_DATA data, key;
73         struct rap_jobid_key jinfo;
74         uint8 buf[2];
75
76         DEBUG(10,("pjobid_to_rap: called.\n"));
77
78         if (!rap_tdb) {
79                 /* Create the in-memory tdb. */
80                 rap_tdb = tdb_open_log(NULL, 0, TDB_INTERNAL, (O_RDWR|O_CREAT), 0644);
81                 if (!rap_tdb)
82                         return 0;
83         }
84
85         ZERO_STRUCT( jinfo );
86         fstrcpy( jinfo.sharename, sharename );
87         jinfo.jobid = jobid;
88         key.dptr = (uint8 *)&jinfo;
89         key.dsize = sizeof(jinfo);
90
91         data = tdb_fetch(rap_tdb, key);
92         if (data.dptr && data.dsize == sizeof(uint16)) {
93                 rap_jobid = SVAL(data.dptr, 0);
94                 SAFE_FREE(data.dptr);
95                 DEBUG(10,("pjobid_to_rap: jobid %u maps to RAP jobid %u\n",
96                         (unsigned int)jobid, (unsigned int)rap_jobid));
97                 return rap_jobid;
98         }
99         SAFE_FREE(data.dptr);
100         /* Not found - create and store mapping. */
101         rap_jobid = ++next_rap_jobid;
102         if (rap_jobid == 0)
103                 rap_jobid = ++next_rap_jobid;
104         SSVAL(buf,0,rap_jobid);
105         data.dptr = buf;
106         data.dsize = sizeof(rap_jobid);
107         tdb_store(rap_tdb, key, data, TDB_REPLACE);
108         tdb_store(rap_tdb, data, key, TDB_REPLACE);
109
110         DEBUG(10,("pjobid_to_rap: created jobid %u maps to RAP jobid %u\n",
111                 (unsigned int)jobid, (unsigned int)rap_jobid));
112         return rap_jobid;
113 }
114
115 bool rap_to_pjobid(uint16 rap_jobid, fstring sharename, uint32 *pjobid)
116 {
117         TDB_DATA data, key;
118         uint8 buf[2];
119
120         DEBUG(10,("rap_to_pjobid called.\n"));
121
122         if (!rap_tdb)
123                 return False;
124
125         SSVAL(buf,0,rap_jobid);
126         key.dptr = buf;
127         key.dsize = sizeof(rap_jobid);
128         data = tdb_fetch(rap_tdb, key);
129         if ( data.dptr && data.dsize == sizeof(struct rap_jobid_key) )
130         {
131                 struct rap_jobid_key *jinfo = (struct rap_jobid_key*)data.dptr;
132                 if (sharename != NULL) {
133                         fstrcpy( sharename, jinfo->sharename );
134                 }
135                 *pjobid = jinfo->jobid;
136                 DEBUG(10,("rap_to_pjobid: jobid %u maps to RAP jobid %u\n",
137                         (unsigned int)*pjobid, (unsigned int)rap_jobid));
138                 SAFE_FREE(data.dptr);
139                 return True;
140         }
141
142         DEBUG(10,("rap_to_pjobid: Failed to lookup RAP jobid %u\n",
143                 (unsigned int)rap_jobid));
144         SAFE_FREE(data.dptr);
145         return False;
146 }
147
148 void rap_jobid_delete(const char* sharename, uint32 jobid)
149 {
150         TDB_DATA key, data;
151         uint16 rap_jobid;
152         struct rap_jobid_key jinfo;
153         uint8 buf[2];
154
155         DEBUG(10,("rap_jobid_delete: called.\n"));
156
157         if (!rap_tdb)
158                 return;
159
160         ZERO_STRUCT( jinfo );
161         fstrcpy( jinfo.sharename, sharename );
162         jinfo.jobid = jobid;
163         key.dptr = (uint8 *)&jinfo;
164         key.dsize = sizeof(jinfo);
165
166         data = tdb_fetch(rap_tdb, key);
167         if (!data.dptr || (data.dsize != sizeof(uint16))) {
168                 DEBUG(10,("rap_jobid_delete: cannot find jobid %u\n",
169                         (unsigned int)jobid ));
170                 SAFE_FREE(data.dptr);
171                 return;
172         }
173
174         DEBUG(10,("rap_jobid_delete: deleting jobid %u\n",
175                 (unsigned int)jobid ));
176
177         rap_jobid = SVAL(data.dptr, 0);
178         SAFE_FREE(data.dptr);
179         SSVAL(buf,0,rap_jobid);
180         data.dptr = buf;
181         data.dsize = sizeof(rap_jobid);
182         tdb_delete(rap_tdb, key);
183         tdb_delete(rap_tdb, data);
184 }
185
186 static int get_queue_status(const char* sharename, print_status_struct *);
187
188 /****************************************************************************
189  Initialise the printing backend. Called once at startup before the fork().
190 ****************************************************************************/
191
192 bool print_backend_init(struct messaging_context *msg_ctx)
193 {
194         const char *sversion = "INFO/version";
195         int services = lp_numservices();
196         int snum;
197
198         unlink(cache_path("printing.tdb"));
199         mkdir(cache_path("printing"),0755);
200
201         /* handle a Samba upgrade */
202
203         for (snum = 0; snum < services; snum++) {
204                 struct tdb_print_db *pdb;
205                 if (!lp_print_ok(snum))
206                         continue;
207
208                 pdb = get_print_db_byname(lp_const_servicename(snum));
209                 if (!pdb)
210                         continue;
211                 if (tdb_lock_bystring(pdb->tdb, sversion) == -1) {
212                         DEBUG(0,("print_backend_init: Failed to open printer %s database\n", lp_const_servicename(snum) ));
213                         release_print_db(pdb);
214                         return False;
215                 }
216                 if (tdb_fetch_int32(pdb->tdb, sversion) != PRINT_DATABASE_VERSION) {
217                         tdb_wipe_all(pdb->tdb);
218                         tdb_store_int32(pdb->tdb, sversion, PRINT_DATABASE_VERSION);
219                 }
220                 tdb_unlock_bystring(pdb->tdb, sversion);
221                 release_print_db(pdb);
222         }
223
224         close_all_print_db(); /* Don't leave any open. */
225
226         /* do NT print initialization... */
227         return nt_printing_init(msg_ctx);
228 }
229
230 /****************************************************************************
231  Shut down printing backend. Called once at shutdown to close the tdb.
232 ****************************************************************************/
233
234 void printing_end(void)
235 {
236         close_all_print_db(); /* Don't leave any open. */
237 }
238
239 /****************************************************************************
240  Retrieve the set of printing functions for a given service.  This allows
241  us to set the printer function table based on the value of the 'printing'
242  service parameter.
243
244  Use the generic interface as the default and only use cups interface only
245  when asked for (and only when supported)
246 ****************************************************************************/
247
248 static struct printif *get_printer_fns_from_type( enum printing_types type )
249 {
250         struct printif *printer_fns = &generic_printif;
251
252 #ifdef HAVE_CUPS
253         if ( type == PRINT_CUPS ) {
254                 printer_fns = &cups_printif;
255         }
256 #endif /* HAVE_CUPS */
257
258 #ifdef HAVE_IPRINT
259         if ( type == PRINT_IPRINT ) {
260                 printer_fns = &iprint_printif;
261         }
262 #endif /* HAVE_IPRINT */
263
264         printer_fns->type = type;
265
266         return printer_fns;
267 }
268
269 static struct printif *get_printer_fns( int snum )
270 {
271         return get_printer_fns_from_type( (enum printing_types)lp_printing(snum) );
272 }
273
274
275 /****************************************************************************
276  Useful function to generate a tdb key.
277 ****************************************************************************/
278
279 static TDB_DATA print_key(uint32 jobid, uint32 *tmp)
280 {
281         TDB_DATA ret;
282
283         SIVAL(tmp, 0, jobid);
284         ret.dptr = (uint8 *)tmp;
285         ret.dsize = sizeof(*tmp);
286         return ret;
287 }
288
289 /****************************************************************************
290  Pack the devicemode to store it in a tdb.
291 ****************************************************************************/
292 static int pack_devicemode(struct spoolss_DeviceMode *devmode, uint8 *buf, int buflen)
293 {
294         enum ndr_err_code ndr_err;
295         DATA_BLOB blob;
296         int len = 0;
297
298         if (devmode) {
299                 ndr_err = ndr_push_struct_blob(&blob, talloc_tos(),
300                                                devmode,
301                                                (ndr_push_flags_fn_t)
302                                                ndr_push_spoolss_DeviceMode);
303                 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
304                         DEBUG(10, ("pack_devicemode: "
305                                    "error encoding spoolss_DeviceMode\n"));
306                         goto done;
307                 }
308         } else {
309                 ZERO_STRUCT(blob);
310         }
311
312         len = tdb_pack(buf, buflen, "B", blob.length, blob.data);
313
314         if (devmode) {
315                 DEBUG(8, ("Packed devicemode [%s]\n", devmode->formname));
316         }
317
318 done:
319         return len;
320 }
321
322 /****************************************************************************
323  Unpack the devicemode to store it in a tdb.
324 ****************************************************************************/
325 static int unpack_devicemode(TALLOC_CTX *mem_ctx,
326                       const uint8 *buf, int buflen,
327                       struct spoolss_DeviceMode **devmode)
328 {
329         struct spoolss_DeviceMode *dm;
330         enum ndr_err_code ndr_err;
331         char *data = NULL;
332         int data_len = 0;
333         DATA_BLOB blob;
334         int len = 0;
335
336         *devmode = NULL;
337
338         len = tdb_unpack(buf, buflen, "B", &data_len, &data);
339         if (!data) {
340                 return len;
341         }
342
343         dm = talloc_zero(mem_ctx, struct spoolss_DeviceMode);
344         if (!dm) {
345                 goto done;
346         }
347
348         blob = data_blob_const(data, data_len);
349
350         ndr_err = ndr_pull_struct_blob(&blob, dm, dm,
351                         (ndr_pull_flags_fn_t)ndr_pull_spoolss_DeviceMode);
352         if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
353                 DEBUG(10, ("unpack_devicemode: "
354                            "error parsing spoolss_DeviceMode\n"));
355                 goto done;
356         }
357
358         DEBUG(8, ("Unpacked devicemode [%s](%s)\n",
359                   dm->devicename, dm->formname));
360         if (dm->driverextra_data.data) {
361                 DEBUG(8, ("with a private section of %d bytes\n",
362                           dm->__driverextra_length));
363         }
364
365         *devmode = dm;
366
367 done:
368         SAFE_FREE(data);
369         return len;
370 }
371
372 /***********************************************************************
373  unpack a pjob from a tdb buffer
374 ***********************************************************************/
375
376 static int unpack_pjob(TALLOC_CTX *mem_ctx, uint8 *buf, int buflen,
377                        struct printjob *pjob)
378 {
379         int     len = 0;
380         int     used;
381         uint32 pjpid, pjjobid, pjsysjob, pjfd, pjstarttime, pjstatus;
382         uint32 pjsize, pjpage_count, pjspooled, pjsmbjob;
383
384         if (!buf || !pjob) {
385                 return -1;
386         }
387
388         len += tdb_unpack(buf+len, buflen-len, "ddddddddddfffff",
389                                 &pjpid,
390                                 &pjjobid,
391                                 &pjsysjob,
392                                 &pjfd,
393                                 &pjstarttime,
394                                 &pjstatus,
395                                 &pjsize,
396                                 &pjpage_count,
397                                 &pjspooled,
398                                 &pjsmbjob,
399                                 pjob->filename,
400                                 pjob->jobname,
401                                 pjob->user,
402                                 pjob->clientmachine,
403                                 pjob->queuename);
404
405         if (len == -1) {
406                 return -1;
407         }
408
409         used = unpack_devicemode(mem_ctx, buf+len, buflen-len, &pjob->devmode);
410         if (used == -1) {
411                 return -1;
412         }
413
414         len += used;
415
416         pjob->pid = pjpid;
417         pjob->jobid = pjjobid;
418         pjob->sysjob = pjsysjob;
419         pjob->fd = pjfd;
420         pjob->starttime = pjstarttime;
421         pjob->status = pjstatus;
422         pjob->size = pjsize;
423         pjob->page_count = pjpage_count;
424         pjob->spooled = pjspooled;
425         pjob->smbjob = pjsmbjob;
426
427         return len;
428
429 }
430
431 /****************************************************************************
432  Useful function to find a print job in the database.
433 ****************************************************************************/
434
435 static struct printjob *print_job_find(TALLOC_CTX *mem_ctx,
436                                        const char *sharename,
437                                        uint32 jobid)
438 {
439         struct printjob         *pjob;
440         uint32_t tmp;
441         TDB_DATA                ret;
442         struct tdb_print_db     *pdb = get_print_db_byname(sharename);
443
444         DEBUG(10,("print_job_find: looking up job %u for share %s\n",
445                         (unsigned int)jobid, sharename ));
446
447         if (!pdb) {
448                 return NULL;
449         }
450
451         ret = tdb_fetch(pdb->tdb, print_key(jobid, &tmp));
452         release_print_db(pdb);
453
454         if (!ret.dptr) {
455                 DEBUG(10, ("print_job_find: failed to find jobid %u.\n",
456                            jobid));
457                 return NULL;
458         }
459
460         pjob = talloc_zero(mem_ctx, struct printjob);
461         if (pjob == NULL) {
462                 goto err_out;
463         }
464
465         if (unpack_pjob(mem_ctx, ret.dptr, ret.dsize, pjob) == -1) {
466                 DEBUG(10, ("failed to unpack jobid %u.\n", jobid));
467                 talloc_free(pjob);
468                 pjob = NULL;
469                 goto err_out;
470         }
471
472         DEBUG(10,("print_job_find: returning system job %d for jobid %u.\n",
473                   pjob->sysjob, jobid));
474         SMB_ASSERT(pjob->jobid == jobid);
475
476 err_out:
477         SAFE_FREE(ret.dptr);
478         return pjob;
479 }
480
481 /* Convert a unix jobid to a smb jobid */
482
483 struct unixjob_traverse_state {
484         int sysjob;
485         uint32 sysjob_to_jobid_value;
486 };
487
488 static int unixjob_traverse_fn(TDB_CONTEXT *the_tdb, TDB_DATA key,
489                                TDB_DATA data, void *private_data)
490 {
491         struct printjob *pjob;
492         struct unixjob_traverse_state *state =
493                 (struct unixjob_traverse_state *)private_data;
494
495         if (!data.dptr || data.dsize == 0)
496                 return 0;
497
498         pjob = (struct printjob *)data.dptr;
499         if (key.dsize != sizeof(uint32))
500                 return 0;
501
502         if (state->sysjob == pjob->sysjob) {
503                 state->sysjob_to_jobid_value = pjob->jobid;
504                 return 1;
505         }
506
507         return 0;
508 }
509
510 static uint32 sysjob_to_jobid_pdb(struct tdb_print_db *pdb, int sysjob)
511 {
512         struct unixjob_traverse_state state;
513
514         state.sysjob = sysjob;
515         state.sysjob_to_jobid_value = (uint32)-1;
516
517         tdb_traverse(pdb->tdb, unixjob_traverse_fn, &state);
518
519         return state.sysjob_to_jobid_value;
520 }
521
522 /****************************************************************************
523  This is a *horribly expensive call as we have to iterate through all the
524  current printer tdb's. Don't do this often ! JRA.
525 ****************************************************************************/
526
527 uint32 sysjob_to_jobid(int unix_jobid)
528 {
529         int services = lp_numservices();
530         int snum;
531         struct unixjob_traverse_state state;
532
533         state.sysjob = unix_jobid;
534         state.sysjob_to_jobid_value = (uint32)-1;
535
536         for (snum = 0; snum < services; snum++) {
537                 struct tdb_print_db *pdb;
538                 if (!lp_print_ok(snum))
539                         continue;
540                 pdb = get_print_db_byname(lp_const_servicename(snum));
541                 if (!pdb) {
542                         continue;
543                 }
544                 tdb_traverse(pdb->tdb, unixjob_traverse_fn, &state);
545                 release_print_db(pdb);
546                 if (state.sysjob_to_jobid_value != (uint32)-1)
547                         return state.sysjob_to_jobid_value;
548         }
549         return (uint32)-1;
550 }
551
552 /****************************************************************************
553  Send notifications based on what has changed after a pjob_store.
554 ****************************************************************************/
555
556 static const struct {
557         uint32_t lpq_status;
558         uint32_t spoolss_status;
559 } lpq_to_spoolss_status_map[] = {
560         { LPQ_QUEUED, JOB_STATUS_QUEUED },
561         { LPQ_PAUSED, JOB_STATUS_PAUSED },
562         { LPQ_SPOOLING, JOB_STATUS_SPOOLING },
563         { LPQ_PRINTING, JOB_STATUS_PRINTING },
564         { LPQ_DELETING, JOB_STATUS_DELETING },
565         { LPQ_OFFLINE, JOB_STATUS_OFFLINE },
566         { LPQ_PAPEROUT, JOB_STATUS_PAPEROUT },
567         { LPQ_PRINTED, JOB_STATUS_PRINTED },
568         { LPQ_DELETED, JOB_STATUS_DELETED },
569         { LPQ_BLOCKED, JOB_STATUS_BLOCKED_DEVQ },
570         { LPQ_USER_INTERVENTION, JOB_STATUS_USER_INTERVENTION },
571         { (uint32_t)-1, 0 }
572 };
573
574 /* Convert a lpq status value stored in printing.tdb into the
575    appropriate win32 API constant. */
576
577 static uint32 map_to_spoolss_status(uint32 lpq_status)
578 {
579         int i = 0;
580
581         while (lpq_to_spoolss_status_map[i].lpq_status != -1) {
582                 if (lpq_to_spoolss_status_map[i].lpq_status == lpq_status)
583                         return lpq_to_spoolss_status_map[i].spoolss_status;
584                 i++;
585         }
586
587         return 0;
588 }
589
590 /***************************************************************************
591  Append a jobid to the 'jobs changed' list.
592 ***************************************************************************/
593
594 static bool add_to_jobs_changed(struct tdb_print_db *pdb, uint32_t jobid)
595 {
596         TDB_DATA data;
597         uint32_t store_jobid;
598
599         SIVAL(&store_jobid, 0, jobid);
600         data.dptr = (uint8 *) &store_jobid;
601         data.dsize = 4;
602
603         DEBUG(10,("add_to_jobs_added: Added jobid %u\n", (unsigned int)jobid ));
604
605         return (tdb_append(pdb->tdb, string_tdb_data("INFO/jobs_changed"),
606                            data) == 0);
607 }
608
609 /***************************************************************************
610  Remove a jobid from the 'jobs changed' list.
611 ***************************************************************************/
612
613 static bool remove_from_jobs_changed(const char* sharename, uint32_t jobid)
614 {
615         struct tdb_print_db *pdb = get_print_db_byname(sharename);
616         TDB_DATA data, key;
617         size_t job_count, i;
618         bool ret = False;
619         bool gotlock = False;
620
621         if (!pdb) {
622                 return False;
623         }
624
625         ZERO_STRUCT(data);
626
627         key = string_tdb_data("INFO/jobs_changed");
628
629         if (tdb_chainlock_with_timeout(pdb->tdb, key, 5) == -1)
630                 goto out;
631
632         gotlock = True;
633
634         data = tdb_fetch(pdb->tdb, key);
635
636         if (data.dptr == NULL || data.dsize == 0 || (data.dsize % 4 != 0))
637                 goto out;
638
639         job_count = data.dsize / 4;
640         for (i = 0; i < job_count; i++) {
641                 uint32 ch_jobid;
642
643                 ch_jobid = IVAL(data.dptr, i*4);
644                 if (ch_jobid == jobid) {
645                         if (i < job_count -1 )
646                                 memmove(data.dptr + (i*4), data.dptr + (i*4) + 4, (job_count - i - 1)*4 );
647                         data.dsize -= 4;
648                         if (tdb_store(pdb->tdb, key, data, TDB_REPLACE) == -1)
649                                 goto out;
650                         break;
651                 }
652         }
653
654         ret = True;
655   out:
656
657         if (gotlock)
658                 tdb_chainunlock(pdb->tdb, key);
659         SAFE_FREE(data.dptr);
660         release_print_db(pdb);
661         if (ret)
662                 DEBUG(10,("remove_from_jobs_changed: removed jobid %u\n", (unsigned int)jobid ));
663         else
664                 DEBUG(10,("remove_from_jobs_changed: Failed to remove jobid %u\n", (unsigned int)jobid ));
665         return ret;
666 }
667
668 static void pjob_store_notify(struct tevent_context *ev,
669                               struct messaging_context *msg_ctx,
670                               const char* sharename, uint32 jobid,
671                               struct printjob *old_data,
672                               struct printjob *new_data,
673                               bool *pchanged)
674 {
675         bool new_job = false;
676         bool changed = false;
677
678         if (old_data == NULL) {
679                 new_job = true;
680         }
681
682         /* ACHTUNG!  Due to a bug in Samba's spoolss parsing of the
683            NOTIFY_INFO_DATA buffer, we *have* to send the job submission
684            time first or else we'll end up with potential alignment
685            errors.  I don't think the systemtime should be spooled as
686            a string, but this gets us around that error.
687            --jerry (i'll feel dirty for this) */
688
689         if (new_job) {
690                 notify_job_submitted(ev, msg_ctx,
691                                      sharename, jobid, new_data->starttime);
692                 notify_job_username(ev, msg_ctx,
693                                     sharename, jobid, new_data->user);
694                 notify_job_name(ev, msg_ctx,
695                                 sharename, jobid, new_data->jobname);
696                 notify_job_status(ev, msg_ctx,
697                                   sharename, jobid, map_to_spoolss_status(new_data->status));
698                 notify_job_total_bytes(ev, msg_ctx,
699                                        sharename, jobid, new_data->size);
700                 notify_job_total_pages(ev, msg_ctx,
701                                        sharename, jobid, new_data->page_count);
702         } else {
703                 if (!strequal(old_data->jobname, new_data->jobname)) {
704                         notify_job_name(ev, msg_ctx, sharename,
705                                         jobid, new_data->jobname);
706                         changed = true;
707                 }
708
709                 if (old_data->status != new_data->status) {
710                         notify_job_status(ev, msg_ctx,
711                                           sharename, jobid,
712                                           map_to_spoolss_status(new_data->status));
713                 }
714
715                 if (old_data->size != new_data->size) {
716                         notify_job_total_bytes(ev, msg_ctx,
717                                                sharename, jobid, new_data->size);
718                 }
719
720                 if (old_data->page_count != new_data->page_count) {
721                         notify_job_total_pages(ev, msg_ctx,
722                                                sharename, jobid,
723                                                new_data->page_count);
724                 }
725         }
726
727         *pchanged = changed;
728 }
729
730 /****************************************************************************
731  Store a job structure back to the database.
732 ****************************************************************************/
733
734 static bool pjob_store(struct tevent_context *ev,
735                        struct messaging_context *msg_ctx,
736                        const char* sharename, uint32 jobid,
737                        struct printjob *pjob)
738 {
739         uint32_t tmp;
740         TDB_DATA                old_data, new_data;
741         bool                    ret = False;
742         struct tdb_print_db     *pdb = get_print_db_byname(sharename);
743         uint8                   *buf = NULL;
744         int                     len, newlen, buflen;
745
746
747         if (!pdb)
748                 return False;
749
750         /* Get old data */
751
752         old_data = tdb_fetch(pdb->tdb, print_key(jobid, &tmp));
753
754         /* Doh!  Now we have to pack/unpack data since the NT_DEVICEMODE was added */
755
756         newlen = 0;
757
758         do {
759                 len = 0;
760                 buflen = newlen;
761                 len += tdb_pack(buf+len, buflen-len, "ddddddddddfffff",
762                                 (uint32)pjob->pid,
763                                 (uint32)pjob->jobid,
764                                 (uint32)pjob->sysjob,
765                                 (uint32)pjob->fd,
766                                 (uint32)pjob->starttime,
767                                 (uint32)pjob->status,
768                                 (uint32)pjob->size,
769                                 (uint32)pjob->page_count,
770                                 (uint32)pjob->spooled,
771                                 (uint32)pjob->smbjob,
772                                 pjob->filename,
773                                 pjob->jobname,
774                                 pjob->user,
775                                 pjob->clientmachine,
776                                 pjob->queuename);
777
778                 len += pack_devicemode(pjob->devmode, buf+len, buflen-len);
779
780                 if (buflen != len) {
781                         buf = (uint8 *)SMB_REALLOC(buf, len);
782                         if (!buf) {
783                                 DEBUG(0,("pjob_store: failed to enlarge buffer!\n"));
784                                 goto done;
785                         }
786                         newlen = len;
787                 }
788         } while ( buflen != len );
789
790
791         /* Store new data */
792
793         new_data.dptr = buf;
794         new_data.dsize = len;
795         ret = (tdb_store(pdb->tdb, print_key(jobid, &tmp), new_data,
796                          TDB_REPLACE) == 0);
797
798         /* Send notify updates for what has changed */
799
800         if (ret) {
801                 bool changed = false;
802                 struct printjob old_pjob;
803
804                 if (old_data.dsize) {
805                         TALLOC_CTX *tmp_ctx = talloc_new(ev);
806                         if (tmp_ctx == NULL)
807                                 goto done;
808
809                         len = unpack_pjob(tmp_ctx, old_data.dptr,
810                                           old_data.dsize, &old_pjob);
811                         if (len != -1 ) {
812                                 pjob_store_notify(ev,
813                                                   msg_ctx,
814                                                   sharename, jobid, &old_pjob,
815                                                   pjob,
816                                                   &changed);
817                                 if (changed) {
818                                         add_to_jobs_changed(pdb, jobid);
819                                 }
820                         }
821                         talloc_free(tmp_ctx);
822
823                 } else {
824                         /* new job */
825                         pjob_store_notify(ev, msg_ctx,
826                                           sharename, jobid, NULL, pjob,
827                                           &changed);
828                 }
829         }
830
831 done:
832         release_print_db(pdb);
833         SAFE_FREE( old_data.dptr );
834         SAFE_FREE( buf );
835
836         return ret;
837 }
838
839 /****************************************************************************
840  Remove a job structure from the database.
841 ****************************************************************************/
842
843 static void pjob_delete(struct tevent_context *ev,
844                         struct messaging_context *msg_ctx,
845                         const char* sharename, uint32 jobid)
846 {
847         uint32_t tmp;
848         struct printjob *pjob;
849         uint32 job_status = 0;
850         struct tdb_print_db *pdb;
851         TALLOC_CTX *tmp_ctx = talloc_new(ev);
852         if (tmp_ctx == NULL) {
853                 return;
854         }
855
856         pdb = get_print_db_byname(sharename);
857         if (!pdb) {
858                 goto err_out;
859         }
860
861         pjob = print_job_find(tmp_ctx, sharename, jobid);
862         if (!pjob) {
863                 DEBUG(5, ("we were asked to delete nonexistent job %u\n",
864                           jobid));
865                 goto err_release;
866         }
867
868         /* We must cycle through JOB_STATUS_DELETING and
869            JOB_STATUS_DELETED for the port monitor to delete the job
870            properly. */
871
872         job_status = JOB_STATUS_DELETING|JOB_STATUS_DELETED;
873         notify_job_status(ev, msg_ctx, sharename, jobid, job_status);
874
875         /* Remove from printing.tdb */
876
877         tdb_delete(pdb->tdb, print_key(jobid, &tmp));
878         remove_from_jobs_added(sharename, jobid);
879         rap_jobid_delete(sharename, jobid);
880 err_release:
881         release_print_db(pdb);
882 err_out:
883         talloc_free(tmp_ctx);
884 }
885
886 /****************************************************************************
887  List a unix job in the print database.
888 ****************************************************************************/
889
890 static void print_unix_job(struct tevent_context *ev,
891                            struct messaging_context *msg_ctx,
892                            const char *sharename, print_queue_struct *q,
893                            uint32 jobid)
894 {
895         struct printjob pj, *old_pj;
896         TALLOC_CTX *tmp_ctx = talloc_new(ev);
897         if (tmp_ctx == NULL) {
898                 return;
899         }
900
901         if (jobid == (uint32)-1) {
902                 jobid = q->sysjob + UNIX_JOB_START;
903         }
904
905         /* Preserve the timestamp on an existing unix print job */
906
907         old_pj = print_job_find(tmp_ctx, sharename, jobid);
908
909         ZERO_STRUCT(pj);
910
911         pj.pid = (pid_t)-1;
912         pj.jobid = jobid;
913         pj.sysjob = q->sysjob;
914         pj.fd = -1;
915         pj.starttime = old_pj ? old_pj->starttime : q->time;
916         pj.status = q->status;
917         pj.size = q->size;
918         pj.spooled = True;
919         fstrcpy(pj.filename, old_pj ? old_pj->filename : "");
920         if (jobid < UNIX_JOB_START) {
921                 pj.smbjob = True;
922                 fstrcpy(pj.jobname, old_pj ? old_pj->jobname : "Remote Downlevel Document");
923         } else {
924                 pj.smbjob = False;
925                 fstrcpy(pj.jobname, old_pj ? old_pj->jobname : q->fs_file);
926         }
927         fstrcpy(pj.user, old_pj ? old_pj->user : q->fs_user);
928         fstrcpy(pj.queuename, old_pj ? old_pj->queuename : sharename );
929
930         pjob_store(ev, msg_ctx, sharename, jobid, &pj);
931         talloc_free(tmp_ctx);
932 }
933
934
935 struct traverse_struct {
936         print_queue_struct *queue;
937         int qcount, snum, maxcount, total_jobs;
938         const char *sharename;
939         time_t lpq_time;
940         const char *lprm_command;
941         struct printif *print_if;
942         struct tevent_context *ev;
943         struct messaging_context *msg_ctx;
944         TALLOC_CTX *mem_ctx;
945 };
946
947 /****************************************************************************
948  Utility fn to delete any jobs that are no longer active.
949 ****************************************************************************/
950
951 static int traverse_fn_delete(TDB_CONTEXT *t, TDB_DATA key, TDB_DATA data, void *state)
952 {
953         struct traverse_struct *ts = (struct traverse_struct *)state;
954         struct printjob pjob;
955         uint32 jobid;
956         int i = 0;
957
958         if (  key.dsize != sizeof(jobid) )
959                 return 0;
960
961         if (unpack_pjob(ts->mem_ctx, data.dptr, data.dsize, &pjob) == -1)
962                 return 0;
963         talloc_free(pjob.devmode);
964         jobid = pjob.jobid;
965
966         if (!pjob.smbjob) {
967                 /* remove a unix job if it isn't in the system queue any more */
968                 for (i=0;i<ts->qcount;i++) {
969                         if (ts->queue[i].sysjob == pjob.sysjob) {
970                                 break;
971                         }
972                 }
973                 if (i == ts->qcount) {
974                         DEBUG(10,("traverse_fn_delete: pjob %u deleted due to !smbjob\n",
975                                                 (unsigned int)jobid ));
976                         pjob_delete(ts->ev, ts->msg_ctx,
977                                     ts->sharename, jobid);
978                         return 0;
979                 }
980
981                 /* need to continue the the bottom of the function to
982                    save the correct attributes */
983         }
984
985         /* maybe it hasn't been spooled yet */
986         if (!pjob.spooled) {
987                 /* if a job is not spooled and the process doesn't
988                    exist then kill it. This cleans up after smbd
989                    deaths */
990                 if (!process_exists_by_pid(pjob.pid)) {
991                         DEBUG(10,("traverse_fn_delete: pjob %u deleted due to !process_exists (%u)\n",
992                                                 (unsigned int)jobid, (unsigned int)pjob.pid ));
993                         pjob_delete(ts->ev, ts->msg_ctx,
994                                     ts->sharename, jobid);
995                 } else
996                         ts->total_jobs++;
997                 return 0;
998         }
999
1000         /* this check only makes sense for jobs submitted from Windows clients */
1001
1002         if (pjob.smbjob) {
1003                 for (i=0;i<ts->qcount;i++) {
1004                         if ( pjob.status == LPQ_DELETED )
1005                                 continue;
1006
1007                         if (ts->queue[i].sysjob == pjob.sysjob) {
1008
1009                                 /* try to clean up any jobs that need to be deleted */
1010
1011                                 if ( pjob.status == LPQ_DELETING ) {
1012                                         int result;
1013
1014                                         result = (*(ts->print_if->job_delete))(
1015                                                 ts->sharename, ts->lprm_command, &pjob );
1016
1017                                         if ( result != 0 ) {
1018                                                 /* if we can't delete, then reset the job status */
1019                                                 pjob.status = LPQ_QUEUED;
1020                                                 pjob_store(ts->ev, ts->msg_ctx,
1021                                                            ts->sharename, jobid, &pjob);
1022                                         }
1023                                         else {
1024                                                 /* if we deleted the job, the remove the tdb record */
1025                                                 pjob_delete(ts->ev,
1026                                                             ts->msg_ctx,
1027                                                             ts->sharename, jobid);
1028                                                 pjob.status = LPQ_DELETED;
1029                                         }
1030
1031                                 }
1032
1033                                 break;
1034                         }
1035                 }
1036         }
1037
1038         /* The job isn't in the system queue - we have to assume it has
1039            completed, so delete the database entry. */
1040
1041         if (i == ts->qcount) {
1042
1043                 /* A race can occur between the time a job is spooled and
1044                    when it appears in the lpq output.  This happens when
1045                    the job is added to printing.tdb when another smbd
1046                    running print_queue_update() has completed a lpq and
1047                    is currently traversing the printing tdb and deleting jobs.
1048                    Don't delete the job if it was submitted after the lpq_time. */
1049
1050                 if (pjob.starttime < ts->lpq_time) {
1051                         DEBUG(10,("traverse_fn_delete: pjob %u deleted due to pjob.starttime (%u) < ts->lpq_time (%u)\n",
1052                                                 (unsigned int)jobid,
1053                                                 (unsigned int)pjob.starttime,
1054                                                 (unsigned int)ts->lpq_time ));
1055                         pjob_delete(ts->ev, ts->msg_ctx,
1056                                     ts->sharename, jobid);
1057                 } else
1058                         ts->total_jobs++;
1059                 return 0;
1060         }
1061
1062         /* Save the pjob attributes we will store. */
1063         ts->queue[i].sysjob = pjob.sysjob;
1064         ts->queue[i].size = pjob.size;
1065         ts->queue[i].page_count = pjob.page_count;
1066         ts->queue[i].status = pjob.status;
1067         ts->queue[i].priority = 1;
1068         ts->queue[i].time = pjob.starttime;
1069         fstrcpy(ts->queue[i].fs_user, pjob.user);
1070         fstrcpy(ts->queue[i].fs_file, pjob.jobname);
1071
1072         ts->total_jobs++;
1073
1074         return 0;
1075 }
1076
1077 /****************************************************************************
1078  Check if the print queue has been updated recently enough.
1079 ****************************************************************************/
1080
1081 static void print_cache_flush(const char *sharename)
1082 {
1083         fstring key;
1084         struct tdb_print_db *pdb = get_print_db_byname(sharename);
1085
1086         if (!pdb)
1087                 return;
1088         slprintf(key, sizeof(key)-1, "CACHE/%s", sharename);
1089         tdb_store_int32(pdb->tdb, key, -1);
1090         release_print_db(pdb);
1091 }
1092
1093 /****************************************************************************
1094  Check if someone already thinks they are doing the update.
1095 ****************************************************************************/
1096
1097 static pid_t get_updating_pid(const char *sharename)
1098 {
1099         fstring keystr;
1100         TDB_DATA data, key;
1101         pid_t updating_pid;
1102         struct tdb_print_db *pdb = get_print_db_byname(sharename);
1103
1104         if (!pdb)
1105                 return (pid_t)-1;
1106         slprintf(keystr, sizeof(keystr)-1, "UPDATING/%s", sharename);
1107         key = string_tdb_data(keystr);
1108
1109         data = tdb_fetch(pdb->tdb, key);
1110         release_print_db(pdb);
1111         if (!data.dptr || data.dsize != sizeof(pid_t)) {
1112                 SAFE_FREE(data.dptr);
1113                 return (pid_t)-1;
1114         }
1115
1116         updating_pid = IVAL(data.dptr, 0);
1117         SAFE_FREE(data.dptr);
1118
1119         if (process_exists_by_pid(updating_pid))
1120                 return updating_pid;
1121
1122         return (pid_t)-1;
1123 }
1124
1125 /****************************************************************************
1126  Set the fact that we're doing the update, or have finished doing the update
1127  in the tdb.
1128 ****************************************************************************/
1129
1130 static void set_updating_pid(const fstring sharename, bool updating)
1131 {
1132         fstring keystr;
1133         TDB_DATA key;
1134         TDB_DATA data;
1135         pid_t updating_pid = sys_getpid();
1136         uint8 buffer[4];
1137
1138         struct tdb_print_db *pdb = get_print_db_byname(sharename);
1139
1140         if (!pdb)
1141                 return;
1142
1143         slprintf(keystr, sizeof(keystr)-1, "UPDATING/%s", sharename);
1144         key = string_tdb_data(keystr);
1145
1146         DEBUG(5, ("set_updating_pid: %s updating lpq cache for print share %s\n",
1147                 updating ? "" : "not ",
1148                 sharename ));
1149
1150         if ( !updating ) {
1151                 tdb_delete(pdb->tdb, key);
1152                 release_print_db(pdb);
1153                 return;
1154         }
1155
1156         SIVAL( buffer, 0, updating_pid);
1157         data.dptr = buffer;
1158         data.dsize = 4;         /* we always assume this is a 4 byte value */
1159
1160         tdb_store(pdb->tdb, key, data, TDB_REPLACE);
1161         release_print_db(pdb);
1162 }
1163
1164 /****************************************************************************
1165  Sort print jobs by submittal time.
1166 ****************************************************************************/
1167
1168 static int printjob_comp(print_queue_struct *j1, print_queue_struct *j2)
1169 {
1170         /* Silly cases */
1171
1172         if (!j1 && !j2)
1173                 return 0;
1174         if (!j1)
1175                 return -1;
1176         if (!j2)
1177                 return 1;
1178
1179         /* Sort on job start time */
1180
1181         if (j1->time == j2->time)
1182                 return 0;
1183         return (j1->time > j2->time) ? 1 : -1;
1184 }
1185
1186 /****************************************************************************
1187  Store the sorted queue representation for later portmon retrieval.
1188  Skip deleted jobs
1189 ****************************************************************************/
1190
1191 static void store_queue_struct(struct tdb_print_db *pdb, struct traverse_struct *pts)
1192 {
1193         TDB_DATA data;
1194         int max_reported_jobs = lp_max_reported_jobs(pts->snum);
1195         print_queue_struct *queue = pts->queue;
1196         size_t len;
1197         size_t i;
1198         unsigned int qcount;
1199
1200         if (max_reported_jobs && (max_reported_jobs < pts->qcount))
1201                 pts->qcount = max_reported_jobs;
1202         qcount = 0;
1203
1204         /* Work out the size. */
1205         data.dsize = 0;
1206         data.dsize += tdb_pack(NULL, 0, "d", qcount);
1207
1208         for (i = 0; i < pts->qcount; i++) {
1209                 if ( queue[i].status == LPQ_DELETED )
1210                         continue;
1211
1212                 qcount++;
1213                 data.dsize += tdb_pack(NULL, 0, "ddddddff",
1214                                 (uint32)queue[i].sysjob,
1215                                 (uint32)queue[i].size,
1216                                 (uint32)queue[i].page_count,
1217                                 (uint32)queue[i].status,
1218                                 (uint32)queue[i].priority,
1219                                 (uint32)queue[i].time,
1220                                 queue[i].fs_user,
1221                                 queue[i].fs_file);
1222         }
1223
1224         if ((data.dptr = (uint8 *)SMB_MALLOC(data.dsize)) == NULL)
1225                 return;
1226
1227         len = 0;
1228         len += tdb_pack(data.dptr + len, data.dsize - len, "d", qcount);
1229         for (i = 0; i < pts->qcount; i++) {
1230                 if ( queue[i].status == LPQ_DELETED )
1231                         continue;
1232
1233                 len += tdb_pack(data.dptr + len, data.dsize - len, "ddddddff",
1234                                 (uint32)queue[i].sysjob,
1235                                 (uint32)queue[i].size,
1236                                 (uint32)queue[i].page_count,
1237                                 (uint32)queue[i].status,
1238                                 (uint32)queue[i].priority,
1239                                 (uint32)queue[i].time,
1240                                 queue[i].fs_user,
1241                                 queue[i].fs_file);
1242         }
1243
1244         tdb_store(pdb->tdb, string_tdb_data("INFO/linear_queue_array"), data,
1245                   TDB_REPLACE);
1246         SAFE_FREE(data.dptr);
1247         return;
1248 }
1249
1250 static TDB_DATA get_jobs_added_data(struct tdb_print_db *pdb)
1251 {
1252         TDB_DATA data;
1253
1254         ZERO_STRUCT(data);
1255
1256         data = tdb_fetch(pdb->tdb, string_tdb_data("INFO/jobs_added"));
1257         if (data.dptr == NULL || data.dsize == 0 || (data.dsize % 4 != 0)) {
1258                 SAFE_FREE(data.dptr);
1259                 ZERO_STRUCT(data);
1260         }
1261
1262         return data;
1263 }
1264
1265 static void check_job_added(const char *sharename, TDB_DATA data, uint32 jobid)
1266 {
1267         unsigned int i;
1268         unsigned int job_count = data.dsize / 4;
1269
1270         for (i = 0; i < job_count; i++) {
1271                 uint32 ch_jobid;
1272
1273                 ch_jobid = IVAL(data.dptr, i*4);
1274                 if (ch_jobid == jobid)
1275                         remove_from_jobs_added(sharename, jobid);
1276         }
1277 }
1278
1279 /****************************************************************************
1280  Check if the print queue has been updated recently enough.
1281 ****************************************************************************/
1282
1283 static bool print_cache_expired(const char *sharename, bool check_pending)
1284 {
1285         fstring key;
1286         time_t last_qscan_time, time_now = time(NULL);
1287         struct tdb_print_db *pdb = get_print_db_byname(sharename);
1288         bool result = False;
1289
1290         if (!pdb)
1291                 return False;
1292
1293         snprintf(key, sizeof(key), "CACHE/%s", sharename);
1294         last_qscan_time = (time_t)tdb_fetch_int32(pdb->tdb, key);
1295
1296         /*
1297          * Invalidate the queue for 3 reasons.
1298          * (1). last queue scan time == -1.
1299          * (2). Current time - last queue scan time > allowed cache time.
1300          * (3). last queue scan time > current time + MAX_CACHE_VALID_TIME (1 hour by default).
1301          * This last test picks up machines for which the clock has been moved
1302          * forward, an lpq scan done and then the clock moved back. Otherwise
1303          * that last lpq scan would stay around for a loooong loooong time... :-). JRA.
1304          */
1305
1306         if (last_qscan_time == ((time_t)-1)
1307                 || (time_now - last_qscan_time) >= lp_lpqcachetime()
1308                 || last_qscan_time > (time_now + MAX_CACHE_VALID_TIME))
1309         {
1310                 uint32 u;
1311                 time_t msg_pending_time;
1312
1313                 DEBUG(4, ("print_cache_expired: cache expired for queue %s "
1314                         "(last_qscan_time = %d, time now = %d, qcachetime = %d)\n",
1315                         sharename, (int)last_qscan_time, (int)time_now,
1316                         (int)lp_lpqcachetime() ));
1317
1318                 /* check if another smbd has already sent a message to update the
1319                    queue.  Give the pending message one minute to clear and
1320                    then send another message anyways.  Make sure to check for
1321                    clocks that have been run forward and then back again. */
1322
1323                 snprintf(key, sizeof(key), "MSG_PENDING/%s", sharename);
1324
1325                 if ( check_pending
1326                         && tdb_fetch_uint32( pdb->tdb, key, &u )
1327                         && (msg_pending_time=u) > 0
1328                         && msg_pending_time <= time_now
1329                         && (time_now - msg_pending_time) < 60 )
1330                 {
1331                         DEBUG(4,("print_cache_expired: message already pending for %s.  Accepting cache\n",
1332                                 sharename));
1333                         goto done;
1334                 }
1335
1336                 result = True;
1337         }
1338
1339 done:
1340         release_print_db(pdb);
1341         return result;
1342 }
1343
1344 /****************************************************************************
1345  main work for updating the lpq cache for a printer queue
1346 ****************************************************************************/
1347
1348 static void print_queue_update_internal(struct tevent_context *ev,
1349                                         struct messaging_context *msg_ctx,
1350                                         const char *sharename,
1351                                         struct printif *current_printif,
1352                                         char *lpq_command, char *lprm_command)
1353 {
1354         int i, qcount;
1355         print_queue_struct *queue = NULL;
1356         print_status_struct status;
1357         print_status_struct old_status;
1358         struct printjob *pjob;
1359         struct traverse_struct tstruct;
1360         TDB_DATA data, key;
1361         TDB_DATA jcdata;
1362         fstring keystr, cachestr;
1363         struct tdb_print_db *pdb = get_print_db_byname(sharename);
1364         TALLOC_CTX *tmp_ctx = talloc_new(ev);
1365
1366         if ((pdb == NULL) || (tmp_ctx == NULL)) {
1367                 return;
1368         }
1369
1370         DEBUG(5,("print_queue_update_internal: printer = %s, type = %d, lpq command = [%s]\n",
1371                 sharename, current_printif->type, lpq_command));
1372
1373         /*
1374          * Update the cache time FIRST ! Stops others even
1375          * attempting to get the lock and doing this
1376          * if the lpq takes a long time.
1377          */
1378
1379         slprintf(cachestr, sizeof(cachestr)-1, "CACHE/%s", sharename);
1380         tdb_store_int32(pdb->tdb, cachestr, (int)time(NULL));
1381
1382         /* get the current queue using the appropriate interface */
1383         ZERO_STRUCT(status);
1384
1385         qcount = (*(current_printif->queue_get))(sharename,
1386                 current_printif->type,
1387                 lpq_command, &queue, &status);
1388
1389         DEBUG(3, ("print_queue_update_internal: %d job%s in queue for %s\n",
1390                 qcount, (qcount != 1) ? "s" : "", sharename));
1391
1392         /* Sort the queue by submission time otherwise they are displayed
1393            in hash order. */
1394
1395         TYPESAFE_QSORT(queue, qcount, printjob_comp);
1396
1397         /*
1398           any job in the internal database that is marked as spooled
1399           and doesn't exist in the system queue is considered finished
1400           and removed from the database
1401
1402           any job in the system database but not in the internal database
1403           is added as a unix job
1404
1405           fill in any system job numbers as we go
1406         */
1407         jcdata = get_jobs_added_data(pdb);
1408
1409         for (i=0; i<qcount; i++) {
1410                 uint32 jobid = sysjob_to_jobid_pdb(pdb, queue[i].sysjob);
1411                 if (jobid == (uint32)-1) {
1412                         /* assume its a unix print job */
1413                         print_unix_job(ev, msg_ctx,
1414                                        sharename, &queue[i], jobid);
1415                         continue;
1416                 }
1417
1418                 /* we have an active SMB print job - update its status */
1419                 pjob = print_job_find(tmp_ctx, sharename, jobid);
1420                 if (!pjob) {
1421                         /* err, somethings wrong. Probably smbd was restarted
1422                            with jobs in the queue. All we can do is treat them
1423                            like unix jobs. Pity. */
1424                         DEBUG(1, ("queued print job %d not found in jobs list, "
1425                                   "assuming unix job\n", jobid));
1426                         print_unix_job(ev, msg_ctx,
1427                                        sharename, &queue[i], jobid);
1428                         continue;
1429                 }
1430
1431                 /* don't reset the status on jobs to be deleted */
1432
1433                 if ( pjob->status != LPQ_DELETING )
1434                         pjob->status = queue[i].status;
1435
1436                 pjob_store(ev, msg_ctx, sharename, jobid, pjob);
1437
1438                 check_job_added(sharename, jcdata, jobid);
1439         }
1440
1441         SAFE_FREE(jcdata.dptr);
1442
1443         /* now delete any queued entries that don't appear in the
1444            system queue */
1445         tstruct.queue = queue;
1446         tstruct.qcount = qcount;
1447         tstruct.snum = -1;
1448         tstruct.total_jobs = 0;
1449         tstruct.lpq_time = time(NULL);
1450         tstruct.sharename = sharename;
1451         tstruct.lprm_command = lprm_command;
1452         tstruct.print_if = current_printif;
1453         tstruct.ev = ev;
1454         tstruct.msg_ctx = msg_ctx;
1455         tstruct.mem_ctx = tmp_ctx;
1456
1457         tdb_traverse(pdb->tdb, traverse_fn_delete, (void *)&tstruct);
1458
1459         /* Store the linearised queue, max jobs only. */
1460         store_queue_struct(pdb, &tstruct);
1461
1462         SAFE_FREE(tstruct.queue);
1463         talloc_free(tmp_ctx);
1464
1465         DEBUG(10,("print_queue_update_internal: printer %s INFO/total_jobs = %d\n",
1466                                 sharename, tstruct.total_jobs ));
1467
1468         tdb_store_int32(pdb->tdb, "INFO/total_jobs", tstruct.total_jobs);
1469
1470         get_queue_status(sharename, &old_status);
1471         if (old_status.qcount != qcount)
1472                 DEBUG(10,("print_queue_update_internal: queue status change %d jobs -> %d jobs for printer %s\n",
1473                                         old_status.qcount, qcount, sharename));
1474
1475         /* store the new queue status structure */
1476         slprintf(keystr, sizeof(keystr)-1, "STATUS/%s", sharename);
1477         key = string_tdb_data(keystr);
1478
1479         status.qcount = qcount;
1480         data.dptr = (uint8 *)&status;
1481         data.dsize = sizeof(status);
1482         tdb_store(pdb->tdb, key, data, TDB_REPLACE);
1483
1484         /*
1485          * Update the cache time again. We want to do this call
1486          * as little as possible...
1487          */
1488
1489         slprintf(keystr, sizeof(keystr)-1, "CACHE/%s", sharename);
1490         tdb_store_int32(pdb->tdb, keystr, (int32)time(NULL));
1491
1492         /* clear the msg pending record for this queue */
1493
1494         snprintf(keystr, sizeof(keystr), "MSG_PENDING/%s", sharename);
1495
1496         if ( !tdb_store_uint32( pdb->tdb, keystr, 0 ) ) {
1497                 /* log a message but continue on */
1498
1499                 DEBUG(0,("print_queue_update: failed to store MSG_PENDING flag for [%s]!\n",
1500                         sharename));
1501         }
1502
1503         release_print_db( pdb );
1504
1505         return;
1506 }
1507
1508 /****************************************************************************
1509  Update the internal database from the system print queue for a queue.
1510  obtain a lock on the print queue before proceeding (needed when mutiple
1511  smbd processes maytry to update the lpq cache concurrently).
1512 ****************************************************************************/
1513
1514 static void print_queue_update_with_lock( struct tevent_context *ev,
1515                                           struct messaging_context *msg_ctx,
1516                                           const char *sharename,
1517                                           struct printif *current_printif,
1518                                           char *lpq_command, char *lprm_command )
1519 {
1520         fstring keystr;
1521         struct tdb_print_db *pdb;
1522
1523         DEBUG(5,("print_queue_update_with_lock: printer share = %s\n", sharename));
1524         pdb = get_print_db_byname(sharename);
1525         if (!pdb)
1526                 return;
1527
1528         if ( !print_cache_expired(sharename, False) ) {
1529                 DEBUG(5,("print_queue_update_with_lock: print cache for %s is still ok\n", sharename));
1530                 release_print_db(pdb);
1531                 return;
1532         }
1533
1534         /*
1535          * Check to see if someone else is doing this update.
1536          * This is essentially a mutex on the update.
1537          */
1538
1539         if (get_updating_pid(sharename) != -1) {
1540                 release_print_db(pdb);
1541                 return;
1542         }
1543
1544         /* Lock the queue for the database update */
1545
1546         slprintf(keystr, sizeof(keystr) - 1, "LOCK/%s", sharename);
1547         /* Only wait 10 seconds for this. */
1548         if (tdb_lock_bystring_with_timeout(pdb->tdb, keystr, 10) == -1) {
1549                 DEBUG(0,("print_queue_update_with_lock: Failed to lock printer %s database\n", sharename));
1550                 release_print_db(pdb);
1551                 return;
1552         }
1553
1554         /*
1555          * Ensure that no one else got in here.
1556          * If the updating pid is still -1 then we are
1557          * the winner.
1558          */
1559
1560         if (get_updating_pid(sharename) != -1) {
1561                 /*
1562                  * Someone else is doing the update, exit.
1563                  */
1564                 tdb_unlock_bystring(pdb->tdb, keystr);
1565                 release_print_db(pdb);
1566                 return;
1567         }
1568
1569         /*
1570          * We're going to do the update ourselves.
1571          */
1572
1573         /* Tell others we're doing the update. */
1574         set_updating_pid(sharename, True);
1575
1576         /*
1577          * Allow others to enter and notice we're doing
1578          * the update.
1579          */
1580
1581         tdb_unlock_bystring(pdb->tdb, keystr);
1582
1583         /* do the main work now */
1584
1585         print_queue_update_internal(ev, msg_ctx,
1586                                     sharename, current_printif,
1587                                     lpq_command, lprm_command);
1588
1589         /* Delete our pid from the db. */
1590         set_updating_pid(sharename, False);
1591         release_print_db(pdb);
1592 }
1593
1594 /****************************************************************************
1595 this is the receive function of the background lpq updater
1596 ****************************************************************************/
1597 void print_queue_receive(struct messaging_context *msg,
1598                                 void *private_data,
1599                                 uint32_t msg_type,
1600                                 struct server_id server_id,
1601                                 DATA_BLOB *data)
1602 {
1603         fstring sharename;
1604         char *lpqcommand = NULL, *lprmcommand = NULL;
1605         int printing_type;
1606         size_t len;
1607
1608         len = tdb_unpack( (uint8 *)data->data, data->length, "fdPP",
1609                 sharename,
1610                 &printing_type,
1611                 &lpqcommand,
1612                 &lprmcommand );
1613
1614         if ( len == -1 ) {
1615                 SAFE_FREE(lpqcommand);
1616                 SAFE_FREE(lprmcommand);
1617                 DEBUG(0,("print_queue_receive: Got invalid print queue update message\n"));
1618                 return;
1619         }
1620
1621         print_queue_update_with_lock(server_event_context(), msg, sharename,
1622                 get_printer_fns_from_type((enum printing_types)printing_type),
1623                 lpqcommand, lprmcommand );
1624
1625         SAFE_FREE(lpqcommand);
1626         SAFE_FREE(lprmcommand);
1627         return;
1628 }
1629
1630 static void printing_pause_fd_handler(struct tevent_context *ev,
1631                                       struct tevent_fd *fde,
1632                                       uint16_t flags,
1633                                       void *private_data)
1634 {
1635         /*
1636          * If pause_pipe[1] is closed it means the parent smbd
1637          * and children exited or aborted.
1638          */
1639         exit_server_cleanly(NULL);
1640 }
1641
1642 extern struct child_pid *children;
1643 extern int num_children;
1644
1645 static void add_child_pid(pid_t pid)
1646 {
1647         struct child_pid *child;
1648
1649         child = SMB_MALLOC_P(struct child_pid);
1650         if (child == NULL) {
1651                 DEBUG(0, ("Could not add child struct -- malloc failed\n"));
1652                 return;
1653         }
1654         child->pid = pid;
1655         DLIST_ADD(children, child);
1656         num_children += 1;
1657 }
1658
1659 static pid_t background_lpq_updater_pid = -1;
1660
1661 /****************************************************************************
1662 main thread of the background lpq updater
1663 ****************************************************************************/
1664 void start_background_queue(struct tevent_context *ev,
1665                             struct messaging_context *msg_ctx)
1666 {
1667         /* Use local variables for this as we don't
1668          * need to save the parent side of this, just
1669          * ensure it closes when the process exits.
1670          */
1671         int pause_pipe[2];
1672
1673         DEBUG(3,("start_background_queue: Starting background LPQ thread\n"));
1674
1675         if (pipe(pause_pipe) == -1) {
1676                 DEBUG(5,("start_background_queue: cannot create pipe. %s\n", strerror(errno) ));
1677                 exit(1);
1678         }
1679
1680         background_lpq_updater_pid = sys_fork();
1681
1682         if (background_lpq_updater_pid == -1) {
1683                 DEBUG(5,("start_background_queue: background LPQ thread failed to start. %s\n", strerror(errno) ));
1684                 exit(1);
1685         }
1686
1687         /* Track the printing pid along with other smbd children */
1688         add_child_pid(background_lpq_updater_pid);
1689
1690         if(background_lpq_updater_pid == 0) {
1691                 struct tevent_fd *fde;
1692                 int ret;
1693                 NTSTATUS status;
1694
1695                 /* Child. */
1696                 DEBUG(5,("start_background_queue: background LPQ thread started\n"));
1697
1698                 close(pause_pipe[0]);
1699                 pause_pipe[0] = -1;
1700
1701                 status = reinit_after_fork(msg_ctx, ev, procid_self(), true);
1702
1703                 if (!NT_STATUS_IS_OK(status)) {
1704                         DEBUG(0,("reinit_after_fork() failed\n"));
1705                         smb_panic("reinit_after_fork() failed");
1706                 }
1707
1708                 smbd_setup_sig_term_handler();
1709                 smbd_setup_sig_hup_handler(ev, msg_ctx);
1710
1711                 if (!serverid_register(procid_self(),
1712                                        FLAG_MSG_GENERAL|FLAG_MSG_SMBD
1713                                        |FLAG_MSG_PRINT_GENERAL)) {
1714                         exit(1);
1715                 }
1716
1717                 if (!locking_init()) {
1718                         exit(1);
1719                 }
1720
1721                 messaging_register(msg_ctx, NULL, MSG_PRINTER_UPDATE,
1722                                    print_queue_receive);
1723
1724                 fde = tevent_add_fd(ev, ev, pause_pipe[1], TEVENT_FD_READ,
1725                                     printing_pause_fd_handler,
1726                                     NULL);
1727                 if (!fde) {
1728                         DEBUG(0,("tevent_add_fd() failed for pause_pipe\n"));
1729                         smb_panic("tevent_add_fd() failed for pause_pipe");
1730                 }
1731
1732                 DEBUG(5,("start_background_queue: background LPQ thread waiting for messages\n"));
1733                 ret = tevent_loop_wait(ev);
1734                 /* should not be reached */
1735                 DEBUG(0,("background_queue: tevent_loop_wait() exited with %d - %s\n",
1736                          ret, (ret == 0) ? "out of events" : strerror(errno)));
1737                 exit(1);
1738         }
1739
1740         close(pause_pipe[1]);
1741 }
1742
1743 /****************************************************************************
1744 update the internal database from the system print queue for a queue
1745 ****************************************************************************/
1746
1747 static void print_queue_update(struct messaging_context *msg_ctx,
1748                                int snum, bool force)
1749 {
1750         fstring key;
1751         fstring sharename;
1752         char *lpqcommand = NULL;
1753         char *lprmcommand = NULL;
1754         uint8 *buffer = NULL;
1755         size_t len = 0;
1756         size_t newlen;
1757         struct tdb_print_db *pdb;
1758         int type;
1759         struct printif *current_printif;
1760         TALLOC_CTX *ctx = talloc_tos();
1761
1762         fstrcpy( sharename, lp_const_servicename(snum));
1763
1764         /* don't strip out characters like '$' from the printername */
1765
1766         lpqcommand = talloc_string_sub2(ctx,
1767                         lp_lpqcommand(snum),
1768                         "%p",
1769                         lp_printername(snum),
1770                         false, false, false);
1771         if (!lpqcommand) {
1772                 return;
1773         }
1774         lpqcommand = talloc_sub_advanced(ctx,
1775                         lp_servicename(snum),
1776                         current_user_info.unix_name,
1777                         "",
1778                         current_user.ut.gid,
1779                         get_current_username(),
1780                         current_user_info.domain,
1781                         lpqcommand);
1782         if (!lpqcommand) {
1783                 return;
1784         }
1785
1786         lprmcommand = talloc_string_sub2(ctx,
1787                         lp_lprmcommand(snum),
1788                         "%p",
1789                         lp_printername(snum),
1790                         false, false, false);
1791         if (!lprmcommand) {
1792                 return;
1793         }
1794         lprmcommand = talloc_sub_advanced(ctx,
1795                         lp_servicename(snum),
1796                         current_user_info.unix_name,
1797                         "",
1798                         current_user.ut.gid,
1799                         get_current_username(),
1800                         current_user_info.domain,
1801                         lprmcommand);
1802         if (!lprmcommand) {
1803                 return;
1804         }
1805
1806         /*
1807          * Make sure that the background queue process exists.
1808          * Otherwise just do the update ourselves
1809          */
1810
1811         if ( force || background_lpq_updater_pid == -1 ) {
1812                 DEBUG(4,("print_queue_update: updating queue [%s] myself\n", sharename));
1813                 current_printif = get_printer_fns( snum );
1814                 print_queue_update_with_lock(server_event_context(), msg_ctx,
1815                                              sharename, current_printif,
1816                                              lpqcommand, lprmcommand);
1817
1818                 return;
1819         }
1820
1821         type = lp_printing(snum);
1822
1823         /* get the length */
1824
1825         len = tdb_pack( NULL, 0, "fdPP",
1826                 sharename,
1827                 type,
1828                 lpqcommand,
1829                 lprmcommand );
1830
1831         buffer = SMB_XMALLOC_ARRAY( uint8, len );
1832
1833         /* now pack the buffer */
1834         newlen = tdb_pack( buffer, len, "fdPP",
1835                 sharename,
1836                 type,
1837                 lpqcommand,
1838                 lprmcommand );
1839
1840         SMB_ASSERT( newlen == len );
1841
1842         DEBUG(10,("print_queue_update: Sending message -> printer = %s, "
1843                 "type = %d, lpq command = [%s] lprm command = [%s]\n",
1844                 sharename, type, lpqcommand, lprmcommand ));
1845
1846         /* here we set a msg pending record for other smbd processes
1847            to throttle the number of duplicate print_queue_update msgs
1848            sent.  */
1849
1850         pdb = get_print_db_byname(sharename);
1851         if (!pdb) {
1852                 SAFE_FREE(buffer);
1853                 return;
1854         }
1855
1856         snprintf(key, sizeof(key), "MSG_PENDING/%s", sharename);
1857
1858         if ( !tdb_store_uint32( pdb->tdb, key, time(NULL) ) ) {
1859                 /* log a message but continue on */
1860
1861                 DEBUG(0,("print_queue_update: failed to store MSG_PENDING flag for [%s]!\n",
1862                         sharename));
1863         }
1864
1865         release_print_db( pdb );
1866
1867         /* finally send the message */
1868
1869         messaging_send_buf(msg_ctx, pid_to_procid(background_lpq_updater_pid),
1870                            MSG_PRINTER_UPDATE, (uint8 *)buffer, len);
1871
1872         SAFE_FREE( buffer );
1873
1874         return;
1875 }
1876
1877 /****************************************************************************
1878  Create/Update an entry in the print tdb that will allow us to send notify
1879  updates only to interested smbd's.
1880 ****************************************************************************/
1881
1882 bool print_notify_register_pid(int snum)
1883 {
1884         TDB_DATA data;
1885         struct tdb_print_db *pdb = NULL;
1886         TDB_CONTEXT *tdb = NULL;
1887         const char *printername;
1888         uint32 mypid = (uint32)sys_getpid();
1889         bool ret = False;
1890         size_t i;
1891
1892         /* if (snum == -1), then the change notify request was
1893            on a print server handle and we need to register on
1894            all print queus */
1895
1896         if (snum == -1)
1897         {
1898                 int num_services = lp_numservices();
1899                 int idx;
1900
1901                 for ( idx=0; idx<num_services; idx++ ) {
1902                         if (lp_snum_ok(idx) && lp_print_ok(idx) )
1903                                 print_notify_register_pid(idx);
1904                 }
1905
1906                 return True;
1907         }
1908         else /* register for a specific printer */
1909         {
1910                 printername = lp_const_servicename(snum);
1911                 pdb = get_print_db_byname(printername);
1912                 if (!pdb)
1913                         return False;
1914                 tdb = pdb->tdb;
1915         }
1916
1917         if (tdb_lock_bystring_with_timeout(tdb, NOTIFY_PID_LIST_KEY, 10) == -1) {
1918                 DEBUG(0,("print_notify_register_pid: Failed to lock printer %s\n",
1919                                         printername));
1920                 if (pdb)
1921                         release_print_db(pdb);
1922                 return False;
1923         }
1924
1925         data = get_printer_notify_pid_list( tdb, printername, True );
1926
1927         /* Add ourselves and increase the refcount. */
1928
1929         for (i = 0; i < data.dsize; i += 8) {
1930                 if (IVAL(data.dptr,i) == mypid) {
1931                         uint32 new_refcount = IVAL(data.dptr, i+4) + 1;
1932                         SIVAL(data.dptr, i+4, new_refcount);
1933                         break;
1934                 }
1935         }
1936
1937         if (i == data.dsize) {
1938                 /* We weren't in the list. Realloc. */
1939                 data.dptr = (uint8 *)SMB_REALLOC(data.dptr, data.dsize + 8);
1940                 if (!data.dptr) {
1941                         DEBUG(0,("print_notify_register_pid: Relloc fail for printer %s\n",
1942                                                 printername));
1943                         goto done;
1944                 }
1945                 data.dsize += 8;
1946                 SIVAL(data.dptr,data.dsize - 8,mypid);
1947                 SIVAL(data.dptr,data.dsize - 4,1); /* Refcount. */
1948         }
1949
1950         /* Store back the record. */
1951         if (tdb_store_bystring(tdb, NOTIFY_PID_LIST_KEY, data, TDB_REPLACE) == -1) {
1952                 DEBUG(0,("print_notify_register_pid: Failed to update pid \
1953 list for printer %s\n", printername));
1954                 goto done;
1955         }
1956
1957         ret = True;
1958
1959  done:
1960
1961         tdb_unlock_bystring(tdb, NOTIFY_PID_LIST_KEY);
1962         if (pdb)
1963                 release_print_db(pdb);
1964         SAFE_FREE(data.dptr);
1965         return ret;
1966 }
1967
1968 /****************************************************************************
1969  Update an entry in the print tdb that will allow us to send notify
1970  updates only to interested smbd's.
1971 ****************************************************************************/
1972
1973 bool print_notify_deregister_pid(int snum)
1974 {
1975         TDB_DATA data;
1976         struct tdb_print_db *pdb = NULL;
1977         TDB_CONTEXT *tdb = NULL;
1978         const char *printername;
1979         uint32 mypid = (uint32)sys_getpid();
1980         size_t i;
1981         bool ret = False;
1982
1983         /* if ( snum == -1 ), we are deregister a print server handle
1984            which means to deregister on all print queues */
1985
1986         if (snum == -1)
1987         {
1988                 int num_services = lp_numservices();
1989                 int idx;
1990
1991                 for ( idx=0; idx<num_services; idx++ ) {
1992                         if ( lp_snum_ok(idx) && lp_print_ok(idx) )
1993                                 print_notify_deregister_pid(idx);
1994                 }
1995
1996                 return True;
1997         }
1998         else /* deregister a specific printer */
1999         {
2000                 printername = lp_const_servicename(snum);
2001                 pdb = get_print_db_byname(printername);
2002                 if (!pdb)
2003                         return False;
2004                 tdb = pdb->tdb;
2005         }
2006
2007         if (tdb_lock_bystring_with_timeout(tdb, NOTIFY_PID_LIST_KEY, 10) == -1) {
2008                 DEBUG(0,("print_notify_register_pid: Failed to lock \
2009 printer %s database\n", printername));
2010                 if (pdb)
2011                         release_print_db(pdb);
2012                 return False;
2013         }
2014
2015         data = get_printer_notify_pid_list( tdb, printername, True );
2016
2017         /* Reduce refcount. Remove ourselves if zero. */
2018
2019         for (i = 0; i < data.dsize; ) {
2020                 if (IVAL(data.dptr,i) == mypid) {
2021                         uint32 refcount = IVAL(data.dptr, i+4);
2022
2023                         refcount--;
2024
2025                         if (refcount == 0) {
2026                                 if (data.dsize - i > 8)
2027                                         memmove( &data.dptr[i], &data.dptr[i+8], data.dsize - i - 8);
2028                                 data.dsize -= 8;
2029                                 continue;
2030                         }
2031                         SIVAL(data.dptr, i+4, refcount);
2032                 }
2033
2034                 i += 8;
2035         }
2036
2037         if (data.dsize == 0)
2038                 SAFE_FREE(data.dptr);
2039
2040         /* Store back the record. */
2041         if (tdb_store_bystring(tdb, NOTIFY_PID_LIST_KEY, data, TDB_REPLACE) == -1) {
2042                 DEBUG(0,("print_notify_register_pid: Failed to update pid \
2043 list for printer %s\n", printername));
2044                 goto done;
2045         }
2046
2047         ret = True;
2048
2049   done:
2050
2051         tdb_unlock_bystring(tdb, NOTIFY_PID_LIST_KEY);
2052         if (pdb)
2053                 release_print_db(pdb);
2054         SAFE_FREE(data.dptr);
2055         return ret;
2056 }
2057
2058 /****************************************************************************
2059  Check if a jobid is valid. It is valid if it exists in the database.
2060 ****************************************************************************/
2061
2062 bool print_job_exists(const char* sharename, uint32 jobid)
2063 {
2064         struct tdb_print_db *pdb = get_print_db_byname(sharename);
2065         bool ret;
2066         uint32_t tmp;
2067
2068         if (!pdb)
2069                 return False;
2070         ret = tdb_exists(pdb->tdb, print_key(jobid, &tmp));
2071         release_print_db(pdb);
2072         return ret;
2073 }
2074
2075 /****************************************************************************
2076  Return the device mode asigned to a specific print job.
2077  Only valid for the process doing the spooling and when the job
2078  has not been spooled.
2079 ****************************************************************************/
2080
2081 struct spoolss_DeviceMode *print_job_devmode(TALLOC_CTX *mem_ctx,
2082                                              const char *sharename,
2083                                              uint32 jobid)
2084 {
2085         struct printjob *pjob = print_job_find(mem_ctx, sharename, jobid);
2086         if (pjob == NULL) {
2087                 return NULL;
2088         }
2089
2090         return pjob->devmode;
2091 }
2092
2093 /****************************************************************************
2094  Set the name of a job. Only possible for owner.
2095 ****************************************************************************/
2096
2097 bool print_job_set_name(struct tevent_context *ev,
2098                         struct messaging_context *msg_ctx,
2099                         const char *sharename, uint32 jobid, const char *name)
2100 {
2101         struct printjob *pjob;
2102         bool ret;
2103         TALLOC_CTX *tmp_ctx = talloc_new(ev);
2104         if (tmp_ctx == NULL) {
2105                 return false;
2106         }
2107
2108         pjob = print_job_find(tmp_ctx, sharename, jobid);
2109         if (!pjob || pjob->pid != sys_getpid()) {
2110                 ret = false;
2111                 goto err_out;
2112         }
2113
2114         fstrcpy(pjob->jobname, name);
2115         ret = pjob_store(ev, msg_ctx, sharename, jobid, pjob);
2116 err_out:
2117         talloc_free(tmp_ctx);
2118         return ret;
2119 }
2120
2121 /****************************************************************************
2122  Get the name of a job. Only possible for owner.
2123 ****************************************************************************/
2124
2125 bool print_job_get_name(TALLOC_CTX *mem_ctx, const char *sharename, uint32_t jobid, char **name)
2126 {
2127         struct printjob *pjob;
2128
2129         pjob = print_job_find(mem_ctx, sharename, jobid);
2130         if (!pjob || pjob->pid != sys_getpid()) {
2131                 return false;
2132         }
2133
2134         *name = pjob->jobname;
2135         return true;
2136 }
2137
2138
2139 /***************************************************************************
2140  Remove a jobid from the 'jobs added' list.
2141 ***************************************************************************/
2142
2143 static bool remove_from_jobs_added(const char* sharename, uint32 jobid)
2144 {
2145         struct tdb_print_db *pdb = get_print_db_byname(sharename);
2146         TDB_DATA data, key;
2147         size_t job_count, i;
2148         bool ret = False;
2149         bool gotlock = False;
2150
2151         if (!pdb) {
2152                 return False;
2153         }
2154
2155         ZERO_STRUCT(data);
2156
2157         key = string_tdb_data("INFO/jobs_added");
2158
2159         if (tdb_chainlock_with_timeout(pdb->tdb, key, 5) == -1)
2160                 goto out;
2161
2162         gotlock = True;
2163
2164         data = tdb_fetch(pdb->tdb, key);
2165
2166         if (data.dptr == NULL || data.dsize == 0 || (data.dsize % 4 != 0))
2167                 goto out;
2168
2169         job_count = data.dsize / 4;
2170         for (i = 0; i < job_count; i++) {
2171                 uint32 ch_jobid;
2172
2173                 ch_jobid = IVAL(data.dptr, i*4);
2174                 if (ch_jobid == jobid) {
2175                         if (i < job_count -1 )
2176                                 memmove(data.dptr + (i*4), data.dptr + (i*4) + 4, (job_count - i - 1)*4 );
2177                         data.dsize -= 4;
2178                         if (tdb_store(pdb->tdb, key, data, TDB_REPLACE) == -1)
2179                                 goto out;
2180                         break;
2181                 }
2182         }
2183
2184         ret = True;
2185   out:
2186
2187         if (gotlock)
2188                 tdb_chainunlock(pdb->tdb, key);
2189         SAFE_FREE(data.dptr);
2190         release_print_db(pdb);
2191         if (ret)
2192                 DEBUG(10,("remove_from_jobs_added: removed jobid %u\n", (unsigned int)jobid ));
2193         else
2194                 DEBUG(10,("remove_from_jobs_added: Failed to remove jobid %u\n", (unsigned int)jobid ));
2195         return ret;
2196 }
2197
2198 /****************************************************************************
2199  Delete a print job - don't update queue.
2200 ****************************************************************************/
2201
2202 static bool print_job_delete1(struct tevent_context *ev,
2203                               struct messaging_context *msg_ctx,
2204                               int snum, uint32 jobid)
2205 {
2206         const char* sharename = lp_const_servicename(snum);
2207         struct printjob *pjob;
2208         int result = 0;
2209         struct printif *current_printif = get_printer_fns( snum );
2210         bool ret;
2211         TALLOC_CTX *tmp_ctx = talloc_new(ev);
2212         if (tmp_ctx == NULL) {
2213                 return false;
2214         }
2215
2216         pjob = print_job_find(tmp_ctx, sharename, jobid);
2217         if (!pjob) {
2218                 ret = false;
2219                 goto err_out;
2220         }
2221
2222         /*
2223          * If already deleting just return.
2224          */
2225
2226         if (pjob->status == LPQ_DELETING) {
2227                 ret = true;
2228                 goto err_out;
2229         }
2230
2231         /* Hrm - we need to be able to cope with deleting a job before it
2232            has reached the spooler.  Just mark it as LPQ_DELETING and
2233            let the print_queue_update() code rmeove the record */
2234
2235
2236         if (pjob->sysjob == -1) {
2237                 DEBUG(5, ("attempt to delete job %u not seen by lpr\n", (unsigned int)jobid));
2238         }
2239
2240         /* Set the tdb entry to be deleting. */
2241
2242         pjob->status = LPQ_DELETING;
2243         pjob_store(ev, msg_ctx, sharename, jobid, pjob);
2244
2245         if (pjob->spooled && pjob->sysjob != -1)
2246         {
2247                 result = (*(current_printif->job_delete))(
2248                         lp_printername(snum),
2249                         lp_lprmcommand(snum),
2250                         pjob);
2251
2252                 /* Delete the tdb entry if the delete succeeded or the job hasn't
2253                    been spooled. */
2254
2255                 if (result == 0) {
2256                         struct tdb_print_db *pdb = get_print_db_byname(sharename);
2257                         int njobs = 1;
2258
2259                         if (!pdb) {
2260                                 ret = false;
2261                                 goto err_out;
2262                         }
2263                         pjob_delete(ev, msg_ctx, sharename, jobid);
2264                         /* Ensure we keep a rough count of the number of total jobs... */
2265                         tdb_change_int32_atomic(pdb->tdb, "INFO/total_jobs", &njobs, -1);
2266                         release_print_db(pdb);
2267                 }
2268         }
2269
2270         remove_from_jobs_added( sharename, jobid );
2271
2272         ret = (result == 0);
2273 err_out:
2274         talloc_free(tmp_ctx);
2275         return ret;
2276 }
2277
2278 /****************************************************************************
2279  Return true if the current user owns the print job.
2280 ****************************************************************************/
2281
2282 static bool is_owner(const struct auth_serversupplied_info *server_info,
2283                      const char *servicename,
2284                      uint32 jobid)
2285 {
2286         struct printjob *pjob;
2287         bool ret;
2288         TALLOC_CTX *tmp_ctx = talloc_new(server_info);
2289         if (tmp_ctx == NULL) {
2290                 return false;
2291         }
2292
2293         pjob = print_job_find(tmp_ctx, servicename, jobid);
2294         if (!pjob || !server_info) {
2295                 ret = false;
2296                 goto err_out;
2297         }
2298
2299         ret = strequal(pjob->user, server_info->sanitized_username);
2300 err_out:
2301         talloc_free(tmp_ctx);
2302         return ret;
2303 }
2304
2305 /****************************************************************************
2306  Delete a print job.
2307 ****************************************************************************/
2308
2309 WERROR print_job_delete(const struct auth_serversupplied_info *server_info,
2310                         struct messaging_context *msg_ctx,
2311                         int snum, uint32_t jobid)
2312 {
2313         const char* sharename = lp_const_servicename(snum);
2314         struct printjob *pjob;
2315         bool    owner;
2316         WERROR werr;
2317         TALLOC_CTX *tmp_ctx = talloc_new(msg_ctx);
2318         if (tmp_ctx == NULL) {
2319                 return WERR_NOT_ENOUGH_MEMORY;
2320         }
2321
2322         owner = is_owner(server_info, lp_const_servicename(snum), jobid);
2323
2324         /* Check access against security descriptor or whether the user
2325            owns their job. */
2326
2327         if (!owner &&
2328             !print_access_check(server_info, msg_ctx, snum,
2329                                 JOB_ACCESS_ADMINISTER)) {
2330                 DEBUG(3, ("delete denied by security descriptor\n"));
2331
2332                 /* BEGIN_ADMIN_LOG */
2333                 sys_adminlog( LOG_ERR,
2334                               "Permission denied-- user not allowed to delete, \
2335 pause, or resume print job. User name: %s. Printer name: %s.",
2336                               uidtoname(server_info->utok.uid),
2337                               lp_printername(snum) );
2338                 /* END_ADMIN_LOG */
2339
2340                 werr = WERR_ACCESS_DENIED;
2341                 goto err_out;
2342         }
2343
2344         /*
2345          * get the spooled filename of the print job
2346          * if this works, then the file has not been spooled
2347          * to the underlying print system.  Just delete the
2348          * spool file & return.
2349          */
2350
2351         pjob = print_job_find(tmp_ctx, sharename, jobid);
2352         if (!pjob || pjob->spooled || pjob->pid != getpid()) {
2353                 DEBUG(10, ("Skipping spool file removal for job %u\n", jobid));
2354         } else {
2355                 DEBUG(10, ("Removing spool file [%s]\n", pjob->filename));
2356                 if (unlink(pjob->filename) == -1) {
2357                         werr = map_werror_from_unix(errno);
2358                         goto err_out;
2359                 }
2360         }
2361
2362         if (!print_job_delete1(server_event_context(), msg_ctx, snum, jobid)) {
2363                 werr = WERR_ACCESS_DENIED;
2364                 goto err_out;
2365         }
2366
2367         /* force update the database and say the delete failed if the
2368            job still exists */
2369
2370         print_queue_update(msg_ctx, snum, True);
2371
2372         pjob = print_job_find(tmp_ctx, sharename, jobid);
2373         if (pjob && (pjob->status != LPQ_DELETING)) {
2374                 werr = WERR_ACCESS_DENIED;
2375                 goto err_out;
2376         }
2377         werr = WERR_PRINTER_HAS_JOBS_QUEUED;
2378
2379 err_out:
2380         talloc_free(tmp_ctx);
2381         return werr;
2382 }
2383
2384 /****************************************************************************
2385  Pause a job.
2386 ****************************************************************************/
2387
2388 WERROR print_job_pause(const struct auth_serversupplied_info *server_info,
2389                      struct messaging_context *msg_ctx,
2390                      int snum, uint32 jobid)
2391 {
2392         const char* sharename = lp_const_servicename(snum);
2393         struct printjob *pjob;
2394         int ret = -1;
2395         struct printif *current_printif = get_printer_fns( snum );
2396         WERROR werr;
2397         TALLOC_CTX *tmp_ctx = talloc_new(msg_ctx);
2398         if (tmp_ctx == NULL) {
2399                 return WERR_NOT_ENOUGH_MEMORY;
2400         }
2401
2402         pjob = print_job_find(tmp_ctx, sharename, jobid);
2403         if (!pjob || !server_info) {
2404                 DEBUG(10, ("print_job_pause: no pjob or user for jobid %u\n",
2405                         (unsigned int)jobid ));
2406                 werr = WERR_INVALID_PARAM;
2407                 goto err_out;
2408         }
2409
2410         if (!pjob->spooled || pjob->sysjob == -1) {
2411                 DEBUG(10, ("print_job_pause: not spooled or bad sysjob = %d for jobid %u\n",
2412                         (int)pjob->sysjob, (unsigned int)jobid ));
2413                 werr = WERR_INVALID_PARAM;
2414                 goto err_out;
2415         }
2416
2417         if (!is_owner(server_info, lp_const_servicename(snum), jobid) &&
2418             !print_access_check(server_info, msg_ctx, snum,
2419                                 JOB_ACCESS_ADMINISTER)) {
2420                 DEBUG(3, ("pause denied by security descriptor\n"));
2421
2422                 /* BEGIN_ADMIN_LOG */
2423                 sys_adminlog( LOG_ERR,
2424                         "Permission denied-- user not allowed to delete, \
2425 pause, or resume print job. User name: %s. Printer name: %s.",
2426                               uidtoname(server_info->utok.uid),
2427                               lp_printername(snum) );
2428                 /* END_ADMIN_LOG */
2429
2430                 werr = WERR_ACCESS_DENIED;
2431                 goto err_out;
2432         }
2433
2434         /* need to pause the spooled entry */
2435         ret = (*(current_printif->job_pause))(snum, pjob);
2436
2437         if (ret != 0) {
2438                 werr = WERR_INVALID_PARAM;
2439                 goto err_out;
2440         }
2441
2442         /* force update the database */
2443         print_cache_flush(lp_const_servicename(snum));
2444
2445         /* Send a printer notify message */
2446
2447         notify_job_status(server_event_context(), msg_ctx, sharename, jobid,
2448                           JOB_STATUS_PAUSED);
2449
2450         /* how do we tell if this succeeded? */
2451         werr = WERR_OK;
2452 err_out:
2453         talloc_free(tmp_ctx);
2454         return werr;
2455 }
2456
2457 /****************************************************************************
2458  Resume a job.
2459 ****************************************************************************/
2460
2461 WERROR print_job_resume(const struct auth_serversupplied_info *server_info,
2462                       struct messaging_context *msg_ctx,
2463                       int snum, uint32 jobid)
2464 {
2465         const char *sharename = lp_const_servicename(snum);
2466         struct printjob *pjob;
2467         int ret;
2468         struct printif *current_printif = get_printer_fns( snum );
2469         WERROR werr;
2470         TALLOC_CTX *tmp_ctx = talloc_new(msg_ctx);
2471         if (tmp_ctx == NULL)
2472                 return WERR_NOT_ENOUGH_MEMORY;
2473
2474         pjob = print_job_find(tmp_ctx, sharename, jobid);
2475         if (!pjob || !server_info) {
2476                 DEBUG(10, ("print_job_resume: no pjob or user for jobid %u\n",
2477                         (unsigned int)jobid ));
2478                 werr = WERR_INVALID_PARAM;
2479                 goto err_out;
2480         }
2481
2482         if (!pjob->spooled || pjob->sysjob == -1) {
2483                 DEBUG(10, ("print_job_resume: not spooled or bad sysjob = %d for jobid %u\n",
2484                         (int)pjob->sysjob, (unsigned int)jobid ));
2485                 werr = WERR_INVALID_PARAM;
2486                 goto err_out;
2487         }
2488
2489         if (!is_owner(server_info, lp_const_servicename(snum), jobid) &&
2490             !print_access_check(server_info, msg_ctx, snum,
2491                                 JOB_ACCESS_ADMINISTER)) {
2492                 DEBUG(3, ("resume denied by security descriptor\n"));
2493
2494                 /* BEGIN_ADMIN_LOG */
2495                 sys_adminlog( LOG_ERR,
2496                          "Permission denied-- user not allowed to delete, \
2497 pause, or resume print job. User name: %s. Printer name: %s.",
2498                               uidtoname(server_info->utok.uid),
2499                               lp_printername(snum) );
2500                 /* END_ADMIN_LOG */
2501                 werr = WERR_ACCESS_DENIED;
2502                 goto err_out;
2503         }
2504
2505         ret = (*(current_printif->job_resume))(snum, pjob);
2506
2507         if (ret != 0) {
2508                 werr = WERR_INVALID_PARAM;
2509                 goto err_out;
2510         }
2511
2512         /* force update the database */
2513         print_cache_flush(lp_const_servicename(snum));
2514
2515         /* Send a printer notify message */
2516
2517         notify_job_status(server_event_context(), msg_ctx, sharename, jobid,
2518                           JOB_STATUS_QUEUED);
2519
2520         werr = WERR_OK;
2521 err_out:
2522         talloc_free(tmp_ctx);
2523         return werr;
2524 }
2525
2526 /****************************************************************************
2527  Write to a print file.
2528 ****************************************************************************/
2529
2530 ssize_t print_job_write(struct tevent_context *ev,
2531                         struct messaging_context *msg_ctx,
2532                         int snum, uint32 jobid, const char *buf, size_t size)
2533 {
2534         const char* sharename = lp_const_servicename(snum);
2535         ssize_t return_code;
2536         struct printjob *pjob;
2537         TALLOC_CTX *tmp_ctx = talloc_new(ev);
2538         if (tmp_ctx == NULL) {
2539                 return -1;
2540         }
2541
2542         pjob = print_job_find(tmp_ctx, sharename, jobid);
2543         if (!pjob) {
2544                 return_code = -1;
2545                 goto err_out;
2546         }
2547
2548         /* don't allow another process to get this info - it is meaningless */
2549         if (pjob->pid != sys_getpid()) {
2550                 return_code = -1;
2551                 goto err_out;
2552         }
2553
2554         /* if SMBD is spooling this can't be allowed */
2555         if (pjob->status == PJOB_SMBD_SPOOLING) {
2556                 return_code = -1;
2557                 goto err_out;
2558         }
2559
2560         return_code = write_data(pjob->fd, buf, size);
2561         if (return_code > 0) {
2562                 pjob->size += size;
2563                 pjob_store(ev, msg_ctx, sharename, jobid, pjob);
2564         }
2565 err_out:
2566         talloc_free(tmp_ctx);
2567         return return_code;
2568 }
2569
2570 /****************************************************************************
2571  Get the queue status - do not update if db is out of date.
2572 ****************************************************************************/
2573
2574 static int get_queue_status(const char* sharename, print_status_struct *status)
2575 {
2576         fstring keystr;
2577         TDB_DATA data;
2578         struct tdb_print_db *pdb = get_print_db_byname(sharename);
2579         int len;
2580
2581         if (status) {
2582                 ZERO_STRUCTP(status);
2583         }
2584
2585         if (!pdb)
2586                 return 0;
2587
2588         if (status) {
2589                 fstr_sprintf(keystr, "STATUS/%s", sharename);
2590                 data = tdb_fetch(pdb->tdb, string_tdb_data(keystr));
2591                 if (data.dptr) {
2592                         if (data.dsize == sizeof(print_status_struct))
2593                                 /* this memcpy is ok since the status struct was
2594                                    not packed before storing it in the tdb */
2595                                 memcpy(status, data.dptr, sizeof(print_status_struct));
2596                         SAFE_FREE(data.dptr);
2597                 }
2598         }
2599         len = tdb_fetch_int32(pdb->tdb, "INFO/total_jobs");
2600         release_print_db(pdb);
2601         return (len == -1 ? 0 : len);
2602 }
2603
2604 /****************************************************************************
2605  Determine the number of jobs in a queue.
2606 ****************************************************************************/
2607
2608 int print_queue_length(struct messaging_context *msg_ctx, int snum,
2609                        print_status_struct *pstatus)
2610 {
2611         const char* sharename = lp_const_servicename( snum );
2612         print_status_struct status;
2613         int len;
2614
2615         ZERO_STRUCT( status );
2616
2617         /* make sure the database is up to date */
2618         if (print_cache_expired(lp_const_servicename(snum), True))
2619                 print_queue_update(msg_ctx, snum, False);
2620
2621         /* also fetch the queue status */
2622         memset(&status, 0, sizeof(status));
2623         len = get_queue_status(sharename, &status);
2624
2625         if (pstatus)
2626                 *pstatus = status;
2627
2628         return len;
2629 }
2630
2631 /***************************************************************************
2632  Allocate a jobid. Hold the lock for as short a time as possible.
2633 ***************************************************************************/
2634
2635 static WERROR allocate_print_jobid(struct tdb_print_db *pdb, int snum,
2636                                    const char *sharename, uint32 *pjobid)
2637 {
2638         int i;
2639         uint32 jobid;
2640         enum TDB_ERROR terr;
2641         int ret;
2642
2643         *pjobid = (uint32)-1;
2644
2645         for (i = 0; i < 3; i++) {
2646                 /* Lock the database - only wait 20 seconds. */
2647                 ret = tdb_lock_bystring_with_timeout(pdb->tdb,
2648                                                      "INFO/nextjob", 20);
2649                 if (ret == -1) {
2650                         DEBUG(0, ("allocate_print_jobid: "
2651                                   "Failed to lock printing database %s\n",
2652                                   sharename));
2653                         terr = tdb_error(pdb->tdb);
2654                         return ntstatus_to_werror(map_nt_error_from_tdb(terr));
2655                 }
2656
2657                 if (!tdb_fetch_uint32(pdb->tdb, "INFO/nextjob", &jobid)) {
2658                         terr = tdb_error(pdb->tdb);
2659                         if (terr != TDB_ERR_NOEXIST) {
2660                                 DEBUG(0, ("allocate_print_jobid: "
2661                                           "Failed to fetch INFO/nextjob "
2662                                           "for print queue %s\n", sharename));
2663                                 tdb_unlock_bystring(pdb->tdb, "INFO/nextjob");
2664                                 return ntstatus_to_werror(map_nt_error_from_tdb(terr));
2665                         }
2666                         DEBUG(10, ("allocate_print_jobid: "
2667                                    "No existing jobid in %s\n", sharename));
2668                         jobid = 0;
2669                 }
2670
2671                 DEBUG(10, ("allocate_print_jobid: "
2672                            "Read jobid %u from %s\n", jobid, sharename));
2673
2674                 jobid = NEXT_JOBID(jobid);
2675
2676                 ret = tdb_store_int32(pdb->tdb, "INFO/nextjob", jobid);
2677                 if (ret == -1) {
2678                         terr = tdb_error(pdb->tdb);
2679                         DEBUG(3, ("allocate_print_jobid: "
2680                                   "Failed to store INFO/nextjob.\n"));
2681                         tdb_unlock_bystring(pdb->tdb, "INFO/nextjob");
2682                         return ntstatus_to_werror(map_nt_error_from_tdb(terr));
2683                 }
2684
2685                 /* We've finished with the INFO/nextjob lock. */
2686                 tdb_unlock_bystring(pdb->tdb, "INFO/nextjob");
2687
2688                 if (!print_job_exists(sharename, jobid)) {
2689                         break;
2690                 }
2691                 DEBUG(10, ("allocate_print_jobid: "
2692                            "Found jobid %u in %s\n", jobid, sharename));
2693         }
2694
2695         if (i > 2) {
2696                 DEBUG(0, ("allocate_print_jobid: "
2697                           "Failed to allocate a print job for queue %s\n",
2698                           sharename));
2699                 /* Probably full... */
2700                 return WERR_NO_SPOOL_SPACE;
2701         }
2702
2703         /* Store a dummy placeholder. */
2704         {
2705                 uint32_t tmp;
2706                 TDB_DATA dum;
2707                 dum.dptr = NULL;
2708                 dum.dsize = 0;
2709                 if (tdb_store(pdb->tdb, print_key(jobid, &tmp), dum,
2710                               TDB_INSERT) == -1) {
2711                         DEBUG(3, ("allocate_print_jobid: "
2712                                   "jobid (%d) failed to store placeholder.\n",
2713                                   jobid ));
2714                         terr = tdb_error(pdb->tdb);
2715                         return ntstatus_to_werror(map_nt_error_from_tdb(terr));
2716                 }
2717         }
2718
2719         *pjobid = jobid;
2720         return WERR_OK;
2721 }
2722
2723 /***************************************************************************
2724  Append a jobid to the 'jobs added' list.
2725 ***************************************************************************/
2726
2727 static bool add_to_jobs_added(struct tdb_print_db *pdb, uint32 jobid)
2728 {
2729         TDB_DATA data;
2730         uint32 store_jobid;
2731
2732         SIVAL(&store_jobid, 0, jobid);
2733         data.dptr = (uint8 *)&store_jobid;
2734         data.dsize = 4;
2735
2736         DEBUG(10,("add_to_jobs_added: Added jobid %u\n", (unsigned int)jobid ));
2737
2738         return (tdb_append(pdb->tdb, string_tdb_data("INFO/jobs_added"),
2739                            data) == 0);
2740 }
2741
2742
2743 /***************************************************************************
2744  Do all checks needed to determine if we can start a job.
2745 ***************************************************************************/
2746
2747 static WERROR print_job_checks(const struct auth_serversupplied_info *server_info,
2748                                struct messaging_context *msg_ctx,
2749                                int snum, int *njobs)
2750 {
2751         const char *sharename = lp_const_servicename(snum);
2752         uint64_t dspace, dsize;
2753         uint64_t minspace;
2754         int ret;
2755
2756         if (!print_access_check(server_info, msg_ctx, snum,
2757                                 PRINTER_ACCESS_USE)) {
2758                 DEBUG(3, ("print_job_checks: "
2759                           "job start denied by security descriptor\n"));
2760                 return WERR_ACCESS_DENIED;
2761         }
2762
2763         if (!print_time_access_check(server_info, msg_ctx, sharename)) {
2764                 DEBUG(3, ("print_job_checks: "
2765                           "job start denied by time check\n"));
2766                 return WERR_ACCESS_DENIED;
2767         }
2768
2769         /* see if we have sufficient disk space */
2770         if (lp_minprintspace(snum)) {
2771                 minspace = lp_minprintspace(snum);
2772                 ret = sys_fsusage(lp_pathname(snum), &dspace, &dsize);
2773                 if (ret == 0 && dspace < 2*minspace) {
2774                         DEBUG(3, ("print_job_checks: "
2775                                   "disk space check failed.\n"));
2776                         return WERR_NO_SPOOL_SPACE;
2777                 }
2778         }
2779
2780         /* for autoloaded printers, check that the printcap entry still exists */
2781         if (lp_autoloaded(snum) && !pcap_printername_ok(sharename)) {
2782                 DEBUG(3, ("print_job_checks: printer name %s check failed.\n",
2783                           sharename));
2784                 return WERR_ACCESS_DENIED;
2785         }
2786
2787         /* Insure the maximum queue size is not violated */
2788         *njobs = print_queue_length(msg_ctx, snum, NULL);
2789         if (*njobs > lp_maxprintjobs(snum)) {
2790                 DEBUG(3, ("print_job_checks: Queue %s number of jobs (%d) "
2791                           "larger than max printjobs per queue (%d).\n",
2792                           sharename, *njobs, lp_maxprintjobs(snum)));
2793                 return WERR_NO_SPOOL_SPACE;
2794         }
2795
2796         return WERR_OK;
2797 }
2798
2799 /***************************************************************************
2800  Create a job file.
2801 ***************************************************************************/
2802
2803 static WERROR print_job_spool_file(int snum, uint32_t jobid,
2804                                    const char *output_file,
2805                                    struct printjob *pjob)
2806 {
2807         WERROR werr;
2808         SMB_STRUCT_STAT st;
2809         const char *path;
2810         int len;
2811
2812         /* if this file is within the printer path, it means that smbd
2813          * is spooling it and will pass us control when it is finished.
2814          * Verify that the file name is ok, within path, and it is
2815          * already already there */
2816         if (output_file) {
2817                 path = lp_pathname(snum);
2818                 len = strlen(path);
2819                 if (strncmp(output_file, path, len) == 0 &&
2820                     (output_file[len - 1] == '/' || output_file[len] == '/')) {
2821
2822                         /* verify path is not too long */
2823                         if (strlen(output_file) >= sizeof(pjob->filename)) {
2824                                 return WERR_INVALID_NAME;
2825                         }
2826
2827                         /* verify that the file exists */
2828                         if (sys_stat(output_file, &st, false) != 0) {
2829                                 return WERR_INVALID_NAME;
2830                         }
2831
2832                         fstrcpy(pjob->filename, output_file);
2833
2834                         DEBUG(3, ("print_job_spool_file:"
2835                                   "External spooling activated"));
2836
2837                         /* we do not open the file until spooling is done */
2838                         pjob->fd = -1;
2839                         pjob->status = PJOB_SMBD_SPOOLING;
2840
2841                         return WERR_OK;
2842                 }
2843         }
2844
2845         slprintf(pjob->filename, sizeof(pjob->filename)-1,
2846                  "%s/%s%.8u.XXXXXX", lp_pathname(snum),
2847                  PRINT_SPOOL_PREFIX, (unsigned int)jobid);
2848         pjob->fd = mkstemp(pjob->filename);
2849
2850         if (pjob->fd == -1) {
2851                 werr = map_werror_from_unix(errno);
2852                 if (W_ERROR_EQUAL(werr, WERR_ACCESS_DENIED)) {
2853                         /* Common setup error, force a report. */
2854                         DEBUG(0, ("print_job_spool_file: "
2855                                   "insufficient permissions to open spool "
2856                                   "file %s.\n", pjob->filename));
2857                 } else {
2858                         /* Normal case, report at level 3 and above. */
2859                         DEBUG(3, ("print_job_spool_file: "
2860                                   "can't open spool file %s\n",
2861                                   pjob->filename));
2862                 }
2863                 return werr;
2864         }
2865
2866         return WERR_OK;
2867 }
2868
2869 /***************************************************************************
2870  Start spooling a job - return the jobid.
2871 ***************************************************************************/
2872
2873 WERROR print_job_start(const struct auth_serversupplied_info *server_info,
2874                        struct messaging_context *msg_ctx,
2875                        const char *clientmachine,
2876                        int snum, const char *docname, const char *filename,
2877                        struct spoolss_DeviceMode *devmode, uint32_t *_jobid)
2878 {
2879         uint32_t jobid;
2880         char *path;
2881         struct printjob pjob;
2882         const char *sharename = lp_const_servicename(snum);
2883         struct tdb_print_db *pdb = get_print_db_byname(sharename);
2884         int njobs;
2885         WERROR werr;
2886
2887         if (!pdb) {
2888                 return WERR_INTERNAL_DB_CORRUPTION;
2889         }
2890
2891         path = lp_pathname(snum);
2892
2893         werr = print_job_checks(server_info, msg_ctx, snum, &njobs);
2894         if (!W_ERROR_IS_OK(werr)) {
2895                 release_print_db(pdb);
2896                 return werr;
2897         }
2898
2899         DEBUG(10, ("print_job_start: "
2900                    "Queue %s number of jobs (%d), max printjobs = %d\n",
2901                    sharename, njobs, lp_maxprintjobs(snum)));
2902
2903         werr = allocate_print_jobid(pdb, snum, sharename, &jobid);
2904         if (!W_ERROR_IS_OK(werr)) {
2905                 goto fail;
2906         }
2907
2908         /* create the database entry */
2909
2910         ZERO_STRUCT(pjob);
2911
2912         pjob.pid = sys_getpid();
2913         pjob.jobid = jobid;
2914         pjob.sysjob = -1;
2915         pjob.fd = -1;
2916         pjob.starttime = time(NULL);
2917         pjob.status = LPQ_SPOOLING;
2918         pjob.size = 0;
2919         pjob.spooled = False;
2920         pjob.smbjob = True;
2921         pjob.devmode = devmode;
2922
2923         fstrcpy(pjob.jobname, docname);
2924
2925         fstrcpy(pjob.clientmachine, clientmachine);
2926
2927         fstrcpy(pjob.user, lp_printjob_username(snum));
2928         standard_sub_advanced(sharename, server_info->sanitized_username,
2929                               path, server_info->utok.gid,
2930                               server_info->sanitized_username,
2931                               server_info->info3->base.domain.string,
2932                               pjob.user, sizeof(pjob.user)-1);
2933         /* ensure NULL termination */
2934         pjob.user[sizeof(pjob.user)-1] = '\0';
2935
2936         fstrcpy(pjob.queuename, lp_const_servicename(snum));
2937
2938         /* we have a job entry - now create the spool file */
2939         werr = print_job_spool_file(snum, jobid, filename, &pjob);
2940         if (!W_ERROR_IS_OK(werr)) {
2941                 goto fail;
2942         }
2943
2944         pjob_store(server_event_context(), msg_ctx, sharename, jobid, &pjob);
2945
2946         /* Update the 'jobs added' entry used by print_queue_status. */
2947         add_to_jobs_added(pdb, jobid);
2948
2949         /* Ensure we keep a rough count of the number of total jobs... */
2950         tdb_change_int32_atomic(pdb->tdb, "INFO/total_jobs", &njobs, 1);
2951
2952         release_print_db(pdb);
2953
2954         *_jobid = jobid;
2955         return WERR_OK;
2956
2957 fail:
2958         if (jobid != -1) {
2959                 pjob_delete(server_event_context(), msg_ctx, sharename, jobid);
2960         }
2961
2962         release_print_db(pdb);
2963
2964         DEBUG(3, ("print_job_start: returning fail. "
2965                   "Error = %s\n", win_errstr(werr)));
2966         return werr;
2967 }
2968
2969 /****************************************************************************
2970  Update the number of pages spooled to jobid
2971 ****************************************************************************/
2972
2973 void print_job_endpage(struct messaging_context *msg_ctx,
2974                        int snum, uint32 jobid)
2975 {
2976         const char* sharename = lp_const_servicename(snum);
2977         struct printjob *pjob;
2978         TALLOC_CTX *tmp_ctx = talloc_new(msg_ctx);
2979         if (tmp_ctx == NULL) {
2980                 return;
2981         }
2982
2983         pjob = print_job_find(tmp_ctx, sharename, jobid);
2984         if (!pjob) {
2985                 goto err_out;
2986         }
2987         /* don't allow another process to get this info - it is meaningless */
2988         if (pjob->pid != sys_getpid()) {
2989                 goto err_out;
2990         }
2991
2992         pjob->page_count++;
2993         pjob_store(server_event_context(), msg_ctx, sharename, jobid, pjob);
2994 err_out:
2995         talloc_free(tmp_ctx);
2996 }
2997
2998 /****************************************************************************
2999  Print a file - called on closing the file. This spools the job.
3000  If normal close is false then we're tearing down the jobs - treat as an
3001  error.
3002 ****************************************************************************/
3003
3004 NTSTATUS print_job_end(struct messaging_context *msg_ctx, int snum,
3005                        uint32 jobid, enum file_close_type close_type)
3006 {
3007         const char* sharename = lp_const_servicename(snum);
3008         struct printjob *pjob;
3009         int ret;
3010         SMB_STRUCT_STAT sbuf;
3011         struct printif *current_printif = get_printer_fns(snum);
3012         NTSTATUS status = NT_STATUS_UNSUCCESSFUL;
3013         char *lpq_cmd;
3014         TALLOC_CTX *tmp_ctx = talloc_new(msg_ctx);
3015         if (tmp_ctx == NULL) {
3016                 return NT_STATUS_NO_MEMORY;
3017         }
3018
3019         pjob = print_job_find(tmp_ctx, sharename, jobid);
3020         if (!pjob) {
3021                 status = NT_STATUS_PRINT_CANCELLED;
3022                 goto err_out;
3023         }
3024
3025         if (pjob->spooled || pjob->pid != sys_getpid()) {
3026                 status = NT_STATUS_ACCESS_DENIED;
3027                 goto err_out;
3028         }
3029
3030         if (close_type == NORMAL_CLOSE || close_type == SHUTDOWN_CLOSE) {
3031                 if (pjob->status == PJOB_SMBD_SPOOLING) {
3032                         /* take over the file now, smbd is done */
3033                         if (sys_stat(pjob->filename, &sbuf, false) != 0) {
3034                                 status = map_nt_error_from_unix(errno);
3035                                 DEBUG(3, ("print_job_end: "
3036                                           "stat file failed for jobid %d\n",
3037                                           jobid));
3038                                 goto fail;
3039                         }
3040
3041                         pjob->status = LPQ_SPOOLING;
3042
3043                 } else {
3044
3045                         if ((sys_fstat(pjob->fd, &sbuf, false) != 0)) {
3046                                 status = map_nt_error_from_unix(errno);
3047                                 close(pjob->fd);
3048                                 DEBUG(3, ("print_job_end: "
3049                                           "stat file failed for jobid %d\n",
3050                                           jobid));
3051                                 goto fail;
3052                         }
3053
3054                         close(pjob->fd);
3055                 }
3056
3057                 pjob->size = sbuf.st_ex_size;
3058         } else {
3059
3060                 /*
3061                  * Not a normal close, something has gone wrong. Cleanup.
3062                  */
3063                 if (pjob->fd != -1) {
3064                         close(pjob->fd);
3065                 }
3066                 goto fail;
3067         }
3068
3069         /* Technically, this is not quite right. If the printer has a separator
3070          * page turned on, the NT spooler prints the separator page even if the
3071          * print job is 0 bytes. 010215 JRR */
3072         if (pjob->size == 0 || pjob->status == LPQ_DELETING) {
3073                 /* don't bother spooling empty files or something being deleted. */
3074                 DEBUG(5,("print_job_end: canceling spool of %s (%s)\n",
3075                         pjob->filename, pjob->size ? "deleted" : "zero length" ));
3076                 unlink(pjob->filename);
3077                 pjob_delete(server_event_context(), msg_ctx, sharename, jobid);
3078                 return NT_STATUS_OK;
3079         }
3080
3081         /* don't strip out characters like '$' from the printername */
3082         lpq_cmd = talloc_string_sub2(tmp_ctx,
3083                                      lp_lpqcommand(snum),
3084                                      "%p",
3085                                      lp_printername(snum),
3086                                      false, false, false);
3087         if (lpq_cmd == NULL) {
3088                 status = NT_STATUS_PRINT_CANCELLED;
3089                 goto fail;
3090         }
3091         lpq_cmd = talloc_sub_advanced(tmp_ctx,
3092                                       lp_servicename(snum),
3093                                       current_user_info.unix_name,
3094                                       "",
3095                                       current_user.ut.gid,
3096                                       get_current_username(),
3097                                       current_user_info.domain,
3098                                       lpq_cmd);
3099         if (lpq_cmd == NULL) {
3100                 status = NT_STATUS_PRINT_CANCELLED;
3101                 goto fail;
3102         }
3103
3104         ret = (*(current_printif->job_submit))(snum, pjob,
3105                                                current_printif->type, lpq_cmd);
3106         if (ret) {
3107                 status = NT_STATUS_PRINT_CANCELLED;
3108                 goto fail;
3109         }
3110
3111         /* The print job has been successfully handed over to the back-end */
3112
3113         pjob->spooled = True;
3114         pjob->status = LPQ_QUEUED;
3115         pjob_store(server_event_context(), msg_ctx, sharename, jobid, pjob);
3116
3117         /* make sure the database is up to date */
3118         if (print_cache_expired(lp_const_servicename(snum), True))
3119                 print_queue_update(msg_ctx, snum, False);
3120
3121         return NT_STATUS_OK;
3122
3123 fail:
3124
3125         /* The print job was not successfully started. Cleanup */
3126         /* Still need to add proper error return propagation! 010122:JRR */
3127         pjob->fd = -1;
3128         unlink(pjob->filename);
3129         pjob_delete(server_event_context(), msg_ctx, sharename, jobid);
3130 err_out:
3131         talloc_free(tmp_ctx);
3132         return status;
3133 }
3134
3135 /****************************************************************************
3136  Get a snapshot of jobs in the system without traversing.
3137 ****************************************************************************/
3138
3139 static bool get_stored_queue_info(struct messaging_context *msg_ctx,
3140                                   struct tdb_print_db *pdb, int snum,
3141                                   int *pcount, print_queue_struct **ppqueue)
3142 {
3143         TDB_DATA data, cgdata, jcdata;
3144         print_queue_struct *queue = NULL;
3145         uint32 qcount = 0;
3146         uint32 extra_count = 0;
3147         uint32_t changed_count = 0;
3148         int total_count = 0;
3149         size_t len = 0;
3150         uint32 i;
3151         int max_reported_jobs = lp_max_reported_jobs(snum);
3152         bool ret = False;
3153         const char* sharename = lp_servicename(snum);
3154         TALLOC_CTX *tmp_ctx = talloc_new(msg_ctx);
3155         if (tmp_ctx == NULL) {
3156                 return false;
3157         }
3158
3159         /* make sure the database is up to date */
3160         if (print_cache_expired(lp_const_servicename(snum), True))
3161                 print_queue_update(msg_ctx, snum, False);
3162
3163         *pcount = 0;
3164         *ppqueue = NULL;
3165
3166         ZERO_STRUCT(data);
3167         ZERO_STRUCT(cgdata);
3168
3169         /* Get the stored queue data. */
3170         data = tdb_fetch(pdb->tdb, string_tdb_data("INFO/linear_queue_array"));
3171
3172         if (data.dptr && data.dsize >= sizeof(qcount))
3173                 len += tdb_unpack(data.dptr + len, data.dsize - len, "d", &qcount);
3174
3175         /* Get the added jobs list. */
3176         cgdata = tdb_fetch(pdb->tdb, string_tdb_data("INFO/jobs_added"));
3177         if (cgdata.dptr != NULL && (cgdata.dsize % 4 == 0))
3178                 extra_count = cgdata.dsize/4;
3179
3180         /* Get the changed jobs list. */
3181         jcdata = tdb_fetch(pdb->tdb, string_tdb_data("INFO/jobs_changed"));
3182         if (jcdata.dptr != NULL && (jcdata.dsize % 4 == 0))
3183                 changed_count = jcdata.dsize / 4;
3184
3185         DEBUG(5,("get_stored_queue_info: qcount = %u, extra_count = %u\n", (unsigned int)qcount, (unsigned int)extra_count));
3186
3187         /* Allocate the queue size. */
3188         if (qcount == 0 && extra_count == 0)
3189                 goto out;
3190
3191         if ((queue = SMB_MALLOC_ARRAY(print_queue_struct, qcount + extra_count)) == NULL)
3192                 goto out;
3193
3194         /* Retrieve the linearised queue data. */
3195
3196         for( i  = 0; i < qcount; i++) {
3197                 uint32 qjob, qsize, qpage_count, qstatus, qpriority, qtime;
3198                 len += tdb_unpack(data.dptr + len, data.dsize - len, "ddddddff",
3199                                 &qjob,
3200                                 &qsize,
3201                                 &qpage_count,
3202                                 &qstatus,
3203                                 &qpriority,
3204                                 &qtime,
3205                                 queue[i].fs_user,
3206                                 queue[i].fs_file);
3207                 queue[i].sysjob = qjob;
3208                 queue[i].size = qsize;
3209                 queue[i].page_count = qpage_count;
3210                 queue[i].status = qstatus;
3211                 queue[i].priority = qpriority;
3212                 queue[i].time = qtime;
3213         }
3214
3215         total_count = qcount;
3216
3217         /* Add new jobids to the queue. */
3218         for( i  = 0; i < extra_count; i++) {
3219                 uint32 jobid;
3220                 struct printjob *pjob;
3221
3222                 jobid = IVAL(cgdata.dptr, i*4);
3223                 DEBUG(5,("get_stored_queue_info: added job = %u\n", (unsigned int)jobid));
3224                 pjob = print_job_find(tmp_ctx, lp_const_servicename(snum), jobid);
3225                 if (!pjob) {
3226                         DEBUG(5,("get_stored_queue_info: failed to find added job = %u\n", (unsigned int)jobid));
3227                         remove_from_jobs_added(sharename, jobid);
3228                         continue;
3229                 }
3230
3231                 queue[total_count].sysjob = jobid;
3232                 queue[total_count].size = pjob->size;
3233                 queue[total_count].page_count = pjob->page_count;
3234                 queue[total_count].status = pjob->status;
3235                 queue[total_count].priority = 1;
3236                 queue[total_count].time = pjob->starttime;
3237                 fstrcpy(queue[total_count].fs_user, pjob->user);
3238                 fstrcpy(queue[total_count].fs_file, pjob->jobname);
3239                 total_count++;
3240                 talloc_free(pjob);
3241         }
3242
3243         /* Update the changed jobids. */
3244         for (i = 0; i < changed_count; i++) {
3245                 uint32_t jobid = IVAL(jcdata.dptr, i * 4);
3246                 uint32_t j;
3247                 bool found = false;
3248
3249                 for (j = 0; j < total_count; j++) {
3250                         if (queue[j].sysjob == jobid) {
3251                                 found = true;
3252                                 break;
3253                         }
3254                 }
3255
3256                 if (found) {
3257                         struct printjob *pjob;
3258
3259                         DEBUG(5,("get_stored_queue_info: changed job: %u\n",
3260                                  (unsigned int) jobid));
3261
3262                         pjob = print_job_find(tmp_ctx, sharename, jobid);
3263                         if (pjob == NULL) {
3264                                 DEBUG(5,("get_stored_queue_info: failed to find "
3265                                          "changed job = %u\n",
3266                                          (unsigned int) jobid));
3267                                 remove_from_jobs_changed(sharename, jobid);
3268                                 continue;
3269                         }
3270
3271                         queue[j].sysjob = jobid;
3272                         queue[j].size = pjob->size;
3273                         queue[j].page_count = pjob->page_count;
3274                         queue[j].status = pjob->status;
3275                         queue[j].priority = 1;
3276                         queue[j].time = pjob->starttime;
3277                         fstrcpy(queue[j].fs_user, pjob->user);
3278                         fstrcpy(queue[j].fs_file, pjob->jobname);
3279                         talloc_free(pjob);
3280
3281                         DEBUG(5,("get_stored_queue_info: updated queue[%u], jobid: %u, jobname: %s\n",
3282                                  (unsigned int) j, (unsigned int) jobid, pjob->jobname));
3283                 }
3284
3285                 remove_from_jobs_changed(sharename, jobid);
3286         }
3287
3288         /* Sort the queue by submission time otherwise they are displayed
3289            in hash order. */
3290
3291         TYPESAFE_QSORT(queue, total_count, printjob_comp);
3292
3293         DEBUG(5,("get_stored_queue_info: total_count = %u\n", (unsigned int)total_count));
3294
3295         if (max_reported_jobs && total_count > max_reported_jobs)
3296                 total_count = max_reported_jobs;
3297
3298         *ppqueue = queue;
3299         *pcount = total_count;
3300
3301         ret = True;
3302
3303   out:
3304
3305         SAFE_FREE(data.dptr);
3306         SAFE_FREE(cgdata.dptr);
3307         talloc_free(tmp_ctx);
3308         return ret;
3309 }
3310
3311 /****************************************************************************
3312  Get a printer queue listing.
3313  set queue = NULL and status = NULL if you just want to update the cache
3314 ****************************************************************************/
3315
3316 int print_queue_status(struct messaging_context *msg_ctx, int snum,
3317                        print_queue_struct **ppqueue,
3318                        print_status_struct *status)
3319 {
3320         fstring keystr;
3321         TDB_DATA data, key;
3322         const char *sharename;
3323         struct tdb_print_db *pdb;
3324         int count = 0;
3325
3326         /* make sure the database is up to date */
3327
3328         if (print_cache_expired(lp_const_servicename(snum), True))
3329                 print_queue_update(msg_ctx, snum, False);
3330
3331         /* return if we are done */
3332         if ( !ppqueue || !status )
3333                 return 0;
3334
3335         *ppqueue = NULL;
3336         sharename = lp_const_servicename(snum);
3337         pdb = get_print_db_byname(sharename);
3338
3339         if (!pdb)
3340                 return 0;
3341
3342         /*
3343          * Fetch the queue status.  We must do this first, as there may
3344          * be no jobs in the queue.
3345          */
3346
3347         ZERO_STRUCTP(status);
3348         slprintf(keystr, sizeof(keystr)-1, "STATUS/%s", sharename);
3349         key = string_tdb_data(keystr);
3350
3351         data = tdb_fetch(pdb->tdb, key);
3352         if (data.dptr) {
3353                 if (data.dsize == sizeof(*status)) {
3354                         /* this memcpy is ok since the status struct was
3355                            not packed before storing it in the tdb */
3356                         memcpy(status, data.dptr, sizeof(*status));
3357                 }
3358                 SAFE_FREE(data.dptr);
3359         }
3360
3361         /*
3362          * Now, fetch the print queue information.  We first count the number
3363          * of entries, and then only retrieve the queue if necessary.
3364          */
3365
3366         if (!get_stored_queue_info(msg_ctx, pdb, snum, &count, ppqueue)) {
3367                 release_print_db(pdb);
3368                 return 0;
3369         }
3370
3371         release_print_db(pdb);
3372         return count;
3373 }
3374
3375 /****************************************************************************
3376  Pause a queue.
3377 ****************************************************************************/
3378
3379 WERROR print_queue_pause(const struct auth_serversupplied_info *server_info,
3380                          struct messaging_context *msg_ctx, int snum)
3381 {
3382         int ret;
3383         struct printif *current_printif = get_printer_fns( snum );
3384
3385         if (!print_access_check(server_info, msg_ctx, snum,
3386                                 PRINTER_ACCESS_ADMINISTER)) {
3387                 return WERR_ACCESS_DENIED;
3388         }
3389
3390
3391         become_root();
3392
3393         ret = (*(current_printif->queue_pause))(snum);
3394
3395         unbecome_root();
3396
3397         if (ret != 0) {
3398                 return WERR_INVALID_PARAM;
3399         }
3400
3401         /* force update the database */
3402         print_cache_flush(lp_const_servicename(snum));
3403
3404         /* Send a printer notify message */
3405
3406         notify_printer_status(server_event_context(), msg_ctx, snum,
3407                               PRINTER_STATUS_PAUSED);
3408
3409         return WERR_OK;
3410 }
3411
3412 /****************************************************************************
3413  Resume a queue.
3414 ****************************************************************************/
3415
3416 WERROR print_queue_resume(const struct auth_serversupplied_info *server_info,
3417                           struct messaging_context *msg_ctx, int snum)
3418 {
3419         int ret;
3420         struct printif *current_printif = get_printer_fns( snum );
3421
3422         if (!print_access_check(server_info, msg_ctx, snum,
3423                                 PRINTER_ACCESS_ADMINISTER)) {
3424                 return WERR_ACCESS_DENIED;
3425         }
3426
3427         become_root();
3428
3429         ret = (*(current_printif->queue_resume))(snum);
3430
3431         unbecome_root();
3432
3433         if (ret != 0) {
3434                 return WERR_INVALID_PARAM;
3435         }
3436
3437         /* make sure the database is up to date */
3438         if (print_cache_expired(lp_const_servicename(snum), True))
3439                 print_queue_update(msg_ctx, snum, True);
3440
3441         /* Send a printer notify message */
3442
3443         notify_printer_status(server_event_context(), msg_ctx, snum,
3444                               PRINTER_STATUS_OK);
3445
3446         return WERR_OK;
3447 }
3448
3449 /****************************************************************************
3450  Purge a queue - implemented by deleting all jobs that we can delete.
3451 ****************************************************************************/
3452
3453 WERROR print_queue_purge(const struct auth_serversupplied_info *server_info,
3454                          struct messaging_context *msg_ctx, int snum)
3455 {
3456         print_queue_struct *queue;
3457         print_status_struct status;
3458         int njobs, i;
3459         bool can_job_admin;
3460
3461         /* Force and update so the count is accurate (i.e. not a cached count) */
3462         print_queue_update(msg_ctx, snum, True);
3463
3464         can_job_admin = print_access_check(server_info,
3465                                            msg_ctx,
3466                                            snum,
3467                                            JOB_ACCESS_ADMINISTER);
3468         njobs = print_queue_status(msg_ctx, snum, &queue, &status);
3469
3470         if ( can_job_admin )
3471                 become_root();
3472
3473         for (i=0;i<njobs;i++) {
3474                 bool owner = is_owner(server_info, lp_const_servicename(snum),
3475                                       queue[i].sysjob);
3476
3477                 if (owner || can_job_admin) {
3478                         print_job_delete1(server_event_context(), msg_ctx,
3479                                           snum, queue[i].sysjob);
3480                 }
3481         }
3482
3483         if ( can_job_admin )
3484                 unbecome_root();
3485
3486         /* update the cache */
3487         print_queue_update(msg_ctx, snum, True);
3488
3489         SAFE_FREE(queue);
3490
3491         return WERR_OK;
3492 }