Skip to content

Commit

Permalink
Merge pull request #6 from EncoreTechnologies/bugfix/duplicate-nsswit…
Browse files Browse the repository at this point in the history
…ch-rhel8-ciphers

Fixing duplicate nsswitch. Added RHEL/CentOS 8 ciphers support
  • Loading branch information
bishopbm1 authored Jan 15, 2021
2 parents bb49539 + b0d8bdd commit 57a9bda
Show file tree
Hide file tree
Showing 8 changed files with 216 additions and 82 deletions.
11 changes: 9 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,12 @@

## Development

## 0.1.0
Initial release
## v0.1.1 (2021-01-15)
* Fixed bug in client install where /etc/nsswitch.conf was declared twice for file_line
Contributed by Nick Maludy (@nmaludy)

* Fixed/added ciphers for RHEL/CentOS 8. Also allowed ciphers to be passed in empty for debugging.
Contributed by Nick Maludy (@nmaludy)

## v0.1.0 (2021-01-14)
* Initial release
58 changes: 58 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,64 @@ If true, then the parameter '--no-ui-redirect' is passed to the IPA server insta
#### `realm`
The name of the IPA realm to create or join (UPPERCASE).

### Cipher hardening on CentOS/RHEL 8

**NOTE:** These settings are automatically applied inside of `ipa::params`,
they are documented here as a reference.

```puppet
# IPA on RHEL/CentOS 8 switched to mod_ssl, away from mod_nss
# mod_ssl in RHEL/CentOS 8 uses the "system" cryto policy for its ciphers and protocols
# see:
# https://www.redhat.com/en/blog/how-customize-crypto-policies-rhel-82
# https://access.redhat.com/articles/3642912
# https://access.redhat.com/documentation/en-us/red_hat_enterprise_linux/8/html/security_hardening/using-the-system-wide-cryptographic-policies_security-hardening
$nss_ssl_ciphers = []
$nss_ssl_protocols = []
$ds_ssl_ciphers = [
# TLS 1.2
'+TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384',
'+TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384',
# TLS 1.3
'+TLS_AES_128_GCM_SHA256',
'+TLS_AES_256_GCM_SHA384',
'+TLS_CHACHA20_POLY1305_SHA256',
]
$ds_ssl_min_version = 'TLS1.2'
# Dogtag PKI Tomcat
# you _must_ set both the TLS 1.2 and 1.3 ciphers here though, otherwise you'll get an error
# when registering your clients:
# Joining realm failed: HTTP POST to URL 'https://freeipa.maludy.home:443/ipa/xml' failed. libcurl failed even to execute the HTTP transaction, explaining: SSL certificate problem: EE certificate key too weak
$pki_ssl_ciphers = [
# TLS 1.2
'+TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384',
'+TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384',
# TLS 1.3
'+TLS_AES_128_GCM_SHA256',
'+TLS_AES_256_GCM_SHA384',
'+TLS_CHACHA20_POLY1305_SHA256',
]
# PKI Tomcat doesn't, yet, support tls1_3 protocol, so leave it to 1.2
# if you try to set it to tls1_2:tls1_3 [email protected] service will fail to start
$pki_ssl_protocol_range = 'tls1_2:tls1_2'
class { 'ipa':
ipa_role => 'master',
# nss ciphers and protocols not used in CentOS 8
nss_ssl_ciphers => $nss_ssl_ciphers,
nss_ssl_protocols => $nss_ssl_protocols,
ds_ssl_ciphers => $ds_ssl_ciphers,
ds_ssl_min_version => $ds_ssl_min_version,
pki_ssl_ciphers => $pki_ssl_ciphers,
pki_ssl_protocol_range => $pki_ssl_protocol_range,
}
```

## Limitations

Expand Down
29 changes: 6 additions & 23 deletions manifests/init.pp
Original file line number Diff line number Diff line change
Expand Up @@ -194,13 +194,8 @@
Array[String] $custom_dns_forwarders = [],
String $sssd_debug_level = '3',
String $ds_password = '',
Array[String] $ds_ssl_ciphers = [
'+TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384',
'+TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384',
],
Enum['TLS1.0','TLS1.1','TLS1.2'] $ds_ssl_min_version = 'TLS1.2',
Optional[Array[String]] $ds_ssl_ciphers = $ipa::params::ds_ssl_ciphers,
Optional[Enum['', 'TLS1.0','TLS1.1','TLS1.2', 'TLS1.3']] $ds_ssl_min_version = $ipa::params::ds_ssl_min_version,
String $domain = '',
String $domain_join_password = '',
String $domain_join_principal = '',
Expand All @@ -224,23 +219,11 @@
Boolean $mkhomedir = false,
Boolean $no_dnssec_validation = false,
Boolean $no_ui_redirect = false,
Optional[Array[String]] $nss_ssl_ciphers = [
'+ecdhe_ecdsa_aes_128_gcm_sha_256',
'+ecdhe_ecdsa_aes_256_gcm_sha_384',
'+ecdhe_ecdsa_chacha20_poly1305_sha_256',
'+ecdhe_rsa_aes_128_gcm_sha_256',
'+ecdhe_rsa_aes_256_gcm_sha_384',
'+ecdhe_rsa_chacha20_poly1305_sha_256',
],
Optional[Array[String]] $nss_ssl_protocols = ['TLSv1.2'],
Optional[Array[String]] $nss_ssl_ciphers = $ipa::params::nss_ssl_ciphers,
Optional[Array[String]] $nss_ssl_protocols = $ipa::params::nss_ssl_protocols,
Optional[String] $override_homedir = undef,
Optional[Array[String]] $pki_ssl_ciphers = [
'+TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384',
'+TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384',
],
Optional[String] $pki_ssl_protocol_range = 'tls1_2:tls1_2',
Optional[Array[String]] $pki_ssl_ciphers = $ipa::params::pki_ssl_ciphers,
Optional[String] $pki_ssl_protocol_range = $ipa::params::pki_ssl_protocol_range,
String $realm = '',
Boolean $server_install_ldaputils = true,
Array[String] $sssd_services = ['nss','sudo','pam','ssh','autofs'],
Expand Down
4 changes: 2 additions & 2 deletions manifests/install/client.pp
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@
}

