Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion 4 CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -184,10 +184,12 @@ The most noteworthy change of this release is the update of the container's base

- **Documentation:**
- A guide for configuring a public server to relay inbound and outbound mail from DMS on a private server ([#3973](https://github.com/docker-mailserver/docker-mailserver/pull/3973))
- Added information on how to configure send-only aliases ([#4044](https://github.com/docker-mailserver/docker-mailserver/pull/4044))
- **Environment Variables:**
- `LOGROTATE_COUNT` defines the number of files kept by logrotate ([#3907](https://github.com/docker-mailserver/docker-mailserver/pull/3907))
- The fail2ban log file is now also taken into account by `LOGROTATE_COUNT` and `LOGROTATE_INTERVAL` ([#3915](https://github.com/docker-mailserver/docker-mailserver/pull/3915), [#3919](https://github.com/docker-mailserver/docker-mailserver/pull/3919))

- **Postfix:**
- `smtpd_sender_login_maps` allows configuration with sender-only aliases out of the box using `postfix-regexp-send-only.cf` ([#4044](https://github.com/docker-mailserver/docker-mailserver/pull/4044))
- **Internal:**
- Regular container restarts are now better supported. Setup scripts that ran previously will now be skipped ([#3929](https://github.com/docker-mailserver/docker-mailserver/pull/3929))

Expand Down
6 changes: 4 additions & 2 deletions 6 docs/content/config/advanced/optional-config.md
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,7 @@ This is a list of all configuration files and directories which are optional, au
- **postfix-sasl-password.cf:** listing of relayed domains with their respective `<username>:<password>`. Modify via `setup.sh relay add-auth <domain> <username> [<password>]`. (Docs: [Relay-Hosts Auth][docs::relay-hosts::advanced])
- **postfix-relaymap.cf:** domain-specific relays and exclusions. Modify via `setup.sh relay add-domain` and `setup.sh relay exclude-domain`. (Docs: [Relay-Hosts Senders][docs::relay-hosts::advanced])
- **postfix-regexp.cf:** Regular expression alias file. (Docs: [Aliases][docs-aliases-regex])
- **postfix-regexp-send-only.cf:** Regular expression alias file for sending only. (Docs: [Send-Only Aliases][docs-aliases-send-only])
- **ldap-users.cf:** Configuration for the virtual user mapping `virtual_mailbox_maps`. See the [`setup-stack.sh`][github-commit-setup-stack.sh-L411] script.
- **ldap-groups.cf:** Configuration for the virtual alias mapping `virtual_alias_maps`. See the [`setup-stack.sh`][github-commit-setup-stack.sh-L411] script.
- **ldap-aliases.cf:** Configuration for the virtual alias mapping `virtual_alias_maps`. See the [`setup-stack.sh`][github-commit-setup-stack.sh-L411] script.
Expand All @@ -97,8 +98,9 @@ This is a list of all configuration files and directories which are optional, au
[docker-docs::volumes]: https://docs.docker.com/storage/volumes/
[docker-docs::volumes::bind-mount]: https://docs.docker.com/storage/bind-mounts/

[docs-accounts-quota]: ../../config/account-management/provisioner/file.md#quotas
[docs-aliases-regex]: ../../config/account-management/provisioner/file.md#configuring-regex-aliases
[docs-accounts-quota]: ../../config/user-management.md#quotas
[docs-aliases-regex]: ../../config/user-management.md#configuring-regexp-aliases
[docs-aliases-send-only]: ../../config/user-management.md#send-only-aliases
[docs-dkim]: ../../config/best-practices/dkim_dmarc_spf.md#dkim
[docs-fail2ban]: ../../config/security/fail2ban.md
[docs-faq-spamrules]: ../../faq.md#how-can-i-manage-my-custom-spamassassin-rules
Expand Down
2 changes: 2 additions & 0 deletions 2 docs/content/config/environment.md
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,8 @@ Configures the handling of creating mails with forged sender addresses.
- **0** => (not recommended) Mail address spoofing allowed. Any logged in user may create email messages with a [forged sender address](https://en.wikipedia.org/wiki/Email_spoofing).
- 1 => Mail spoofing denied. Each user may only send with their own or their alias addresses. Addresses with [extension delimiters](http://www.postfix.org/postconf.5.html#recipient_delimiter) are not able to send messages.

To allow certain accounts to send as other addresses, set the `SPOOF_PROTECTION` to `1` and see [the Aliases page in the documentation][docs-aliases].

##### ENABLE_SRS

Enables the Sender Rewriting Scheme. SRS is needed if DMS acts as forwarder. See [postsrsd](https://github.com/roehling/postsrsd/blob/main/README.rst) for further explanation.
Expand Down
7 changes: 4 additions & 3 deletions 7 target/scripts/check-for-changes.sh
Original file line number Diff line number Diff line change
Expand Up @@ -136,9 +136,10 @@ function _postfix_dovecot_changes() {
fi

# Regenerate system + virtual account aliases via `helpers/aliases.sh`:
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-virtual.cf ]] && _handle_postfix_virtual_config
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-regexp.cf ]] && _handle_postfix_regexp_config
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-aliases.cf ]] && _handle_postfix_aliases_config
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-virtual.cf ]] && _handle_postfix_virtual_config
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-regexp.cf ]] && _handle_postfix_regexp_config
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-regexp-send-only.cf ]] && _handle_postfix_regexp_send_only_config
[[ ${CHANGED} =~ ${DMS_DIR}/postfix-aliases.cf ]] && _handle_postfix_aliases_config

# Legacy workaround handled here, only seems necessary for _create_accounts:
# - `helpers/accounts.sh` logic creates folders/files with wrong ownership.
Expand Down
12 changes: 12 additions & 0 deletions 12 target/scripts/helpers/aliases.sh
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,17 @@ function _handle_postfix_regexp_config() {
fi
}

function _handle_postfix_regexp_send_only_config() {
: >/etc/postfix/regexp-send-only
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd prefer not creating a file explicitly when it's not used.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was just copying the regular postfix-regexp logic here — would I be OK to also remove the same thing in the _handle_postfix_regexp_config() above (and corresponding # TODO: Investigate why this file is always created, nothing seems to append only the cp below? comment)?

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's probably a related issue already open about details for that.

Without looking for that, I can't quite say. I've not had as much time for DMS as I'd like, but if the change was delayed I may have detailed why. I'd leave it alone for now, unless you have time to sink 😅

Proper actionable feedback from me is going to need to wait until I have the time to refresh on related context like this. I'll try to get that sorted for you by this weekend if possible, sorry about the friction that adds.


if [[ -f /tmp/docker-mailserver/postfix-regexp-send-only.cf ]]; then
_log 'trace' "Adding regexp-send-only alias file postfix-regexp-send-only.cf"

cp -f /tmp/docker-mailserver/postfix-regexp-send-only.cf /etc/postfix/regexp-send-only
# we specifically do NOT append this to virtual_alias_maps
fi
}

function _handle_postfix_aliases_config() {
_log 'trace' 'Configuring root alias'

Expand All @@ -46,5 +57,6 @@ function _handle_postfix_aliases_config() {
function _create_aliases() {
_handle_postfix_virtual_config
_handle_postfix_regexp_config
_handle_postfix_regexp_send_only_config
_handle_postfix_aliases_config
}
1 change: 1 addition & 0 deletions 1 target/scripts/helpers/change-detection.sh
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ function _monitored_files_checksums() {
"${DMS_DIR}/postfix-accounts.cf"
"${DMS_DIR}/postfix-virtual.cf"
"${DMS_DIR}/postfix-regexp.cf"
"${DMS_DIR}/postfix-regexp-send-only.cf"
"${DMS_DIR}/postfix-aliases.cf"
"${DMS_DIR}/postfix-relaymap.cf"
"${DMS_DIR}/postfix-sasl-password.cf"
Expand Down
6 changes: 5 additions & 1 deletion 6 target/scripts/startup/setup.d/security/spoofing.sh
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,11 @@ function _setup_spoof_protection() {
# NOTE: This file is always created at startup, it potentially has content added.
# TODO: From section: "SPOOF_PROTECTION=1 handling for smtpd_sender_login_maps"
# https://github.com/docker-mailserver/docker-mailserver/issues/2819#issue-1402114383
if [[ -f /etc/postfix/regexp ]]; then
if [[ -f /etc/postfix/regexp && -f /etc/postfix/regexp-send-only ]]; then
postconf 'smtpd_sender_login_maps = unionmap:{ texthash:/etc/postfix/virtual, hash:/etc/aliases, pcre:/etc/postfix/maps/sender_login_maps.pcre, pcre:/etc/postfix/regexp, pcre:/etc/postfix/regexp-send-only }'
elif [[ -f /etc/postfix/regexp-send-only ]]; then
postconf 'smtpd_sender_login_maps = unionmap:{ texthash:/etc/postfix/virtual, hash:/etc/aliases, pcre:/etc/postfix/maps/sender_login_maps.pcre, pcre:/etc/postfix/regexp-send-only }'
elif [[ -f /etc/postfix/regexp ]]; then
Comment on lines +17 to +21
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not acceptable. See the related SPOOF_PROTECTION=1 issue.

This section needs to be refactored to unify with LDAP. You'll need to wait on that being resolved. I am adding friction here due to blockers I introduce external to this PR, I'll need to address those first.

postconf 'smtpd_sender_login_maps = unionmap:{ texthash:/etc/postfix/virtual, hash:/etc/aliases, pcre:/etc/postfix/maps/sender_login_maps.pcre, pcre:/etc/postfix/regexp }'
else
postconf 'smtpd_sender_login_maps = texthash:/etc/postfix/virtual, hash:/etc/aliases, pcre:/etc/postfix/maps/sender_login_maps.pcre'
Expand Down
1 change: 1 addition & 0 deletions 1 test/config/postfix-regexp-send-only.cf
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
/^user3@localhost.localdomain/ user1@localhost.localdomain
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
From: Not_My_Business <user2@localhost.localdomain>
From: test123_alias <test123@localhost.localdomain>
To: Existing Local User <user1@localhost.localdomain>
Date: Sat, 22 May 2010 07:43:25 -0400
Subject: Test Message
Expand Down
5 changes: 5 additions & 0 deletions 5 test/files/emails/auth/added-smtp-auth-spoofed-from-user1.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
From: User 1 <user1@localhost.localdomain>
To: Existing Local User <user1@localhost.localdomain>
Date: Sat, 22 May 2010 07:43:25 -0400
Subject: Test Message
This is a test mail.
5 changes: 5 additions & 0 deletions 5 test/files/emails/auth/added-smtp-auth-spoofed-from-user3.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
From: User 3 <user3@localhost.localdomain>
To: Existing Local User <user3@localhost.localdomain>
Date: Sat, 22 May 2010 07:43:25 -0400
Subject: Test Message
This is a test mail.
105 changes: 105 additions & 0 deletions 105 test/tests/parallel/set2/auth/spoofing.bats
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
load "${REPOSITORY_ROOT}/test/helper/common"
load "${REPOSITORY_ROOT}/test/helper/setup"

BATS_TEST_NAME_PREFIX='[Postfix] (sender spoofing) '
CONTAINER_NAME='dms-test_postfix-spoofing'

function setup_file() {
_init_with_defaults

local CUSTOM_SETUP_ARGUMENTS=(
--env SPOOF_PROTECTION=1
--env LOG_LEVEL=trace
--env SSL_TYPE='snakeoil'
)

_common_container_setup 'CUSTOM_SETUP_ARGUMENTS'

_wait_for_service postfix
_wait_for_smtp_port_in_container_to_respond
}

function teardown_file() { _default_teardown ; }

# These tests ensure spoofing protection works, and that exceptions are available for aliases.
# user1 has aliases configured for the following accounts:
# - test\d* via /etc/postfix/regexp
# - alias1@localhost via /etc/postfix/virtual
# - user3@localhost via /etc/postfix/regexp-send-only

@test "allows forging as send-only alias" {
# An authenticated account should be able to send mail from a send-only alias,
# Verifies `main.cf:smtpd_sender_login_maps` includes /etc/postfix/regexp-send-only
_send_email \
--port 587 -tls --auth PLAIN \
--auth-user user1@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from user3@localhost.localdomain \
--data 'auth/added-smtp-auth-spoofed-from-user3.txt'
assert_success
assert_output --partial 'End data with'
}

@test "allows forging as regular alias" {
# An authenticated account should be able to send mail from an alias,
# Verifies `main.cf:smtpd_sender_login_maps` includes /etc/postfix/virtual
_send_email \
--port 587 -tls --auth PLAIN \
--auth-user user1@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from alias1@localhost.localdomain \
--data 'auth/added-smtp-auth-spoofed-from-alias1.txt'
assert_success
assert_output --partial 'End data with'
}

@test "allows forging as regular (regex) alias" {
# An authenticated account should be able to send mail from an alias,
# Verifies `main.cf:smtpd_sender_login_maps` includes /etc/postfix/regexp
_send_email \
--port 587 -tls --auth PLAIN \
--auth-user user1@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from test123@localhost.localdomain \
--data 'auth/added-smtp-auth-spoofed-from-test123.txt'
assert_success
assert_output --partial 'End data with'
}

@test "rejects sender forging" {
# An authenticated user cannot use an envelope sender (MAIL FROM)
# address they do not own according to `main.cf:smtpd_sender_login_maps` lookup
_send_email --expect-rejection \
--port 587 -tls --auth PLAIN \
--auth-user user3@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from user1@localhost.localdomain \
--data 'auth/added-smtp-auth-spoofed-from-user1.txt'
assert_output --partial 'Sender address rejected: not owned by user'
}

@test "send-only alias does not affect incoming mail" {
# user1 is allowed to send as user3, however, mail to user3 should still be delivered to user3.
# Verifies that /etc/postfix/regexp-send-only does not affect incoming mail.
_send_email \
--port 587 -tls --auth PLAIN \
--auth-user user1@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from user1@localhost.localdomain \
--to user3@localhost.localdomain \
--data 'test-email.txt'
assert_success
assert_output --partial 'End data with'

_wait_for_empty_mail_queue_in_container

# would have an orig_to if it got forwarded
_service_log_should_contain_string 'mail' ': to=<user3@localhost.localdomain>'
assert_output --partial 'status=sent'
_should_output_number_of_lines 1
}
33 changes: 0 additions & 33 deletions 33 test/tests/serial/tests.bats
Original file line number Diff line number Diff line change
Expand Up @@ -281,39 +281,6 @@ EOF
assert_success
}

@test "spoofing: rejects sender forging" {
# rejection of spoofed sender
_wait_for_smtp_port_in_container_to_respond

# An authenticated user cannot use an envelope sender (MAIL FROM)
# address they do not own according to `main.cf:smtpd_sender_login_maps` lookup
_send_email --expect-rejection \
--port 465 -tlsc --auth PLAIN \
--auth-user added@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from user2@localhost.localdomain \
--data 'auth/added-smtp-auth-spoofed.txt'
assert_output --partial 'Sender address rejected: not owned by user'
}

@test "spoofing: accepts sending as alias" {
# An authenticated account should be able to send mail from an alias,
# Verifies `main.cf:smtpd_sender_login_maps` includes /etc/postfix/virtual
# The envelope sender address (MAIL FROM) is the lookup key
# to each table. Address is authorized when a result that maps to
# the DMS account is returned.
_send_email \
--port 465 -tlsc --auth PLAIN \
--auth-user user1@localhost.localdomain \
--auth-password mypassword \
--ehlo mail \
--from alias1@localhost.localdomain \
--data 'auth/added-smtp-auth-spoofed-alias.txt'
assert_success
assert_output --partial 'End data with'
}

#
# Pflogsumm delivery check
#
Expand Down
Morty Proxy This is a proxified and sanitized view of the page, visit original site.