From 6e50fae9ec6dea35e12a65dbc46228a1e6276e07 Mon Sep 17 00:00:00 2001 From: Jan Cholasta Date: Tue, 22 Nov 2016 15:38:43 +0100 Subject: [PATCH] ipautil: move file encryption functions to installutils The encrypt_file() and decrypt_file() functions depend on ipaplatform. Move them to ipaserver.install.installutils, as they are only used for the server installer. https://fedorahosted.org/freeipa/ticket/6474 Reviewed-By: Stanislav Laznicka --- ipapython/ipautil.py | 57 ----------------- ipaserver/install/installutils.py | 80 +++++++++++++++++++++++- ipaserver/install/ipa_replica_prepare.py | 2 +- ipaserver/install/server/install.py | 13 ++-- 4 files changed, 89 insertions(+), 63 deletions(-) diff --git a/ipapython/ipautil.py b/ipapython/ipautil.py index 6a2118bc8..654fdd97e 100644 --- a/ipapython/ipautil.py +++ b/ipapython/ipautil.py @@ -49,7 +49,6 @@ from six.moves import input from six.moves import urllib from ipapython.ipa_log_manager import root_logger -from ipaplatform.paths import paths from ipapython.dn import DN GEN_PWD_LEN = 22 @@ -535,62 +534,6 @@ def backup_file(fname): if file_exists(fname): os.rename(fname, fname + ".orig") -def _ensure_nonempty_string(string, message): - if not isinstance(string, str) or not string: - raise ValueError(message) - -# uses gpg to compress and encrypt a file -def encrypt_file(source, dest, password, workdir = None): - _ensure_nonempty_string(source, 'Missing Source File') - #stat it so that we get back an exception if it does no t exist - os.stat(source) - - _ensure_nonempty_string(dest, 'Missing Destination File') - _ensure_nonempty_string(password, 'Missing Password') - - #create a tempdir so that we can clean up with easily - tempdir = tempfile.mkdtemp('', 'ipa-', workdir) - gpgdir = tempdir+"/.gnupg" - - try: - try: - #give gpg a fake dir so that we can leater remove all - #the cruft when we clean up the tempdir - os.mkdir(gpgdir) - args = [paths.GPG_AGENT, '--batch', '--homedir', gpgdir, '--daemon', paths.GPG, '--batch', '--homedir', gpgdir, '--passphrase-fd', '0', '--yes', '--no-tty', '-o', dest, '-c', source] - run(args, password, skip_output=True) - except: - raise - finally: - #job done, clean up - shutil.rmtree(tempdir, ignore_errors=True) - - -def decrypt_file(source, dest, password, workdir = None): - _ensure_nonempty_string(source, 'Missing Source File') - #stat it so that we get back an exception if it does no t exist - os.stat(source) - - _ensure_nonempty_string(dest, 'Missing Destination File') - _ensure_nonempty_string(password, 'Missing Password') - - #create a tempdir so that we can clean up with easily - tempdir = tempfile.mkdtemp('', 'ipa-', workdir) - gpgdir = tempdir+"/.gnupg" - - try: - try: - #give gpg a fake dir so that we can leater remove all - #the cruft when we clean up the tempdir - os.mkdir(gpgdir) - args = [paths.GPG_AGENT, '--batch', '--homedir', gpgdir, '--daemon', paths.GPG, '--batch', '--homedir', gpgdir, '--passphrase-fd', '0', '--yes', '--no-tty', '-o', dest, '-d', source] - run(args, password, skip_output=True) - except: - raise - finally: - #job done, clean up - shutil.rmtree(tempdir, ignore_errors=True) - class CIDict(dict): """ diff --git a/ipaserver/install/installutils.py b/ipaserver/install/installutils.py index a3e7aedea..16386979a 100644 --- a/ipaserver/install/installutils.py +++ b/ipaserver/install/installutils.py @@ -593,6 +593,84 @@ def update_hosts_file(ip_addresses, host_name, fstore): add_record_to_hosts(str(ip_address), host_name) +def _ensure_nonempty_string(string, message): + if not isinstance(string, str) or not string: + raise ValueError(message) + + +# uses gpg to compress and encrypt a file +def encrypt_file(source, dest, password, workdir=None): + _ensure_nonempty_string(source, 'Missing Source File') + # stat it so that we get back an exception if it does no t exist + os.stat(source) + + _ensure_nonempty_string(dest, 'Missing Destination File') + _ensure_nonempty_string(password, 'Missing Password') + + # create a tempdir so that we can clean up with easily + tempdir = tempfile.mkdtemp('', 'ipa-', workdir) + gpgdir = os.path.join(tempdir, ".gnupg") + + try: + try: + # give gpg a fake dir so that we can leater remove all + # the cruft when we clean up the tempdir + os.mkdir(gpgdir) + args = [paths.GPG_AGENT, + '--batch', + '--homedir', gpgdir, + '--daemon', paths.GPG, + '--batch', + '--homedir', gpgdir, + '--passphrase-fd', '0', + '--yes', + '--no-tty', + '-o', dest, + '-c', source] + ipautil.run(args, password, skip_output=True) + except: + raise + finally: + # job done, clean up + shutil.rmtree(tempdir, ignore_errors=True) + + +def decrypt_file(source, dest, password, workdir=None): + _ensure_nonempty_string(source, 'Missing Source File') + # stat it so that we get back an exception if it does no t exist + os.stat(source) + + _ensure_nonempty_string(dest, 'Missing Destination File') + _ensure_nonempty_string(password, 'Missing Password') + + # create a tempdir so that we can clean up with easily + tempdir = tempfile.mkdtemp('', 'ipa-', workdir) + gpgdir = os.path.join(tempdir, ".gnupg") + + try: + try: + # give gpg a fake dir so that we can leater remove all + # the cruft when we clean up the tempdir + os.mkdir(gpgdir) + args = [paths.GPG_AGENT, + '--batch', + '--homedir', gpgdir, + '--daemon', paths.GPG, + '--batch', + '--homedir', gpgdir, + '--passphrase-fd', '0', + '--yes', + '--no-tty', + '-o', dest, + '-d', source] + ipautil.run(args, password, skip_output=True) + except: + raise + finally: + # job done, clean up + shutil.rmtree(tempdir, ignore_errors=True) + + def expand_replica_info(filename, password): """ Decrypt and expand a replica installation file into a temporary @@ -601,7 +679,7 @@ def expand_replica_info(filename, password): top_dir = tempfile.mkdtemp("ipa") tarfile = top_dir+"/files.tar" dir_path = top_dir + "/realm_info" - ipautil.decrypt_file(filename, tarfile, password, top_dir) + decrypt_file(filename, tarfile, password, top_dir) ipautil.run(["tar", "xf", tarfile, "-C", top_dir]) os.remove(tarfile) diff --git a/ipaserver/install/ipa_replica_prepare.py b/ipaserver/install/ipa_replica_prepare.py index 069110fff..04328acbb 100644 --- a/ipaserver/install/ipa_replica_prepare.py +++ b/ipaserver/install/ipa_replica_prepare.py @@ -480,7 +480,7 @@ class ReplicaPrepare(admintool.AdminTool): self.log.info("Packaging replica information into %s", encfile) ipautil.run( [paths.TAR, "cf", replicafile, "-C", self.top_dir, "realm_info"]) - ipautil.encrypt_file( + installutils.encrypt_file( replicafile, encfile, self.dirman_password, self.top_dir) os.chmod(encfile, 0o600) diff --git a/ipaserver/install/server/install.py b/ipaserver/install/server/install.py index 9bb1e120a..decbeab19 100644 --- a/ipaserver/install/server/install.py +++ b/ipaserver/install/server/install.py @@ -19,7 +19,7 @@ from ipapython import ipautil from ipapython.dn import DN from ipapython.ipa_log_manager import root_logger from ipapython.ipautil import ( - decrypt_file, format_netloc, ipa_generate_password, run, user_input) + format_netloc, ipa_generate_password, run, user_input) from ipapython.admintool import ScriptError from ipaplatform import services from ipaplatform.paths import paths @@ -107,7 +107,10 @@ def read_cache(dm_password): top_dir = tempfile.mkdtemp("ipa") fname = "%s/cache" % top_dir try: - decrypt_file(paths.ROOT_IPA_CACHE, fname, dm_password, top_dir) + installutils.decrypt_file(paths.ROOT_IPA_CACHE, + fname, + dm_password, + top_dir) except Exception as e: shutil.rmtree(top_dir) raise Exception("Decryption of answer cache in %s failed, please " @@ -144,8 +147,10 @@ def write_cache(options): try: with open(fname, 'wb') as f: pickle.dump(options, f) - ipautil.encrypt_file(fname, paths.ROOT_IPA_CACHE, - options['dm_password'], top_dir) + installutils.encrypt_file(fname, + paths.ROOT_IPA_CACHE, + options['dm_password'], + top_dir) except IOError as e: raise Exception("Unable to cache command-line options %s" % str(e)) finally: