From 582691dd29cfcd29010ba17853f517870fb6f221 Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: May 06 2020 00:50:54 +0000 Subject: [PATCH 1/2] Issue 51042 - switch from c_rehash to openssl rehash Bug Description: 389-ds-base depends on an additional Fedora package openssl-perl for the /usr/bin/c_rehash script, which just wraps /usr/bin/openssl and drags in a perl interpreter in the process. The openssl program contains a builtin 'rehash' subcommand that does the same thing, only faster and with fewer dependencies. And openssl developers refer to c_rehash as a fallback and suggest it might be feasible to remove it entirely. Fix Description: Switch all call sites and inline documentation to refer to `openssl rehash`, and drop the unneeded dependency from the spec file. One less dependency on perl! Fixes https://pagure.io/389-ds-base/issue/51042 Author: eschwartz --- diff --git a/rpm/389-ds-base.spec.in b/rpm/389-ds-base.spec.in index 5f8c3dc..cdec146 100644 --- a/rpm/389-ds-base.spec.in +++ b/rpm/389-ds-base.spec.in @@ -289,8 +289,6 @@ BuildArch: noarch Group: Development/Libraries Requires: krb5-workstation Requires: openssl -# This is for /usr/bin/c_rehash tool -Requires: openssl-perl Requires: iproute Requires: python%{python3_pkgversion} Requires: python%{python3_pkgversion}-distro @@ -1054,20 +1052,20 @@ Ticket #173 ds-logpipe.py script's man page and script help should be updated f Ticket #196 RFE: Interpret IPV6 addresses for ACIs, replication, and chaining Ticket #218 RFE - Make RIP working with Replicated Entries Ticket #328 make sure all internal search filters are properly escaped -Ticket #329 389-admin build fails on F-18 with new apache +Ticket #329 389-admin build fails on F-18 with new apache Ticket #344 deadlock in replica_write_ruv Ticket #351 use betxn plugins by default Ticket #352 make cos, roles, views betxn aware Ticket #356 logconv.pl - RFE - track bind info Ticket #365 Audit log - clear text password in user changes Ticket #370 Opening merge qualifier CoS entry using RHDS console changes the entry. -Ticket #372 Setting nsslapd-listenhost or nsslapd-securelistenhost breaks ACI processing -Ticket #386 Overconsumption of memory with large cachememsize and heavy use of ldapmodify -Ticket #402 unhashedTicket #userTicket #password in entry extension -Ticket #408 Create a normalized dn cache -Ticket #453 db2index with -tattrname:type,type fails -Ticket #461 fix build problem with mozldap c sdk -Ticket #462 add test for include file mntent.h +Ticket #372 Setting nsslapd-listenhost or nsslapd-securelistenhost breaks ACI processing +Ticket #386 Overconsumption of memory with large cachememsize and heavy use of ldapmodify +Ticket #402 unhashedTicket #userTicket #password in entry extension +Ticket #408 Create a normalized dn cache +Ticket #453 db2index with -tattrname:type,type fails +Ticket #461 fix build problem with mozldap c sdk +Ticket #462 add test for include file mntent.h Ticket #463 different parameters of getmntent in Solaris * Tue Sep 25 2012 Rich Megginson - 1.2.11.15-1 diff --git a/src/lib389/lib389/cli_idm/client_config.py b/src/lib389/lib389/cli_idm/client_config.py index 09366cd..aeee7ac 100644 --- a/src/lib389/lib389/cli_idm/client_config.py +++ b/src/lib389/lib389/cli_idm/client_config.py @@ -39,7 +39,7 @@ ldap_uri = {ldap_uri} ldap_tls_reqcert = demand # To use cacert dir, place *.crt files in this path then run: -# /usr/bin/c_rehash /etc/openldap/certs +# /usr/bin/openssl rehash /etc/openldap/certs ldap_tls_cacertdir = /etc/openldap/certs # Path to the cacert @@ -123,7 +123,7 @@ URI {ldap_uri} DEREF never # To use cacert dir, place *.crt files in this path then run: -# /usr/bin/c_rehash /etc/openldap/certs +# /usr/bin/openssl rehash /etc/openldap/certs TLS_CACERTDIR /etc/openldap/certs # TLS_CACERT /etc/openldap/certs/ca.crt @@ -284,4 +284,3 @@ def create_parser(subparsers): display_parser = subcommands.add_parser('display', help="Display generic application parameters for LDAP connection") display_parser.set_defaults(func=display) - diff --git a/src/lib389/lib389/nss_ssl.py b/src/lib389/lib389/nss_ssl.py index d14e7ce..6d13199 100644 --- a/src/lib389/lib389/nss_ssl.py +++ b/src/lib389/lib389/nss_ssl.py @@ -271,7 +271,7 @@ only. certdetails = check_output(cmd, stderr=subprocess.STDOUT) with open('%s/ca.crt' % self._certdb, 'w') as f: f.write(ensure_str(certdetails)) - cmd = ['/usr/bin/c_rehash', self._certdb] + cmd = ['/usr/bin/openssl', 'rehash', self._certdb] self.log.debug("nss cmd: %s", format_cmd_list(cmd)) check_output(cmd, stderr=subprocess.STDOUT) return True @@ -353,7 +353,7 @@ only. self.log.debug("nss cmd: %s", format_cmd_list(cmd)) check_output(cmd, stderr=subprocess.STDOUT) - cmd = ['/usr/bin/c_rehash', self._certdb] + cmd = ['/usr/bin/openssl', 'rehash', self._certdb] self.log.debug("nss cmd: %s", format_cmd_list(cmd)) check_output(cmd, stderr=subprocess.STDOUT) @@ -611,7 +611,7 @@ only. if ca is not None: shutil.copyfile(ca, '%s/ca.crt' % self._certdb) - cmd = ['/usr/bin/c_rehash', self._certdb] + cmd = ['/usr/bin/openssl', 'rehash', self._certdb] self.log.debug("nss cmd: %s", format_cmd_list(cmd)) check_output(cmd, stderr=subprocess.STDOUT) cmd = [ @@ -968,5 +968,3 @@ only. # Remove the p12 if os.path.exists(p12_bundle): os.remove(p12_bundle) - - From 151a96785d59050a03c88409be6d51c627fe86c1 Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: May 06 2020 00:50:54 +0000 Subject: [PATCH 2/2] Issue 51042 - try to use both c_rehash and openssl rehash Bug Description: It's not possible to fully migrate to openssl rehash, since it is not available everywhere. And versions of openssl which don't have rehash, also cannot check if rehash is available, or try running it at all as a fallback, because the return value is meaningless. Fix Description: Add a utility function that checks the openssl version and parses it into a LegacyVersion class. `openssl version` should work everywhere, despite being unfriendly to parse. On versions of openssl >= 1.1.0a (LegacyVersion also considers 1.1.0 > 1.1.0a), use openssl rehash, otherwise fall back to c_rehash. Fixes https://pagure.io/389-ds-base/issue/51042 Author: eschwartz --- diff --git a/rpm/389-ds-base.spec.in b/rpm/389-ds-base.spec.in index cdec146..43d1d5b 100644 --- a/rpm/389-ds-base.spec.in +++ b/rpm/389-ds-base.spec.in @@ -289,6 +289,8 @@ BuildArch: noarch Group: Development/Libraries Requires: krb5-workstation Requires: openssl +# This is for /usr/bin/c_rehash tool, only needed for openssl < 1.1.0 +Requires: openssl-perl Requires: iproute Requires: python%{python3_pkgversion} Requires: python%{python3_pkgversion}-distro diff --git a/src/lib389/lib389/cli_idm/client_config.py b/src/lib389/lib389/cli_idm/client_config.py index aeee7ac..3cd8f3e 100644 --- a/src/lib389/lib389/cli_idm/client_config.py +++ b/src/lib389/lib389/cli_idm/client_config.py @@ -40,6 +40,8 @@ ldap_uri = {ldap_uri} ldap_tls_reqcert = demand # To use cacert dir, place *.crt files in this path then run: # /usr/bin/openssl rehash /etc/openldap/certs +# or (for older versions of openssl) +# /usr/bin/c_rehash /etc/openldap/certs ldap_tls_cacertdir = /etc/openldap/certs # Path to the cacert @@ -124,6 +126,8 @@ URI {ldap_uri} DEREF never # To use cacert dir, place *.crt files in this path then run: # /usr/bin/openssl rehash /etc/openldap/certs +# or (for older versions of openssl) +# /usr/bin/c_rehash /etc/openldap/certs TLS_CACERTDIR /etc/openldap/certs # TLS_CACERT /etc/openldap/certs/ca.crt diff --git a/src/lib389/lib389/nss_ssl.py b/src/lib389/lib389/nss_ssl.py index 6d13199..fbf708e 100644 --- a/src/lib389/lib389/nss_ssl.py +++ b/src/lib389/lib389/nss_ssl.py @@ -25,6 +25,13 @@ from lib389.lint import DSCERTLE0001, DSCERTLE0002 from lib389.utils import ensure_str, format_cmd_list import uuid +# Setuptools ships with 'packaging' module, let's use it from there +try: + from pkg_resources.extern.packaging.version import LegacyVersion +# Fallback to a normal 'packaging' module in case 'setuptools' is stripped +except: + from packaging.version import LegacyVersion + KEYBITS = 4096 CA_NAME = 'Self-Signed-CA' CERT_NAME = 'Server-Cert' @@ -218,6 +225,24 @@ only. assert not self._db_exists() return True + def openssl_rehash(self, certdir): + """ + Compatibly run c_rehash (on old openssl versions) or openssl rehash (on + new ones). Prefers openssl rehash, because openssl on versions where + the rehash command doesn't exist, also doesn't correctly set the return + code. Instead, we parse the output of `openssl version` and try to + figure out if we have a new enough version to unconditionally run rehash. + """ + openssl_version = check_output(['/usr/bin/openssl', 'version']).decode('utf-8').strip() + rehash_available = LegacyVersion(openssl_version.split(' ')[1]) >= LegacyVersion('1.1.0') + + if rehash_available: + cmd = ['/usr/bin/openssl', 'rehash', certdir] + else: + cmd = ['/usr/bin/c_rehash', certdir] + self.log.debug("nss cmd: %s", format_cmd_list(cmd)) + check_output(cmd, stderr=subprocess.STDOUT) + def create_rsa_ca(self, months=VALID): """ Create a self signed CA. @@ -271,9 +296,7 @@ only. certdetails = check_output(cmd, stderr=subprocess.STDOUT) with open('%s/ca.crt' % self._certdb, 'w') as f: f.write(ensure_str(certdetails)) - cmd = ['/usr/bin/openssl', 'rehash', self._certdb] - self.log.debug("nss cmd: %s", format_cmd_list(cmd)) - check_output(cmd, stderr=subprocess.STDOUT) + self.openssl_rehash(self._certdb) return True def rsa_ca_needs_renew(self): @@ -353,9 +376,7 @@ only. self.log.debug("nss cmd: %s", format_cmd_list(cmd)) check_output(cmd, stderr=subprocess.STDOUT) - cmd = ['/usr/bin/openssl', 'rehash', self._certdb] - self.log.debug("nss cmd: %s", format_cmd_list(cmd)) - check_output(cmd, stderr=subprocess.STDOUT) + self.openssl_rehash(self._certdb) # Import the new CA to our DB instead of the old CA cmd = [ @@ -611,9 +632,7 @@ only. if ca is not None: shutil.copyfile(ca, '%s/ca.crt' % self._certdb) - cmd = ['/usr/bin/openssl', 'rehash', self._certdb] - self.log.debug("nss cmd: %s", format_cmd_list(cmd)) - check_output(cmd, stderr=subprocess.STDOUT) + self.openssl_rehash(self._certdb) cmd = [ '/usr/bin/certutil', '-A',