- PVSM.RU - https://www.pvsm.ru -

суБД — Безопасность Данных

В ходе реализации нового проекта заказчик часто задаёт вопрос о том, каким образом защищена внедряемая СУБД. Один из вероятных ответов (неправильный на мой взгляд): «БД находится во внутреннем периметре вычислительной сети и недоступна для злоумышленника». По статистике инсайдеры [1] более опасны, так как у них есть возможность легитимно исследовать уязвимости в предоставленных сервисах.
Предлагаю попробовать самостоятельно настроить уже имеющийся функционал, позволяющий повысить уровень защищённости вашей системы.

Предисловие: мне поручили задачу по написанию утилитки, которая должна проверять настройки PostgreSQL. В этой статье я хочу поделиться аналитикой возможностей данной СУБД, используемых для предотвращения несанкционированного доступа.

1. Обновление программного обеспечения.

Однозначно нужно стараться ставить последнюю версию софта или специальных патчей для закрытия обнаруженных интернет-сообществом [2] уязвимостей. На момент написания стати это — 9.5.4. Далее мы будем изменять параметры в файле postgresql.conf из каталога PGDATA, так как все из них требуют перезапуска службы СУБД.

2. Установка нестандартных настроек.

Изменим порт подключения:

port = '5333'

Конечно nmap обнаружит сервис postgres, однако детектировать активное сканирование в сети легче, чем точечное обращение к целевому хосту. При желании можно задействовать port knocking [3].

3. Ограничение числа возможных подключений.

Явно указываем ip-пользователей. Пользователям не часто выдают доступ к написанию SQL-запросов, поэтому ограничиваем количество продуктивных серверов:

listen_addresses = 'ip_1, ip_2, ip_3'

Изменяем максимальное количество одновременных подключений (+1 для суперюзера или репликации). По умолчанию стоит значение 100 (видимо исходя из работы с web-сервером), но если у вас стандартная связка с пулом 1С, то устанавливаем:

max_connections = '4'

В файле pg_hba.conf убираем записи host, hostnossl и local (последний — если не используются доменные сокеты Unix). Оставляемустанавливаем только hostssl.
Убираем стандартную учётную запись postgres и параметры all: для DATABASE указываем конкретное имя БД, а для USER — имя пользователя, которому разрешено подключение.
В поле METHOD записываем тип аутентификации пользователя + дополнительные опции. В моём примере проверяем валидность пользователей по сертификатам SSL, то есть добавляем параметр cert. У нас получаются строчки вида:

hostssl    test_database             test_user             192.168.23.2/24           cert 

Вообще здесь много свободы для фантазии, так как в postgres реализовали совместимость с GSS, SSPI, IDENT, LDAP, RADIUS и PAM.

4. Усложнение подбора пароля.

Ограниченим время для аутентификации на СУБД:

authentication_timeout = '1s'

Если не используется прямой доступ человеков, то я бы поставил значение «1s» — достаточно для ввода корректной парольной информации роботом, но недостаточно для полноценного брутфорса. Скрываем при помощи MD5 пароли пользователей PostgreSQL:

password_encryption = 'on'

Требуем, чтобы в случае успешного подключения СУБД проводила проверку доступа пользователя к БД. В случае активации этой настройки пользователей придётся создавать в формате <имя_пользователя>@<имя_рабочей_БД>.

db_user_namespace = 'on'

Если хотим использовать аутентификацию GSSAPI — устанавливаем:

krb_server_keyfile = 'файл_гсcапи'
krb_caseins_users = 'on' 

Примечание: Имена становятся регистрозависимыми. При использовании этой настройки пользователям нужно создавать имена в формате <имя_пользователя>@<имя_домена>. Соответственно db_user_namespace нужно переключить в режим off.

5. Использование архитектурных особенностей.

Если у вас используется репликация, то можно ограничить количество репликантов при помощи параметров max_wal_senders = 2 и max_replication_slots = 2. Потенциальный злоумышленник даже если и получит доступ к БД, то не сможет сразу скачать все данные бэкапом при условии, что ваши реплики находятся в рабочем состоянии.

Хотя дефолтный уровень изоляции REPEATABLE READ в Postgres более строгий, чем того требует ISO/IEC 9075, тот же стандарт SQL рекомендует [4] использовать:

default_transaction_isolation = 'serializable'

Можно задать default_transaction_read_only = on, а затем создать триггер, который будет срабатывать на изменение уровня транзакций в сессии. Таким образом можно вести журнал вносимых изменений в СУБД.

6. Шифрование канала передачи данных

Включаем ssl — защищаем КПД между PostgreSQL и клиентом:

ssl = 'on'
ssl_ciphers = 'HIGH:+3DES:!aNULL'

Параметр !aNULL запрещает вход анонимных юзеров. На всякий случай явно указываем, что наш сервер будет диктовать свои правила при установлении защищённого соединения (по дефолту так и работает):

ssl_prefer_server_ciphers = 'on'

Генерим сертификаты для SSL — можно по этой инструкции [5]. Учитываем что Postgres требует идентичности имени выданного сертификата и имени пользователя, который производит подключение. Если используем винду, то на неё можно поставить OpenSSL и выполнять те же команды. Сертификаты по умолчанию должны находиться в PGDATA:

  • сертификат нашей СУБД (без ключа):
    ssl_cert_file = 'серт.crt'	
    
  • ключ для СУБД:
    ssl_key_file = 'ключ.key'
    
  • если хотим отслеживать цепочки сертификатов, то добавляем сертификат удостоверяющего центра (УЦ):
    ssl_ca_file = 'ваш_са.crt'	
    
  • при активации предыдущего пункта можно отслеживать список отозванных сертификатов (СОС):
    ssl_crl_file = 'ваш_сос.crl'
    

Перезапускаем службу postgresql, проверяем отсутствие ошибок. На стороне пользователя устанавливаем цепочку сертификатов. Проверить корректность подключения можно при помощи утилиты psql с параметрами:

psql -U test_user sslcert=test_user.crt

Вывод в случае успешного подключения:

SSL-соединение (протокол: TLSv1.2, шифр: ECDHE-RSA-AES256-GCM-SHA384, бит: 256)

Послесловие: Начиная с версии 9.5 была добавлена политика безопасности строк [6]. Про неё и использование нативного шифрования данных в БД надеюсь у меня получиться написать отдельный текст.

Автор: postgrez4ik

Источник [7]


Сайт-источник PVSM.RU: https://www.pvsm.ru

Путь до страницы источника: https://www.pvsm.ru/informatsionnaya-bezopasnost/195904

Ссылки в тексте:

[1] По статистике инсайдеры: http://www.aselibrary.ru/press_center/journal/irr/2009/number_4/number_4_5/number_4_5966/

[2] обнаруженных интернет-сообществом: https://www.cvedetails.com/vulnerability-list/vendor_id-336/product_id-575/Postgresql-Postgresql.html

[3] port knocking: https://habrahabr.ru/post/194412/

[4] стандарт SQL рекомендует: https://www.pvsm.ruftp://ftp.iks-jena.de/mitarb/lutz/standards/sql/ansi-iso-9075-2-1999.pdf

[5] по этой инструкции: https://www.postgresql.org/docs/current/static/ssl-tcp.html

[6] политика безопасности строк: https://www.postgresql.org/docs/9.5/static/ddl-rowsecurity.html

[7] Источник: https://habrahabr.ru/post/311630/?utm_source=habrahabr&utm_medium=rss&utm_campaign=best