# Update nsswitch if autofs enabled.
~> file_line { '/etc/nsswitch.conf':
~> file_line { '/etc/nsswitch.conf_automount':
path => '/etc/nsswitch.conf',
line => 'automount: files sss',
match => '^automount: ',
Expand All @@ -116,7 +116,7 @@
}

# Update nsswitch with sudoers config
file_line { '/etc/nsswitch.conf':
file_line { '/etc/nsswitch.conf_sudoers':
path => '/etc/nsswitch.conf',
line => 'sudoers: files sss',
match => '^sudoers: ',
Expand Down
97 changes: 50 additions & 47 deletions manifests/install/server/dirsrv.pp
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
# Private class to manage IPA directory services
class ipa::install::server::dirsrv (
String $admin_password = $ipa::admin_password,
Array[String] $ds_ssl_ciphers = $ipa::ds_ssl_ciphers,
String $ds_ssl_min_version = $ipa::ds_ssl_min_version,
Optional[Array[String]] $ds_ssl_ciphers = $ipa::ds_ssl_ciphers,
Optional[String] $ds_ssl_min_version = $ipa::ds_ssl_min_version,
String $ds_password = $ipa::ds_password,
String $ipa_realm = $ipa::final_realm,
) inherits ipa {
Expand All @@ -17,62 +17,65 @@
$_ipa_realm_dash = regsubst($ipa_realm, '\.', '-', 'G')

## Idempotent check for change
$chk_ds_ssl_protocols = @("EOC")
grep -q 'sslVersionMin: ${ds_ssl_min_version}' \
/etc/dirsrv/slapd-${_ipa_realm_dash}/dse.ldif
| EOC
if $ds_ssl_min_version and !$ds_ssl_min_version.empty() {
$chk_ds_ssl_protocols = @("EOC")
grep -q 'sslVersionMin: ${ds_ssl_min_version}' \
/etc/dirsrv/slapd-${_ipa_realm_dash}/dse.ldif
| EOC

## dirsrv command to modify 'sslVersionMin' parameter
$configure_ds_ssl_protocols = @("EOC")
ldapmodify -h localhost -p 389 -D 'cn=directory manager' -w '${_ds_password}' << EOF
dn: cn=encryption,cn=config
changeType: modify
replace: sslVersionMin
sslVersionMin: ${ds_ssl_min_version}
EOF
| EOC
## dirsrv command to modify 'sslVersionMin' parameter
$configure_ds_ssl_protocols = @("EOC")
ldapmodify -h localhost -p 389 -D 'cn=directory manager' -w '${_ds_password}' << EOF
dn: cn=encryption,cn=config
changeType: modify
replace: sslVersionMin
sslVersionMin: ${ds_ssl_min_version}
EOF
| EOC

## Configure DS SSL minimum version
exec { 'ds_ssl_config':
command => $configure_ds_ssl_protocols,
path => '/bin',
unless => $chk_ds_ssl_protocols,
notify => Service["dirsrv@${_ipa_realm_dash}"],
## Configure DS SSL minimum version
exec { 'ds_ssl_config':
command => $configure_ds_ssl_protocols,
path => '/bin',
unless => $chk_ds_ssl_protocols,
notify => Service["dirsrv@${_ipa_realm_dash}"],
}
}


## Harden SSL/TLS ciphers for dirsrv
#
# Reference:
# https://directory.fedoraproject.org/docs/389ds/design/nss-cipher-design.html
$ds_ssl_ciphers_str = $ds_ssl_ciphers.join(',')
if $ds_ssl_ciphers and !$ds_ssl_ciphers.empty() {
$ds_ssl_ciphers_str = $ds_ssl_ciphers.join(',')

## Idempotent check for change
### -LLL : supresses a lot of verbose output
### -o ldif-wrap=no : Turns off line wrapping on the results so we can grep
### the full cipher suite string in one go.
$chk_ds_ssl_ciphers = @("EOC")
ldapsearch -LLL -o ldif-wrap=no -h localhost -p 389 -D 'cn=directory manager' \
-w '${_ds_password}' -b "cn=encryption,cn=config" 'nsSSL3Ciphers' \
| grep -q 'nsSSL3Ciphers: ${ds_ssl_ciphers_str}'
| EOC
## Idempotent check for change
### -LLL : supresses a lot of verbose output
### -o ldif-wrap=no : Turns off line wrapping on the results so we can grep
### the full cipher suite string in one go.
$chk_ds_ssl_ciphers = @("EOC")
ldapsearch -LLL -o ldif-wrap=no -h localhost -p 389 -D 'cn=directory manager' \
-w '${_ds_password}' -b "cn=encryption,cn=config" 'nsSSL3Ciphers' \
| grep -q 'nsSSL3Ciphers: ${ds_ssl_ciphers_str}'
| EOC

## dirsrv command to modify 'nsSSL3Ciphers' parameter
$configure_ds_ssl_ciphers = @("EOC")
ldapmodify -h localhost -p 389 -D 'cn=directory manager' -w '${_ds_password}' << EOF
dn: cn=encryption,cn=config
changeType: modify
replace: nsSSL3Ciphers
nsSSL3Ciphers: ${ds_ssl_ciphers_str}
EOF
| EOC
## dirsrv command to modify 'nsSSL3Ciphers' parameter
$configure_ds_ssl_ciphers = @("EOC")
ldapmodify -h localhost -p 389 -D 'cn=directory manager' -w '${_ds_password}' << EOF
dn: cn=encryption,cn=config
changeType: modify
replace: nsSSL3Ciphers
nsSSL3Ciphers: ${ds_ssl_ciphers_str}
EOF
| EOC

## Configure DS SSL minimum version
exec { 'ds_ssl_ciphers':
command => $configure_ds_ssl_ciphers,
path => '/bin',
unless => $chk_ds_ssl_ciphers,
notify => Service["dirsrv@${_ipa_realm_dash}"],
## Configure DS SSL minimum version
exec { 'ds_ssl_ciphers':
command => $configure_ds_ssl_ciphers,
path => '/bin',
unless => $chk_ds_ssl_ciphers,
notify => Service["dirsrv@${_ipa_realm_dash}"],
}
}

## Restart dirsrv if changed
Expand Down
6 changes: 3 additions & 3 deletions manifests/install/server/pki.pp
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
# Private class to manage IPA PKI certificate server (Dogtag)
class ipa::install::server::pki (
String $ssl_protocol_range = $ipa::pki_ssl_protocol_range,
Optional[String] $ssl_protocol_range = $ipa::pki_ssl_protocol_range,
Optional[Array[String]] $ssl_ciphers = $ipa::pki_ssl_ciphers,
) inherits ipa {
$config_file = '/etc/pki/pki-tomcat/server.xml'

# Setup PKI CA service (Dogtag) with secure SSL settings
if $ssl_protocol_range {
if $ssl_protocol_range and !$ssl_protocol_range.empty() {
exec { '/etc/pki/pki-tomcat/server.xml:sslVersionRangeStream':
command => "sed -i 's/sslVersionRangeStream=\"[^\"]*\"/sslVersionRangeStream=\"${ssl_protocol_range}\"/g' ${config_file}",
path => ['/bin', '/sbin', '/usr/sbin'],
Expand All @@ -21,7 +21,7 @@
}
}

if $ssl_ciphers {
if $ssl_ciphers and !$ssl_ciphers.empty() {
$ciphers = $ssl_ciphers.join(',')

exec { '/etc/pki/pki-tomcat/server.xml:sslRangeCiphers':
Expand Down
91 changes: 87 additions & 4 deletions manifests/params.pp
Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,92 @@
$autofs_service = 'autofs'
$sssd_service = 'sssd'

$ds_ssl_min_version_tls12 = 'TLS1.2'
$ds_ssl_ciphers_tls12 = [
'+TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384',
'+TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256',
'+TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384',
]
$ds_ssl_ciphers_tls13 = [
'+TLS_AES_128_GCM_SHA256',
'+TLS_AES_256_GCM_SHA384',
'+TLS_CHACHA20_POLY1305_SHA256',
]
$pki_ssl_ciphers_tls12 = $ds_ssl_ciphers_tls12
$pki_ssl_ciphers_tls13 = $ds_ssl_ciphers_tls13
$pki_ssl_protocol_range_tls12 = 'tls1_2:tls1_2'

$nss_ssl_ciphers_tls12 = [
'+ecdhe_ecdsa_aes_128_gcm_sha_256',
'+ecdhe_ecdsa_aes_256_gcm_sha_384',
'+ecdhe_ecdsa_chacha20_poly1305_sha_256',
'+ecdhe_rsa_aes_128_gcm_sha_256',
'+ecdhe_rsa_aes_256_gcm_sha_384',
'+ecdhe_rsa_chacha20_poly1305_sha_256',
]
$nss_ssl_protocols_tls12 = ['TLSv1.2']

case $facts['os']['family'] {
'RedHat': {
case $facts['os']['release']['major'] {
/(7)/, /(8)/: {
$service_stop_epp = 'systemctl stop <%= $service %>'
$service_restart_epp = 'systemctl restart <%= $service %>'
}
/(6)/: {
$service_stop_epp = 'service <%= $service %> stop'
$service_restart_epp = 'service <%= $service %> restart'

$ds_ssl_ciphers = undef
$ds_ssl_min_version = undef
$nss_ssl_ciphers = undef
$nss_ssl_protocols = undef
$pki_ssl_ciphers = undef
$pki_ssl_protocol_range = undef
}
/(7)/: {
$service_stop_epp = 'systemctl stop <%= $service %>'
$service_restart_epp = 'systemctl restart <%= $service %>'

$ds_ssl_ciphers = $ds_ssl_ciphers_tls12
$ds_ssl_min_version = $ds_ssl_min_version_tls12
$nss_ssl_ciphers = $nss_ssl_ciphers_tls12
$nss_ssl_protocols = $nss_ssl_protocols_tls12
$pki_ssl_ciphers = $pki_ssl_ciphers_tls12
$pki_ssl_protocol_range = $pki_ssl_protocol_range_tls12
}
/(8)/: {
$service_stop_epp = 'systemctl stop <%= $service %>'
$service_restart_epp = 'systemctl restart <%= $service %>'

# dirsrv allows for TLS 1.2 and 1.3
# note: if you don't have TLS 1.3 enabled, you'll get an SSL error when trying to register clients:
# Joining realm failed: Unable to initialize STARTTLS session
# Connect error: error:14094410:SSL routines:ssl3_read_bytes:sslv3 alert handshake failure
# Failed to bind to server!
# Retrying with pre-4.0 keytab retrieval method...
# Unable to initialize STARTTLS session
# Connect error: error:14094410:SSL routines:ssl3_read_bytes:sslv3 alert handshake failure
# Failed to bind to server!
# Failed to get keytab
# child exited with 9
$ds_ssl_ciphers = $ds_ssl_ciphers_tls12 + $ds_ssl_ciphers_tls13
$ds_ssl_min_version = $ds_ssl_min_version_tls12

# IPA on RHEL/CentOS 8 switched to mod_ssl, away from mod_nss
# mod_ssl in RHEL/CentOS 8 uses the "system" cryto policy for its ciphers and protocols
# see:
# https://www.redhat.com/en/blog/how-customize-crypto-policies-rhel-82
# https://access.redhat.com/articles/3642912
# https://access.redhat.com/documentation/en-us/red_hat_enterprise_linux/8/html/security_hardening/using-the-system-wide-cryptographic-policies_security-hardening
$nss_ssl_ciphers = []
$nss_ssl_protocols = []

# Dogtag PKI Tomcat
# you _must_ set both the TLS 1.2 and 1.3 ciphers here though, otherwise you'll get an error
# when registering your clients:
# Joining realm failed: HTTP POST to URL 'https://freeipa.maludy.home:443/ipa/xml' failed. libcurl failed even to execute the HTTP transaction, explaining: SSL certificate problem: EE certificate key too weak
$pki_ssl_ciphers = $pki_ssl_ciphers_tls12 + $pki_ssl_ciphers_tls13
# PKI Tomcat doesn't, yet, support tls1_3 protocol, so leave it to 1.2
# if you try to set it to tls1_2:tls1_3 [email protected] service will fail to start
$pki_ssl_protocol_range = $pki_ssl_protocol_range_tls12
}
default: { fail("ERROR: Unsupported RHEL version: ${facts['os']['full']}") }
}
Expand All @@ -33,6 +109,13 @@
/(16.04)/: {
$service_stop_epp = 'systemctl stop <%= $service %>'
$service_restart_epp = 'systemctl restart <%= $service %>'
$ds_ssl_ciphers = undef
$ds_ssl_min_version = undef
$nss_ssl_ciphers = undef
$nss_ssl_protocols = undef
$pki_ssl_ciphers = undef
$pki_ssl_protocol_range = undef
}
default: { fail("ERROR: Unsupported Ubuntu version: ${facts['os']['full']}") }
}
Expand Down
Loading

0 comments on commit 57a9bda

Please sign in to comment.