Introduction
A major Debian upgrade can also introduce a newer Postfix release. Mail delivery may continue to work normally while Postfix begins reporting compatibility and deprecation warnings inherited from an older configuration.
Two common examples are:
support for parameter "smtp_use_tls" will be removed;
instead, specify "smtp_tls_security_level"
and:
Postfix is using backwards-compatible default settings
Neither message necessarily indicates a broken mail system.
The correct response is not to replace settings mechanically, but to determine the effective SMTP relay behavior first and then modernize the configuration without changing delivery semantics.
This article uses a fully sanitized example architecture. All domains, addresses, usernames, ports, queue identifiers, and deployment-specific values are placeholders.
1. Example Architecture
A virtualization or backup server may use local Postfix only for outbound system notifications.
A typical architecture is:
System notification
|
v
Local Postfix
|
| authenticated encrypted SMTP
v
External Mailcow relay
|
v
Administrator mailbox
The local Postfix instance is not intended to operate as a public Internet-facing mail server.
A generic configuration might resemble:
inet_interfaces = loopback-only
inet_protocols = ipv4
mynetworks = 127.0.0.0/8
relayhost = [mail.example.net]:<relay-port>
smtp_tls_wrappermode = yes
smtp_tls_security_level = encrypt
smtp_sasl_auth_enable = yes
smtp_sasl_password_maps = hash:/etc/postfix/sasl_passwd
smtp_sasl_security_options = noanonymous
smtp_sasl_tls_security_options = noanonymous
The placeholder:
<relay-port>
represents an installation-specific SMTP relay port and should be replaced only with the value already configured in the environment being maintained.
2. Audit Before Changing Anything
Before modifying Postfix, inspect the effective configuration:
postconf -n
Useful individual parameters include:
postconf \
mail_version \
compatibility_level \
relayhost \
inet_interfaces \
inet_protocols \
mynetworks \
smtp_use_tls \
smtp_tls_wrappermode \
smtp_tls_security_level \
smtp_sasl_auth_enable \
smtp_sasl_password_maps \
smtp_sasl_security_options \
smtp_sasl_tls_security_options
Also inspect service and queue health:
systemctl status postfix --no-pager
systemctl --failed
postqueue -p
A healthy baseline should normally show:
- Postfix active;
- no failed mail-related service;
- no persistent deferred queue;
- relay configuration present;
- TLS behavior explicitly defined;
- SASL authentication enabled if required by the relay.
3. Understand the smtp_use_tls Deprecation
Older Postfix configurations may contain:
smtp_use_tls = yes
Newer Postfix releases warn that this parameter is being retired in favor of:
smtp_tls_security_level
The important question is not simply whether smtp_use_tls exists.
The important question is whether modern TLS parameters already define the effective behavior.
For example:
smtp_tls_wrappermode = yes
smtp_tls_security_level = encrypt
already means that TLS is mandatory for the configured relay path.
In such a configuration:
smtp_use_tls = yes
is redundant.
4. Why may Is Not Always an Equivalent Replacement
A common but potentially incorrect migration is:
smtp_use_tls = yes
to:
smtp_tls_security_level = may
These settings do not necessarily preserve the same security behavior.
may
smtp_tls_security_level = may
means Postfix may use TLS when available, but plaintext fallback can be permitted.
encrypt
smtp_tls_security_level = encrypt
means TLS is required.
If the relay is deliberately configured for encrypted wrapper-mode SMTP:
smtp_tls_wrappermode = yes
smtp_tls_security_level = encrypt
then changing the security level to may would weaken the existing policy.
The correct modernization is therefore often:
remove smtp_use_tls
keep smtp_tls_wrappermode = yes
keep smtp_tls_security_level = encrypt
The existing delivery semantics remain unchanged.
5. Safe Removal of the Deprecated Parameter
Create a timestamped backup first:
cp -a /etc/postfix/main.cf \
/etc/postfix/main.cf.$(date +%Y%m%d-%H%M%S)
Remove only the deprecated parameter:
sed -i \
'/^[[:space:]]*smtp_use_tls[[:space:]]*=/d' \
/etc/postfix/main.cf
Validate the configuration:
postfix check
Inspect the resulting TLS settings:
postconf -n | grep -E \
'^(smtp_use_tls|smtp_tls_wrappermode|smtp_tls_security_level)'
A correct result for a mandatory encrypted relay may look like:
smtp_tls_security_level = encrypt
smtp_tls_wrappermode = yes
There should be no remaining smtp_use_tls entry.
6. Understanding compatibility_level
Another common post-upgrade warning is:
Postfix is using backwards-compatible default settings
Inspect the current value:
postconf compatibility_level
An installation upgraded repeatedly across Debian releases may still use an older value such as:
compatibility_level = 2
A newer Postfix release may recommend moving to:
compatibility_level = 3.6
This setting controls groups of defaults introduced by newer Postfix releases.
It should not be changed merely to silence the warning.
The relevant default changes should be reviewed first.
7. Inspect Compatibility-Sensitive Parameters
Useful parameters include:
postconf \
append_dot_mydomain \
smtputf8_enable \
mynetworks_style \
relay_domains \
smtpd_relay_restrictions \
smtpd_relay_before_recipient_restrictions \
respectful_logging \
smtp_tls_fingerprint_digest \
smtpd_tls_fingerprint_digest \
lmtp_tls_fingerprint_digest
The output may contain conditional expressions based on compatibility_level, for example:
smtp_tls_fingerprint_digest =
${{$compatibility_level} <level {3.6} ? {md5} : {sha256}}
This does not mean both values are active.
It means the effective value depends on the configured compatibility level.
8. Why the Upgrade Is Usually Low Risk for a Relay-Only Host
A Postfix instance used only as a local outbound relay client commonly has explicit settings such as:
inet_interfaces = loopback-only
mynetworks = 127.0.0.0/8
relayhost = [mail.example.net]:<relay-port>
smtp_tls_security_level = encrypt
smtp_tls_wrappermode = yes
smtp_sasl_auth_enable = yes
In such a design:
- inbound SMTP exposure is minimal;
- relay destination is explicit;
- TLS policy is explicit;
- authentication behavior is explicit;
- network scope is explicit.
This reduces dependence on compatibility-controlled defaults.
The exact environment should still be audited before changing the compatibility level.
9. Notable Changes at Compatibility Level 3.6
Moving to compatibility level 3.6 may change several defaults.
One notable example is TLS fingerprint hashing:
smtp_tls_fingerprint_digest
smtpd_tls_fingerprint_digest
lmtp_tls_fingerprint_digest
The newer default becomes:
sha256
instead of the older:
md5
Other compatibility-controlled settings include:
smtpd_relay_before_recipient_restrictions
respectful_logging
The first affects SMTP server-side restriction evaluation order.
The second affects terminology used in logs.
On a loopback-only outbound relay client, these changes often have little or no effect on actual message delivery.
10. Raising the Compatibility Level
After confirming that no required legacy behavior depends on the old defaults:
postconf 'compatibility_level = 3.6'
Validate before reloading:
postfix check
Then reload Postfix:
systemctl reload postfix
Verify:
postconf compatibility_level
systemctl status postfix --no-pager
journalctl -u postfix -n 30 --no-pager
postqueue -p
A clean result should show:
compatibility_level = 3.6
with:
- Postfix still active;
- no configuration error;
- no compatibility warning on the new reload;
- no unexpected mail queue buildup.
11. Temporary SMTP Debugging Can Produce Extremely Noisy Logs
Postfix supports peer-specific debugging.
An older troubleshooting session may have left settings such as:
debug_peer_level = 3
debug_peer_list = mail.example.net
These settings can cause the journal to contain large amounts of low-level SMTP implementation output, including messages such as:
vstream_buf_get_ready
rec_get
vstream_fflush_some
smtp_stream_setup
These messages are not SMTP failures.
They are debugging traces.
If the relay is already stable, peer-specific debugging can be removed:
postconf -X debug_peer_level
postconf -X debug_peer_list
Then validate:
postfix check
and reload:
systemctl reload postfix
Historical debug entries remain in the system journal, but future mail transactions should produce much cleaner logs.
12. Verify SASL Credential File Security Without Exposing Secrets
The contents of the SASL password file should never be copied into maintenance reports or public documentation.
Only metadata should be inspected:
stat -c '%n | owner=%U:%G | mode=%a' \
/etc/postfix/sasl_passwd \
/etc/postfix/sasl_passwd.db
A typical secure state is:
owner=root:root
mode=600
The following data should not appear in documentation:
- SMTP usernames;
- passwords;
- password hashes;
- complete SASL map entries;
- private relay credentials.
13. Confirm That Mail Is Actually Being Delivered
Existing mail logs can confirm end-to-end delivery without generating a test message.
A successful transaction generally contains:
dsn=2.0.0
status=sent
250 2.0.0 Ok
A fully sanitized example:
relay=mail.example.net[192.0.2.25]:<relay-port>
dsn=2.0.0
status=sent
The documentation-only address:
192.0.2.25
belongs to an address range reserved for examples and should not be replaced with a real public IP in published material.
A successful relay confirms multiple layers:
- DNS resolution;
- TCP connectivity;
- encrypted SMTP transport;
- authentication;
- relay acceptance;
- local queue processing.
14. Historical Deferred Messages Do Not Necessarily Indicate a Current Fault
A mail log may contain:
status=deferred
connection timed out
followed later by:
status=sent
This represents a temporary delivery failure that recovered.
Possible causes include:
- temporary relay unavailability;
- DNS transition;
- network restart;
- firewall transition;
- remote server restart;
- stale cached address information.
If the message is later accepted successfully and the queue becomes empty, the earlier timeout should be classified as a historical recovered event rather than an active mail failure.
Published examples should avoid real timestamps, queue IDs, IP addresses, and hostnames.
15. Inspect the Queue
Use:
postqueue -p
A healthy idle relay often reports:
Mail queue is empty
A non-empty queue is not automatically a fault.
Queued messages should be evaluated according to:
- age;
- retry reason;
- whether the remote relay is reachable;
- whether messages are eventually delivered.
16. Confirm Service Health After Changes
After modernizing the configuration:
systemctl status postfix --no-pager
should report an active service.
Then inspect only recent logs:
journalctl -u postfix -n 30 --no-pager -l
Useful checks include:
journalctl -u postfix --no-pager | \
grep -Ei \
'deprecated|backwards-compatible|fatal|panic|deferred|bounced|SASL.*fail|TLS.*fail'
Old warnings remain in the journal until log retention removes them.
The presence of an old warning does not mean the current configuration still generates it.
Timestamp comparison is essential.
17. A Clean Modern Relay Configuration
A sanitized relay-only Postfix configuration may conceptually resemble:
compatibility_level = 3.6
inet_interfaces = loopback-only
inet_protocols = ipv4
mynetworks = 127.0.0.0/8
relayhost = [mail.example.net]:<relay-port>
smtp_tls_wrappermode = yes
smtp_tls_security_level = encrypt
smtp_sasl_auth_enable = yes
smtp_sasl_password_maps = hash:/etc/postfix/sasl_passwd
smtp_sasl_security_options = noanonymous
smtp_sasl_tls_security_options = noanonymous
Deprecated or temporary parameters should be absent:
smtp_use_tls
debug_peer_level
debug_peer_list
The exact relay hostname, port, credentials, sender identity, and administrator address are deployment-specific and should not appear in public documentation.
18. What Should Be Sanitized Before Publishing Mail Configuration
Mail-system documentation deserves stricter sanitization than ordinary Linux configuration examples.
The following should always be replaced:
| Sensitive field | Safe public form |
|---|---|
| Real relay hostname | mail.example.net |
| Real public IP | 192.0.2.25 |
| Real internal IP | 192.168.10.10 |
| Real SMTP port | <relay-port> |
| Administrator mailbox | admin@example.net |
| SMTP login | <smtp-user> |
| SMTP password | never publish |
| Queue ID | <queue-id> |
| Certificate fingerprint | <fingerprint> |
| SASL map contents | never publish |
| Real timestamps | generic or omitted |
This keeps the technical lesson intact without exposing the deployment.
19. Recommended Maintenance Sequence
A safe modernization sequence is:
1. Inspect effective Postfix configuration
2. Confirm current relay architecture
3. Confirm TLS and SASL behavior
4. Verify successful historical deliveries
5. Back up main.cf
6. Remove deprecated smtp_use_tls
7. Audit compatibility-sensitive defaults
8. Raise compatibility_level if appropriate
9. Remove temporary peer debugging
10. Run postfix check
11. Reload Postfix
12. Check service state
13. Check recent journal entries
14. Check mail queue
15. Allow the next normal system notification to provide end-to-end confirmation
This sequence minimizes unnecessary changes and preserves existing relay behavior.
Conclusion
Postfix warnings after a Debian major-version upgrade are often compatibility warnings rather than service failures.
The correct approach is to modernize the configuration while preserving its original security and relay semantics.
For an authenticated encrypted relay architecture, this commonly means:
remove deprecated smtp_use_tls
retain smtp_tls_security_level = encrypt
retain smtp_tls_wrappermode = yes
review compatibility defaults
move compatibility_level to the supported modern value
remove temporary SMTP debug settings
The final objective is not simply to eliminate warning messages.
The objective is a configuration that is:
- explicit;
- maintainable;
- compatible with current Postfix releases;
- no less secure than before;
- easy to audit;
- free of unnecessary debug noise;
- safe to document without exposing infrastructure details.