import ipa-4.9.8-7.el9_0
This commit is contained in:
parent
9ea9b7ab0a
commit
3a117a41e7
326
SOURCES/0024-ipatests-Tests-for-Autoprivate-group.patch
Normal file
326
SOURCES/0024-ipatests-Tests-for-Autoprivate-group.patch
Normal file
@ -0,0 +1,326 @@
|
||||
From 6b70e3c49acc55b5553101cf850fc40978861979 Mon Sep 17 00:00:00 2001
|
||||
From: Anuja More <amore@redhat.com>
|
||||
Date: Mon, 17 Jan 2022 16:57:52 +0530
|
||||
Subject: [PATCH] ipatests: Tests for Autoprivate group.
|
||||
|
||||
Added tests using posix AD trust and non posix AD trust.
|
||||
For option --auto-private-groups=[hybrid/true/false]
|
||||
|
||||
Related : https://pagure.io/freeipa/issue/8807
|
||||
|
||||
Signed-off-by: Anuja More <amore@redhat.com>
|
||||
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
|
||||
Reviewed-By: Anuja More <amore@redhat.com>
|
||||
---
|
||||
.../nightly_ipa-4-9_latest.yaml | 2 +-
|
||||
.../nightly_ipa-4-9_latest_selinux.yaml | 2 +-
|
||||
.../nightly_ipa-4-9_previous.yaml | 2 +-
|
||||
ipatests/test_integration/test_trust.py | 242 +++++++++++++++++-
|
||||
4 files changed, 240 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/ipatests/prci_definitions/nightly_ipa-4-9_latest.yaml b/ipatests/prci_definitions/nightly_ipa-4-9_latest.yaml
|
||||
index 6817421b278999c52c32b3e28dd06587e30d874f..8b1f58c4d99e744e319e6c758050a62a8d35c9ee 100644
|
||||
--- a/ipatests/prci_definitions/nightly_ipa-4-9_latest.yaml
|
||||
+++ b/ipatests/prci_definitions/nightly_ipa-4-9_latest.yaml
|
||||
@@ -1627,7 +1627,7 @@ jobs:
|
||||
build_url: '{fedora-latest-ipa-4-9/build_url}'
|
||||
test_suite: test_integration/test_trust.py
|
||||
template: *ci-ipa-4-9-latest
|
||||
- timeout: 9000
|
||||
+ timeout: 10000
|
||||
topology: *adroot_adchild_adtree_master_1client
|
||||
|
||||
fedora-latest-ipa-4-9/test_backup_and_restore_TestBackupAndRestoreTrust:
|
||||
diff --git a/ipatests/prci_definitions/nightly_ipa-4-9_latest_selinux.yaml b/ipatests/prci_definitions/nightly_ipa-4-9_latest_selinux.yaml
|
||||
index 817329756dc145fa5e6bc7aa0477e5df2a6ece5b..a11376ab836e7ed2f942c29753707e5b8e88a00f 100644
|
||||
--- a/ipatests/prci_definitions/nightly_ipa-4-9_latest_selinux.yaml
|
||||
+++ b/ipatests/prci_definitions/nightly_ipa-4-9_latest_selinux.yaml
|
||||
@@ -1743,7 +1743,7 @@ jobs:
|
||||
selinux_enforcing: True
|
||||
test_suite: test_integration/test_trust.py
|
||||
template: *ci-ipa-4-9-latest
|
||||
- timeout: 9000
|
||||
+ timeout: 10000
|
||||
topology: *adroot_adchild_adtree_master_1client
|
||||
|
||||
fedora-latest-ipa-4-9/test_backup_and_restore_TestBackupAndRestoreTrust:
|
||||
diff --git a/ipatests/prci_definitions/nightly_ipa-4-9_previous.yaml b/ipatests/prci_definitions/nightly_ipa-4-9_previous.yaml
|
||||
index 4196265c772ec393ebb8f8bbdc4af845cd6d2d24..3f8ce8b7641fdfdc27278651cbf83c2b152e1a16 100644
|
||||
--- a/ipatests/prci_definitions/nightly_ipa-4-9_previous.yaml
|
||||
+++ b/ipatests/prci_definitions/nightly_ipa-4-9_previous.yaml
|
||||
@@ -1627,7 +1627,7 @@ jobs:
|
||||
build_url: '{fedora-previous-ipa-4-9/build_url}'
|
||||
test_suite: test_integration/test_trust.py
|
||||
template: *ci-ipa-4-9-previous
|
||||
- timeout: 9000
|
||||
+ timeout: 10000
|
||||
topology: *adroot_adchild_adtree_master_1client
|
||||
|
||||
fedora-previous-ipa-4-9/test_backup_and_restore_TestBackupAndRestoreTrust:
|
||||
diff --git a/ipatests/test_integration/test_trust.py b/ipatests/test_integration/test_trust.py
|
||||
index 0634badbb6a9aa148db2e3062e866215e61e89e7..ff2dd9cc819e1c5620ce449384957a633ae6d1f0 100644
|
||||
--- a/ipatests/test_integration/test_trust.py
|
||||
+++ b/ipatests/test_integration/test_trust.py
|
||||
@@ -62,11 +62,12 @@ class BaseTestTrust(IntegrationTest):
|
||||
cls.check_sid_generation()
|
||||
tasks.sync_time(cls.master, cls.ad)
|
||||
|
||||
- cls.child_ad = cls.ad_subdomains[0]
|
||||
- cls.ad_subdomain = cls.child_ad.domain.name
|
||||
- cls.tree_ad = cls.ad_treedomains[0]
|
||||
- cls.ad_treedomain = cls.tree_ad.domain.name
|
||||
-
|
||||
+ if cls.num_ad_subdomains > 0:
|
||||
+ cls.child_ad = cls.ad_subdomains[0]
|
||||
+ cls.ad_subdomain = cls.child_ad.domain.name
|
||||
+ if cls.num_ad_treedomains > 0:
|
||||
+ cls.tree_ad = cls.ad_treedomains[0]
|
||||
+ cls.ad_treedomain = cls.tree_ad.domain.name
|
||||
# values used in workaround for
|
||||
# https://bugzilla.redhat.com/show_bug.cgi?id=1711958
|
||||
cls.srv_gc_record_name = \
|
||||
@@ -106,6 +107,63 @@ class BaseTestTrust(IntegrationTest):
|
||||
expected_text = 'iparangetype: %s\n' % expected_type
|
||||
assert expected_text in result.stdout_text
|
||||
|
||||
+ def mod_idrange_auto_private_group(
|
||||
+ self, option='false'
|
||||
+ ):
|
||||
+ """
|
||||
+ Set the auto-private-group option of the default trusted
|
||||
+ AD domain range.
|
||||
+ """
|
||||
+ tasks.kinit_admin(self.master)
|
||||
+ rangename = self.ad_domain.upper() + '_id_range'
|
||||
+ error_msg = "ipa: ERROR: no modifications to be performed"
|
||||
+ cmd = ["ipa", "idrange-mod", rangename,
|
||||
+ "--auto-private-groups", option]
|
||||
+ result = self.master.run_command(cmd, raiseonerr=False)
|
||||
+ if result.returncode != 0:
|
||||
+ tasks.assert_error(result, error_msg)
|
||||
+ tasks.clear_sssd_cache(self.master)
|
||||
+ tasks.clear_sssd_cache(self.clients[0])
|
||||
+ test = self.master.run_command(["ipa", "idrange-show", rangename])
|
||||
+ assert "Auto private groups: {0}".format(option) in test.stdout_text
|
||||
+
|
||||
+ def get_user_id(self, host, username):
|
||||
+ """
|
||||
+ User uid gid is parsed from the output of id user command.
|
||||
+ """
|
||||
+ tasks.clear_sssd_cache(self.master)
|
||||
+ tasks.clear_sssd_cache(self.clients[0])
|
||||
+ self.master.run_command(["id", username])
|
||||
+ test_id = host.run_command(["id", username])
|
||||
+ regex = r"^uid=(?P<uid>\d+).*gid=(?P<gid>\d+).*groups=(?P<groups>\d+)"
|
||||
+ match = re.match(regex, test_id.stdout_text)
|
||||
+ uid = match.group('uid')
|
||||
+ gid = match.group('gid')
|
||||
+ return uid, gid
|
||||
+
|
||||
+ @contextmanager
|
||||
+ def set_idoverrideuser(self, user, uid, gid):
|
||||
+ """
|
||||
+ Fixture to add/remove idoverrideuser for default idview,
|
||||
+ also creates idm group with the provided gid because
|
||||
+ gid overrides requires an existing group.
|
||||
+ """
|
||||
+ tasks.clear_sssd_cache(self.master)
|
||||
+ tasks.clear_sssd_cache(self.clients[0])
|
||||
+ tasks.kinit_admin(self.master)
|
||||
+ try:
|
||||
+ args = ["ipa", "idoverrideuser-add", "Default Trust View",
|
||||
+ "--gid", gid, "--uid", uid, user]
|
||||
+ self.master.run_command(args)
|
||||
+ tasks.group_add(self.master, "idgroup",
|
||||
+ extra_args=["--gid", gid])
|
||||
+ yield
|
||||
+ finally:
|
||||
+ self.master.run_command([
|
||||
+ "ipa", "idoverrideuser-del", "Default Trust View", user]
|
||||
+ )
|
||||
+ self.master.run_command(["ipa", "group-del", "idgroup"])
|
||||
+
|
||||
def remove_trust(self, ad):
|
||||
tasks.remove_trust_with_ad(self.master,
|
||||
ad.domain.name, ad.hostname)
|
||||
@@ -993,3 +1051,177 @@ class TestTrust(BaseTestTrust):
|
||||
self.master.run_command(['rm', '-f', ad_zone_file])
|
||||
tasks.configure_dns_for_trust(self.master, self.ad)
|
||||
self.remove_trust(self.ad)
|
||||
+
|
||||
+
|
||||
+class TestNonPosixAutoPrivateGroup(BaseTestTrust):
|
||||
+ """
|
||||
+ Tests for auto-private-groups option with non posix AD trust
|
||||
+ Related : https://pagure.io/freeipa/issue/8807
|
||||
+ """
|
||||
+ topology = 'line'
|
||||
+ num_ad_domains = 1
|
||||
+ num_clients = 1
|
||||
+ num_ad_subdomains = 0
|
||||
+ num_ad_treedomains = 0
|
||||
+ uid_override = "99999999"
|
||||
+ gid_override = "78878787"
|
||||
+
|
||||
+ def test_add_nonposix_trust(self):
|
||||
+ tasks.configure_dns_for_trust(self.master, self.ad)
|
||||
+ tasks.establish_trust_with_ad(
|
||||
+ self.master, self.ad_domain,
|
||||
+ extra_args=['--range-type', 'ipa-ad-trust'])
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_auto_private_groups_default_trusted_range(self, type):
|
||||
+ """
|
||||
+ Modify existing range for default trusted AD domain range
|
||||
+ with auto-private-groups set as true/hybrid/false and test
|
||||
+ user with no posix attributes.
|
||||
+ """
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ nonposixuser = "nonposixuser@%s" % self.ad_domain
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], nonposixuser)
|
||||
+ if type == "true":
|
||||
+ assert uid == gid
|
||||
+ else:
|
||||
+ test_group = self.clients[0].run_command(["id", nonposixuser])
|
||||
+ gid_str = "gid={0}(domain users@{1})".format(gid, self.ad_domain)
|
||||
+ grp_str = "groups={0}(domain users@{1})".format(gid,
|
||||
+ self.ad_domain)
|
||||
+ assert gid_str in test_group.stdout_text
|
||||
+ assert grp_str in test_group.stdout_text
|
||||
+ assert uid != gid
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_idoverride_with_auto_private_group(self, type):
|
||||
+ """
|
||||
+ Override ad trusted user in default trust view
|
||||
+ and set auto-private-groups=[hybrid,true,false]
|
||||
+ and ensure that overridden values takes effect.
|
||||
+ """
|
||||
+ nonposixuser = "nonposixuser@%s" % self.ad_domain
|
||||
+ with self.set_idoverrideuser(nonposixuser,
|
||||
+ self.uid_override,
|
||||
+ self.gid_override
|
||||
+ ):
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], nonposixuser)
|
||||
+ assert (uid == self.uid_override and gid == self.gid_override)
|
||||
+ test_group = self.clients[0].run_command(
|
||||
+ ["id", nonposixuser]).stdout_text
|
||||
+ assert "domain users@{0}".format(self.ad_domain) in test_group
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_nonposixuser_nondefault_primary_group(self, type):
|
||||
+ """
|
||||
+ Test for non default primary group.
|
||||
+ For hybrid/false gid corresponds to the group testgroup1.
|
||||
+ """
|
||||
+ nonposixuser1 = "nonposixuser1@%s" % self.ad_domain
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], nonposixuser1)
|
||||
+ if type == "true":
|
||||
+ assert uid == gid
|
||||
+ else:
|
||||
+ test_group = self.clients[0].run_command(["id", nonposixuser1])
|
||||
+ gid_str = "gid={0}(testgroup1@{1})".format(gid, self.ad_domain)
|
||||
+ group = "groups={0}(testgroup1@{1})".format(gid, self.ad_domain)
|
||||
+ assert (gid_str in test_group.stdout_text
|
||||
+ and group in test_group.stdout_text)
|
||||
+
|
||||
+
|
||||
+class TestPosixAutoPrivateGroup(BaseTestTrust):
|
||||
+ """
|
||||
+ Tests for auto-private-groups option with posix AD trust
|
||||
+ Related : https://pagure.io/freeipa/issue/8807
|
||||
+ """
|
||||
+ topology = 'line'
|
||||
+ num_ad_domains = 1
|
||||
+ num_clients = 1
|
||||
+ num_ad_subdomains = 0
|
||||
+ num_ad_treedomains = 0
|
||||
+ uid_override = "99999999"
|
||||
+ gid_override = "78878787"
|
||||
+
|
||||
+ def test_add_posix_trust(self):
|
||||
+ tasks.configure_dns_for_trust(self.master, self.ad)
|
||||
+ tasks.establish_trust_with_ad(
|
||||
+ self.master, self.ad_domain,
|
||||
+ extra_args=['--range-type', 'ipa-ad-trust-posix'])
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_gidnumber_not_corresponding_existing_group(self, type):
|
||||
+ """
|
||||
+ Test checks that sssd can resolve AD users which
|
||||
+ contain posix attributes (uidNumber and gidNumber)
|
||||
+ but there is no group with the corresponding gidNumber.
|
||||
+ """
|
||||
+ posixuser = "testuser2@%s" % self.ad_domain
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ if type != "true":
|
||||
+ result = self.clients[0].run_command(['id', posixuser],
|
||||
+ raiseonerr=False)
|
||||
+ tasks.assert_error(result, "no such user")
|
||||
+ else:
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], posixuser)
|
||||
+ assert uid == gid
|
||||
+ assert uid == '10060'
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_only_uid_number_auto_private_group_default(self, type):
|
||||
+ """
|
||||
+ Test checks that posix user with only uidNumber defined
|
||||
+ and gidNumber not set, auto-private-group
|
||||
+ is set to false/true/hybrid
|
||||
+ """
|
||||
+ posixuser = "testuser1@%s" % self.ad_domain
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ if type == "true":
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], posixuser)
|
||||
+ assert uid == gid
|
||||
+ else:
|
||||
+ for host in [self.master, self.clients[0]]:
|
||||
+ result = host.run_command(['id', posixuser], raiseonerr=False)
|
||||
+ tasks.assert_error(result, "no such user")
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_auto_private_group_primary_group(self, type):
|
||||
+ """
|
||||
+ Test checks that AD users which contain posix attributes
|
||||
+ (uidNumber and gidNumber) and there is primary group
|
||||
+ with gid number defined.
|
||||
+ """
|
||||
+ posixuser = "testuser@%s" % self.ad_domain
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], posixuser)
|
||||
+ test_grp = self.clients[0].run_command(["id", posixuser])
|
||||
+ assert uid == '10042'
|
||||
+ if type == "true":
|
||||
+ assert uid == gid
|
||||
+ groups = "groups=10042(testuser@{0}),10047(testgroup@{1})".format(
|
||||
+ self.ad_domain, self.ad_domain)
|
||||
+ assert groups in test_grp.stdout_text
|
||||
+ else:
|
||||
+ assert gid == '10047'
|
||||
+ groups = "10047(testgroup@{0})".format(self.ad_domain)
|
||||
+ assert groups in test_grp.stdout_text
|
||||
+
|
||||
+ @pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
+ def test_idoverride_with_auto_private_group(self, type):
|
||||
+ """
|
||||
+ Override ad trusted user in default trust view
|
||||
+ and set auto-private-groups=[hybrid,true,false]
|
||||
+ and ensure that overridden values takes effect.
|
||||
+ """
|
||||
+ posixuser = "testuser@%s" % self.ad_domain
|
||||
+ with self.set_idoverrideuser(posixuser,
|
||||
+ self.uid_override,
|
||||
+ self.gid_override):
|
||||
+ self.mod_idrange_auto_private_group(type)
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], posixuser)
|
||||
+ assert(uid == self.uid_override
|
||||
+ and gid == self.gid_override)
|
||||
+ result = self.clients[0].run_command(['id', posixuser])
|
||||
+ assert "10047(testgroup@{0})".format(
|
||||
+ self.ad_domain) in result.stdout_text
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,43 @@
|
||||
From 84381001d2e114b1f29fe89e16155c040b56b80f Mon Sep 17 00:00:00 2001
|
||||
From: Anuja More <amore@redhat.com>
|
||||
Date: Thu, 10 Feb 2022 17:07:45 +0530
|
||||
Subject: [PATCH] mark xfail for
|
||||
test_idoverride_with_auto_private_group[hybrid]
|
||||
|
||||
Related : https://github.com/SSSD/sssd/issues/5989
|
||||
|
||||
Signed-off-by: Anuja More <amore@redhat.com>
|
||||
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
|
||||
Reviewed-By: Anuja More <amore@redhat.com>
|
||||
---
|
||||
ipatests/test_integration/test_trust.py | 7 ++++++-
|
||||
1 file changed, 6 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/ipatests/test_integration/test_trust.py b/ipatests/test_integration/test_trust.py
|
||||
index ff2dd9cc819e1c5620ce449384957a633ae6d1f0..54bd154628cb8fb063d9839d7928acd37647e2a4 100644
|
||||
--- a/ipatests/test_integration/test_trust.py
|
||||
+++ b/ipatests/test_integration/test_trust.py
|
||||
@@ -15,6 +15,7 @@ from ipaplatform.paths import paths
|
||||
from ipatests.test_integration.base import IntegrationTest
|
||||
from ipatests.pytest_ipa.integration import tasks
|
||||
from ipatests.pytest_ipa.integration import fips
|
||||
+from ipatests.util import xfail_context
|
||||
from ipapython.dn import DN
|
||||
from collections import namedtuple
|
||||
from contextlib import contextmanager
|
||||
@@ -1110,7 +1111,11 @@ class TestNonPosixAutoPrivateGroup(BaseTestTrust):
|
||||
assert (uid == self.uid_override and gid == self.gid_override)
|
||||
test_group = self.clients[0].run_command(
|
||||
["id", nonposixuser]).stdout_text
|
||||
- assert "domain users@{0}".format(self.ad_domain) in test_group
|
||||
+ version = tasks.get_sssd_version(self.clients[0])
|
||||
+ with xfail_context(version <= tasks.parse_version('2.6.3')
|
||||
+ and type == "hybrid",
|
||||
+ 'https://github.com/SSSD/sssd/issues/5989'):
|
||||
+ assert "domain users@{0}".format(self.ad_domain) in test_group
|
||||
|
||||
@pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
def test_nonposixuser_nondefault_primary_group(self, type):
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,38 @@
|
||||
From 7ad500e5d3f7d9af81e8a3137158672c6fafb0b4 Mon Sep 17 00:00:00 2001
|
||||
From: Anuja More <amore@redhat.com>
|
||||
Date: Thu, 10 Feb 2022 17:29:45 +0530
|
||||
Subject: [PATCH] Mark xfail
|
||||
test_gidnumber_not_corresponding_existing_group[true,hybrid]
|
||||
|
||||
Related : https://github.com/SSSD/sssd/issues/5988
|
||||
|
||||
Signed-off-by: Anuja More <amore@redhat.com>
|
||||
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
|
||||
Reviewed-By: Anuja More <amore@redhat.com>
|
||||
---
|
||||
ipatests/test_integration/test_trust.py | 9 ++++++---
|
||||
1 file changed, 6 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/ipatests/test_integration/test_trust.py b/ipatests/test_integration/test_trust.py
|
||||
index 54bd154628cb8fb063d9839d7928acd37647e2a4..c128378151ec4c0fb295823d75f2a04df2f7ffa0 100644
|
||||
--- a/ipatests/test_integration/test_trust.py
|
||||
+++ b/ipatests/test_integration/test_trust.py
|
||||
@@ -1169,9 +1169,12 @@ class TestPosixAutoPrivateGroup(BaseTestTrust):
|
||||
raiseonerr=False)
|
||||
tasks.assert_error(result, "no such user")
|
||||
else:
|
||||
- (uid, gid) = self.get_user_id(self.clients[0], posixuser)
|
||||
- assert uid == gid
|
||||
- assert uid == '10060'
|
||||
+ sssd_version = tasks.get_sssd_version(self.clients[0])
|
||||
+ with xfail_context(sssd_version <= tasks.parse_version('2.6.3'),
|
||||
+ 'https://github.com/SSSD/sssd/issues/5988'):
|
||||
+ (uid, gid) = self.get_user_id(self.clients[0], posixuser)
|
||||
+ assert uid == gid
|
||||
+ assert uid == '10060'
|
||||
|
||||
@pytest.mark.parametrize('type', ['hybrid', 'true', "false"])
|
||||
def test_only_uid_number_auto_private_group_default(self, type):
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,108 @@
|
||||
From a51900819bd5332bc05ec9d513f062844b3a7763 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Fri, 25 Feb 2022 08:58:24 +0200
|
||||
Subject: [PATCH] KRB instance: make provision to work with crypto policy
|
||||
without SHA-1 HMAC types
|
||||
|
||||
RHEL 9 system-wide crypto policies aim at eventual removal of SHA-1 use.
|
||||
|
||||
Due to bootstrapping process, force explicitly supported encryption
|
||||
types in kdc.conf or we may end up with AES128-SHA1 and AES256-SHA2 only
|
||||
in FIPS mode at bootstrap time which then fails to initialize kadmin
|
||||
principals requiring use of AES256-SHA2 and AES128-SHA2.
|
||||
|
||||
Camellia ciphers must be filtered out in FIPS mode, we do that already
|
||||
in the kerberos.ldif.
|
||||
|
||||
At this point we are not changing the master key encryption type to
|
||||
AES256-SHA2 because upgrading existing deployments is complicated and
|
||||
at the time when a replica configuration is deployed, we don't know what
|
||||
is the encryption type of the master key of the original server as well.
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Julien Rische <jrische@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
install/share/kdc.conf.template | 3 ++-
|
||||
install/share/kerberos.ldif | 2 ++
|
||||
ipaserver/install/krbinstance.py | 21 ++++++++++++++++++++-
|
||||
3 files changed, 24 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/install/share/kdc.conf.template b/install/share/kdc.conf.template
|
||||
index 232fedc445f660c30a88d8844d9f1b6042db41a7..685d42f3b7fb263e86b7a6db98be8bcc53e7bbe6 100644
|
||||
--- a/install/share/kdc.conf.template
|
||||
+++ b/install/share/kdc.conf.template
|
||||
@@ -6,7 +6,8 @@
|
||||
|
||||
[realms]
|
||||
$REALM = {
|
||||
- master_key_type = aes256-cts
|
||||
+ master_key_type = $MASTER_KEY_TYPE
|
||||
+ supported_enctypes = $SUPPORTED_ENCTYPES
|
||||
max_life = 7d
|
||||
max_renewable_life = 14d
|
||||
acl_file = $KRB5KDC_KADM5_ACL
|
||||
diff --git a/install/share/kerberos.ldif b/install/share/kerberos.ldif
|
||||
index 3b75b445641fd86e2029ceb51e479c6ccb17856c..51e5cf9bca4b0b2cf2e1fe3ec85777deb61b76b0 100644
|
||||
--- a/install/share/kerberos.ldif
|
||||
+++ b/install/share/kerberos.ldif
|
||||
@@ -28,6 +28,8 @@ ${FIPS}krbSupportedEncSaltTypes: camellia256-cts-cmac:normal
|
||||
${FIPS}krbSupportedEncSaltTypes: camellia256-cts-cmac:special
|
||||
krbMaxTicketLife: 86400
|
||||
krbMaxRenewableAge: 604800
|
||||
+krbDefaultEncSaltTypes: aes256-sha2:special
|
||||
+krbDefaultEncSaltTypes: aes128-sha2:special
|
||||
krbDefaultEncSaltTypes: aes256-cts:special
|
||||
krbDefaultEncSaltTypes: aes128-cts:special
|
||||
|
||||
diff --git a/ipaserver/install/krbinstance.py b/ipaserver/install/krbinstance.py
|
||||
index 216c1032d8abd9fc119d98d8f9976ce17d246ea4..852edcd9978f4a47d355e206fbb4a513ea699865 100644
|
||||
--- a/ipaserver/install/krbinstance.py
|
||||
+++ b/ipaserver/install/krbinstance.py
|
||||
@@ -51,6 +51,14 @@ logger = logging.getLogger(__name__)
|
||||
|
||||
PKINIT_ENABLED = 'pkinitEnabled'
|
||||
|
||||
+MASTER_KEY_TYPE = 'aes256-sha1'
|
||||
+SUPPORTED_ENCTYPES = ('aes256-sha2:special', 'aes128-sha2:special',
|
||||
+ 'aes256-sha2:normal', 'aes128-sha2:normal',
|
||||
+ 'aes256-cts:special', 'aes128-cts:special',
|
||||
+ 'aes256-cts:normal', 'aes128-cts:normal',
|
||||
+ 'camellia256-cts:special', 'camellia128-cts:special',
|
||||
+ 'camellia256-cts:normal', 'camellia128-cts:normal')
|
||||
+
|
||||
|
||||
def get_pkinit_request_ca():
|
||||
"""
|
||||
@@ -252,6 +260,7 @@ class KrbInstance(service.Service):
|
||||
else:
|
||||
includes = ''
|
||||
|
||||
+ fips_enabled = tasks.is_fips_enabled()
|
||||
self.sub_dict = dict(FQDN=self.fqdn,
|
||||
IP=self.ip,
|
||||
PASSWORD=self.kdc_password,
|
||||
@@ -269,7 +278,17 @@ class KrbInstance(service.Service):
|
||||
KDC_CA_BUNDLE_PEM=paths.KDC_CA_BUNDLE_PEM,
|
||||
CA_BUNDLE_PEM=paths.CA_BUNDLE_PEM,
|
||||
INCLUDES=includes,
|
||||
- FIPS='#' if tasks.is_fips_enabled() else '')
|
||||
+ FIPS='#' if fips_enabled else '')
|
||||
+
|
||||
+ if fips_enabled:
|
||||
+ supported_enctypes = list(
|
||||
+ filter(lambda e: not e.startswith('camelia'),
|
||||
+ SUPPORTED_ENCTYPES))
|
||||
+ else:
|
||||
+ supported_enctypes = SUPPORTED_ENCTYPES
|
||||
+ self.sub_dict['SUPPORTED_ENCTYPES'] = ' '.join(supported_enctypes)
|
||||
+
|
||||
+ self.sub_dict['MASTER_KEY_TYPE'] = MASTER_KEY_TYPE
|
||||
|
||||
# IPA server/KDC is not a subdomain of default domain
|
||||
# Proper domain-realm mapping needs to be specified
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,58 @@
|
||||
From b016683552a58f9cc2a05cf628cc467234eaf599 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Mon, 28 Feb 2022 11:10:49 +0200
|
||||
Subject: [PATCH] tests: ensure AD-SUPPORT subpolicy is active
|
||||
|
||||
Use AD-SUPPORT subpolicy when testing trust to Active Directory in FIPS
|
||||
mode. This is required in FIPS mode due to AD not supporting Kerberos
|
||||
AES-bases encryption types using FIPS-compliant PBKDF2 and KDF, as
|
||||
defined in RFC 8009.
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Julien Rische <jrische@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
ipatests/pytest_ipa/integration/fips.py | 6 ++++++
|
||||
ipatests/pytest_ipa/integration/tasks.py | 3 +++
|
||||
2 files changed, 9 insertions(+)
|
||||
|
||||
diff --git a/ipatests/pytest_ipa/integration/fips.py b/ipatests/pytest_ipa/integration/fips.py
|
||||
index 694ec8a9927da917fe99482094f68540a1032c14..b33aa91b14552d6f47191c913db4f974a5a5948c 100644
|
||||
--- a/ipatests/pytest_ipa/integration/fips.py
|
||||
+++ b/ipatests/pytest_ipa/integration/fips.py
|
||||
@@ -68,3 +68,9 @@ def disable_userspace_fips(host):
|
||||
# sanity check
|
||||
assert not is_fips_enabled(host)
|
||||
host.run_command(["openssl", "md5", "/dev/null"])
|
||||
+
|
||||
+
|
||||
+def enable_crypto_subpolicy(host, subpolicy):
|
||||
+ result = host.run_command(["update-crypto-policies", "--show"])
|
||||
+ policy = result.stdin_text.strip() + ":" + subpolicy
|
||||
+ host.run_command(["update-crypto-policies", "--set", policy])
|
||||
diff --git a/ipatests/pytest_ipa/integration/tasks.py b/ipatests/pytest_ipa/integration/tasks.py
|
||||
index 7e1b7c24dab00986ff6e75430bf55e55dd1a6b8e..13d84e23fa7dc8a5e562e8498c9142e2bcad696a 100755
|
||||
--- a/ipatests/pytest_ipa/integration/tasks.py
|
||||
+++ b/ipatests/pytest_ipa/integration/tasks.py
|
||||
@@ -66,6 +66,7 @@ from .env_config import env_to_script
|
||||
from .host import Host
|
||||
from .firewall import Firewall
|
||||
from .resolver import ResolvedResolver
|
||||
+from .fips import is_fips_enabled, enable_crypto_subpolicy
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -362,6 +363,8 @@ def install_master(host, setup_dns=True, setup_kra=False, setup_adtrust=False,
|
||||
if setup_adtrust:
|
||||
args.append('--setup-adtrust')
|
||||
fw_services.append("freeipa-trust")
|
||||
+ if is_fips_enabled(host):
|
||||
+ enable_crypto_subpolicy(host, "AD-SUPPORT")
|
||||
if external_ca:
|
||||
args.append('--external-ca')
|
||||
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,46 @@
|
||||
From 49d9147e38c5b50c52a1ebc7283753c779c2f81f Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Thu, 3 Mar 2022 14:38:57 +0200
|
||||
Subject: [PATCH] ipatests: extend AES keyset to SHA2-based ones
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Julien Rische <jrische@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
ipaserver/install/plugins/adtrust.py | 3 ++-
|
||||
ipatests/pytest_ipa/integration/tasks.py | 3 ++-
|
||||
2 files changed, 4 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/ipaserver/install/plugins/adtrust.py b/ipaserver/install/plugins/adtrust.py
|
||||
index 5b87ac47c6919de287b07c9ceef7ae22e1e79398..67e372bdb40a0b1f6815f107fc567f0ae056dad8 100644
|
||||
--- a/ipaserver/install/plugins/adtrust.py
|
||||
+++ b/ipaserver/install/plugins/adtrust.py
|
||||
@@ -754,7 +754,8 @@ class update_host_cifs_keytabs(Updater):
|
||||
"""
|
||||
|
||||
host_princ_template = "host/{master}@{realm}"
|
||||
- valid_etypes = ['aes256-cts-hmac-sha1-96', 'aes128-cts-hmac-sha1-96']
|
||||
+ valid_etypes = ['aes256-cts-hmac-sha384-192', 'aes128-cts-hmac-sha256-128',
|
||||
+ 'aes256-cts-hmac-sha1-96', 'aes128-cts-hmac-sha1-96']
|
||||
|
||||
def extract_key_refs(self, keytab):
|
||||
host_princ = self.host_princ_template.format(
|
||||
diff --git a/ipatests/pytest_ipa/integration/tasks.py b/ipatests/pytest_ipa/integration/tasks.py
|
||||
index 13d84e23fa7dc8a5e562e8498c9142e2bcad696a..d06f8eb2cf6c36956ec200a1abb7c488d1dad9aa 100755
|
||||
--- a/ipatests/pytest_ipa/integration/tasks.py
|
||||
+++ b/ipatests/pytest_ipa/integration/tasks.py
|
||||
@@ -2261,7 +2261,8 @@ class KerberosKeyCopier:
|
||||
copier.copy_keys('/etc/krb5.keytab', tmpname, replacement=replacement)
|
||||
"""
|
||||
host_princ_template = "host/{master}@{realm}"
|
||||
- valid_etypes = ['aes256-cts-hmac-sha1-96', 'aes128-cts-hmac-sha1-96']
|
||||
+ valid_etypes = ['aes256-cts-hmac-sha384-192', 'aes128-cts-hmac-sha256-128',
|
||||
+ 'aes256-cts-hmac-sha1-96', 'aes128-cts-hmac-sha1-96']
|
||||
|
||||
def __init__(self, host):
|
||||
self.host = host
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,35 @@
|
||||
From ee39de46a1c1ea96bbe524f159ae435319b2d072 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Thu, 3 Mar 2022 14:43:11 +0200
|
||||
Subject: [PATCH] freeipa.spec: bump crypto-policies dependency for CentOS 9
|
||||
Stream
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Julien Rische <jrische@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
freeipa.spec.in | 6 ++++++
|
||||
1 file changed, 6 insertions(+)
|
||||
|
||||
diff --git a/freeipa.spec.in b/freeipa.spec.in
|
||||
index 0b24febc0baff6f60fd2b4cb254971bd3e3aa3b8..c1d81605068c6fc3e6c765ad01c4967fa9f03c95 100755
|
||||
--- a/freeipa.spec.in
|
||||
+++ b/freeipa.spec.in
|
||||
@@ -695,6 +695,12 @@ Provides: %{name}-admintools = %{version}-%{release}
|
||||
Conflicts: crypto-policies < 20200629-1
|
||||
%endif
|
||||
|
||||
+%if 0%{?rhel} == 9
|
||||
+# Conflict with crypto-policies < 20220223-1 to get upgraded AD-SUPPORT and
|
||||
+# AD-SUPPORT-LEGACY policy modules
|
||||
+Conflicts: crypto-policies < 20220223-1
|
||||
+%endif
|
||||
+
|
||||
%description client
|
||||
IPA is an integrated solution to provide centrally managed Identity (users,
|
||||
hosts, services), Authentication (SSO, 2FA), and Authorization
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,56 @@
|
||||
From 3e54c4362490b4da1b6cb3e141bb6e08fecc58c0 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Mon, 14 Mar 2022 13:23:04 +0200
|
||||
Subject: [PATCH] Kerberos instance: default to AES256-SHA2 for master key
|
||||
encryption
|
||||
|
||||
KDC configuration in /var/kerberos/krb5kdc/kdc.conf is generated from
|
||||
the template in install/share/kdc.conf.template. Master key encryption
|
||||
type specified there is used to bootstrap the master key in LDAP
|
||||
database. Once it is done, actual deployment does not rely on the
|
||||
master_key_type value anymore. The actual master key(s) get loaded from
|
||||
LDAP database where they stored in a BER-encoded format, preserving all
|
||||
parameters, including encryption type.
|
||||
|
||||
This means we can safely migrate to AES256-SHA2 as the default master
|
||||
key encryption type for new installations. Replicas will get their
|
||||
master key encryption type details from the server they were provisioned
|
||||
from.
|
||||
|
||||
MIT Kerberos supports AES256-SHA2 since 1.15 (2015), meaning RHEL 7.4 is
|
||||
the earliest supported version as it provides krb5 1.15.1. Current
|
||||
supported RHEL 7 version is RHEL 7.9. Since RHEL 6 already cannot be
|
||||
used as a replica to IPA 4.5+ due to a domain level 1 upgrade, this
|
||||
change does not affect old releases.
|
||||
|
||||
Migration from the previously deployed master key encryption type is
|
||||
described by MIT Kerberos upstream in
|
||||
http://web.mit.edu/kerberos/krb5-latest/doc/admin/advanced/retiring-des.html#the-database-master-key
|
||||
|
||||
One would need to use '-x ipa-setup-override-restrictions' to allow
|
||||
the `kdb5_util` utility to modify the data over IPA KDB driver.
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
ipaserver/install/krbinstance.py | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/ipaserver/install/krbinstance.py b/ipaserver/install/krbinstance.py
|
||||
index 01b3309d50c0e8025e3381eac577225b1ef0be9d..a5eaa7b17133498f08e84d01c90764236e8ebe84 100644
|
||||
--- a/ipaserver/install/krbinstance.py
|
||||
+++ b/ipaserver/install/krbinstance.py
|
||||
@@ -51,7 +51,7 @@ logger = logging.getLogger(__name__)
|
||||
|
||||
PKINIT_ENABLED = 'pkinitEnabled'
|
||||
|
||||
-MASTER_KEY_TYPE = 'aes256-sha1'
|
||||
+MASTER_KEY_TYPE = 'aes256-sha2'
|
||||
SUPPORTED_ENCTYPES = ('aes256-sha2:special', 'aes128-sha2:special',
|
||||
'aes256-sha2:normal', 'aes128-sha2:normal',
|
||||
'aes256-cts:special', 'aes128-cts:special',
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,44 @@
|
||||
From 3baae8d1bd0a0c4c707314524289e86e6ecbc0df Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Mon, 14 Mar 2022 21:09:36 +0200
|
||||
Subject: [PATCH] test_otp: do not use paramiko unless it is really needed
|
||||
|
||||
paramiko cannot be used in FIPS mode. We have few tests that import
|
||||
generic methods from test_otp (add_token/del_token) and those tests fail
|
||||
in FIPS mode due to unconditional 'import paramiko'.
|
||||
|
||||
Instead, move 'import paramiko' to the ssh_2f() helper which is not used
|
||||
in FIPS mode (the whole SSH 2FA test is skipped then).
|
||||
|
||||
Related: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
ipatests/test_integration/test_otp.py | 3 ++-
|
||||
1 file changed, 2 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/ipatests/test_integration/test_otp.py b/ipatests/test_integration/test_otp.py
|
||||
index bec76d205bf37699483b65ebbc5613cbbb466bb4..04bef4626077e727654898b07a76acab4f1d5971 100644
|
||||
--- a/ipatests/test_integration/test_otp.py
|
||||
+++ b/ipatests/test_integration/test_otp.py
|
||||
@@ -5,7 +5,6 @@
|
||||
"""
|
||||
import base64
|
||||
import logging
|
||||
-import paramiko
|
||||
import pytest
|
||||
import re
|
||||
import time
|
||||
@@ -102,6 +101,8 @@ def ssh_2f(hostname, username, answers_dict, port=22):
|
||||
logger.info(
|
||||
"Answer to ssh prompt is: '%s'", answers_dict[prmpt_str])
|
||||
return resp
|
||||
+
|
||||
+ import paramiko
|
||||
trans = paramiko.Transport((hostname, port))
|
||||
trans.connect()
|
||||
trans.auth_interactive(username, answer_handler)
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,44 @@
|
||||
From 2e70535f74e7d9dd76e728eca1119ce522fd138a Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Date: Tue, 15 Mar 2022 11:39:46 +0200
|
||||
Subject: [PATCH] test_krbtpolicy: skip SPAKE-related tests in FIPS mode
|
||||
|
||||
SPAKE is based on the crypto primitives which are not FIPS compliant
|
||||
yet. This means that in FIPS mode use of 'hardened' authentication
|
||||
indicator is not possible. Skip corresponding tests in FIPS mode.
|
||||
|
||||
Related: https://pagure.io/freeipa/issue/9119
|
||||
|
||||
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
|
||||
---
|
||||
ipatests/test_integration/test_krbtpolicy.py | 6 ++++++
|
||||
1 file changed, 6 insertions(+)
|
||||
|
||||
diff --git a/ipatests/test_integration/test_krbtpolicy.py b/ipatests/test_integration/test_krbtpolicy.py
|
||||
index 9489fbc97b7836aecf491b57627f254d4849eb56..eae16247bdfb195c1d91209cf2d11eac4c25018f 100644
|
||||
--- a/ipatests/test_integration/test_krbtpolicy.py
|
||||
+++ b/ipatests/test_integration/test_krbtpolicy.py
|
||||
@@ -105,6 +105,9 @@ class TestPWPolicy(IntegrationTest):
|
||||
|
||||
def test_krbtpolicy_password_and_hardended(self):
|
||||
"""Test a pwd and hardened kerberos ticket policy with 10min tickets"""
|
||||
+ if self.master.is_fips_mode:
|
||||
+ pytest.skip("SPAKE pre-auth is not compatible with FIPS mode")
|
||||
+
|
||||
master = self.master
|
||||
master.run_command(['ipa', 'user-mod', USER1,
|
||||
'--user-auth-type', 'password',
|
||||
@@ -133,6 +136,9 @@ class TestPWPolicy(IntegrationTest):
|
||||
|
||||
def test_krbtpolicy_hardended(self):
|
||||
"""Test a hardened kerberos ticket policy with 30min tickets"""
|
||||
+ if self.master.is_fips_mode:
|
||||
+ pytest.skip("SPAKE pre-auth is not compatible with FIPS mode")
|
||||
+
|
||||
master = self.master
|
||||
master.run_command(['ipa', 'user-mod', USER1,
|
||||
'--user-auth-type', 'hardened'])
|
||||
--
|
||||
2.34.1
|
||||
|
555
SOURCES/0034-Support-AES-for-KRA-archival-wrapping.patch
Normal file
555
SOURCES/0034-Support-AES-for-KRA-archival-wrapping.patch
Normal file
@ -0,0 +1,555 @@
|
||||
From 895e99b6843c2fa2274acab824607c33c1a560a4 Mon Sep 17 00:00:00 2001
|
||||
From: Christian Heimes <cheimes@redhat.com>
|
||||
Date: Mon, 7 Oct 2019 14:13:03 +0200
|
||||
Subject: [PATCH] Support AES for KRA archival wrapping
|
||||
|
||||
The vault plugin has used TripleDES (des-ede3-cbc) as default wrapping
|
||||
algorithm since the plugin was introduced. Allow use of AES-128-CBC as
|
||||
alternative wrapping algorithm for transport of secrets.
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/6524
|
||||
|
||||
Signed-off-by: Christian Heimes <cheimes@redhat.com>
|
||||
Reviewed-By: Christian Heimes <cheimes@redhat.com>
|
||||
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
---
|
||||
API.txt | 7 +-
|
||||
VERSION.m4 | 5 +-
|
||||
ipaclient/plugins/vault.py | 155 +++++++++++++++++++++++++------------
|
||||
ipalib/capabilities.py | 4 +
|
||||
ipalib/constants.py | 12 +++
|
||||
ipaserver/plugins/vault.py | 61 ++++++++++++---
|
||||
6 files changed, 180 insertions(+), 64 deletions(-)
|
||||
|
||||
diff --git a/API.txt b/API.txt
|
||||
index 576fa7c51e31886b257ccf176aaf232c0f2ea5ee..f95f2c8457e39f2268386a8a2336952d3285e008 100644
|
||||
--- a/API.txt
|
||||
+++ b/API.txt
|
||||
@@ -6548,7 +6548,7 @@ output: Output('completed', type=[<type 'int'>])
|
||||
output: Output('failed', type=[<type 'dict'>])
|
||||
output: Entry('result')
|
||||
command: vault_archive_internal/1
|
||||
-args: 1,9,3
|
||||
+args: 1,10,3
|
||||
arg: Str('cn', cli_name='name')
|
||||
option: Flag('all', autofill=True, cli_name='all', default=False)
|
||||
option: Bytes('nonce')
|
||||
@@ -6559,6 +6559,7 @@ option: Flag('shared?', autofill=True, default=False)
|
||||
option: Str('username?', cli_name='user')
|
||||
option: Bytes('vault_data')
|
||||
option: Str('version?')
|
||||
+option: StrEnum('wrapping_algo?', autofill=True, default=u'des-ede3-cbc', values=[u'des-ede3-cbc', u'aes-128-cbc'])
|
||||
output: Entry('result')
|
||||
output: Output('summary', type=[<type 'unicode'>, <type 'NoneType'>])
|
||||
output: PrimaryKey('value')
|
||||
@@ -6649,7 +6650,7 @@ output: Output('completed', type=[<type 'int'>])
|
||||
output: Output('failed', type=[<type 'dict'>])
|
||||
output: Entry('result')
|
||||
command: vault_retrieve_internal/1
|
||||
-args: 1,7,3
|
||||
+args: 1,8,3
|
||||
arg: Str('cn', cli_name='name')
|
||||
option: Flag('all', autofill=True, cli_name='all', default=False)
|
||||
option: Flag('raw', autofill=True, cli_name='raw', default=False)
|
||||
@@ -6658,6 +6659,7 @@ option: Bytes('session_key')
|
||||
option: Flag('shared?', autofill=True, default=False)
|
||||
option: Str('username?', cli_name='user')
|
||||
option: Str('version?')
|
||||
+option: StrEnum('wrapping_algo?', autofill=True, default=u'des-ede3-cbc', values=[u'des-ede3-cbc', u'aes-128-cbc'])
|
||||
output: Entry('result')
|
||||
output: Output('summary', type=[<type 'unicode'>, <type 'NoneType'>])
|
||||
output: PrimaryKey('value')
|
||||
@@ -7327,6 +7329,7 @@ default: vaultcontainer_del/1
|
||||
default: vaultcontainer_remove_owner/1
|
||||
default: vaultcontainer_show/1
|
||||
default: whoami/1
|
||||
+capability: vault_aes_keywrap 2.246
|
||||
capability: messages 2.52
|
||||
capability: optional_uid_params 2.54
|
||||
capability: permissions2 2.69
|
||||
diff --git a/VERSION.m4 b/VERSION.m4
|
||||
index 70aaff4c9b9514a5937eae60074376e1a592464e..997ac35e74fa6f2a96da027ed3ce93cf809b62a7 100644
|
||||
--- a/VERSION.m4
|
||||
+++ b/VERSION.m4
|
||||
@@ -86,9 +86,8 @@ define(IPA_DATA_VERSION, 20100614120000)
|
||||
# #
|
||||
########################################################
|
||||
define(IPA_API_VERSION_MAJOR, 2)
|
||||
-# Last change: add enable_sid to config
|
||||
-define(IPA_API_VERSION_MINOR, 245)
|
||||
-
|
||||
+# Last change: Add wrapping algorithm to vault archive/retrieve
|
||||
+define(IPA_API_VERSION_MINOR, 246)
|
||||
|
||||
########################################################
|
||||
# Following values are auto-generated from values above
|
||||
diff --git a/ipaclient/plugins/vault.py b/ipaclient/plugins/vault.py
|
||||
index d3a1d370efaccc7e5b0088bd3df341d76884d509..115171c7768d44251c17d0bcdac9c37b3a25db99 100644
|
||||
--- a/ipaclient/plugins/vault.py
|
||||
+++ b/ipaclient/plugins/vault.py
|
||||
@@ -25,11 +25,12 @@ import io
|
||||
import json
|
||||
import logging
|
||||
import os
|
||||
+import ssl
|
||||
import tempfile
|
||||
|
||||
from cryptography.fernet import Fernet, InvalidToken
|
||||
from cryptography.hazmat.backends import default_backend
|
||||
-from cryptography.hazmat.primitives import hashes, serialization
|
||||
+from cryptography.hazmat.primitives import hashes
|
||||
from cryptography.hazmat.primitives.kdf.pbkdf2 import PBKDF2HMAC
|
||||
from cryptography.hazmat.primitives.asymmetric import padding
|
||||
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
|
||||
@@ -39,7 +40,7 @@ from cryptography.hazmat.primitives.serialization import (
|
||||
|
||||
from ipaclient.frontend import MethodOverride
|
||||
from ipalib import x509
|
||||
-from ipalib.constants import USER_CACHE_PATH
|
||||
+from ipalib import constants
|
||||
from ipalib.frontend import Local, Method, Object
|
||||
from ipalib.util import classproperty
|
||||
from ipalib import api, errors
|
||||
@@ -546,42 +547,49 @@ class vault_mod(Local):
|
||||
return response
|
||||
|
||||
|
||||
-class _TransportCertCache:
|
||||
+class _KraConfigCache:
|
||||
+ """The KRA config cache stores vaultconfig-show result.
|
||||
+ """
|
||||
def __init__(self):
|
||||
self._dirname = os.path.join(
|
||||
- USER_CACHE_PATH, 'ipa', 'kra-transport-certs'
|
||||
+ constants.USER_CACHE_PATH, 'ipa', 'kra-config'
|
||||
)
|
||||
|
||||
def _get_filename(self, domain):
|
||||
- basename = DNSName(domain).ToASCII() + '.pem'
|
||||
+ basename = DNSName(domain).ToASCII() + '.json'
|
||||
return os.path.join(self._dirname, basename)
|
||||
|
||||
- def load_cert(self, domain):
|
||||
- """Load cert from cache
|
||||
+ def load(self, domain):
|
||||
+ """Load config from cache
|
||||
|
||||
:param domain: IPA domain
|
||||
- :return: cryptography.x509.Certificate or None
|
||||
+ :return: dict or None
|
||||
"""
|
||||
filename = self._get_filename(domain)
|
||||
try:
|
||||
try:
|
||||
- return x509.load_certificate_from_file(filename)
|
||||
- except EnvironmentError as e:
|
||||
+ with open(filename) as f:
|
||||
+ return json.load(f)
|
||||
+ except OSError as e:
|
||||
if e.errno != errno.ENOENT:
|
||||
raise
|
||||
except Exception:
|
||||
logger.warning("Failed to load %s", filename, exc_info=True)
|
||||
return None
|
||||
|
||||
- def store_cert(self, domain, transport_cert):
|
||||
- """Store a new cert or override existing cert
|
||||
+ def store(self, domain, response):
|
||||
+ """Store config in cache
|
||||
|
||||
:param domain: IPA domain
|
||||
- :param transport_cert: cryptography.x509.Certificate
|
||||
- :return: True if cert was stored successfully
|
||||
+ :param config: ipa vaultconfig-show response
|
||||
+ :return: True if config was stored successfully
|
||||
"""
|
||||
+ config = response['result'].copy()
|
||||
+ # store certificate as PEM-encoded ASCII
|
||||
+ config['transport_cert'] = ssl.DER_cert_to_PEM_cert(
|
||||
+ config['transport_cert']
|
||||
+ )
|
||||
filename = self._get_filename(domain)
|
||||
- pem = transport_cert.public_bytes(serialization.Encoding.PEM)
|
||||
try:
|
||||
try:
|
||||
os.makedirs(self._dirname)
|
||||
@@ -589,9 +597,9 @@ class _TransportCertCache:
|
||||
if e.errno != errno.EEXIST:
|
||||
raise
|
||||
with tempfile.NamedTemporaryFile(dir=self._dirname, delete=False,
|
||||
- mode='wb') as f:
|
||||
+ mode='w') as f:
|
||||
try:
|
||||
- f.write(pem)
|
||||
+ json.dump(config, f)
|
||||
ipautil.flush_sync(f)
|
||||
f.close()
|
||||
os.rename(f.name, filename)
|
||||
@@ -604,8 +612,8 @@ class _TransportCertCache:
|
||||
else:
|
||||
return True
|
||||
|
||||
- def remove_cert(self, domain):
|
||||
- """Remove a cert from cache, ignores errors
|
||||
+ def remove(self, domain):
|
||||
+ """Remove a config from cache, ignores errors
|
||||
|
||||
:param domain: IPA domain
|
||||
:return: True if cert was found and removed
|
||||
@@ -621,7 +629,7 @@ class _TransportCertCache:
|
||||
return True
|
||||
|
||||
|
||||
-_transport_cert_cache = _TransportCertCache()
|
||||
+_kra_config_cache = _KraConfigCache()
|
||||
|
||||
|
||||
@register(override=True, no_fail=True)
|
||||
@@ -636,13 +644,8 @@ class vaultconfig_show(MethodOverride):
|
||||
|
||||
response = super(vaultconfig_show, self).forward(*args, **options)
|
||||
|
||||
- # cache transport certificate
|
||||
- transport_cert = x509.load_der_x509_certificate(
|
||||
- response['result']['transport_cert'])
|
||||
-
|
||||
- _transport_cert_cache.store_cert(
|
||||
- self.api.env.domain, transport_cert
|
||||
- )
|
||||
+ # cache config
|
||||
+ _kra_config_cache.store(self.api.env.domain, response)
|
||||
|
||||
if file:
|
||||
with open(file, 'wb') as f:
|
||||
@@ -652,10 +655,54 @@ class vaultconfig_show(MethodOverride):
|
||||
|
||||
|
||||
class ModVaultData(Local):
|
||||
- def _generate_session_key(self):
|
||||
- key_length = max(algorithms.TripleDES.key_sizes)
|
||||
- algo = algorithms.TripleDES(os.urandom(key_length // 8))
|
||||
- return algo
|
||||
+ def _generate_session_key(self, name):
|
||||
+ if name not in constants.VAULT_WRAPPING_SUPPORTED_ALGOS:
|
||||
+ msg = _("{algo} is not a supported vault wrapping algorithm")
|
||||
+ raise errors.ValidationError(msg.format(algo=repr(name)))
|
||||
+ if name == constants.VAULT_WRAPPING_AES128_CBC:
|
||||
+ return algorithms.AES(os.urandom(128 // 8))
|
||||
+ elif name == constants.VAULT_WRAPPING_3DES:
|
||||
+ return algorithms.TripleDES(os.urandom(196 // 8))
|
||||
+ else:
|
||||
+ # unreachable
|
||||
+ raise ValueError(name)
|
||||
+
|
||||
+ def _get_vaultconfig(self, force_refresh=False):
|
||||
+ config = None
|
||||
+ if not force_refresh:
|
||||
+ config = _kra_config_cache.load(self.api.env.domain)
|
||||
+ if config is None:
|
||||
+ # vaultconfig_show also caches data
|
||||
+ response = self.api.Command.vaultconfig_show()
|
||||
+ config = response['result']
|
||||
+ transport_cert = x509.load_der_x509_certificate(
|
||||
+ config['transport_cert']
|
||||
+ )
|
||||
+ else:
|
||||
+ # cached JSON uses PEM-encoded ASCII string
|
||||
+ transport_cert = x509.load_pem_x509_certificate(
|
||||
+ config['transport_cert'].encode('ascii')
|
||||
+ )
|
||||
+
|
||||
+ default_algo = config.get('wrapping_default_algorithm')
|
||||
+ if default_algo is None:
|
||||
+ # old server
|
||||
+ wrapping_algo = constants.VAULT_WRAPPING_AES128_CBC
|
||||
+ elif default_algo in constants.VAULT_WRAPPING_SUPPORTED_ALGOS:
|
||||
+ # try to use server default
|
||||
+ wrapping_algo = default_algo
|
||||
+ else:
|
||||
+ # prefer server's sorting order
|
||||
+ for algo in config['wrapping_supported_algorithms']:
|
||||
+ if algo in constants.VAULT_WRAPPING_SUPPORTED_ALGOS:
|
||||
+ wrapping_algo = algo
|
||||
+ break
|
||||
+ else:
|
||||
+ raise errors.ValidationError(
|
||||
+ "No overlapping wrapping algorithm between server and "
|
||||
+ "client."
|
||||
+ )
|
||||
+ return transport_cert, wrapping_algo
|
||||
|
||||
def _do_internal(self, algo, transport_cert, raise_unexpected,
|
||||
*args, **options):
|
||||
@@ -675,29 +722,23 @@ class ModVaultData(Local):
|
||||
except (errors.InternalError,
|
||||
errors.ExecutionError,
|
||||
errors.GenericError):
|
||||
- _transport_cert_cache.remove_cert(self.api.env.domain)
|
||||
+ _kra_config_cache.remove(self.api.env.domain)
|
||||
if raise_unexpected:
|
||||
raise
|
||||
return None
|
||||
|
||||
- def internal(self, algo, *args, **options):
|
||||
+ def internal(self, algo, transport_cert, *args, **options):
|
||||
"""
|
||||
Calls the internal counterpart of the command.
|
||||
"""
|
||||
- domain = self.api.env.domain
|
||||
-
|
||||
# try call with cached transport certificate
|
||||
- transport_cert = _transport_cert_cache.load_cert(domain)
|
||||
- if transport_cert is not None:
|
||||
- result = self._do_internal(algo, transport_cert, False,
|
||||
+ result = self._do_internal(algo, transport_cert, False,
|
||||
*args, **options)
|
||||
- if result is not None:
|
||||
- return result
|
||||
+ if result is not None:
|
||||
+ return result
|
||||
|
||||
# retrieve transport certificate (cached by vaultconfig_show)
|
||||
- response = self.api.Command.vaultconfig_show()
|
||||
- transport_cert = x509.load_der_x509_certificate(
|
||||
- response['result']['transport_cert'])
|
||||
+ transport_cert = self._get_vaultconfig(force_refresh=True)[0]
|
||||
# call with the retrieved transport certificate
|
||||
return self._do_internal(algo, transport_cert, True,
|
||||
*args, **options)
|
||||
@@ -777,7 +818,7 @@ class vault_archive(ModVaultData):
|
||||
def _wrap_data(self, algo, json_vault_data):
|
||||
"""Encrypt data with wrapped session key and transport cert
|
||||
|
||||
- :param bytes algo: wrapping algorithm instance
|
||||
+ :param algo: wrapping algorithm instance
|
||||
:param bytes json_vault_data: dumped vault data
|
||||
:return:
|
||||
"""
|
||||
@@ -929,15 +970,24 @@ class vault_archive(ModVaultData):
|
||||
|
||||
json_vault_data = json.dumps(vault_data).encode('utf-8')
|
||||
|
||||
+ # get config
|
||||
+ transport_cert, wrapping_algo = self._get_vaultconfig()
|
||||
+ # let options override wrapping algo
|
||||
+ # For backwards compatibility do not send old legacy wrapping algo
|
||||
+ # to server. Only send the option when non-3DES is used.
|
||||
+ wrapping_algo = options.pop('wrapping_algo', wrapping_algo)
|
||||
+ if wrapping_algo != constants.VAULT_WRAPPING_3DES:
|
||||
+ options['wrapping_algo'] = wrapping_algo
|
||||
+
|
||||
# generate session key
|
||||
- algo = self._generate_session_key()
|
||||
+ algo = self._generate_session_key(wrapping_algo)
|
||||
# wrap vault data
|
||||
nonce, wrapped_vault_data = self._wrap_data(algo, json_vault_data)
|
||||
options.update(
|
||||
nonce=nonce,
|
||||
vault_data=wrapped_vault_data
|
||||
)
|
||||
- return self.internal(algo, *args, **options)
|
||||
+ return self.internal(algo, transport_cert, *args, **options)
|
||||
|
||||
|
||||
@register(no_fail=True)
|
||||
@@ -1061,10 +1111,19 @@ class vault_retrieve(ModVaultData):
|
||||
vault = self.api.Command.vault_show(*args, **options)['result']
|
||||
vault_type = vault['ipavaulttype'][0]
|
||||
|
||||
+ # get config
|
||||
+ transport_cert, wrapping_algo = self._get_vaultconfig()
|
||||
+ # let options override wrapping algo
|
||||
+ # For backwards compatibility do not send old legacy wrapping algo
|
||||
+ # to server. Only send the option when non-3DES is used.
|
||||
+ wrapping_algo = options.pop('wrapping_algo', wrapping_algo)
|
||||
+ if wrapping_algo != constants.VAULT_WRAPPING_3DES:
|
||||
+ options['wrapping_algo'] = wrapping_algo
|
||||
+
|
||||
# generate session key
|
||||
- algo = self._generate_session_key()
|
||||
+ algo = self._generate_session_key(wrapping_algo)
|
||||
# send retrieval request to server
|
||||
- response = self.internal(algo, *args, **options)
|
||||
+ response = self.internal(algo, transport_cert, *args, **options)
|
||||
# unwrap data with session key
|
||||
vault_data = self._unwrap_response(
|
||||
algo,
|
||||
diff --git a/ipalib/capabilities.py b/ipalib/capabilities.py
|
||||
index 55b84aa6bc73d583e7bd5d03d2f4f1cc5c8e7c0b..4d8ae408bf67c280d27ce494baa9db9aaff0cd69 100644
|
||||
--- a/ipalib/capabilities.py
|
||||
+++ b/ipalib/capabilities.py
|
||||
@@ -54,6 +54,10 @@ capabilities = dict(
|
||||
|
||||
# dns_name_values: dnsnames as objects
|
||||
dns_name_values=u'2.88',
|
||||
+
|
||||
+ # vault supports aes key wrapping
|
||||
+ vault_aes_keywrap='2.246'
|
||||
+
|
||||
)
|
||||
|
||||
|
||||
diff --git a/ipalib/constants.py b/ipalib/constants.py
|
||||
index 9f19b0f9941ba5068f1e6c218092e3b76fdc7599..11171b2e8aeb6f7306299b2bd7db3a3f39d29d4a 100644
|
||||
--- a/ipalib/constants.py
|
||||
+++ b/ipalib/constants.py
|
||||
@@ -374,3 +374,15 @@ KRA_TRACKING_REQS = {
|
||||
}
|
||||
|
||||
ALLOWED_NETBIOS_CHARS = string.ascii_uppercase + string.digits + '-'
|
||||
+
|
||||
+# vault data wrapping algorithms
|
||||
+VAULT_WRAPPING_3DES = 'des-ede3-cbc'
|
||||
+VAULT_WRAPPING_AES128_CBC = 'aes-128-cbc'
|
||||
+VAULT_WRAPPING_SUPPORTED_ALGOS = (
|
||||
+ # old default was 3DES
|
||||
+ VAULT_WRAPPING_3DES,
|
||||
+ # supported since pki-kra >= 10.4
|
||||
+ VAULT_WRAPPING_AES128_CBC,
|
||||
+)
|
||||
+# 3DES for backwards compatibility
|
||||
+VAULT_WRAPPING_DEFAULT_ALGO = VAULT_WRAPPING_3DES
|
||||
diff --git a/ipaserver/plugins/vault.py b/ipaserver/plugins/vault.py
|
||||
index aebac7dff7bb9d183c6012cc685577d476e18c4e..4d40f66c6a793a831e91c5fe25c8b5277cbd1972 100644
|
||||
--- a/ipaserver/plugins/vault.py
|
||||
+++ b/ipaserver/plugins/vault.py
|
||||
@@ -23,6 +23,10 @@ from ipalib.frontend import Command, Object
|
||||
from ipalib import api, errors
|
||||
from ipalib import Bytes, Flag, Str, StrEnum
|
||||
from ipalib import output
|
||||
+from ipalib.constants import (
|
||||
+ VAULT_WRAPPING_SUPPORTED_ALGOS, VAULT_WRAPPING_DEFAULT_ALGO,
|
||||
+ VAULT_WRAPPING_3DES, VAULT_WRAPPING_AES128_CBC,
|
||||
+)
|
||||
from ipalib.crud import PKQuery, Retrieve
|
||||
from ipalib.parameters import Principal
|
||||
from ipalib.plugable import Registry
|
||||
@@ -39,14 +43,8 @@ from ipaserver.masters import is_service_enabled
|
||||
if api.env.in_server:
|
||||
import pki.account
|
||||
import pki.key
|
||||
- # pylint: disable=no-member
|
||||
- try:
|
||||
- # pki >= 10.4.0
|
||||
- from pki.crypto import DES_EDE3_CBC_OID
|
||||
- except ImportError:
|
||||
- DES_EDE3_CBC_OID = pki.key.KeyClient.DES_EDE3_CBC_OID
|
||||
- # pylint: enable=no-member
|
||||
-
|
||||
+ from pki.crypto import DES_EDE3_CBC_OID
|
||||
+ from pki.crypto import AES_128_CBC_OID
|
||||
|
||||
if six.PY3:
|
||||
unicode = str
|
||||
@@ -652,6 +652,20 @@ class vault(LDAPObject):
|
||||
),
|
||||
)
|
||||
|
||||
+ def _translate_algorithm(self, name):
|
||||
+ if name is None:
|
||||
+ name = VAULT_WRAPPING_DEFAULT_ALGO
|
||||
+ if name not in VAULT_WRAPPING_SUPPORTED_ALGOS:
|
||||
+ msg = _("{algo} is not a supported vault wrapping algorithm")
|
||||
+ raise errors.ValidationError(msg.format(algo=name))
|
||||
+ if name == VAULT_WRAPPING_3DES:
|
||||
+ return DES_EDE3_CBC_OID
|
||||
+ elif name == VAULT_WRAPPING_AES128_CBC:
|
||||
+ return AES_128_CBC_OID
|
||||
+ else:
|
||||
+ # unreachable
|
||||
+ raise ValueError(name)
|
||||
+
|
||||
def get_dn(self, *keys, **options):
|
||||
"""
|
||||
Generates vault DN from parameters.
|
||||
@@ -992,14 +1006,18 @@ class vaultconfig_show(Retrieve):
|
||||
)
|
||||
|
||||
def execute(self, *args, **options):
|
||||
-
|
||||
if not self.api.Command.kra_is_enabled()['result']:
|
||||
raise errors.InvocationError(
|
||||
format=_('KRA service is not enabled'))
|
||||
|
||||
+ config = dict(
|
||||
+ wrapping_supported_algorithms=VAULT_WRAPPING_SUPPORTED_ALGOS,
|
||||
+ wrapping_default_algorithm=VAULT_WRAPPING_DEFAULT_ALGO,
|
||||
+ )
|
||||
+
|
||||
with self.api.Backend.kra.get_client() as kra_client:
|
||||
transport_cert = kra_client.system_certs.get_transport_cert()
|
||||
- config = {'transport_cert': transport_cert.binary}
|
||||
+ config['transport_cert'] = transport_cert.binary
|
||||
|
||||
self.api.Object.config.show_servroles_attributes(
|
||||
config, "KRA server", **options)
|
||||
@@ -1029,6 +1047,13 @@ class vault_archive_internal(PKQuery):
|
||||
'nonce',
|
||||
doc=_('Nonce'),
|
||||
),
|
||||
+ StrEnum(
|
||||
+ 'wrapping_algo?',
|
||||
+ doc=_('Key wrapping algorithm'),
|
||||
+ values=VAULT_WRAPPING_SUPPORTED_ALGOS,
|
||||
+ default=VAULT_WRAPPING_DEFAULT_ALGO,
|
||||
+ autofill=True,
|
||||
+ ),
|
||||
)
|
||||
|
||||
has_output = output.standard_entry
|
||||
@@ -1045,6 +1070,9 @@ class vault_archive_internal(PKQuery):
|
||||
nonce = options.pop('nonce')
|
||||
wrapped_session_key = options.pop('session_key')
|
||||
|
||||
+ wrapping_algo = options.pop('wrapping_algo', None)
|
||||
+ algorithm_oid = self.obj._translate_algorithm(wrapping_algo)
|
||||
+
|
||||
# retrieve vault info
|
||||
vault = self.api.Command.vault_show(*args, **options)['result']
|
||||
|
||||
@@ -1071,7 +1099,7 @@ class vault_archive_internal(PKQuery):
|
||||
pki.key.KeyClient.PASS_PHRASE_TYPE,
|
||||
wrapped_vault_data,
|
||||
wrapped_session_key,
|
||||
- algorithm_oid=DES_EDE3_CBC_OID,
|
||||
+ algorithm_oid=algorithm_oid,
|
||||
nonce_iv=nonce,
|
||||
)
|
||||
|
||||
@@ -1098,6 +1126,13 @@ class vault_retrieve_internal(PKQuery):
|
||||
'session_key',
|
||||
doc=_('Session key wrapped with transport certificate'),
|
||||
),
|
||||
+ StrEnum(
|
||||
+ 'wrapping_algo?',
|
||||
+ doc=_('Key wrapping algorithm'),
|
||||
+ values=VAULT_WRAPPING_SUPPORTED_ALGOS,
|
||||
+ default=VAULT_WRAPPING_DEFAULT_ALGO,
|
||||
+ autofill=True,
|
||||
+ ),
|
||||
)
|
||||
|
||||
has_output = output.standard_entry
|
||||
@@ -1112,6 +1147,9 @@ class vault_retrieve_internal(PKQuery):
|
||||
|
||||
wrapped_session_key = options.pop('session_key')
|
||||
|
||||
+ wrapping_algo = options.pop('wrapping_algo', None)
|
||||
+ algorithm_oid = self.obj._translate_algorithm(wrapping_algo)
|
||||
+
|
||||
# retrieve vault info
|
||||
vault = self.api.Command.vault_show(*args, **options)['result']
|
||||
|
||||
@@ -1132,6 +1170,9 @@ class vault_retrieve_internal(PKQuery):
|
||||
|
||||
key_info = response.key_infos[0]
|
||||
|
||||
+ # XXX hack
|
||||
+ kra_client.keys.encrypt_alg_oid = algorithm_oid
|
||||
+
|
||||
# retrieve encrypted data from KRA
|
||||
key = kra_client.keys.retrieve_key(
|
||||
key_info.get_key_id(),
|
||||
--
|
||||
2.34.1
|
||||
|
@ -0,0 +1,86 @@
|
||||
From 984190eea01ac42cd1f97567a67dd9446e5b0bf9 Mon Sep 17 00:00:00 2001
|
||||
From: Francisco Trivino <ftrivino@redhat.com>
|
||||
Date: Fri, 11 Mar 2022 17:47:38 +0100
|
||||
Subject: [PATCH] Set AES as default for KRA archival wrapping
|
||||
|
||||
This commit sets AES-128-CBC as default wrapping algorithm as
|
||||
TripleDES (des-ede3-cbc) is not supported anymore in C9S.
|
||||
|
||||
Fixes: https://pagure.io/freeipa/issue/6524
|
||||
|
||||
Signed-off-by: Francisco Trivino <ftrivino@redhat.com>
|
||||
Reviewed-By: Christian Heimes <cheimes@redhat.com>
|
||||
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
|
||||
---
|
||||
API.txt | 6 +++---
|
||||
ipalib/constants.py | 14 +++++++++-----
|
||||
2 files changed, 12 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/API.txt b/API.txt
|
||||
index f95f2c8457e39f2268386a8a2336952d3285e008..1f27dcc616a6395c56ef91f3453e7620625c7645 100644
|
||||
--- a/API.txt
|
||||
+++ b/API.txt
|
||||
@@ -6559,7 +6559,7 @@ option: Flag('shared?', autofill=True, default=False)
|
||||
option: Str('username?', cli_name='user')
|
||||
option: Bytes('vault_data')
|
||||
option: Str('version?')
|
||||
-option: StrEnum('wrapping_algo?', autofill=True, default=u'des-ede3-cbc', values=[u'des-ede3-cbc', u'aes-128-cbc'])
|
||||
+option: StrEnum('wrapping_algo?', autofill=True, default=u'aes-128-cbc', values=[u'aes-128-cbc', u'des-ede3-cbc'])
|
||||
output: Entry('result')
|
||||
output: Output('summary', type=[<type 'unicode'>, <type 'NoneType'>])
|
||||
output: PrimaryKey('value')
|
||||
@@ -6659,7 +6659,7 @@ option: Bytes('session_key')
|
||||
option: Flag('shared?', autofill=True, default=False)
|
||||
option: Str('username?', cli_name='user')
|
||||
option: Str('version?')
|
||||
-option: StrEnum('wrapping_algo?', autofill=True, default=u'des-ede3-cbc', values=[u'des-ede3-cbc', u'aes-128-cbc'])
|
||||
+option: StrEnum('wrapping_algo?', autofill=True, default=u'aes-128-cbc', values=[u'aes-128-cbc', u'des-ede3-cbc'])
|
||||
output: Entry('result')
|
||||
output: Output('summary', type=[<type 'unicode'>, <type 'NoneType'>])
|
||||
output: PrimaryKey('value')
|
||||
@@ -7329,10 +7329,10 @@ default: vaultcontainer_del/1
|
||||
default: vaultcontainer_remove_owner/1
|
||||
default: vaultcontainer_show/1
|
||||
default: whoami/1
|
||||
-capability: vault_aes_keywrap 2.246
|
||||
capability: messages 2.52
|
||||
capability: optional_uid_params 2.54
|
||||
capability: permissions2 2.69
|
||||
capability: primary_key_types 2.83
|
||||
capability: datetime_values 2.84
|
||||
capability: dns_name_values 2.88
|
||||
+capability: vault_aes_keywrap 2.246
|
||||
diff --git a/ipalib/constants.py b/ipalib/constants.py
|
||||
index 11171b2e8aeb6f7306299b2bd7db3a3f39d29d4a..68178004181bebcc8c093dac55e18d5afe0251e5 100644
|
||||
--- a/ipalib/constants.py
|
||||
+++ b/ipalib/constants.py
|
||||
@@ -29,6 +29,8 @@ from ipaplatform.constants import constants as _constants
|
||||
from ipapython.dn import DN
|
||||
from ipapython.fqdn import gethostfqdn
|
||||
from ipapython.version import VERSION, API_VERSION
|
||||
+from cryptography.hazmat.primitives.ciphers import algorithms, modes
|
||||
+from cryptography.hazmat.backends.openssl.backend import backend
|
||||
|
||||
|
||||
FQDN = gethostfqdn()
|
||||
@@ -379,10 +381,12 @@ ALLOWED_NETBIOS_CHARS = string.ascii_uppercase + string.digits + '-'
|
||||
VAULT_WRAPPING_3DES = 'des-ede3-cbc'
|
||||
VAULT_WRAPPING_AES128_CBC = 'aes-128-cbc'
|
||||
VAULT_WRAPPING_SUPPORTED_ALGOS = (
|
||||
- # old default was 3DES
|
||||
- VAULT_WRAPPING_3DES,
|
||||
- # supported since pki-kra >= 10.4
|
||||
+ # new default and supported since pki-kra >= 10.4
|
||||
VAULT_WRAPPING_AES128_CBC,
|
||||
)
|
||||
-# 3DES for backwards compatibility
|
||||
-VAULT_WRAPPING_DEFAULT_ALGO = VAULT_WRAPPING_3DES
|
||||
+VAULT_WRAPPING_DEFAULT_ALGO = VAULT_WRAPPING_AES128_CBC
|
||||
+
|
||||
+# Add 3DES for backwards compatibility if supported
|
||||
+if backend.cipher_supported(algorithms.TripleDES(b"\x00" * 8),
|
||||
+ modes.CBC(b"\x00" * 8)):
|
||||
+ VAULT_WRAPPING_SUPPORTED_ALGOS += (VAULT_WRAPPING_3DES,)
|
||||
--
|
||||
2.34.1
|
||||
|
@ -66,7 +66,7 @@
|
||||
%if 0%{?rhel}
|
||||
%global package_name ipa
|
||||
%global alt_name freeipa
|
||||
%global krb5_version 1.18.2-2
|
||||
%global krb5_version 1.19.1-15
|
||||
%global krb5_kdb_version 8.0
|
||||
# 0.7.16: https://github.com/drkjam/netaddr/issues/71
|
||||
%global python_netaddr_version 0.7.19
|
||||
@ -198,7 +198,7 @@
|
||||
|
||||
Name: %{package_name}
|
||||
Version: %{IPA_VERSION}
|
||||
Release: 5%{?rc_version:.%rc_version}%{?dist}
|
||||
Release: 7%{?rc_version:.%rc_version}%{?dist}
|
||||
Summary: The Identity, Policy and Audit system
|
||||
|
||||
License: GPLv3+
|
||||
@ -241,6 +241,18 @@ Patch0020: 0020-Test-ipa-ccache-sweep.timer-enabled-by-default-durin.patch
|
||||
Patch0021: 0021-ipa_cldap-fix-memory-leak.patch
|
||||
Patch0022: 0022-ipatests-remove-additional-check-for-failed-units_rhbz#2053025.patch
|
||||
Patch0023: 0023-ipatests-fix-TestOTPToken-rhbz#2053025.patch
|
||||
Patch0024: 0024-ipatests-Tests-for-Autoprivate-group.patch
|
||||
Patch0025: 0025-mark-xfail-for-test_idoverride_with_auto_private_gro.patch
|
||||
Patch0026: 0026-Mark-xfail-test_gidnumber_not_corresponding_existing.patch
|
||||
Patch0027: 0027-KRB-instance-make-provision-to-work-with-crypto-poli.patch
|
||||
Patch0028: 0028-tests-ensure-AD-SUPPORT-subpolicy-is-active.patch
|
||||
Patch0029: 0029-ipatests-extend-AES-keyset-to-SHA2-based-ones.patch
|
||||
Patch0030: 0030-freeipa.spec-bump-crypto-policies-dependency-for-Cen.patch
|
||||
Patch0031: 0031-Kerberos-instance-default-to-AES256-SHA2-for-master-.patch
|
||||
Patch0032: 0032-test_otp-do-not-use-paramiko-unless-it-is-really-nee.patch
|
||||
Patch0033: 0033-test_krbtpolicy-skip-SPAKE-related-tests-in-FIPS-mod.patch
|
||||
Patch0034: 0034-Support-AES-for-KRA-archival-wrapping.patch
|
||||
Patch0035: 0035-Set-AES-as-default-for-KRA-archival-wrapping.patch
|
||||
Patch1001: 1001-Change-branding-to-IPA-and-Identity-Management.patch
|
||||
%endif
|
||||
%endif
|
||||
@ -713,6 +725,12 @@ Provides: %{name}-admintools = %{version}-%{release}
|
||||
Conflicts: crypto-policies < 20200629-1
|
||||
%endif
|
||||
|
||||
%if 0%{?rhel} == 9
|
||||
# Conflict with crypto-policies < 20220223-1 to get upgraded AD-SUPPORT and
|
||||
# AD-SUPPORT-LEGACY policy modules
|
||||
Conflicts: crypto-policies < 20220223-1
|
||||
%endif
|
||||
|
||||
%description client
|
||||
IPA is an integrated solution to provide centrally managed Identity (users,
|
||||
hosts, services), Authentication (SSO, 2FA), and Authorization
|
||||
@ -1732,6 +1750,24 @@ fi
|
||||
%endif
|
||||
|
||||
%changelog
|
||||
* Mon Mar 21 2022 Florence Blanc-Renaud <frenaud@redhat.com> - 4.9.8-7
|
||||
- Resolves: rhbz#2057471 Consequences of FIPS crypto policy tightening in RHEL 9
|
||||
- KRB instance: make provision to work with crypto policy without SHA-1 HMAC types
|
||||
- tests: ensure AD-SUPPORT subpolicy is active
|
||||
- ipatests: extend AES keyset to SHA2-based ones
|
||||
- freeipa.spec: bump crypto-policies dependency for CentOS 9 Stream
|
||||
- Kerberos instance: default to AES256-SHA2 for master key encryption
|
||||
- test_otp: do not use paramiko unless it is really needed
|
||||
- test_krbtpolicy: skip SPAKE-related tests in FIPS mode
|
||||
- Support AES for KRA archival wrapping
|
||||
- Set AES as default for KRA archival wrapping
|
||||
|
||||
* Thu Feb 24 2022 Florence Blanc-Renaud <frenaud@redhat.com> - 4.9.8-6
|
||||
- Resolves: rhbz#2057467 Backport latest test fixes in python3-ipatests
|
||||
- ipatests: Tests for Autoprivate group.
|
||||
- mark xfail for test_idoverride_with_auto_private_group[hybrid]
|
||||
- Mark xfail test_gidnumber_not_corresponding_existing_group[true,hybrid]
|
||||
|
||||
* Mon Feb 14 2022 Alexander Bokovoy <abokovoy@redhat.com> - 4.9.8-5
|
||||
- Resolves: rhbz#2053025
|
||||
- add IPA test suite fixes
|
||||
|
Loading…
Reference in New Issue
Block a user