From 509a2bb97c5ccb13c4c2f885f3961f2880aceb91 Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Sat, 19 Sep 2009 20:40:17 -0700 Subject: s4:provision split provision of DNS zone and self join keytab --- source4/scripting/python/samba/provision.py | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/provision.py b/source4/scripting/python/samba/provision.py index fe11b94d67..68a50b2e37 100644 --- a/source4/scripting/python/samba/provision.py +++ b/source4/scripting/python/samba/provision.py @@ -669,7 +669,14 @@ def secretsdb_become_dc(secretsdb, setup_path, domain, realm, dnsdomain, :param setup_path: Setup path function :param machinepass: Machine password """ - setup_ldb(secretsdb, setup_path("secrets_dc.ldif"), { + setup_ldb(secretsdb, setup_path("secrets_dns.ldif"), { + "REALM": realm, + "DNSDOMAIN": dnsdomain, + "DNS_KEYTAB": dns_keytab_path, + "DNSPASS_B64": b64encode(dnspass), + }) + + setup_ldb(secretsdb, setup_path("secrets_self_join.ldif"), { "MACHINEPASS_B64": b64encode(machinepass), "DOMAIN": domain, "REALM": realm, @@ -677,9 +684,8 @@ def secretsdb_become_dc(secretsdb, setup_path, domain, realm, dnsdomain, "DOMAINSID": str(domainsid), "SECRETS_KEYTAB": keytab_path, "NETBIOSNAME": netbiosname, - "SAM_LDB": samdb_url, - "DNS_KEYTAB": dns_keytab_path, - "DNSPASS_B64": b64encode(dnspass), + "SALT_PRINCIPAL": "host/%s.%s@%s" % (netbiosname.lower(), dnsdomain.lower(), realm.upper()), + "KEY_VERSION_NUMBER": "1" }) -- cgit From bfddb6816f50f629d29e476327a921212fd63a2d Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Sun, 20 Sep 2009 16:27:24 -0700 Subject: s4:provision Use code to store domain join in 'net join' as well This ensures we only have one codepath to store the secret, and therefore that we have a single choke point for setting the saltPrincipal, which we were previously skipping. Andrew Bartlett --- source4/scripting/python/samba/provision.py | 103 +++++++++++++++++++++------- 1 file changed, 80 insertions(+), 23 deletions(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/provision.py b/source4/scripting/python/samba/provision.py index 68a50b2e37..8af24f21cf 100644 --- a/source4/scripting/python/samba/provision.py +++ b/source4/scripting/python/samba/provision.py @@ -48,11 +48,13 @@ from samba import DS_DOMAIN_FUNCTION_2000, DS_DC_FUNCTION_2008_R2 from samba.samdb import SamDB from samba.idmap import IDmapDB from samba.dcerpc import security +from samba.ndr import ndr_pack import urllib from ldb import SCOPE_SUBTREE, SCOPE_ONELEVEL, SCOPE_BASE, LdbError, timestring from ms_schema import read_ms_schema from ms_display_specifiers import read_ms_ldif from signal import SIGTERM +from dcerpc.misc import SEC_CHAN_BDC, SEC_CHAN_WKSTA __docformat__ = "restructuredText" @@ -318,7 +320,6 @@ def provision_paths_from_lp(lp, dnsdomain): """ paths = ProvisionPaths() paths.private_dir = lp.get("private dir") - paths.keytab = "secrets.keytab" paths.dns_keytab = "dns.keytab" paths.shareconf = os.path.join(paths.private_dir, "share.ldb") @@ -658,12 +659,75 @@ def setup_samdb_partitions(samdb_path, setup_path, message, lp, session_info, samdb.transaction_commit() +def secretsdb_self_join(secretsdb, domain, + netbiosname, domainsid, machinepass, + realm=None, dnsdomain=None, + keytab_path=None, + key_version_number=1, + secure_channel_type=SEC_CHAN_WKSTA): + """Add domain join-specific bits to a secrets database. + + :param secretsdb: Ldb Handle to the secrets database + :param machinepass: Machine password + """ + attrs=["whenChanged", + "secret", + "priorSecret", + "priorChanged", + "krb5Keytab", + "privateKeytab"] + + + msg = ldb.Message(ldb.Dn(secretsdb, "flatname=%s,cn=Primary Domains" % domain)); + msg["secureChannelType"] = str(secure_channel_type) + msg["flatname"] = [domain] + msg["objectClass"] = ["top", "primaryDomain"] + if realm is not None: + if dnsdomain is None: + dnsdomain = realm.lower() + msg["objectClass"] = ["top", "primaryDomain", "kerberosSecret"] + msg["realm"] = realm + msg["saltPrincipal"] = "host/%s.%s@%s" % (netbiosname.lower(), dnsdomain.lower(), realm.upper()) + msg["msDS-KeyVersionNumber"] = [str(key_version_number)] + msg["privateKeytab"] = ["secrets.keytab"]; + + + msg["secret"] = [machinepass] + msg["samAccountName"] = ["%s$" % netbiosname] + msg["secureChannelType"] = [str(secure_channel_type)] + msg["objectSid"] = [ndr_pack(domainsid)] + + res = secretsdb.search(base="cn=Primary Domains", + attrs=attrs, + expression=("(&(|(flatname=%s)(realm=%s)(objectSid=%s))(objectclass=primaryDomain))" % (domain, realm, str(domainsid))), + scope=SCOPE_ONELEVEL) + + for del_msg in res: + if del_msg.dn is not msg.dn: + secretsdb.delete(del_msg.dn) + + res = secretsdb.search(base=msg.dn, attrs=attrs, scope=SCOPE_BASE) + + if len(res) == 1: + msg["priorSecret"] = res[0]["secret"] + msg["priorWhenChanged"] = res[0]["whenChanged"] + + if res["privateKeytab"] is not None: + msg["privateKeytab"] = res[0]["privateKeytab"] + if res["krb5Keytab"] is not None: + msg["krb5Keytab"] = res[0]["krb5Keytab"] -def secretsdb_become_dc(secretsdb, setup_path, domain, realm, dnsdomain, - netbiosname, domainsid, keytab_path, samdb_url, - dns_keytab_path, dnspass, machinepass): - """Add DC-specific bits to a secrets database. + for el in msg: + el.set_flags(ldb.FLAG_MOD_REPLACE) + secretsdb.modify(msg) + else: + secretsdb.add(msg) + + +def secretsdb_setup_dns(secretsdb, setup_path, realm, dnsdomain, + dns_keytab_path, dnspass): + """Add DNS specific bits to a secrets database. :param secretsdb: Ldb Handle to the secrets database :param setup_path: Setup path function @@ -676,18 +740,6 @@ def secretsdb_become_dc(secretsdb, setup_path, domain, realm, dnsdomain, "DNSPASS_B64": b64encode(dnspass), }) - setup_ldb(secretsdb, setup_path("secrets_self_join.ldif"), { - "MACHINEPASS_B64": b64encode(machinepass), - "DOMAIN": domain, - "REALM": realm, - "DNSDOMAIN": dnsdomain, - "DOMAINSID": str(domainsid), - "SECRETS_KEYTAB": keytab_path, - "NETBIOSNAME": netbiosname, - "SALT_PRINCIPAL": "host/%s.%s@%s" % (netbiosname.lower(), dnsdomain.lower(), realm.upper()), - "KEY_VERSION_NUMBER": "1" - }) - def setup_secretsdb(path, setup_path, session_info, credentials, lp): """Setup the secrets database. @@ -707,6 +759,7 @@ def setup_secretsdb(path, setup_path, session_info, credentials, lp): secrets_ldb.load_ldif_file_add(setup_path("secrets_init.ldif")) secrets_ldb = Ldb(path, session_info=session_info, credentials=credentials, lp=lp) + secrets_ldb.transaction_start() secrets_ldb.load_ldif_file_add(setup_path("secrets.ldif")) if credentials is not None and credentials.authentication_requested(): @@ -1242,16 +1295,18 @@ def provision(setup_dir, message, session_info, # Only make a zone file on the first DC, it should be replicated with DNS replication if serverrole == "domain controller": - secrets_ldb = Ldb(paths.secrets, session_info=session_info, - credentials=credentials, lp=lp) - secretsdb_become_dc(secrets_ldb, setup_path, domain=domain, + secretsdb_self_join(secrets_ldb, domain=domain, realm=names.realm, + dnsdomain=names.dnsdomain, netbiosname=names.netbiosname, domainsid=domainsid, - keytab_path=paths.keytab, samdb_url=paths.samdb, + machinepass=machinepass, + secure_channel_type=SEC_CHAN_BDC) + + secretsdb_setup_dns(secrets_ldb, setup_path, + realm=names.realm, dnsdomain=names.dnsdomain, dns_keytab_path=paths.dns_keytab, - dnspass=dnspass, machinepass=machinepass, - dnsdomain=names.dnsdomain) + dnspass=dnspass) domainguid = samdb.searchone(basedn=domaindn, attribute="objectGUID") assert isinstance(domainguid, str) @@ -1276,6 +1331,8 @@ def provision(setup_dir, message, session_info, realm=names.realm) message("A Kerberos configuration suitable for Samba 4 has been generated at %s" % paths.krb5conf) + #Now commit the secrets.ldb to disk + secrets_ldb.transaction_commit() if provision_backend is not None: if ldap_backend_type == "fedora-ds": -- cgit From 23ffccd5d7c9a88d479f82043ff1b6efe938cc6a Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Sun, 20 Sep 2009 21:32:16 -0700 Subject: s4:provision Make us Windows 2008 level by defualt again Also add a note to clarify that this should not be changed without discussion and consensus. We don't want this bouncing around. Paramater support to allow optional selection of Win2003 mode welcomed. Andrew Bartlett --- source4/scripting/python/samba/provision.py | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/provision.py b/source4/scripting/python/samba/provision.py index 8af24f21cf..b00f240257 100644 --- a/source4/scripting/python/samba/provision.py +++ b/source4/scripting/python/samba/provision.py @@ -44,7 +44,7 @@ from credentials import Credentials, DONT_USE_KERBEROS from auth import system_session, admin_session from samba import version, Ldb, substitute_var, valid_netbios_name from samba import check_all_substituted -from samba import DS_DOMAIN_FUNCTION_2000, DS_DC_FUNCTION_2008_R2 +from samba import DS_DOMAIN_FUNCTION_2000, DS_DOMAIN_FUNCTION_2008, DS_DC_FUNCTION_2008, DS_DC_FUNCTION_2008_R2 from samba.samdb import SamDB from samba.idmap import IDmapDB from samba.dcerpc import security @@ -895,9 +895,10 @@ def setup_samdb(path, setup_path, session_info, credentials, lp, :note: This will wipe the main SAM database file! """ - domainFunctionality = DS_DOMAIN_FUNCTION_2000 - forestFunctionality = DS_DOMAIN_FUNCTION_2000 - domainControllerFunctionality = DS_DC_FUNCTION_2008_R2 + # Do NOT change these default values without discussion with the team and reslease manager. + domainFunctionality = DS_DOMAIN_FUNCTION_2008 + forestFunctionality = DS_DOMAIN_FUNCTION_2008 + domainControllerFunctionality = DS_DC_FUNCTION_2008 # Also wipes the database setup_samdb_partitions(path, setup_path, message=message, lp=lp, -- cgit From 7373bb79d415ae1cc1336aea779e9c2a2ed028d4 Mon Sep 17 00:00:00 2001 From: Matthias Dieter Wallnöfer Date: Mon, 21 Sep 2009 13:53:47 +0200 Subject: s4:samdb/tools - That should fix now the last failures --- source4/scripting/python/samba/samdb.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/samdb.py b/source4/scripting/python/samba/samdb.py index 239dd6a6ea..39cf1d6c40 100644 --- a/source4/scripting/python/samba/samdb.py +++ b/source4/scripting/python/samba/samdb.py @@ -202,8 +202,8 @@ userPassword:: %s self.transaction_start() try: res = self.search(base=self.domain_dn(), scope=ldb.SCOPE_SUBTREE, - expression=filter, - attrs=["userAccountControl", "accountExpires"]) + expression=filter, + attrs=["userAccountControl", "accountExpires"]) assert(len(res) == 1) user_dn = res[0].dn -- cgit From 63f280cfefdd0c0281a25c4068481dab226d0c3e Mon Sep 17 00:00:00 2001 From: Matthias Dieter Wallnöfer Date: Mon, 21 Sep 2009 17:20:49 +0200 Subject: s4:provision - Fix up ProvisioningError class as suggested by Jelmer --- source4/scripting/python/samba/provision.py | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/provision.py b/source4/scripting/python/samba/provision.py index b00f240257..9a41709830 100644 --- a/source4/scripting/python/samba/provision.py +++ b/source4/scripting/python/samba/provision.py @@ -58,11 +58,6 @@ from dcerpc.misc import SEC_CHAN_BDC, SEC_CHAN_WKSTA __docformat__ = "restructuredText" - -class ProvisioningError(ValueError): - pass - - def find_setup_dir(): """Find the setup directory used by provision.""" dirname = os.path.dirname(__file__) @@ -81,6 +76,11 @@ def find_setup_dir(): DEFAULTSITE = "Default-First-Site-Name" +# Exception classes + +class ProvisioningError(Exception): + """A generic provision error.""" + class InvalidNetbiosName(Exception): """A specified name was not a valid NetBIOS name.""" def __init__(self, name): -- cgit From 8738b83a446ef667bc162b04affc17dbba7e58a8 Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Mon, 21 Sep 2009 11:59:33 -0700 Subject: s4:provision Make our default salt match our server behaviour We need to look into salting algorithms further. Andrew Bartlett --- source4/scripting/python/samba/provision.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/provision.py b/source4/scripting/python/samba/provision.py index 9a41709830..af706d08dd 100644 --- a/source4/scripting/python/samba/provision.py +++ b/source4/scripting/python/samba/provision.py @@ -687,7 +687,7 @@ def secretsdb_self_join(secretsdb, domain, dnsdomain = realm.lower() msg["objectClass"] = ["top", "primaryDomain", "kerberosSecret"] msg["realm"] = realm - msg["saltPrincipal"] = "host/%s.%s@%s" % (netbiosname.lower(), dnsdomain.lower(), realm.upper()) + msg["saltPrincipal"] = "host/%s.%s@%s" % (netbiosname, dnsdomain.lower(), realm.upper()) msg["msDS-KeyVersionNumber"] = [str(key_version_number)] msg["privateKeytab"] = ["secrets.keytab"]; -- cgit From 1afc7c453c1d5f7e761e46cdc69900305a149820 Mon Sep 17 00:00:00 2001 From: Andrew Bartlett Date: Mon, 21 Sep 2009 12:28:38 -0700 Subject: s4:kerberos Fix the salt to match Windows 2008. The previous commit changed the wrong end - we must fix our server, not our client. Andrew Bartlett --- source4/scripting/python/samba/provision.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source4/scripting/python') diff --git a/source4/scripting/python/samba/provision.py b/source4/scripting/python/samba/provision.py index af706d08dd..9a41709830 100644 --- a/source4/scripting/python/samba/provision.py +++ b/source4/scripting/python/samba/provision.py @@ -687,7 +687,7 @@ def secretsdb_self_join(secretsdb, domain, dnsdomain = realm.lower() msg["objectClass"] = ["top", "primaryDomain", "kerberosSecret"] msg["realm"] = realm - msg["saltPrincipal"] = "host/%s.%s@%s" % (netbiosname, dnsdomain.lower(), realm.upper()) + msg["saltPrincipal"] = "host/%s.%s@%s" % (netbiosname.lower(), dnsdomain.lower(), realm.upper()) msg["msDS-KeyVersionNumber"] = [str(key_version_number)] msg["privateKeytab"] = ["secrets.keytab"]; -- cgit