The TLSRPT protocol is defined in RFC 8460. With this, an email receiving domain can publish a policy in DNS, and request daily summary reports for successful and failed SMTP over TLS connections to that domain's MX hosts. Support for TLSRPT was added in Postfix 3.10.
A policy example looks like this:
_smtp._tls.example.com. IN TXT "v=TLSRPTv1; rua=mailto:[email protected]"
Translation: email sending systems are requested to generate daily summaries of successful and failed SMTP over TLS connections to domain example.com, and to report those summaries via email to the specified address. Instead of mailto:, a policy may specify an https: destination.
The high-level diagram shows how Postfix reports summaries to domains that publish a TLSRPT policy.
Postfix SMTP and
TLS client engines--> TLSRPT client
library--> TLSRPT summary
generator--> Email or HTTP
delivery
When Postfix TLSRPT support is enabled (with "smtp_tlsrpt_enable = yes"):
The Postfix SMTP and TLS client engines will generate a "success" or "failure" event for each TLS handshake,
They will pass those events to an in-process TLSRPT client library that sends data over a local socket to
A TLSRPT report generator that produces daily summary reports.
The TLSRPT client library and report generator are maintained by sys4.
The Postfix implementation supports both DANE (Postfix built-in) and MTA-STS (through an smtp_tls_policy_maps plug-in).
The Postfix smtp(8) client process implements the SMTP client engine. With "smtp_tls_connection_reuse = no", the smtp(8) client process also implements the TLS client engine. With "smtp_tls_connection_reuse = yes", the smtp(8) client process delegates TLS processing to a Postfix tlsproxy(8) process. Either way, Postfix will generate the exact same TLSRPT events.
These instructions assume that you build Postfix from source code as described in the INSTALL document. Some modification may be required if you build Postfix from a vendor-specific source package.
The Postfix TLSRPT client builds on a TLSRPT client library whose source code can be obtained from:
The library is typically installed as a header file in /usr/local/include/tlsrpt.h and an object library in /usr/local/lib/libtlsrpt.a or /usr/local/lib/libtlsrpt.so. The actual pathnames will depend on OS platform conventions.
In order to build Postfix with TLSRPT support, you will need to add compiler options -DUSE_TLSRPT (to build with TLSRPT support), and -I (with the directory containing the tlsrpt.h header file), and you will need to add linker options to link with the TLSRPT client library, for example:
make -f Makefile.init makefiles \ "CCARGS=-DUSE_TLSRPT -I/usr/local/include" \ "AUXLIBS=-L/usr/local/lib -ltlsrpt"
Then, just run 'make'.
Note: if your build command line already has CCARGS or AUXLIBS settings, then simply append the above settings to the existing CCARGS or AUXLIBS values.
make -f Makefile.init makefiles \ "CCARGS=existing settings... -DUSE_TLSRPT -I/usr/local/include" \ "AUXLIBS=existing settings... -L/usr/local/lib -ltlsrpt"
After installing Postfix TLSRPT support, you can enable TLSRPT support in main.cf like this:
smtp_tlsrpt_enable = yes smtp_tlsrpt_socket_name = /path/to/socket
The smtp_tlsrpt_socket_name parameter specifies an absolute pathname, or a pathname that is relative to $queue_directory.
Note: the recommended socket location is still to be determined. A good socket location would be under the Postfix queue directory, for example: "smtp_tlsrpt_socket_name = run/tlsrpt/tlsrpt.sock". The advantage of using a relative name is that it will work equally well whether or not Postfix chroot is turned on.
Do not specify a location under a directory such as private or public that is already used by Postfix programs. Only Postfix programs should create sockets there.
With TLSRPT support turned on, the Postfix TLSRPT client will not only report an event to an invisible daily success/fail summary queue, but it will also log a visible record to the mail logfile.
Below are a few examples of logging from a Postfix SMTP client or tlsproxy daemon:
TLSRPT: status=success, domain=example.com, receiving_mx=mail.example.com[ipaddr] TLSRPT: status=failure, domain=example.org, receiving_mx=mail.example.org[ipaddr], failure_type=starttls_not_supported TLSRPT: status=failure, domain=example.net, receiving_mx=mail.example.net[ipaddr], failure_type=validation_failure, failure_reason=self-signed_certificate
Notes:
Postfix logs and reports the TLSRPT status only for TLS handshakes on a new SMTP connection. There is no TLS handshake, and thus no TLSRPT status logging, when an SMTP connection is reused. Such connections have Postfix SMTP client logging like this:
Verified TLS connection reused to mail.example.com[ipaddr]:25: TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits) Untrusted TLS connection reused to mail.example.com[ipaddr]:25: TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)
By default, Postfix does not report the TLSRPT status for a TLS handshake that reuses a previously-negotiated TLS session (there would be no new information to report). Specify "smtp_tlsrpt_skip_reused_handshakes = no" to report the TLSRPT status for all TLS handshakes. This may be useful for troubleshooting.
Postfix logging for certificate verification failures may differ between new or reused TLS sessions.
New TLS session:
TLSRPT: status=failure, domain=example.org, receiving_mx=mail.example.org[ipaddr], failure_type=validation_failure, failure_reason=self-signed_certificate
Reused TLS session:
mail.example.org[ipaddr]:25: re-using session with untrusted peer credential, look for details earlier in the log TLSRPT: status=failure, domain=example.org, receiving_mx=mail.example.org[ipaddr], failure_type=certificate_not_trusted
The logging may differ because a reused TLS session does not have the details for why TLS authentication failed.
RFC 8460 Section 3 specifies that an MTA must not enforce TLS security when sending failure reports via email. However, Postfix currently has no way to request that TLS enforcement will be disabled when submitting an email message.
Options:
Do nothing. When TLS security enforcement is required but fails, a TLSRPT summary message will be delayed until the problem is addressed, or until the message expires in the mail queue. Keep in mind that TLSRPT is not a real-time monitoring service; it takes on average 12 hours before a failure is reported through TLSRPT.
Exclude the sender of TLSRPT summaries from TLS security enforcement. Implement the configuration below on outbound MTA instances (replace [email protected] with your actual report generator's sender address):
/etc/postfix/main.cf: # Limitation: this setting is overruled with transport_maps. sender_dependent_default_transport_maps = inline:{ { [email protected] = allow-plaintext } }   /etc/postfix/master.cf: # service name type private unpriv chroot wakeup maxproc command allow-plaintext unix - - - - - smtp -o { smtp_tls_security_level = may } -o { smtp_tls_policy_maps = static:may }
Postfix supports MTA-STS though an smtp_tls_policy_maps policy plugin, which replies with a TLS security level and optional matching requirements. Postfix 3.10 and later optionally also accept the name=value attributes described below. Specify { name = value } when a value may contain whitespace.
Note 1: Postfix 3.10 and later will accept these attributes in an MTA-STS response even if TLSRPT support is disabled (at build time or run time). With TLSRPT support turned off, Postfix will use the ttl and policy_failure attributes, and will ignore the attributes that are used only for TLSRPT.
Note 2: It is an error to specify these attributes for a non-STS policy.
The examples in the table apply to the MTA-STS policy example given in RFC 8461 Section 3.2:
version: STSv1 mode: enforce mx: mail.example.com mx: *.example.net mx: backupmx.example.com max_age: 604800
A policy response may contain line breaks.
policy_type=type
Specify sts or no-policy-found.
policy_domain=name
The domain that the MTA-STS policy applies to.
policy_ttl=time
How long (in seconds) a Postfix SMTP client process will cache the MTA-STS plugin response.
{ policy_string = value }
Specify one policy_string instance for each MTA-STS policy feature, enclosed inside "{" and "}" to protect whitespace in attribute values.
Example:
{ policy_string = version: STSv1 } { policy_string = mode: enforce } ...
This form ignores whitespace after the opening "{", around the "=", and before the closing "}".
mx_host_pattern=pattern
Specify one mx_host_pattern instance for each "mx:" feature in the MTA-STS policy.
Example:
mx_host_pattern=mail.example.com mx_host_pattern=*.example.net ...
policy_failure=type
If specified, forces MTA-STS policy enforcement to fail with the indicated error, even if a server certificate would satisfy conventional PKI constraints.
Valid errors are sts-policy-fetch-error, sts-policy-invalid, sts-webpki-invalid, or the less informative validation-failure.
Example:
policy_failure=sts-webpki-invalid
The Postfix TLSRPT implementation reports only TLS handshake success or failure. It does not report failure to connect, or connections that break before or after a TLS handshake.
The Postfix TLSRPT implementation reports at most one final TLS handshake status (either 'success' or 'failure') per SMTP connection. Postfix TLSRPT will not report a recoverable failure and then later report a final status of 'success' for that same connection. The reason is that it's too complicated to filter TLS errors and to report error details from the TLS engine back to the SMTP protocol engine. It just is not how Postfix works internally.