xref: /netbsd-src/external/ibm-public/postfix/dist/proto/POSTSCREEN_README.html (revision 059c16a85b0b39d60ad6d18f53c09510815afa2b)
1<!doctype html public "-//W3C//DTD HTML 4.01 Transitional//EN"
2        "http://www.w3.org/TR/html4/loose.dtd">
3
4<head>
5
6<title>Postfix Postscreen Howto</title>
7
8<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
9<link rel='stylesheet' type='text/css' href='postfix-doc.css'>
10
11</head>
12
13<body>
14
15<h1><img src="postfix-logo.jpg" width="203" height="98" ALT="">Postfix Postscreen Howto</h1>
16
17<hr>
18
19<h2> <a name="intro">Introduction</a> </h2>
20
21<p> This document describes features that are available in Postfix
223.6 and later. See <a href="POSTSCREEN_3_5_README.html">
23POSTSCREEN_3_5_README.html</a> for Postfix versions 2.8 - 3.5. </p>
24
25<p> The Postfix postscreen(8) daemon provides additional protection
26against mail server overload. One postscreen(8) process handles
27multiple inbound SMTP connections, and decides which clients may
28talk to a Postfix SMTP server process.  By keeping spambots away,
29postscreen(8) leaves more SMTP server processes available for
30legitimate clients, and delays the onset of <a
31href="STRESS_README.html">server overload</a> conditions. </p>
32
33<p> postscreen(8) should not be used on SMTP ports that receive
34mail from end-user clients (MUAs). In a typical deployment,
35postscreen(8) handles the MX service on TCP port 25, while MUA
36clients submit mail via the submission service on TCP port 587 which
37requires client authentication. Alternatively, a site could set up
38a dedicated, non-postscreen, "port 25" server that provides submission
39service and client authentication, but no MX service.  </p>
40
41<p> postscreen(8) maintains a temporary allowlist for clients that
42pass its tests; by allowing allowlisted clients to skip tests,
43postscreen(8) minimizes its impact on legitimate email traffic.
44</p>
45
46<p> postscreen(8) is part of a multi-layer defense. <p>
47
48<ul>
49
50<li> <p> As the first layer, postscreen(8) blocks connections from
51zombies and other spambots that are responsible for about 90% of
52all spam.  It is implemented as a single process to make this defense
53as inexpensive as possible. </p>
54
55<li> <p> The second layer implements more complex SMTP-level access
56checks with <a href="SMTPD_ACCESS_README.html">Postfix SMTP servers</a>,
57<a href="SMTPD_POLICY_README.html">policy daemons</a>, and
58<a href="MILTER_README.html">Milter applications</a>. </p>
59
60<li> <p> The third layer performs light-weight content inspection
61with the Postfix built-in header_checks and body_checks. This can
62block unacceptable attachments such as executable programs, and
63worms or viruses with easy-to-recognize signatures. </p>
64
65<li> <p> The fourth layer provides heavy-weight content inspection
66with external content filters. Typical examples are <a
67href="http://www.ijs.si/software/amavisd/">Amavisd-new</a>, <a
68href="http://spamassassin.apache.org/">SpamAssassin</a>, and <a
69href="MILTER_README.html">Milter applications</a>. </p>
70
71</ul>
72
73<p> Each layer reduces the spam volume. The general strategy is to
74use the less expensive defenses first, and to use the more expensive
75defenses only for the spam that remains. </p>
76
77<p> Topics in this document: </p>
78
79<ul>
80
81<li> <a href="#intro">Introduction</a>
82
83<li> <a href="#basic">The basic idea behind postscreen(8)</a>
84
85<li> <a href="#general"> General operation </a>
86
87<li> <a href="#quick">Quick tests before everything else</a>
88
89<li> <a href="#before_220"> Tests before the 220 SMTP server greeting </a>
90
91<li> <a href="#after_220">Tests after the 220 SMTP server greeting</a>
92
93<li> <a href="#other_error">Other errors</a>
94
95<li> <a href="#victory">When all tests succeed</a>
96
97<li> <a href="#config"> Configuring the postscreen(8) service</a>
98
99<li> <a href="#historical"> Historical notes and credits </a>
100
101</ul>
102
103<h2> <a name="basic">The basic idea behind postscreen(8)</a> </h2>
104
105<p> Most email is spam, and most spam is sent out by zombies (malware
106on compromised end-user computers).  Wietse expects that the zombie
107problem will get worse before things improve, if ever. Without a
108tool like postscreen(8) that keeps the zombies away, Postfix would be
109spending most of its resources not receiving email. </p>
110
111<p> The main challenge for postscreen(8) is to make an is-a-zombie
112decision based on a single measurement. This is necessary because
113many zombies try to fly under the radar and avoid spamming the same
114site repeatedly.  Once postscreen(8) decides that a client is
115not-a-zombie, it allowlists the client temporarily to avoid further
116delays for legitimate mail. </p>
117
118<p> Zombies have challenges too: they have only a limited amount
119of time to deliver spam before their IP address becomes denylisted.
120To speed up spam deliveries, zombies make compromises in their SMTP
121protocol implementation.  For example, they speak before their turn,
122or they ignore responses from SMTP servers and continue sending
123mail even when the server tells them to go away. </p>
124
125<p> postscreen(8) uses a variety of measurements to recognize
126zombies.  First, postscreen(8) determines if the remote SMTP client
127IP address is denylisted.  Second, postscreen(8) looks for protocol
128compromises that are made to speed up delivery.  These are good
129indicators for making is-a-zombie decisions based on single
130measurements.  </p>
131
132<p> postscreen(8) does not inspect message content. Message content
133can vary from one delivery to the next, especially with clients
134that (also) send legitimate email.  Content is not a good indicator
135for making is-a-zombie decisions based on single measurements,
136and that is the problem that postscreen(8) is focused on.  </p>
137
138<h2> <a name="general"> General operation </a> </h2>
139
140<p> For each connection from an SMTP client, postscreen(8) performs
141a number of tests
142in the order as described below.  Some tests introduce a delay of
143a few seconds.  postscreen(8) maintains a temporary allowlist for
144clients that pass its tests; by allowing allowlisted clients to
145skip tests, postscreen(8) minimizes its impact on legitimate email
146traffic.  </p>
147
148<p> By default, postscreen(8) hands off all connections to a Postfix
149SMTP server process after logging its findings. This mode is useful
150for non-destructive testing. </p>
151
152<p> In a typical production setting, postscreen(8) is configured
153to reject mail from clients that fail one or more tests, after
154logging the helo, sender and recipient information. </p>
155
156<p> Note: postscreen(8) is not an SMTP proxy; this is intentional.
157The purpose is to keep zombies away from Postfix, with minimal
158overhead for legitimate clients. </p>
159
160<h2> <a name="quick">Quick tests before everything else</a> </h2>
161
162<p> Before engaging in SMTP-level tests. postscreen(8) queries a
163number of local deny and allowlists. These tests speed up the
164handling of known clients. </p>
165
166<ul>
167
168<li> <a href="#perm_allow_deny"> Permanent allow/denylist test </a>
169
170<li> <a href="#temp_allow"> Temporary allowlist test </a>
171
172<li> <a href="#allow_veto"> MX Policy test </a>
173
174</ul>
175
176<h3> <a name="perm_allow_deny"> Permanent allow/denylist test </a> </h3>
177
178<p> The postscreen_access_list parameter (default: permit_mynetworks)
179specifies a permanent access list for SMTP client IP addresses. Typically
180one would specify something that allowlists local networks, followed
181by a CIDR table for selective allow- and denylisting. </p>
182
183<p> Example: </p>
184
185<pre>
186/etc/postfix/main.cf:
187    postscreen_access_list = permit_mynetworks,
188        cidr:/etc/postfix/postscreen_access.cidr
189
190/etc/postfix/postscreen_access.cidr:
191   # Rules are evaluated in the order as specified.
192   # Denylist 192.168.* except 192.168.0.1.
193   192.168.0.1          permit
194   192.168.0.0/16       reject
195</pre>
196
197<p> See the postscreen_access_list manpage documentation for more
198details.  </p>
199
200<p> When the SMTP client address matches a "permit" action,
201postscreen(8) logs this with the client address and port number as:
202</p>
203
204<blockquote>
205<pre>
206<b>ALLOWLISTED</b> <i>[address]:port</i>
207</pre>
208</blockquote>
209
210<blockquote> <p> Use the respectful_logging configuration parameter to
211select a deprecated form of this logging. </p> </blockquote>
212
213<p> The allowlist action is not configurable: immediately hand off the
214connection to a Postfix SMTP server process. </p>
215
216<p> When the SMTP client address matches a "reject" action,
217postscreen(8) logs this with the client address and port number as:
218</p>
219
220<blockquote>
221<pre>
222<b>DENYLISTED</b> <i>[address]:port</i>
223</pre>
224</blockquote>
225
226<blockquote> <p> Use the respectful_logging configuration parameter to
227select a deprecated form of this logging. </p> </blockquote>
228
229<p> The postscreen_denylist_action parameter specifies the action
230that is taken next.  See "<a href="#fail_before_220">When tests
231fail before the 220 SMTP server greeting</a>" below. </p>
232
233<h3> <a name="temp_allow"> Temporary allowlist test </a> </h3>
234
235<p> The postscreen(8) daemon maintains a <i>temporary</i>
236allowlist for SMTP client IP addresses that have passed all
237the tests described below. The postscreen_cache_map parameter
238specifies the location of the temporary allowlist.  The
239temporary allowlist is not used for SMTP client addresses
240that appear on the <i>permanent</i> access list. </p>
241
242<p> By default the temporary allowlist is not shared with other
243postscreen(8) daemons. See
244<a href="#temp_allow_sharing"> Sharing
245the temporary allowlist </a> below for alternatives. </p>
246
247<p> When the SMTP client address appears on the temporary
248allowlist, postscreen(8) logs this with the client address and port
249number as: </p>
250
251<pre>
252    <b>PASS OLD</b> <i>[address]:port</i>
253</pre>
254
255<p> The action is not configurable: immediately hand off the
256connection to a Postfix SMTP server process.  The client is
257excluded from further tests until its temporary allowlist
258entry expires, as controlled with the postscreen_*_ttl
259parameters.  Expired entries are silently renewed if possible. </p>
260
261<h3> <a name="allow_veto"> MX Policy test </a> </h3>
262
263<p> When the remote SMTP client is not on the static access list
264or temporary allowlist, postscreen(8) can implement a number of
265allowlist tests, before it grants the client a temporary allowlist
266status that allows it to talk to a Postfix SMTP server process. </p>
267
268<p> When postscreen(8) is configured to monitor all primary and
269backup MX addresses, it can refuse to allowlist clients that connect
270to a backup MX address only (an old spammer trick to take advantage
271of backup MX hosts with weaker anti-spam policies than primary MX
272hosts). </p>
273
274<blockquote> <p> NOTE: The following solution is for small sites.
275Larger sites would have to share the postscreen(8) cache between
276primary and backup MTAs, which would introduce a common point of
277failure.  </p> </blockquote>
278
279<ul>
280
281<li> <p> First, configure the host to listen on both primary and
282backup MX addresses. Use the appropriate <tt>ifconfig</tt> or <tt>ip</tt>
283command for the local operating system, or update the appropriate
284configuration files and "refresh" the network protocol stack. </p>
285
286<p> <p> Second, configure Postfix to listen on the new IP address
287(this step is needed when you have specified inet_interfaces in
288main.cf). </p>
289
290<li> <p> Then, configure postscreen(8) to deny the temporary allowlist
291status on the backup MX address(es).  An example for Wietse's
292server is: </p>
293
294<pre>
295/etc/postfix/main.cf:
296    postscreen_allowlist_interfaces = !168.100.189.8 static:all
297</pre>
298
299<p> Translation: allow clients to obtain the temporary allowlist
300status on all server IP addresses except 168.100.189.8, which is a
301backup MX address.  </p>
302
303</ul>
304
305<p> When a non-allowlisted client connects the backup MX address,
306postscreen(8) logs this with the client address and port number as:
307</p>
308
309<blockquote> <pre>
310<b>CONNECT from</b> <i>[address]:port</i> <b>to [168.100.189.8]:25</b>
311<b>ALLOWLIST VETO</b> <i>[address]:port</i>
312</pre> </blockquote>
313
314<blockquote> <p> Use the respectful_logging configuration parameter to
315select a deprecated form of this logging. </p> </blockquote>
316
317<p> Translation: the client at <i>[address]:port</i> connected to
318the backup MX address 168.100.189.8 while it was not allowlisted.
319The client will not be granted the temporary allowlist status, even
320if passes all the allowlist tests described below. </p>
321
322<h2> <a name="before_220"> Tests before the 220 SMTP server greeting </a> </h2>
323
324<p> The postscreen_greet_wait parameter specifies a short time
325interval before the "220 <i>text</i>..." server greeting, where
326postscreen(8) can run a number of tests in parallel. </p>
327
328<p> When a good client passes these tests, and no "<a
329href="#after_220">deep protocol tests</a>"
330are configured, postscreen(8)
331adds the client to the temporary allowlist and hands off the "live"
332connection to a Postfix SMTP server process.  The client can then
333continue as if postscreen(8) never even existed (except of course
334for the short postscreen_greet_wait delay).  </p>
335
336<ul>
337
338<li> <a href="#pregreet"> Pregreet test </a>
339
340<li> <a href="#dnsbl"> DNS Allow/denylist test </a>
341
342<li> <a href="#fail_before_220">When tests fail before the 220 SMTP server greeting</a>
343
344</ul>
345
346<h3> <a name="pregreet"> Pregreet test </a> </h3>
347
348<p> The SMTP protocol is a classic example of a protocol where the
349server speaks before the client. postscreen(8) detects zombies
350that are in a hurry and that speak before their turn. This test is
351enabled by default. </p>
352
353<p> The postscreen_greet_banner parameter specifies the <i>text</i>
354portion of a "220-<i>text</i>..." teaser banner (default: $smtpd_banner).
355Note that this becomes the first part of a multi-line server greeting.
356The postscreen(8) daemon sends this before the postscreen_greet_wait
357timer is started.  The purpose of the teaser banner is to confuse
358zombies so that they speak before their turn. It has no effect on
359SMTP clients that correctly implement the protocol.  </p>
360
361<p> To avoid problems with poorly-implemented SMTP engines in network
362appliances or network testing tools, either exclude them from all
363tests with the postscreen_access_list feature or else specify
364an empty teaser banner: </p>
365
366<pre>
367/etc/postfix/main.cf:
368    # Exclude broken clients by allowlisting. Clients in mynetworks
369    # should always be allowlisted.
370    postscreen_access_list = permit_mynetworks,
371        cidr:/etc/postfix/postscreen_access.cidr
372
373/etc/postfix/postscreen_access.cidr:
374    192.168.254.0/24 permit
375</pre>
376
377<pre>
378/etc/postfix/main.cf:
379    # Disable the teaser banner (try allowlisting first if you can).
380    postscreen_greet_banner =
381</pre>
382
383<p> When an SMTP client sends a command before the
384postscreen_greet_wait time has elapsed, postscreen(8) logs this as:
385</p>
386
387<pre>
388    <b>PREGREET</b> <i>count</i> <b>after</b> <i>time</i> <b>from</b> <i>[address]:port text...</i>
389</pre>
390
391<p> Translation: the client at <i>[address]:port</i> sent <i>count</i>
392bytes before its turn to speak. This happened <i>time</i> seconds
393after the postscreen_greet_wait timer was started.  The <i>text</i>
394is what the client sent (truncated to 100 bytes, and with non-printable
395characters replaced with C-style escapes such as \r for carriage-return
396and \n for newline). </p>
397
398<p> The postscreen_greet_action parameter specifies the action that
399is taken next.  See "<a href="#fail_before_220">When tests fail
400before the 220 SMTP server greeting</a>" below. </p>
401
402<h3> <a name="dnsbl"> DNS Allow/denylist test </a> </h3>
403
404<p> The postscreen_dnsbl_sites parameter (default: empty) specifies
405a list of DNS blocklist servers with optional filters and weight
406factors (positive weights for denylisting, negative for allowlisting).
407These servers will be queried in parallel with the reverse client
408IP address.  This test is disabled by default. </p>
409
410<blockquote>
411<p>
412CAUTION: when postscreen rejects mail, its SMTP reply contains the
413DNSBL domain name. Use the postscreen_dnsbl_reply_map feature to
414hide "password" information in DNSBL domain names.
415</p>
416</blockquote>
417
418<p> When the postscreen_greet_wait time has elapsed, and the combined
419DNSBL score is equal to or greater than the postscreen_dnsbl_threshold
420parameter value, postscreen(8) logs this as: </p>
421
422<pre>
423    <b>DNSBL rank</b> <i>count</i> <b>for</b> <i>[address]:port</i>
424</pre>
425
426<p> Translation: the SMTP client at <i>[address]:port</i> has a combined
427DNSBL score of <i>count</i>. </p>
428
429<p> The postscreen_dnsbl_action parameter specifies the action that
430is taken when the combined DNSBL score is equal to or greater than
431the threshold.  See "<a href="#fail_before_220">When tests fail
432before the 220 SMTP server greeting</a>" below. </p>
433
434<h3> <a name="fail_before_220">When tests fail before the 220 SMTP server greeting</a> </h3>
435
436<p> When the client address matches the permanent denylist, or
437when the client fails the pregreet or DNSBL tests, the action is
438specified with postscreen_denylist_action, postscreen_greet_action,
439or postscreen_dnsbl_action, respectively. </p>
440
441<dl>
442
443<dt> <b>ignore</b> (default) </dt>
444
445<dd> Ignore the failure of this test. Allow other tests to complete.
446Repeat this test the next time the client connects.  This option
447is useful for testing and collecting statistics without blocking
448mail. </dd>
449
450<dt> <b>enforce</b> </dt>
451
452<dd> Allow other tests to complete.  Reject attempts to deliver mail
453with a 550 SMTP reply, and log the helo/sender/recipient information.
454Repeat this test the next time the client connects. </dd>
455
456<dt> <b>drop</b> </dt>
457
458<dd> Drop the connection immediately with a 521 SMTP reply.  Repeat
459this test the next time the client connects. </dd>
460
461</dl>
462
463<h2> <a name="after_220">Tests after the 220 SMTP server greeting</a> </h2>
464
465<p> In this phase of the protocol, postscreen(8) implements a
466number of "deep protocol" tests. These tests use an SMTP protocol
467engine that is built into the postscreen(8) server. </p>
468
469<p> Important note: these protocol tests are disabled by default.
470They are more intrusive than the pregreet and DNSBL tests, and they
471have limitations as discussed next. </p>
472
473<ul>
474
475<li> <p> The main limitation of "after 220 greeting" tests is that
476a new client must disconnect after passing these tests (reason:
477postscreen is not a proxy).  Then the client must reconnect from
478the same IP address before it can deliver mail.  The following
479measures may help to avoid email delays: </p>
480
481<ul>
482
483<li> <p> Allow "good" clients to skip tests with the
484postscreen_dnsbl_allowlist_threshold feature. This is especially effective
485for large providers that usually don't retry from the same IP
486address. </p>
487
488<li> <p> Small sites: Configure postscreen(8) to listen on multiple
489IP addresses, published in DNS as different IP addresses for the
490same MX hostname or for different MX hostnames. This avoids mail
491delivery delays with clients that reconnect immediately from the
492same IP address.  </p>
493
494<li> <p> Large sites: Share the postscreen(8) cache between different
495Postfix MTAs with a large-enough memcache_table(5). Again, this
496avoids mail delivery delays with clients that reconnect immediately
497from the same IP address. </p>
498
499</ul>
500
501<li> <p> postscreen(8)'s built-in SMTP engine does not implement the
502AUTH, XCLIENT, and XFORWARD features. If you need to make these
503services available on port 25, then do not enable the tests after
504the 220 server greeting. </p>
505
506<li> <p> End-user clients should connect directly to the submission
507service, so that they never have to deal with postscreen(8)'s tests.
508</p>
509
510</ul>
511
512<p> The following "after 220 greeting" tests are available: </p>
513
514<ul>
515
516<li> <a href="#pipelining">Command pipelining test</a>
517
518<li> <a href="#non_smtp">Non-SMTP command test</a>
519
520<li> <a href="#barelf">Bare newline test</a>
521
522<li> <a href="#fail_after_220">When tests fail after the 220 SMTP server greeting</a>
523
524</ul>
525
526<h3> <a name="pipelining">Command pipelining test</a> </h3>
527
528<p> By default, SMTP is a half-duplex protocol: the sender and
529receiver send one command and one response at a time.  Unlike the
530Postfix SMTP server, postscreen(8) does not announce support
531for ESMTP command pipelining.  Therefore, clients are not allowed
532to send multiple commands. postscreen(8)'s
533<a href="#after_220">deep
534protocol test</a> for this is disabled by default. </p>
535
536<p> With "postscreen_pipelining_enable = yes", postscreen(8) detects
537zombies that send multiple commands, instead of sending one command
538and waiting for the server to reply.  </p>
539
540<p> This test is opportunistically enabled when postscreen(8) has
541to use the built-in SMTP engine anyway. This is to make postscreen(8)
542logging more informative. </p>
543
544<p> When a client sends multiple commands, postscreen(8) logs this
545as: </p>
546
547<pre>
548    <b>COMMAND PIPELINING from</b> <i>[address]:port</i> <b>after</b> <i>command</i>: <i>text</i>
549</pre>
550
551<p> Translation: the SMTP client at <i>[address]:port</i> sent
552multiple SMTP commands, instead of sending one command and then
553waiting for the server to reply. This happened after the client
554sent <i>command</i>. The <i>text</i> shows part of the input that
555was sent too early; it is not logged with Postfix 2.8. </p>
556
557<p> The postscreen_pipelining_action parameter specifies the action
558that is taken next.  See "<a href="#fail_after_220">When tests fail
559after the 220 SMTP server greeting</a>" below. </p>
560
561<h3> <a name="non_smtp">Non-SMTP command test</a> </h3>
562
563<p> Some spambots send their mail through open proxies. A symptom
564of this is the usage of commands such as CONNECT and other non-SMTP
565commands. Just like the Postfix SMTP server's smtpd_forbidden_commands
566feature, postscreen(8) has an equivalent postscreen_forbidden_commands
567feature to block these clients. postscreen(8)'s
568<a href="#after_220">deep
569protocol test</a> for this is disabled by default.  </p>
570
571<p> With "postscreen_non_smtp_command_enable = yes", postscreen(8)
572detects zombies that send commands specified with the
573postscreen_forbidden_commands parameter. This also detects commands
574with the syntax of a message header label. The latter is a symptom
575that the client is sending message content after ignoring all the
576responses from postscreen(8) that reject mail. </p>
577
578<p> This test is opportunistically enabled when postscreen(8) has
579to use the built-in SMTP engine anyway. This is to make postscreen(8)
580logging more informative.  </p>
581
582<p> When a client sends non-SMTP commands, postscreen(8) logs this
583as: </p>
584
585<pre>
586    <b>NON-SMTP COMMAND from</b> <i>[address]:port</i> <b>after</b> <i>command: text</i>
587</pre>
588
589<p> Translation: the SMTP client at <i>[address]:port</i> sent a
590command that matches the postscreen_forbidden_commands
591parameter, or that has the syntax of a message header label (text
592followed by optional space and ":").
593The "<tt><b>after</b> <i>command</i></tt>" portion is logged with
594Postfix 2.10 and later. </p>
595
596<p> The postscreen_non_smtp_command_action parameter specifies
597the action that is taken next.  See "<a href="#fail_after_220">When
598tests fail after the 220 SMTP server greeting</a>" below. </p>
599
600<h3> <a name="barelf">Bare newline test</a> </h3>
601
602<p> SMTP is a line-oriented protocol: lines have a limited length,
603and are terminated with &lt;CR&gt;&lt;LF&gt;. Lines ending in a
604"bare" &lt;LF&gt;, that is newline not preceded by carriage return,
605are not allowed in SMTP.  postscreen(8)'s
606<a href="#after_220">deep
607protocol test</a> for this is disabled by default.  </p>
608
609<p> With "postscreen_bare_newline_enable = yes", postscreen(8)
610detects clients that send lines ending in bare newline characters.
611</p>
612
613<p> This test is opportunistically enabled when postscreen(8) has
614to use the built-in SMTP engine anyway. This is to make postscreen(8)
615logging more informative.  </p>
616
617<p> When a client sends bare newline characters, postscreen(8) logs
618this as:
619</p>
620
621<pre>
622    <b>BARE NEWLINE from</b> <i>[address]:port</i> <b>after</b> <i>command</i>
623</pre>
624
625<p> Translation: the SMTP client at <i>[address]:port</i> sent a bare
626newline character, that is newline not preceded by carriage
627return.
628The "<tt><b>after</b> <i>command</i></tt>" portion is logged with
629Postfix 2.10 and later. </p>
630
631<p> The postscreen_bare_newline_action parameter specifies the
632action that is taken next.  See "<a href="#fail_after_220">When
633tests fail after the 220 SMTP server greeting</a>" below. </p>
634
635<h3> <a name="fail_after_220">When tests fail after the 220 SMTP server greeting</a> </h3>
636
637<p> When the client fails the pipelining, non-SMTP command or bare
638newline tests, the action is specified with postscreen_pipelining_action,
639postscreen_non_smtp_command_action or postscreen_bare_newline_action,
640respectively. </p>
641
642<dl>
643
644<dt> <b>ignore</b> (default for bare newline) </dt>
645
646<dd> Ignore the failure of this test. Allow other tests to complete.
647Do NOT repeat this test before the result from some other test
648expires.
649
650This option is useful for testing and collecting statistics without
651blocking mail permanently. </dd>
652
653<dt> <b>enforce</b> (default for pipelining) </dt>
654
655<dd> Allow other tests to complete.  Reject attempts to deliver
656mail with a 550 SMTP reply, and log the helo/sender/recipient
657information.  Repeat this test the next time the client connects.
658</dd>
659
660<dt> <b>drop</b> (default for non-SMTP commands) </dt>
661
662<dd> Drop the connection immediately with a 521 SMTP reply.  Repeat
663this test the next time the client connects.  This action is
664compatible with the Postfix SMTP server's smtpd_forbidden_commands
665feature. </dd>
666
667</dl>
668
669<h2> <a name="other_error">Other errors</a> </h2>
670
671<p> When an SMTP client hangs up unexpectedly, postscreen(8) logs
672this as: </p>
673
674<pre>
675    <b>HANGUP after</b> <i>time</i> <b>from</b> <i>[address]:port</i> <b>in</b> <i>test name</i>
676</pre>
677
678<p> Translation: the SMTP client at <i>[address]:port</i> disconnected
679unexpectedly, <i>time</i> seconds after the start of the
680test named <i>test name</i>. </p>
681
682<p> There is no punishment for hanging up. A client that hangs up
683without sending the QUIT command can still pass all postscreen(8)
684tests. </p>
685
686<!--
687
688<p> While an unexpired penalty is in effect, an SMTP client is not
689allowed to pass any tests, and  postscreen(8) logs each connection
690with the remaining amount of penalty time as: </p>
691
692<pre>
693    <b>PENALTY</b> <i>time</i> <b>for</b> <i>[address]:port</i>
694</pre>
695
696<p> During this time, all attempts by the client to deliver mail
697will be deferred with a 450 SMTP status.  </p>
698
699-->
700
701<p> The following errors are reported by the built-in SMTP engine.
702This engine never accepts mail, therefore it has per-session limits
703on the number of commands and on the session length. </p>
704
705<pre>
706    <b>COMMAND TIME LIMIT</b> <b>from</b> <i>[address]:port</i> <b>after</b> <i>command</i>
707</pre>
708
709<p> Translation: the SMTP client at <i>[address]:port</i> reached the
710per-command time limit as specified with the postscreen_command_time_limit
711parameter.  The session is terminated immediately.
712The "<tt><b>after</b> <i>command</i></tt>" portion is logged with
713Postfix 2.10 and later. </p>
714
715<pre>
716    <b>COMMAND COUNT LIMIT from</b> <i>[address]:port</i> <b>after</b> <i>command</i>
717</pre>
718
719<p> Translation: the SMTP client at <i>[address]:port</i> reached the
720per-session command count limit as specified with the
721postscreen_command_count_limit parameter.  The session is terminated
722immediately.
723The "<tt><b>after</b> <i>command</i></tt>" portion is logged with
724Postfix 2.10 and later. </p>
725
726<pre>
727    <b>COMMAND LENGTH LIMIT from</b> <i>[address]:port</i> <b>after</b> <i>command</i>
728</pre>
729
730<p> Translation: the SMTP client at <i>[address]:port</i> reached the
731per-command length limit, as specified with the line_length_limit
732parameter.  The session is terminated immediately.
733The "<tt><b>after</b> <i>command</i></tt>" portion is logged with
734Postfix 2.10 and later. </p>
735
736<p> When an SMTP client makes too many connections at the same time,
737postscreen(8) rejects the connection with a 421 status code and logs: </p>
738
739<pre>
740    <b>NOQUEUE: reject: CONNECT from</b> <i>[address]:port</i><b>: too many connections</b>
741</pre>
742
743<p> The postscreen_client_connection_count_limit parameter controls this limit. </p>
744
745<p> When an SMTP client connects after postscreen(8) has reached a
746connection count limit, postscreen(8) rejects the connection with
747a 421 status code and logs: </p>
748
749<pre>
750    <b>NOQUEUE: reject: CONNECT from</b> <i>[address]:port</i><b>: all screening ports busy</b>
751    <b>NOQUEUE: reject: CONNECT from</b> <i>[address]:port</i><b>: all server ports busy</b>
752</pre>
753
754<p> The postscreen_pre_queue_limit and postscreen_post_queue_limit
755parameters control these limits.  </p>
756
757<h2> <a name="victory">When all tests succeed</a> </h2>
758
759<p> When a new SMTP client passes all tests (i.e. it is not allowlisted
760via some mechanism), postscreen(8) logs this as: </p>
761
762<pre>
763    <b>PASS NEW</b> <i>[address]:port</i>
764</pre>
765
766<p> Where <i>[address]:port</i> are the client IP address and port.
767Then, postscreen(8)
768creates a temporary allowlist entry that excludes the client IP
769address from further tests until the temporary allowlist entry
770expires, as controlled with the postscreen_*_ttl parameters. </p>
771
772<p> When no "<a href="#after_220">deep protocol tests</a>" are
773configured, postscreen(8) hands off the "live" connection to a Postfix
774SMTP server process.  The client can then continue as if postscreen(8)
775never even existed (except for the short postscreen_greet_wait delay).
776</p>
777
778<p> When any "<a href="#after_220">deep protocol tests</a>" are
779configured, postscreen(8) cannot hand off the "live" connection to
780a Postfix SMTP server process in the middle of the session.  Instead,
781postscreen(8) defers mail delivery attempts with a 4XX status, logs
782the helo/sender/recipient information, and waits for the client to
783disconnect.  The next time the client connects it will be allowed
784to talk to a Postfix SMTP server process to deliver its mail.
785postscreen(8) mitigates the impact of this limitation by giving
786<a href="#after_220">deep protocol tests</a> a long expiration
787time. </p>
788
789<h2> <a name="config"> Configuring the postscreen(8) service</a>
790</h2>
791
792<p> postscreen(8) has been tested on FreeBSD [4-8], Linux 2.[4-6]
793and Solaris 9 systems. </p>
794
795<ul>
796
797<li> <a href="#enable"> Turning on postscreen(8) without blocking
798mail</a>
799
800<li> <a href="#starttls"> postscreen(8) TLS configuration </a>
801
802<li> <a href="#blocking"> Blocking mail with postscreen(8) </a>
803
804<li> <a href="#turnoff"> Turning off postscreen(8) </a>
805
806<li> <a href="#temp_allow_sharing"> Sharing the temporary allowlist
807</a>
808
809</ul>
810
811<h3> <a name="enable"> Turning on postscreen(8) without blocking mail</a> </h3>
812
813<p> To enable the postscreen(8) service and log client information
814without blocking mail: </p>
815
816<ol>
817
818<li> <p> Make sure that local clients and systems with non-standard
819SMTP implementations are excluded from any postscreen(8) tests. The
820default is to exclude all clients in mynetworks. To exclude additional
821clients, for example, third-party performance monitoring tools (these
822tend to have broken SMTP implementations): </p>
823
824<pre>
825/etc/postfix/main.cf:
826    # Exclude broken clients by allowlisting. Clients in mynetworks
827    # should always be allowlisted.
828    postscreen_access_list = permit_mynetworks,
829        cidr:/etc/postfix/postscreen_access.cidr
830
831/etc/postfix/postscreen_access.cidr:
832    192.168.254.0/24 permit
833</pre>
834
835<li> <p> Comment out the "<tt>smtp  inet ... smtpd</tt>" service
836in master.cf, including any "<tt>-o parameter=value</tt>" entries
837that follow.  </p>
838
839<pre>
840/etc/postfix/master.cf:
841    #smtp      inet  n       -       n       -       -       smtpd
842    #    -o parameter=value ...
843</pre>
844
845<li> <p> Uncomment the new "<tt>smtpd pass ... smtpd</tt>" service
846in master.cf, and duplicate any "<tt>-o parameter=value</tt>" entries
847from the smtpd service that was commented out in the previous step.
848</p>
849
850<pre>
851/etc/postfix/master.cf:
852    smtpd     pass  -       -       n       -       -       smtpd
853        -o parameter=value ...
854</pre>
855
856<li> <p> Uncomment the new "<tt>smtp inet ... postscreen</tt>"
857service in master.cf. </p>
858
859<pre>
860/etc/postfix/master.cf:
861    smtp      inet  n       -       n       -       1       postscreen
862</pre>
863
864<li> <p> Uncomment the new "<tt>tlsproxy unix ... tlsproxy</tt>"
865service in master.cf.  This service implements STARTTLS support for
866postscreen(8). </p>
867
868<pre>
869/etc/postfix/master.cf:
870    tlsproxy  unix  -       -       n       -       0       tlsproxy
871</pre>
872
873<li> <p> Uncomment the new "<tt>dnsblog  unix ... dnsblog</tt>"
874service in master.cf.  This service does DNSBL lookups for postscreen(8)
875and logs results. </p>
876
877<pre>
878/etc/postfix/master.cf:
879    dnsblog   unix  -       -       n       -       0       dnsblog
880</pre>
881
882<li> <p> To enable DNSBL lookups, list some DNS blocklist sites in
883main.cf, separated by whitespace. Different sites can have different
884weights. For example:
885
886<pre>
887/etc/postfix/main.cf:
888    postscreen_dnsbl_threshold = 2
889    postscreen_dnsbl_sites = zen.spamhaus.org*2
890        bl.spamcop.net*1 b.barracudacentral.org*1
891</pre>
892
893<p> Note: if your DNSBL queries have a "secret" in the domain name,
894you must censor this information from the postscreen(8) SMTP replies.
895For example: </p>
896
897<pre>
898/etc/postfix/main.cf:
899    postscreen_dnsbl_reply_map = texthash:/etc/postfix/dnsbl_reply
900</pre>
901
902<pre>
903/etc/postfix/dnsbl_reply:
904    # Secret DNSBL name           Name in postscreen(8) replies
905    secret.zen.dq.spamhaus.net    zen.spamhaus.org
906</pre>
907
908<p> The texthash: format is similar to hash: except that there is
909no need to run postmap(1) before the file can be used, and that it
910does not detect changes after the file is read. It is new with
911Postfix version 2.8. </p>
912
913<li> <p> Read the new configuration with "<tt>postfix reload</tt>".
914</p>
915
916</ol>
917
918<p> Notes: </p>
919
920<ul>
921
922<li> <p> Some postscreen(8) configuration parameters implement
923stress-dependent behavior. This is supported only when the default
924value is stress-dependent (that is, "postconf -d <i>parametername</i>"
925output shows
926"<i>parametername</i>&nbsp;=&nbsp;${stress?<i>something</i>}${stress:<i>something</i>}" or
927"<i>parametername</i>&nbsp;=&nbsp;${stress?{<i>something</i>}:{<i>something</i>}}").
928Other parameters always evaluate as if the stress value is the empty
929string. </p>
930
931<li> <p> See "<a href="#before_220">Tests before the 220 SMTP server
932greeting</a>" for details about the logging from these
933postscreen(8) tests. </p>
934
935<li> <p> If you run Postfix 2.6 or earlier you must stop and start
936the master daemon ("<tt>postfix stop; postfix start</tt>").  This
937is needed because the Postfix "pass" master service type did not
938work reliably on all systems. </p>
939
940</ul>
941
942<h3> <a name="starttls"> postscreen(8) TLS configuration </a> </h3>
943
944<p> postscreen(8) TLS support is available for remote SMTP clients
945that aren't allowlisted, including clients that need to renew their
946temporary allowlist status.  When a remote SMTP client requests TLS
947service, postscreen(8) invisibly hands off the connection to a
948tlsproxy(8) process. Then, tlsproxy(8) encrypts and decrypts the
949traffic between postscreen(8) and the remote SMTP client. One
950tlsproxy(8) process can handle multiple SMTP sessions. The number
951of tlsproxy(8) processes slowly increases with server load, but it
952should always be much smaller than the number of postscreen(8) TLS
953sessions.  </p>
954
955<p> TLS support for postscreen(8) and tlsproxy(8) uses the same
956parameters as with smtpd(8). We recommend that you keep the relevant
957configuration parameters in main.cf.  If you must specify "-o
958smtpd_mumble=value" parameter overrides in master.cf for a
959postscreen-protected smtpd(8) service, then you should specify those
960same parameter overrides for the postscreen(8) and tlsproxy(8)
961services. </p>
962
963<h3> <a name="blocking"> Blocking mail with postscreen(8) </a> </h3>
964
965<p> For compatibility with smtpd(8), postscreen(8) implements the
966soft_bounce safety feature. This causes Postfix to reject mail with
967a "try again" reply code. </p>
968
969<ul>
970
971<li> <p> To turn this on for all of Postfix, specify "<tt>soft_bounce
972= yes</tt>" in main.cf. </p>
973
974<li> <p> To turn this on for postscreen(8) only, append "<tt>-o
975soft_bounce=yes</tt>" (note: NO SPACES around '=') to the postscreen
976entry in master.cf. <p>
977
978</ul>
979
980<p> Execute "<tt>postfix reload</tt>" to make the change effective. </p>
981
982<p> After testing, do not forget to remove the soft_bounce feature,
983otherwise senders won't receive their non-delivery notification
984until many days later.  </p>
985
986<p> To use the postscreen(8) service to block mail, edit main.cf and
987specify one or more of: </p>
988
989<ul>
990
991<li> <p> "<tt>postscreen_dnsbl_action = enforce</tt>", to reject
992clients that are on DNS blocklists, and to log the helo/sender/recipient
993information. With good DNSBLs this reduces the amount of load on
994Postfix SMTP servers dramatically.  </p>
995
996<li> <p> "<tt>postscreen_greet_action = enforce</tt>", to reject
997clients that talk before their turn, and to log the helo/sender/recipient
998information. This stops over half of all known-to-be illegitimate
999connections to Wietse's mail server. It is backup protection for
1000zombies that haven't yet been denylisted. </p>
1001
1002<li> <p> You can also enable "<a href="#after_220">deep protocol
1003tests</a>", but these are more intrusive than the pregreet or DNSBL
1004tests. </p>
1005
1006<p> When a good client passes the "<a href="#after_220">deep
1007protocol tests</a>",
1008postscreen(8) adds the client to the temporary
1009allowlist but it cannot hand off the "live" connection to a Postfix
1010SMTP server process in the middle of the session. Instead, postscreen(8)
1011defers mail delivery attempts with a 4XX status, logs the
1012helo/sender/recipient information, and waits for the client to
1013disconnect. </p>
1014
1015<p> When the good client comes back in a later session, it is allowed
1016to talk directly to a Postfix SMTP server.  See "<a href="#after_220">Tests
1017after the 220 SMTP server greeting</a>" above for limitations with
1018AUTH and other features that clients may need.  </p>
1019
1020<p> An unexpected benefit from "<a href="#after_220">deep protocol
1021tests</a>" is that some "good" clients don't return after the 4XX
1022reply; these clients were not so good after all. </p>
1023
1024<p> Unfortunately, some senders will retry requests from different
1025IP addresses, and may never get allowlisted.  For this reason,
1026Wietse stopped using "<a href="#after_220">deep protocol tests</a>"
1027on his own internet-facing mail server.  </p>
1028
1029<li> <p> There is also support for permanent denylisting and
1030allowlisting; see the description of the postscreen_access_list
1031parameter for details. </p>
1032
1033</ul>
1034
1035<h3> <a name="turnoff"> Turning off postscreen(8) </a> </h3>
1036
1037<p> To turn off postscreen(8) and handle mail directly with Postfix
1038SMTP server processes: </p>
1039
1040<ol>
1041
1042<li> <p> Comment out the "<tt>smtp inet ... postscreen</tt>" service
1043in master.cf, including any "<tt>-o parameter=value</tt>" entries
1044that follow. </p>
1045
1046<pre>
1047/etc/postfix/master.cf:
1048    #smtp      inet  n       -       n       -       1       postscreen
1049    #    -o parameter=value ...
1050</pre>
1051
1052<li> <p> Comment out the "<tt>dnsblog  unix ... dnsblog</tt>" service
1053in master.cf.  </p>
1054
1055<pre>
1056/etc/postfix/master.cf:
1057    #dnsblog   unix  -       -       n       -       0       dnsblog
1058</pre>
1059
1060<li> <p> Comment out the "<tt>smtpd pass ... smtpd</tt>" service
1061in master.cf, including any "<tt>-o parameter=value</tt>" entries
1062that follow. </p>
1063
1064<pre>
1065/etc/postfix/master.cf:
1066    #smtpd     pass  -       -       n       -       -       smtpd
1067    #    -o parameter=value ...
1068</pre>
1069
1070<li> <p> Comment out the "<tt>tlsproxy unix ... tlsproxy</tt>"
1071service in master.cf, including any "<tt>-o parameter=value</tt>"
1072entries that follow. </p>
1073
1074<pre>
1075/etc/postfix/master.cf:
1076    #tlsproxy  unix  -       -       n       -       0       tlsproxy
1077    #    -o parameter=value ...
1078</pre>
1079
1080<li> <p> Uncomment the "<tt>smtp  inet ... smtpd</tt>" service in
1081master.cf, including any "<tt>-o parameter=value</tt>" entries that
1082may follow.  </p>
1083
1084<pre>
1085/etc/postfix/master.cf:
1086    smtp       inet  n       -       n       -       -       smtpd
1087        -o parameter=value ...
1088</pre>
1089
1090<li> <p> Read the new configuration with "<tt>postfix reload</tt>".
1091</p>
1092
1093</ol>
1094
1095<h3> <a name="temp_allow_sharing"> Sharing the temporary allowlist </a> </h3>
1096
1097<p> By default, the temporary allowlist is not shared between
1098multiple postscreen(8) daemons.  To enable sharing, choose one
1099of the following options: </p>
1100
1101<ul>
1102
1103<li> <p> A non-persistent memcache: temporary allowlist can be shared
1104    between postscreen(8) daemons on the same host or different
1105    hosts.  Disable cache cleanup (postscreen_cache_cleanup_interval
1106    = 0) in all postscreen(8) daemons because memcache: has no
1107    first-next API (but see example 4 below for memcache: with
1108    persistent backup). This requires Postfix 2.9 or later. </p>
1109
1110    <pre>
1111    # Example 1: non-persistent memcache: allowlist.
1112    /etc/postfix/main.cf:
1113	postscreen_cache_map = memcache:/etc/postfix/postscreen_cache
1114	postscreen_cache_cleanup_interval = 0
1115
1116    /etc/postfix/postscreen_cache:
1117	memcache = inet:127.0.0.1:11211
1118	key_format = postscreen:%s
1119    </pre>
1120
1121<li> <p>
1122    A persistent lmdb: temporary allowlist can be shared between
1123    postscreen(8) daemons that run under the same master(8) daemon,
1124    or under different master(8) daemons on the same host.  Disable
1125    cache cleanup (postscreen_cache_cleanup_interval = 0) in all
1126    postscreen(8) daemons except one that is responsible for cache
1127    cleanup. This requires Postfix 2.11 or later. </p>
1128
1129    <pre>
1130    # Example 2: persistent lmdb: allowlist.
1131    /etc/postfix/main.cf:
1132	postscreen_cache_map = lmdb:$data_directory/postscreen_cache
1133	# See note 1 below.
1134	# postscreen_cache_cleanup_interval = 0
1135    </pre>
1136
1137<li> <p> Other kinds of persistent temporary allowlist can be shared
1138    only between postscreen(8) daemons that run under the same
1139    master(8) daemon. In this case, temporary allowlist access must
1140    be shared through the proxymap(8) daemon. This requires Postfix
1141    2.9 or later. </p>
1142
1143    <pre>
1144    # Example 3: proxied btree: allowlist.
1145    /etc/postfix/main.cf:
1146	postscreen_cache_map =
1147	    proxy:btree:/var/lib/postfix/postscreen_cache
1148	# See note 1 below.
1149	# postscreen_cache_cleanup_interval = 0
1150
1151    # Example 4: proxied btree: allowlist with memcache: accelerator.
1152    /etc/postfix/main.cf:
1153	postscreen_cache_map = memcache:/etc/postfix/postscreen_cache
1154	proxy_write_maps =
1155	    proxy:btree:/var/lib/postfix/postscreen_cache
1156	    ... other proxied tables ...
1157	# See note 1 below.
1158	# postscreen_cache_cleanup_interval = 0
1159
1160    /etc/postfix/postscreen_cache:
1161	# Note: the $data_directory macro is not defined in this context.
1162	memcache = inet:127.0.0.1:11211
1163	backup = proxy:btree:/var/lib/postfix/postscreen_cache
1164	key_format = postscreen:%s
1165    </pre>
1166
1167    <p> Note 1: disable cache cleanup (postscreen_cache_cleanup_interval
1168    = 0) in all postscreen(8) daemons except one that is responsible
1169    for cache cleanup. </p>
1170
1171    <p> Note 2: postscreen(8) cache sharing via proxymap(8) requires Postfix
1172    2.9 or later; earlier proxymap(8) implementations don't support
1173    cache cleanup.  </p>
1174
1175</ul>
1176
1177<h2> <a name="historical"> Historical notes and credits </a> </h2>
1178
1179<p> Many ideas in postscreen(8) were explored in earlier work by
1180Michael Tokarev, in OpenBSD spamd, and in MailChannels Traffic
1181Control. </p>
1182
1183<p> Wietse threw together a crude prototype with pregreet and dnsbl
1184support in June 2009, because he needed something new for a Mailserver
1185conference presentation in July. Ralf Hildebrandt ran this code on
1186several servers to collect real-world statistics. This version used
1187the dnsblog(8) ad-hoc DNS client program. </p>
1188
1189<p> Wietse needed new material for a LISA conference presentation
1190in November 2010, so he added support for DNSBL weights and filters
1191in August, followed by a major code rewrite, deep protocol tests,
1192helo/sender/recipient logging, and stress-adaptive behavior in
1193September. Ralf Hildebrandt ran this code on several servers to
1194collect real-world statistics. This version still used the embarrassing
1195dnsblog(8) ad-hoc DNS client program.  </p>
1196
1197<p> Wietse added STARTTLS support in December 2010. This makes
1198postscreen(8) usable for sites that require TLS support.  The
1199implementation introduces the tlsproxy(8) event-driven TLS proxy
1200that decrypts/encrypts the sessions for multiple SMTP clients. </p>
1201
1202<p> The tlsproxy(8) implementation led to the discovery of a "new"
1203class of vulnerability (<a
1204href="http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2011-0411"
1205>CVE-2011-0411</a>) that affected multiple implementations of SMTP,
1206POP, IMAP, NNTP, and FTP over TLS. </p>
1207
1208<p> postscreen(8) was officially released as part of the Postfix
12092.8 stable release in January 2011.</p>
1210
1211<p> Noel Jones helped with the Postfix 3.6 transition towards respectful
1212documentation. </p>
1213
1214</body>
1215</html>
1216