Expand PMF_FN_* macros.
[netbsd-mini2440.git] / external / ibm-public / postfix / dist / src / oqmgr / qmgr_scan.c
blobd7902bcbd4fb07b244feb8b6abc6fcea69c0047c
1 /* $NetBSD$ */
3 /*++
4 /* NAME
5 /* qmgr_scan 3
6 /* SUMMARY
7 /* queue scanning
8 /* SYNOPSIS
9 /* #include "qmgr.h"
11 /* QMGR_SCAN *qmgr_scan_create(queue_name)
12 /* const char *queue_name;
14 /* char *qmgr_scan_next(scan_info)
15 /* QMGR_SCAN *scan_info;
17 /* void qmgr_scan_request(scan_info, flags)
18 /* QMGR_SCAN *scan_info;
19 /* int flags;
20 /* DESCRIPTION
21 /* This module implements queue scans. A queue scan always runs
22 /* to completion, so that all files get a fair chance. The caller
23 /* can request that a queue scan be restarted once it completes.
25 /* qmgr_scan_create() creates a context for scanning the named queue,
26 /* but does not start a queue scan.
28 /* qmgr_scan_next() returns the base name of the next queue file.
29 /* A null pointer means that no file was found. qmgr_scan_next()
30 /* automagically restarts a queue scan when a scan request had
31 /* arrived while the scan was in progress.
33 /* qmgr_scan_request() records a request for the next queue scan. The
34 /* flags argument is the bit-wise OR of zero or more of the following,
35 /* unrecognized flags being ignored:
36 /* .IP QMGR_FLUSH_ONCE
37 /* Forget state information about dead hosts or transports.
38 /* This request takes effect immediately.
39 /* .IP QMGR_FLUSH_DFXP
40 /* Override the defer_transports setting. This takes effect
41 /* immediately when a queue scan is in progress, and affects
42 /* the next queue scan.
43 /* .IP QMGR_SCAN_ALL
44 /* Ignore queue file time stamps. This takes effect immediately
45 /* when a queue scan is in progress, and affects the next queue
46 /* scan.
47 /* .IP QMGR_SCAN_START
48 /* Start a queue scan when none is in progress, or restart the
49 /* current scan upon completion.
50 /* DIAGNOSTICS
51 /* Fatal: out of memory.
52 /* Panic: interface violations, internal consistency errors.
53 /* LICENSE
54 /* .ad
55 /* .fi
56 /* The Secure Mailer license must be distributed with this software.
57 /* AUTHOR(S)
58 /* Wietse Venema
59 /* IBM T.J. Watson Research
60 /* P.O. Box 704
61 /* Yorktown Heights, NY 10598, USA
62 /*--*/
64 /* System library. */
66 #include <sys_defs.h>
68 /* Utility library. */
70 #include <msg.h>
71 #include <mymalloc.h>
72 #include <scan_dir.h>
74 /* Global library. */
76 #include <mail_scan_dir.h>
78 /* Application-specific. */
80 #include "qmgr.h"
82 /* qmgr_scan_start - start queue scan */
84 static void qmgr_scan_start(QMGR_SCAN *scan_info)
86 const char *myname = "qmgr_scan_start";
89 * Sanity check.
91 if (scan_info->handle)
92 msg_panic("%s: %s queue scan in progress",
93 myname, scan_info->queue);
96 * Give the poor tester a clue.
98 if (msg_verbose)
99 msg_info("%s: %sstart %s queue scan",
100 myname,
101 scan_info->nflags & QMGR_SCAN_START ? "re" : "",
102 scan_info->queue);
105 * Start or restart the scan.
107 scan_info->flags = scan_info->nflags;
108 scan_info->nflags = 0;
109 scan_info->handle = scan_dir_open(scan_info->queue);
112 /* qmgr_scan_request - request for future scan */
114 void qmgr_scan_request(QMGR_SCAN *scan_info, int flags)
118 * Apply "forget all dead destinations" requests immediately. Throttle
119 * dead transports and queues at the earliest opportunity: preferably
120 * during an already ongoing queue scan, otherwise the throttling will
121 * have to wait until a "start scan" trigger arrives.
123 * The QMGR_FLUSH_ONCE request always comes with QMGR_FLUSH_DFXP, and
124 * sometimes it also comes with QMGR_SCAN_ALL. It becomes a completely
125 * different story when a flush request is encoded in file permissions.
127 if (flags & QMGR_FLUSH_ONCE)
128 qmgr_enable_all();
131 * Apply "ignore time stamp" requests also towards the scan that is
132 * already in progress.
134 if (scan_info->handle != 0 && (flags & QMGR_SCAN_ALL))
135 scan_info->flags |= QMGR_SCAN_ALL;
138 * Apply "override defer_transports" requests also towards the scan that
139 * is already in progress.
141 if (scan_info->handle != 0 && (flags & QMGR_FLUSH_DFXP))
142 scan_info->flags |= QMGR_FLUSH_DFXP;
145 * If a scan is in progress, just record the request.
147 scan_info->nflags |= flags;
148 if (scan_info->handle == 0 && (flags & QMGR_SCAN_START) != 0) {
149 scan_info->nflags &= ~QMGR_SCAN_START;
150 qmgr_scan_start(scan_info);
154 /* qmgr_scan_next - look for next queue file */
156 char *qmgr_scan_next(QMGR_SCAN *scan_info)
158 char *path = 0;
161 * Restart the scan if we reach the end and a queue scan request has
162 * arrived in the mean time.
164 if (scan_info->handle && (path = mail_scan_dir_next(scan_info->handle)) == 0) {
165 scan_info->handle = scan_dir_close(scan_info->handle);
166 if (msg_verbose && (scan_info->nflags & QMGR_SCAN_START) == 0)
167 msg_info("done %s queue scan", scan_info->queue);
169 if (!scan_info->handle && (scan_info->nflags & QMGR_SCAN_START)) {
170 qmgr_scan_start(scan_info);
171 path = mail_scan_dir_next(scan_info->handle);
173 return (path);
176 /* qmgr_scan_create - create queue scan context */
178 QMGR_SCAN *qmgr_scan_create(const char *queue)
180 QMGR_SCAN *scan_info;
182 scan_info = (QMGR_SCAN *) mymalloc(sizeof(*scan_info));
183 scan_info->queue = mystrdup(queue);
184 scan_info->flags = scan_info->nflags = 0;
185 scan_info->handle = 0;
186 return (scan_info);