summaryrefslogtreecommitdiffstats
path: root/README_FILES/POSTSCREEN_README
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-10 19:59:03 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-10 19:59:03 +0000
commita848231ae0f346dc7cc000973fbeb65b0894ee92 (patch)
tree44b60b367c86723cc78383ef247885d72b388afe /README_FILES/POSTSCREEN_README
parentInitial commit. (diff)
downloadpostfix-a848231ae0f346dc7cc000973fbeb65b0894ee92.tar.xz
postfix-a848231ae0f346dc7cc000973fbeb65b0894ee92.zip
Adding upstream version 3.8.5.upstream/3.8.5
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'README_FILES/POSTSCREEN_README')
-rw-r--r--README_FILES/POSTSCREEN_README876
1 files changed, 876 insertions, 0 deletions
diff --git a/README_FILES/POSTSCREEN_README b/README_FILES/POSTSCREEN_README
new file mode 100644
index 0000000..9467e68
--- /dev/null
+++ b/README_FILES/POSTSCREEN_README
@@ -0,0 +1,876 @@
+PPoossttffiixx PPoossttssccrreeeenn HHoowwttoo
+
+-------------------------------------------------------------------------------
+
+IInnttrroodduuccttiioonn
+
+This document describes features that are available in Postfix 3.6 and later.
+See POSTSCREEN_3_5_README.html for Postfix versions 2.8 - 3.5.
+
+The Postfix postscreen(8) daemon provides additional protection against mail
+server overload. One postscreen(8) process handles multiple inbound SMTP
+connections, and decides which clients may talk to a Postfix SMTP server
+process. By keeping spambots away, postscreen(8) leaves more SMTP server
+processes available for legitimate clients, and delays the onset of server
+overload conditions.
+
+postscreen(8) should not be used on SMTP ports that receive mail from end-user
+clients (MUAs). In a typical deployment, postscreen(8) handles the MX service
+on TCP port 25, while MUA clients submit mail via the submission service on TCP
+port 587 which requires client authentication. Alternatively, a site could set
+up a dedicated, non-postscreen, "port 25" server that provides submission
+service and client authentication, but no MX service.
+
+postscreen(8) maintains a temporary allowlist for clients that pass its tests;
+by allowing allowlisted clients to skip tests, postscreen(8) minimizes its
+impact on legitimate email traffic.
+
+postscreen(8) is part of a multi-layer defense.
+
+ * As the first layer, postscreen(8) blocks connections from zombies and other
+ spambots that are responsible for about 90% of all spam. It is implemented
+ as a single process to make this defense as inexpensive as possible.
+
+ * The second layer implements more complex SMTP-level access checks with
+ Postfix SMTP servers, policy daemons, and Milter applications.
+
+ * The third layer performs light-weight content inspection with the Postfix
+ built-in header_checks and body_checks. This can block unacceptable
+ attachments such as executable programs, and worms or viruses with easy-to-
+ recognize signatures.
+
+ * The fourth layer provides heavy-weight content inspection with external
+ content filters. Typical examples are Amavisd-new, SpamAssassin, and Milter
+ applications.
+
+Each layer reduces the spam volume. The general strategy is to use the less
+expensive defenses first, and to use the more expensive defenses only for the
+spam that remains.
+
+Topics in this document:
+
+ * Introduction
+ * The basic idea behind postscreen(8)
+ * General operation
+ * Quick tests before everything else
+ * Tests before the 220 SMTP server greeting
+ * Tests after the 220 SMTP server greeting
+ * Other errors
+ * When all tests succeed
+ * Configuring the postscreen(8) service
+ * Historical notes and credits
+
+TThhee bbaassiicc iiddeeaa bbeehhiinndd ppoossttssccrreeeenn((88))
+
+Most email is spam, and most spam is sent out by zombies (malware on
+compromised end-user computers). Wietse expects that the zombie problem will
+get worse before things improve, if ever. Without a tool like postscreen(8)
+that keeps the zombies away, Postfix would be spending most of its resources
+not receiving email.
+
+The main challenge for postscreen(8) is to make an is-a-zombie decision based
+on a single measurement. This is necessary because many zombies try to fly
+under the radar and avoid spamming the same site repeatedly. Once postscreen(8)
+decides that a client is not-a-zombie, it allowlists the client temporarily to
+avoid further delays for legitimate mail.
+
+Zombies have challenges too: they have only a limited amount of time to deliver
+spam before their IP address becomes denylisted. To speed up spam deliveries,
+zombies make compromises in their SMTP protocol implementation. For example,
+they speak before their turn, or they ignore responses from SMTP servers and
+continue sending mail even when the server tells them to go away.
+
+postscreen(8) uses a variety of measurements to recognize zombies. First,
+postscreen(8) determines if the remote SMTP client IP address is denylisted.
+Second, postscreen(8) looks for protocol compromises that are made to speed up
+delivery. These are good indicators for making is-a-zombie decisions based on
+single measurements.
+
+postscreen(8) does not inspect message content. Message content can vary from
+one delivery to the next, especially with clients that (also) send legitimate
+email. Content is not a good indicator for making is-a-zombie decisions based
+on single measurements, and that is the problem that postscreen(8) is focused
+on.
+
+GGeenneerraall ooppeerraattiioonn
+
+For each connection from an SMTP client, postscreen(8) performs a number of
+tests in the order as described below. Some tests introduce a delay of a few
+seconds. postscreen(8) maintains a temporary allowlist for clients that pass
+its tests; by allowing allowlisted clients to skip tests, postscreen(8)
+minimizes its impact on legitimate email traffic.
+
+By default, postscreen(8) hands off all connections to a Postfix SMTP server
+process after logging its findings. This mode is useful for non-destructive
+testing.
+
+In a typical production setting, postscreen(8) is configured to reject mail
+from clients that fail one or more tests, after logging the helo, sender and
+recipient information.
+
+Note: postscreen(8) is not an SMTP proxy; this is intentional. The purpose is
+to keep zombies away from Postfix, with minimal overhead for legitimate
+clients.
+
+QQuuiicckk tteessttss bbeeffoorree eevveerryytthhiinngg eellssee
+
+Before engaging in SMTP-level tests. postscreen(8) queries a number of local
+deny and allowlists. These tests speed up the handling of known clients.
+
+ * Permanent allow/denylist test
+ * Temporary allowlist test
+ * MX Policy test
+
+PPeerrmmaanneenntt aallllooww//ddeennyylliisstt tteesstt
+
+The postscreen_access_list parameter (default: permit_mynetworks) specifies a
+permanent access list for SMTP client IP addresses. Typically one would specify
+something that allowlists local networks, followed by a CIDR table for
+selective allow- and denylisting.
+
+Example:
+
+/etc/postfix/main.cf:
+ postscreen_access_list = permit_mynetworks,
+ cidr:/etc/postfix/postscreen_access.cidr
+
+/etc/postfix/postscreen_access.cidr:
+ # Rules are evaluated in the order as specified.
+ # Denylist 192.168.* except 192.168.0.1.
+ 192.168.0.1 permit
+ 192.168.0.0/16 reject
+
+See the postscreen_access_list manpage documentation for more details.
+
+When the SMTP client address matches a "permit" action, postscreen(8) logs this
+with the client address and port number as:
+
+ AALLLLOOWWLLIISSTTEEDD [address]:port
+
+ Use the respectful_logging configuration parameter to select a deprecated
+ form of this logging.
+
+The allowlist action is not configurable: immediately hand off the connection
+to a Postfix SMTP server process.
+
+When the SMTP client address matches a "reject" action, postscreen(8) logs this
+with the client address and port number as:
+
+ DDEENNYYLLIISSTTEEDD [address]:port
+
+ Use the respectful_logging configuration parameter to select a deprecated
+ form of this logging.
+
+The postscreen_denylist_action parameter specifies the action that is taken
+next. See "When tests fail before the 220 SMTP server greeting" below.
+
+TTeemmppoorraarryy aalllloowwlliisstt tteesstt
+
+The postscreen(8) daemon maintains a temporary allowlist for SMTP client IP
+addresses that have passed all the tests described below. The
+postscreen_cache_map parameter specifies the location of the temporary
+allowlist. The temporary allowlist is not used for SMTP client addresses that
+appear on the permanent access list.
+
+By default the temporary allowlist is not shared with other postscreen(8)
+daemons. See Sharing the temporary allowlist below for alternatives.
+
+When the SMTP client address appears on the temporary allowlist, postscreen(8)
+logs this with the client address and port number as:
+
+ PPAASSSS OOLLDD [address]:port
+
+The action is not configurable: immediately hand off the connection to a
+Postfix SMTP server process. The client is excluded from further tests until
+its temporary allowlist entry expires, as controlled with the postscreen_*_ttl
+parameters. Expired entries are silently renewed if possible.
+
+MMXX PPoolliiccyy tteesstt
+
+When the remote SMTP client is not on the static access list or temporary
+allowlist, postscreen(8) can implement a number of allowlist tests, before it
+grants the client a temporary allowlist status that allows it to talk to a
+Postfix SMTP server process.
+
+When postscreen(8) is configured to monitor all primary and backup MX
+addresses, it can refuse to allowlist clients that connect to a backup MX
+address only (an old spammer trick to take advantage of backup MX hosts with
+weaker anti-spam policies than primary MX hosts).
+
+ NOTE: The following solution is for small sites. Larger sites would have to
+ share the postscreen(8) cache between primary and backup MTAs, which would
+ introduce a common point of failure.
+
+ * First, configure the host to listen on both primary and backup MX
+ addresses. Use the appropriate ifconfig or ip command for the local
+ operating system, or update the appropriate configuration files and
+ "refresh" the network protocol stack.
+
+ Second, configure Postfix to listen on the new IP address (this step is
+ needed when you have specified inet_interfaces in main.cf).
+
+ * Then, configure postscreen(8) to deny the temporary allowlist status on the
+ backup MX address(es). An example for Wietse's server is:
+
+ /etc/postfix/main.cf:
+ postscreen_allowlist_interfaces = !168.100.189.8 static:all
+
+ Translation: allow clients to obtain the temporary allowlist status on all
+ server IP addresses except 168.100.189.8, which is a backup MX address.
+
+When a non-allowlisted client connects the backup MX address, postscreen(8)
+logs this with the client address and port number as:
+
+ CCOONNNNEECCTT ffrroomm [address]:port ttoo [[116688..110000..118899..88]]::2255
+ AALLLLOOWWLLIISSTT VVEETTOO [address]:port
+
+ Use the respectful_logging configuration parameter to select a deprecated
+ form of this logging.
+
+Translation: the client at [address]:port connected to the backup MX address
+168.100.189.8 while it was not allowlisted. The client will not be granted the
+temporary allowlist status, even if passes all the allowlist tests described
+below.
+
+TTeessttss bbeeffoorree tthhee 222200 SSMMTTPP sseerrvveerr ggrreeeettiinngg
+
+The postscreen_greet_wait parameter specifies a short time interval before the
+"220 text..." server greeting, where postscreen(8) can run a number of tests in
+parallel.
+
+When a good client passes these tests, and no "deep protocol tests" are
+configured, postscreen(8) adds the client to the temporary allowlist and hands
+off the "live" connection to a Postfix SMTP server process. The client can then
+continue as if postscreen(8) never even existed (except of course for the short
+postscreen_greet_wait delay).
+
+ * Pregreet test
+ * DNS Allow/denylist test
+ * When tests fail before the 220 SMTP server greeting
+
+PPrreeggrreeeett tteesstt
+
+The SMTP protocol is a classic example of a protocol where the server speaks
+before the client. postscreen(8) detects zombies that are in a hurry and that
+speak before their turn. This test is enabled by default.
+
+The postscreen_greet_banner parameter specifies the text portion of a "220-
+text..." teaser banner (default: $smtpd_banner). Note that this becomes the
+first part of a multi-line server greeting. The postscreen(8) daemon sends this
+before the postscreen_greet_wait timer is started. The purpose of the teaser
+banner is to confuse zombies so that they speak before their turn. It has no
+effect on SMTP clients that correctly implement the protocol.
+
+To avoid problems with poorly-implemented SMTP engines in network appliances or
+network testing tools, either exclude them from all tests with the
+postscreen_access_list feature or else specify an empty teaser banner:
+
+/etc/postfix/main.cf:
+ # Exclude broken clients by allowlisting. Clients in mynetworks
+ # should always be allowlisted.
+ postscreen_access_list = permit_mynetworks,
+ cidr:/etc/postfix/postscreen_access.cidr
+
+/etc/postfix/postscreen_access.cidr:
+ 192.168.254.0/24 permit
+
+/etc/postfix/main.cf:
+ # Disable the teaser banner (try allowlisting first if you can).
+ postscreen_greet_banner =
+
+When an SMTP client sends a command before the postscreen_greet_wait time has
+elapsed, postscreen(8) logs this as:
+
+ PPRREEGGRREEEETT count aafftteerr time ffrroomm [address]:port text...
+
+Translation: the client at [address]:port sent count bytes before its turn to
+speak. This happened time seconds after the postscreen_greet_wait timer was
+started. The text is what the client sent (truncated to 100 bytes, and with
+non-printable characters replaced with C-style escapes such as \r for carriage-
+return and \n for newline).
+
+The postscreen_greet_action parameter specifies the action that is taken next.
+See "When tests fail before the 220 SMTP server greeting" below.
+
+DDNNSS AAllllooww//ddeennyylliisstt tteesstt
+
+The postscreen_dnsbl_sites parameter (default: empty) specifies a list of DNS
+blocklist servers with optional filters and weight factors (positive weights
+for denylisting, negative for allowlisting). These servers will be queried in
+parallel with the reverse client IP address. This test is disabled by default.
+
+ CAUTION: when postscreen rejects mail, its SMTP reply contains the DNSBL
+ domain name. Use the postscreen_dnsbl_reply_map feature to hide "password"
+ information in DNSBL domain names.
+
+When the postscreen_greet_wait time has elapsed, and the combined DNSBL score
+is equal to or greater than the postscreen_dnsbl_threshold parameter value,
+postscreen(8) logs this as:
+
+ DDNNSSBBLL rraannkk count ffoorr [address]:port
+
+Translation: the SMTP client at [address]:port has a combined DNSBL score of
+count.
+
+The postscreen_dnsbl_action parameter specifies the action that is taken when
+the combined DNSBL score is equal to or greater than the threshold. See "When
+tests fail before the 220 SMTP server greeting" below.
+
+WWhheenn tteessttss ffaaiill bbeeffoorree tthhee 222200 SSMMTTPP sseerrvveerr ggrreeeettiinngg
+
+When the client address matches the permanent denylist, or when the client
+fails the pregreet or DNSBL tests, the action is specified with
+postscreen_denylist_action, postscreen_greet_action, or
+postscreen_dnsbl_action, respectively.
+
+iiggnnoorree (default)
+ Ignore the failure of this test. Allow other tests to complete. Repeat this
+ test the next time the client connects. This option is useful for testing
+ and collecting statistics without blocking mail.
+eennffoorrccee
+ Allow other tests to complete. Reject attempts to deliver mail with a 550
+ SMTP reply, and log the helo/sender/recipient information. Repeat this test
+ the next time the client connects.
+ddrroopp
+ Drop the connection immediately with a 521 SMTP reply. Repeat this test the
+ next time the client connects.
+
+TTeessttss aafftteerr tthhee 222200 SSMMTTPP sseerrvveerr ggrreeeettiinngg
+
+In this phase of the protocol, postscreen(8) implements a number of "deep
+protocol" tests. These tests use an SMTP protocol engine that is built into the
+postscreen(8) server.
+
+Important note: these protocol tests are disabled by default. They are more
+intrusive than the pregreet and DNSBL tests, and they have limitations as
+discussed next.
+
+ * The main limitation of "after 220 greeting" tests is that a new client must
+ disconnect after passing these tests (reason: postscreen is not a proxy).
+ Then the client must reconnect from the same IP address before it can
+ deliver mail. The following measures may help to avoid email delays:
+
+ o Allow "good" clients to skip tests with the
+ postscreen_dnsbl_allowlist_threshold feature. This is especially
+ effective for large providers that usually don't retry from the same IP
+ address.
+
+ o Small sites: Configure postscreen(8) to listen on multiple IP
+ addresses, published in DNS as different IP addresses for the same MX
+ hostname or for different MX hostnames. This avoids mail delivery
+ delays with clients that reconnect immediately from the same IP
+ address.
+
+ o Large sites: Share the postscreen(8) cache between different Postfix
+ MTAs with a large-enough memcache_table(5). Again, this avoids mail
+ delivery delays with clients that reconnect immediately from the same
+ IP address.
+
+ * postscreen(8)'s built-in SMTP engine does not implement the AUTH, XCLIENT,
+ and XFORWARD features. If you need to make these services available on port
+ 25, then do not enable the tests after the 220 server greeting.
+
+ * End-user clients should connect directly to the submission service, so that
+ they never have to deal with postscreen(8)'s tests.
+
+The following "after 220 greeting" tests are available:
+
+ * Command pipelining test
+ * Non-SMTP command test
+ * Bare newline test
+ * When tests fail after the 220 SMTP server greeting
+
+CCoommmmaanndd ppiippeelliinniinngg tteesstt
+
+By default, SMTP is a half-duplex protocol: the sender and receiver send one
+command and one response at a time. Unlike the Postfix SMTP server, postscreen
+(8) does not announce support for ESMTP command pipelining. Therefore, clients
+are not allowed to send multiple commands. postscreen(8)'s deep protocol test
+for this is disabled by default.
+
+With "postscreen_pipelining_enable = yes", postscreen(8) detects zombies that
+send multiple commands, instead of sending one command and waiting for the
+server to reply.
+
+This test is opportunistically enabled when postscreen(8) has to use the built-
+in SMTP engine anyway. This is to make postscreen(8) logging more informative.
+
+When a client sends multiple commands, postscreen(8) logs this as:
+
+ CCOOMMMMAANNDD PPIIPPEELLIINNIINNGG ffrroomm [address]:port aafftteerr command: text
+
+Translation: the SMTP client at [address]:port sent multiple SMTP commands,
+instead of sending one command and then waiting for the server to reply. This
+happened after the client sent command. The text shows part of the input that
+was sent too early; it is not logged with Postfix 2.8.
+
+The postscreen_pipelining_action parameter specifies the action that is taken
+next. See "When tests fail after the 220 SMTP server greeting" below.
+
+NNoonn--SSMMTTPP ccoommmmaanndd tteesstt
+
+Some spambots send their mail through open proxies. A symptom of this is the
+usage of commands such as CONNECT and other non-SMTP commands. Just like the
+Postfix SMTP server's smtpd_forbidden_commands feature, postscreen(8) has an
+equivalent postscreen_forbidden_commands feature to block these clients.
+postscreen(8)'s deep protocol test for this is disabled by default.
+
+With "postscreen_non_smtp_command_enable = yes", postscreen(8) detects zombies
+that send commands specified with the postscreen_forbidden_commands parameter.
+This also detects commands with the syntax of a message header label. The
+latter is a symptom that the client is sending message content after ignoring
+all the responses from postscreen(8) that reject mail.
+
+This test is opportunistically enabled when postscreen(8) has to use the built-
+in SMTP engine anyway. This is to make postscreen(8) logging more informative.
+
+When a client sends non-SMTP commands, postscreen(8) logs this as:
+
+ NNOONN--SSMMTTPP CCOOMMMMAANNDD ffrroomm [address]:port aafftteerr command: text
+
+Translation: the SMTP client at [address]:port sent a command that matches the
+postscreen_forbidden_commands parameter, or that has the syntax of a message
+header label (text followed by optional space and ":"). The "aafftteerr command"
+portion is logged with Postfix 2.10 and later.
+
+The postscreen_non_smtp_command_action parameter specifies the action that is
+taken next. See "When tests fail after the 220 SMTP server greeting" below.
+
+BBaarree nneewwlliinnee tteesstt
+
+SMTP is a line-oriented protocol: lines have a limited length, and are
+terminated with <CR><LF>. Lines ending in a "bare" <LF>, that is newline not
+preceded by carriage return, are not allowed in SMTP. postscreen(8)'s deep
+protocol test for this is disabled by default.
+
+With "postscreen_bare_newline_enable = yes", postscreen(8) detects clients that
+send lines ending in bare newline characters.
+
+This test is opportunistically enabled when postscreen(8) has to use the built-
+in SMTP engine anyway. This is to make postscreen(8) logging more informative.
+
+When a client sends bare newline characters, postscreen(8) logs this as:
+
+ BBAARREE NNEEWWLLIINNEE ffrroomm [address]:port aafftteerr command
+
+Translation: the SMTP client at [address]:port sent a bare newline character,
+that is newline not preceded by carriage return. The "aafftteerr command" portion is
+logged with Postfix 2.10 and later.
+
+The postscreen_bare_newline_action parameter specifies the action that is taken
+next. See "When tests fail after the 220 SMTP server greeting" below.
+
+WWhheenn tteessttss ffaaiill aafftteerr tthhee 222200 SSMMTTPP sseerrvveerr ggrreeeettiinngg
+
+When the client fails the pipelining, non-SMTP command or bare newline tests,
+the action is specified with postscreen_pipelining_action,
+postscreen_non_smtp_command_action or postscreen_bare_newline_action,
+respectively.
+
+iiggnnoorree (default for bare newline)
+ Ignore the failure of this test. Allow other tests to complete. Do NOT
+ repeat this test before the result from some other test expires. This
+ option is useful for testing and collecting statistics without blocking
+ mail permanently.
+eennffoorrccee (default for pipelining)
+ Allow other tests to complete. Reject attempts to deliver mail with a 550
+ SMTP reply, and log the helo/sender/recipient information. Repeat this test
+ the next time the client connects.
+ddrroopp (default for non-SMTP commands)
+ Drop the connection immediately with a 521 SMTP reply. Repeat this test the
+ next time the client connects. This action is compatible with the Postfix
+ SMTP server's smtpd_forbidden_commands feature.
+
+OOtthheerr eerrrroorrss
+
+When an SMTP client hangs up unexpectedly, postscreen(8) logs this as:
+
+ HHAANNGGUUPP aafftteerr time ffrroomm [address]:port iinn test name
+
+Translation: the SMTP client at [address]:port disconnected unexpectedly, time
+seconds after the start of the test named test name.
+
+There is no punishment for hanging up. A client that hangs up without sending
+the QUIT command can still pass all postscreen(8) tests.
+
+The following errors are reported by the built-in SMTP engine. This engine
+never accepts mail, therefore it has per-session limits on the number of
+commands and on the session length.
+
+ CCOOMMMMAANNDD TTIIMMEE LLIIMMIITT ffrroomm [address]:port aafftteerr command
+
+Translation: the SMTP client at [address]:port reached the per-command time
+limit as specified with the postscreen_command_time_limit parameter. The
+session is terminated immediately. The "aafftteerr command" portion is logged with
+Postfix 2.10 and later.
+
+ CCOOMMMMAANNDD CCOOUUNNTT LLIIMMIITT ffrroomm [address]:port aafftteerr command
+
+Translation: the SMTP client at [address]:port reached the per-session command
+count limit as specified with the postscreen_command_count_limit parameter. The
+session is terminated immediately. The "aafftteerr command" portion is logged with
+Postfix 2.10 and later.
+
+ CCOOMMMMAANNDD LLEENNGGTTHH LLIIMMIITT ffrroomm [address]:port aafftteerr command
+
+Translation: the SMTP client at [address]:port reached the per-command length
+limit, as specified with the line_length_limit parameter. The session is
+terminated immediately. The "aafftteerr command" portion is logged with Postfix 2.10
+and later.
+
+When an SMTP client makes too many connections at the same time, postscreen(8)
+rejects the connection with a 421 status code and logs:
+
+ NNOOQQUUEEUUEE:: rreejjeecctt:: CCOONNNNEECCTT ffrroomm [address]:port:: ttoooo mmaannyy ccoonnnneeccttiioonnss
+
+The postscreen_client_connection_count_limit parameter controls this limit.
+
+When an SMTP client connects after postscreen(8) has reached a connection count
+limit, postscreen(8) rejects the connection with a 421 status code and logs:
+
+ NNOOQQUUEEUUEE:: rreejjeecctt:: CCOONNNNEECCTT ffrroomm [address]:port:: aallll ssccrreeeenniinngg ppoorrttss bbuussyy
+ NNOOQQUUEEUUEE:: rreejjeecctt:: CCOONNNNEECCTT ffrroomm [address]:port:: aallll sseerrvveerr ppoorrttss bbuussyy
+
+The postscreen_pre_queue_limit and postscreen_post_queue_limit parameters
+control these limits.
+
+WWhheenn aallll tteessttss ssuucccceeeedd
+
+When a new SMTP client passes all tests (i.e. it is not allowlisted via some
+mechanism), postscreen(8) logs this as:
+
+ PPAASSSS NNEEWW [address]:port
+
+Where [address]:port are the client IP address and port. Then, postscreen(8)
+creates a temporary allowlist entry that excludes the client IP address from
+further tests until the temporary allowlist entry expires, as controlled with
+the postscreen_*_ttl parameters.
+
+When no "deep protocol tests" are configured, postscreen(8) hands off the
+"live" connection to a Postfix SMTP server process. The client can then
+continue as if postscreen(8) never even existed (except for the short
+postscreen_greet_wait delay).
+
+When any "deep protocol tests" are configured, postscreen(8) cannot hand off
+the "live" connection to a Postfix SMTP server process in the middle of the
+session. Instead, postscreen(8) defers mail delivery attempts with a 4XX
+status, logs the helo/sender/recipient information, and waits for the client to
+disconnect. The next time the client connects it will be allowed to talk to a
+Postfix SMTP server process to deliver its mail. postscreen(8) mitigates the
+impact of this limitation by giving deep protocol tests a long expiration time.
+
+CCoonnffiigguurriinngg tthhee ppoossttssccrreeeenn((88)) sseerrvviiccee
+
+postscreen(8) has been tested on FreeBSD [4-8], Linux 2.[4-6] and Solaris 9
+systems.
+
+ * Turning on postscreen(8) without blocking mail
+ * postscreen(8) TLS configuration
+ * Blocking mail with postscreen(8)
+ * Turning off postscreen(8)
+ * Sharing the temporary allowlist
+
+TTuurrnniinngg oonn ppoossttssccrreeeenn((88)) wwiitthhoouutt bblloocckkiinngg mmaaiill
+
+To enable the postscreen(8) service and log client information without blocking
+mail:
+
+ 1. Make sure that local clients and systems with non-standard SMTP
+ implementations are excluded from any postscreen(8) tests. The default is
+ to exclude all clients in mynetworks. To exclude additional clients, for
+ example, third-party performance monitoring tools (these tend to have
+ broken SMTP implementations):
+
+ /etc/postfix/main.cf:
+ # Exclude broken clients by allowlisting. Clients in mynetworks
+ # should always be allowlisted.
+ postscreen_access_list = permit_mynetworks,
+ cidr:/etc/postfix/postscreen_access.cidr
+
+ /etc/postfix/postscreen_access.cidr:
+ 192.168.254.0/24 permit
+
+ 2. Comment out the "smtp inet ... smtpd" service in master.cf, including any
+ "-o parameter=value" entries that follow.
+
+ /etc/postfix/master.cf:
+ #smtp inet n - n - - smtpd
+ # -o parameter=value ...
+
+ 3. Uncomment the new "smtpd pass ... smtpd" service in master.cf, and
+ duplicate any "-o parameter=value" entries from the smtpd service that was
+ commented out in the previous step.
+
+ /etc/postfix/master.cf:
+ smtpd pass - - n - - smtpd
+ -o parameter=value ...
+
+ 4. Uncomment the new "smtp inet ... postscreen" service in master.cf.
+
+ /etc/postfix/master.cf:
+ smtp inet n - n - 1 postscreen
+
+ 5. Uncomment the new "tlsproxy unix ... tlsproxy" service in master.cf. This
+ service implements STARTTLS support for postscreen(8).
+
+ /etc/postfix/master.cf:
+ tlsproxy unix - - n - 0 tlsproxy
+
+ 6. Uncomment the new "dnsblog unix ... dnsblog" service in master.cf. This
+ service does DNSBL lookups for postscreen(8) and logs results.
+
+ /etc/postfix/master.cf:
+ dnsblog unix - - n - 0 dnsblog
+
+ 7. To enable DNSBL lookups, list some DNS blocklist sites in main.cf,
+ separated by whitespace. Different sites can have different weights. For
+ example:
+
+ /etc/postfix/main.cf:
+ postscreen_dnsbl_threshold = 2
+ postscreen_dnsbl_sites = zen.spamhaus.org*2
+ bl.spamcop.net*1 b.barracudacentral.org*1
+
+ Note: if your DNSBL queries have a "secret" in the domain name, you must
+ censor this information from the postscreen(8) SMTP replies. For example:
+
+ /etc/postfix/main.cf:
+ postscreen_dnsbl_reply_map = texthash:/etc/postfix/dnsbl_reply
+
+ /etc/postfix/dnsbl_reply:
+ # Secret DNSBL name Name in postscreen(8) replies
+ secret.zen.dq.spamhaus.net zen.spamhaus.org
+
+ The texthash: format is similar to hash: except that there is no need to
+ run postmap(1) before the file can be used, and that it does not detect
+ changes after the file is read. It is new with Postfix version 2.8.
+
+ 8. Read the new configuration with "postfix reload".
+
+Notes:
+
+ * Some postscreen(8) configuration parameters implement stress-dependent
+ behavior. This is supported only when the default value is stress-dependent
+ (that is, "postconf -d parametername" output shows "parametername = $
+ {stress?something}${stress:something}" or "parametername = ${stress?
+ {something}:{something}}"). Other parameters always evaluate as if the
+ stress value is the empty string.
+
+ * See "Tests before the 220 SMTP server greeting" for details about the
+ logging from these postscreen(8) tests.
+
+ * If you run Postfix 2.6 or earlier you must stop and start the master daemon
+ ("postfix stop; postfix start"). This is needed because the Postfix "pass"
+ master service type did not work reliably on all systems.
+
+ppoossttssccrreeeenn((88)) TTLLSS ccoonnffiigguurraattiioonn
+
+postscreen(8) TLS support is available for remote SMTP clients that aren't
+allowlisted, including clients that need to renew their temporary allowlist
+status. When a remote SMTP client requests TLS service, postscreen(8) invisibly
+hands off the connection to a tlsproxy(8) process. Then, tlsproxy(8) encrypts
+and decrypts the traffic between postscreen(8) and the remote SMTP client. One
+tlsproxy(8) process can handle multiple SMTP sessions. The number of tlsproxy
+(8) processes slowly increases with server load, but it should always be much
+smaller than the number of postscreen(8) TLS sessions.
+
+TLS support for postscreen(8) and tlsproxy(8) uses the same parameters as with
+smtpd(8). We recommend that you keep the relevant configuration parameters in
+main.cf. If you must specify "-o smtpd_mumble=value" parameter overrides in
+master.cf for a postscreen-protected smtpd(8) service, then you should specify
+those same parameter overrides for the postscreen(8) and tlsproxy(8) services.
+
+BBlloocckkiinngg mmaaiill wwiitthh ppoossttssccrreeeenn((88))
+
+For compatibility with smtpd(8), postscreen(8) implements the soft_bounce
+safety feature. This causes Postfix to reject mail with a "try again" reply
+code.
+
+ * To turn this on for all of Postfix, specify "soft_bounce = yes" in main.cf.
+
+ * To turn this on for postscreen(8) only, append "-o soft_bounce=yes" (note:
+ NO SPACES around '=') to the postscreen entry in master.cf.
+
+Execute "postfix reload" to make the change effective.
+
+After testing, do not forget to remove the soft_bounce feature, otherwise
+senders won't receive their non-delivery notification until many days later.
+
+To use the postscreen(8) service to block mail, edit main.cf and specify one or
+more of:
+
+ * "postscreen_dnsbl_action = enforce", to reject clients that are on DNS
+ blocklists, and to log the helo/sender/recipient information. With good
+ DNSBLs this reduces the amount of load on Postfix SMTP servers
+ dramatically.
+
+ * "postscreen_greet_action = enforce", to reject clients that talk before
+ their turn, and to log the helo/sender/recipient information. This stops
+ over half of all known-to-be illegitimate connections to Wietse's mail
+ server. It is backup protection for zombies that haven't yet been
+ denylisted.
+
+ * You can also enable "deep protocol tests", but these are more intrusive
+ than the pregreet or DNSBL tests.
+
+ When a good client passes the "deep protocol tests", postscreen(8) adds the
+ client to the temporary allowlist but it cannot hand off the "live"
+ connection to a Postfix SMTP server process in the middle of the session.
+ Instead, postscreen(8) defers mail delivery attempts with a 4XX status,
+ logs the helo/sender/recipient information, and waits for the client to
+ disconnect.
+
+ When the good client comes back in a later session, it is allowed to talk
+ directly to a Postfix SMTP server. See "Tests after the 220 SMTP server
+ greeting" above for limitations with AUTH and other features that clients
+ may need.
+
+ An unexpected benefit from "deep protocol tests" is that some "good"
+ clients don't return after the 4XX reply; these clients were not so good
+ after all.
+
+ Unfortunately, some senders will retry requests from different IP
+ addresses, and may never get allowlisted. For this reason, Wietse stopped
+ using "deep protocol tests" on his own internet-facing mail server.
+
+ * There is also support for permanent denylisting and allowlisting; see the
+ description of the postscreen_access_list parameter for details.
+
+TTuurrnniinngg ooffff ppoossttssccrreeeenn((88))
+
+To turn off postscreen(8) and handle mail directly with Postfix SMTP server
+processes:
+
+ 1. Comment out the "smtp inet ... postscreen" service in master.cf, including
+ any "-o parameter=value" entries that follow.
+
+ /etc/postfix/master.cf:
+ #smtp inet n - n - 1 postscreen
+ # -o parameter=value ...
+
+ 2. Comment out the "dnsblog unix ... dnsblog" service in master.cf.
+
+ /etc/postfix/master.cf:
+ #dnsblog unix - - n - 0 dnsblog
+
+ 3. Comment out the "smtpd pass ... smtpd" service in master.cf, including any
+ "-o parameter=value" entries that follow.
+
+ /etc/postfix/master.cf:
+ #smtpd pass - - n - - smtpd
+ # -o parameter=value ...
+
+ 4. Comment out the "tlsproxy unix ... tlsproxy" service in master.cf,
+ including any "-o parameter=value" entries that follow.
+
+ /etc/postfix/master.cf:
+ #tlsproxy unix - - n - 0 tlsproxy
+ # -o parameter=value ...
+
+ 5. Uncomment the "smtp inet ... smtpd" service in master.cf, including any "-
+ o parameter=value" entries that may follow.
+
+ /etc/postfix/master.cf:
+ smtp inet n - n - - smtpd
+ -o parameter=value ...
+
+ 6. Read the new configuration with "postfix reload".
+
+SShhaarriinngg tthhee tteemmppoorraarryy aalllloowwlliisstt
+
+By default, the temporary allowlist is not shared between multiple postscreen
+(8) daemons. To enable sharing, choose one of the following options:
+
+ * A non-persistent memcache: temporary allowlist can be shared between
+ postscreen(8) daemons on the same host or different hosts. Disable cache
+ cleanup (postscreen_cache_cleanup_interval = 0) in all postscreen(8)
+ daemons because memcache: has no first-next API (but see example 4 below
+ for memcache: with persistent backup). This requires Postfix 2.9 or later.
+
+ # Example 1: non-persistent memcache: allowlist.
+ /etc/postfix/main.cf:
+ postscreen_cache_map = memcache:/etc/postfix/postscreen_cache
+ postscreen_cache_cleanup_interval = 0
+
+ /etc/postfix/postscreen_cache:
+ memcache = inet:127.0.0.1:11211
+ key_format = postscreen:%s
+
+ * A persistent lmdb: temporary allowlist can be shared between postscreen(8)
+ daemons that run under the same master(8) daemon, or under different master
+ (8) daemons on the same host. Disable cache cleanup
+ (postscreen_cache_cleanup_interval = 0) in all postscreen(8) daemons except
+ one that is responsible for cache cleanup. This requires Postfix 2.11 or
+ later.
+
+ # Example 2: persistent lmdb: allowlist.
+ /etc/postfix/main.cf:
+ postscreen_cache_map = lmdb:$data_directory/postscreen_cache
+ # See note 1 below.
+ # postscreen_cache_cleanup_interval = 0
+
+ * Other kinds of persistent temporary allowlist can be shared only between
+ postscreen(8) daemons that run under the same master(8) daemon. In this
+ case, temporary allowlist access must be shared through the proxymap(8)
+ daemon. This requires Postfix 2.9 or later.
+
+ # Example 3: proxied btree: allowlist.
+ /etc/postfix/main.cf:
+ postscreen_cache_map =
+ proxy:btree:/var/lib/postfix/postscreen_cache
+ # See note 1 below.
+ # postscreen_cache_cleanup_interval = 0
+
+ # Example 4: proxied btree: allowlist with memcache: accelerator.
+ /etc/postfix/main.cf:
+ postscreen_cache_map = memcache:/etc/postfix/postscreen_cache
+ proxy_write_maps =
+ proxy:btree:/var/lib/postfix/postscreen_cache
+ ... other proxied tables ...
+ # See note 1 below.
+ # postscreen_cache_cleanup_interval = 0
+
+ /etc/postfix/postscreen_cache:
+ # Note: the $data_directory macro is not defined in this context.
+ memcache = inet:127.0.0.1:11211
+ backup = proxy:btree:/var/lib/postfix/postscreen_cache
+ key_format = postscreen:%s
+
+ Note 1: disable cache cleanup (postscreen_cache_cleanup_interval = 0) in
+ all postscreen(8) daemons except one that is responsible for cache cleanup.
+
+ Note 2: postscreen(8) cache sharing via proxymap(8) requires Postfix 2.9 or
+ later; earlier proxymap(8) implementations don't support cache cleanup.
+
+HHiissttoorriiccaall nnootteess aanndd ccrreeddiittss
+
+Many ideas in postscreen(8) were explored in earlier work by Michael Tokarev,
+in OpenBSD spamd, and in MailChannels Traffic Control.
+
+Wietse threw together a crude prototype with pregreet and dnsbl support in June
+2009, because he needed something new for a Mailserver conference presentation
+in July. Ralf Hildebrandt ran this code on several servers to collect real-
+world statistics. This version used the dnsblog(8) ad-hoc DNS client program.
+
+Wietse needed new material for a LISA conference presentation in November 2010,
+so he added support for DNSBL weights and filters in August, followed by a
+major code rewrite, deep protocol tests, helo/sender/recipient logging, and
+stress-adaptive behavior in September. Ralf Hildebrandt ran this code on
+several servers to collect real-world statistics. This version still used the
+embarrassing dnsblog(8) ad-hoc DNS client program.
+
+Wietse added STARTTLS support in December 2010. This makes postscreen(8) usable
+for sites that require TLS support. The implementation introduces the tlsproxy
+(8) event-driven TLS proxy that decrypts/encrypts the sessions for multiple
+SMTP clients.
+
+The tlsproxy(8) implementation led to the discovery of a "new" class of
+vulnerability (CVE-2011-0411) that affected multiple implementations of SMTP,
+POP, IMAP, NNTP, and FTP over TLS.
+
+postscreen(8) was officially released as part of the Postfix 2.8 stable release
+in January 2011.
+
+Noel Jones helped with the Postfix 3.6 transition towards respectful
+documentation.
+