CVE-2021-43799: Write rabbitmq configuration before starting.

Zulip writes a `rabbitmq.config` configuration file which locks down
RabbitMQ to listen only on localhost:5672, as well as the RabbitMQ
distribution port, on localhost:25672.

The "distribution port" is part of Erlang's clustering configuration;
while it is documented that the protocol is fundamentally
insecure ([1], [2]) and can result in remote arbitrary execution of
code, by default the RabbitMQ configuration on Debian and Ubuntu
leaves it publicly accessible, with weak credentials.

The configuration file that Zulip writes, while effective, is only
written _after_ the package has been installed and the service
started, which leaves the port exposed until RabbitMQ or system
restart.

Ensure that rabbitmq's `/etc/rabbitmq/rabbitmq.config` is written
before rabbitmq is installed or starts, and that changes to that file
trigger a restart of the service, such that the ports are only ever
bound to localhost.  This does not mitigate existing installs, since
it does not force a rabbitmq restart.

[1] https://www.erlang.org/doc/apps/erts/erl_dist_protocol.html
[2] https://www.erlang.org/doc/reference_manual/distributed.html#distributed-erlang-system
This commit is contained in:
Alex Vandiver 2021-12-04 03:08:52 +00:00
parent 43d63bd5a1
commit a46f6df91e
2 changed files with 22 additions and 11 deletions

View File

@ -121,6 +121,9 @@ log][commit-log] for an up-to-date list of raw changes.
## Zulip 4.x series
- Closed access to RabbitMQ port 25672; initial installs tried to
close this port, but failed to restart RabbitMQ for the
configuration.
- Removed the `rabbitmq.nodename` configuration in `zulip.conf`; all
RabbitMQ instances will be reconfigured to have a nodename of
`zulip@localhost`. You can remove this setting from your

View File

@ -8,8 +8,6 @@ class zulip::profile::rabbitmq {
$erlang,
'rabbitmq-server',
]
package { $rabbitmq_packages: ensure => 'installed' }
# Removed 2020-09 in version 4.0; these lines can be removed in
# Zulip version 5.0 and later.
file { ['/etc/cron.d/rabbitmq-queuesize', '/etc/cron.d/rabbitmq-numconsumers']:
@ -21,14 +19,20 @@ class zulip::profile::rabbitmq {
owner => 'root',
group => 'root',
mode => '0755',
before => Package['rabbitmq-server'],
}
file { '/etc/rabbitmq/rabbitmq.config':
ensure => file,
require => Package[rabbitmq-server],
owner => 'root',
group => 'root',
mode => '0644',
source => 'puppet:///modules/zulip/rabbitmq/rabbitmq.config',
ensure => file,
owner => 'root',
group => 'root',
mode => '0644',
source => 'puppet:///modules/zulip/rabbitmq/rabbitmq.config',
# This config file must be installed before the package, so that
# port 25672 is not even briefly open to the Internet world, which
# would be a security risk, due to insecure defaults in the
# RabbitMQ package.
before => Package['rabbitmq-server'],
notify => Service['rabbitmq-server'],
}
exec { 'warn-rabbitmq-nodename-change':
command => "${::zulip_scripts_path}/lib/warn-rabbitmq-nodename-change",
@ -52,6 +56,9 @@ class zulip::profile::rabbitmq {
Exec['configure-rabbitmq'],
],
}
package { $rabbitmq_packages:
ensure => 'installed',
}
# epmd doesn't have an init script, so we just check if it is
# running, and if it isn't, start it. Even in case of a race, this
# won't leak epmd processes, because epmd checks if one is already
@ -65,9 +72,10 @@ class zulip::profile::rabbitmq {
service { 'rabbitmq-server':
ensure => running,
require => [Exec['epmd'],
File['/etc/rabbitmq/rabbitmq.config'],
File['/etc/default/rabbitmq-server']],
require => [
Exec['epmd'],
Package['rabbitmq-server'],
],
}
exec { 'configure-rabbitmq':