1
0
mirror of https://github.com/samba-team/samba.git synced 2025-03-12 20:58:37 +03:00

Fixes to periodically scan printing.tdb in idle time and occasionally

on exit. Needed to fix printing.tdb from groving to 300Mb+ if being
driven by smbclient clients that never ask for status... (effective
DOS attack :-).
Jeremy.
This commit is contained in:
Jeremy Allison -
parent b41cc5fea7
commit 6581066b93
4 changed files with 53 additions and 1 deletions

View File

@ -1787,6 +1787,7 @@ int print_queue_snum(char *qname);
BOOL print_queue_pause(struct current_user *user, int snum, int *errcode);
BOOL print_queue_resume(struct current_user *user, int snum, int *errcode);
BOOL print_queue_purge(struct current_user *user, int snum, int *errcode);
void process_print_queue(time_t t);
#endif
/*The following definitions come from profile/profile.c */

View File

@ -300,6 +300,14 @@ static void print_queue_update(int snum)
fstring keystr;
TDB_DATA data, key;
/*
* Update the cache time FIRST ! Stops others doing this
* if the lpq takes a long time.
*/
slprintf(keystr, sizeof(keystr), "CACHE/%s", lp_servicename(snum));
tdb_store_int(tdb, keystr, (int)time(NULL));
slprintf(tmp_file, sizeof(tmp_file), "%s/smblpq.%d", path, local_pid);
unlink(tmp_file);
@ -380,7 +388,11 @@ static void print_queue_update(int snum)
key.dsize = strlen(keystr);
tdb_store(tdb, key, data, TDB_REPLACE);
/* update the cache time */
/*
* Update the cache time again. We want to do this call
* as little as possible...
*/
slprintf(keystr, sizeof(keystr), "CACHE/%s", lp_servicename(snum));
tdb_store_int(tdb, keystr, (int)time(NULL));
}
@ -1008,7 +1020,36 @@ BOOL print_queue_purge(struct current_user *user, int snum, int *errcode)
}
print_cache_flush(snum);
safe_free(queue);
return True;
}
/****************************************************************************
Periodically run a status on all the queues to ensure the tdb doesn't grow.
Note that this will have no effect if the client is doing its own status
queries. This code is here to clean up jobs submitted by non-Windows printer
clients (eg. smbclient) that never do a status check.
****************************************************************************/
void process_print_queue(time_t t)
{
static time_t last_check_time;
int services = lp_numservices();
print_queue_struct *queue;
print_status_struct status;
int snum;
if ((t != (time_t)-1) && ((t - last_check_time) < lp_lpqcachetime()))
return;
last_check_time = t;
for (snum = 0; snum < services; snum++) {
if (lp_snum_ok(snum) && lp_print_ok(snum) && lp_browseable(snum)) {
(void)print_queue_status(snum, &queue,&status);
safe_free(queue);
}
}
}
#undef OLD_NTDOMAIN

View File

@ -993,6 +993,12 @@ machine %s in domain %s.\n", global_myname, global_myworkgroup ));
*/
process_pending_change_notify_queue(t);
/*
* Ensure the print queue tdb doesn't grow too
* big by periodically scanning it.
*/
process_print_queue(t);
/*
* Now we are root, check if the log files need pruning.
*/

View File

@ -422,6 +422,10 @@ void exit_server(char *reason)
respond_to_all_remaining_local_messages();
/* Don't do this on every exit... */
if (sys_random() % 10)
process_print_queue(time(NULL));
#ifdef WITH_DFS
if (dcelogin_atmost_once) {
dfs_unlogin();