Be consistant about --ldap-backend-type
[samba.git] / source / setup / provision
index 8766688de9c7c9f306564e8ea596a258b358fceb..328754fd9c8afd17e9dc7195c8978d9faf97551d 100755 (executable)
@@ -1,19 +1,21 @@
-#!/usr/bin/env smbscript
+#!/bin/sh
+exec smbscript "$0" ${1+"$@"}
 /*
        provision a Samba4 server
        Copyright Andrew Tridgell 2005
        Released under the GNU GPL v2 or later
 */
 
-var options = new Object();
-ok = GetOptions(ARGV, options, 
+options = GetOptions(ARGV,
                "POPT_AUTOHELP",
                "POPT_COMMON_SAMBA",
                "POPT_COMMON_VERSION",
+               "POPT_COMMON_CREDENTIALS",
                'realm=s',
                'domain=s',
                'domain-guid=s',
                'domain-sid=s',
+               'policy-guid=s',
                'host-name=s',
                'host-ip=s',
                'host-guid=s',
@@ -21,167 +23,37 @@ ok = GetOptions(ARGV, options,
                'adminpass=s',
                'krbtgtpass=s',
                'machinepass=s',
+               'dnspass=s',
                'root=s',
                'nobody=s',
                'nogroup=s',
                'wheel=s',
                'users=s',
-               'outputdir=s',
-               'quiet');
-if (ok == false) {
-   println("Failed to parse options: " + options.ERROR);
+               'quiet',
+               'blank',
+               'server-role=s',
+               'partitions-only',
+               'ldap-base',
+               'ldap-backend=s',
+                'ldap-backend-type=s',
+                'aci=s');
+
+if (options == undefined) {
+   println("Failed to parse options");
    return -1;
 }
 
 libinclude("base.js");
-
-/* used to generate sequence numbers for records */
-next_usn = 1;
+libinclude("provision.js");
 
 /*
   print a message if quiet is not set
 */
-function message(s) 
+function message()
 {
        if (options["quiet"] == undefined) {
-               println(s);
-       }
-}
-
-/*
-  find a user or group from a list of possibilities
-*/
-function findnss()
-{
-       var i;
-       assert(arguments.length >= 2);
-       var nssfn = arguments[0];
-       var name = arguments[1];
-       if (options[name] != undefined) {
-               return options[name];
-       }
-       for (i=2;i<arguments.length;i++) {
-               if (nssfn(arguments[i]) != undefined) {
-                       return arguments[i];
-               }
-       }
-       println("Unable to find user/group for " + name);
-       exit(1);
-}
-
-/*
-   add a foreign security principle
- */
-function add_foreign(str, sid, desc, unixname)
-{
-       var add = "
-dn: CN=${SID},CN=ForeignSecurityPrincipals,${BASEDN}
-objectClass: top
-objectClass: foreignSecurityPrincipal
-cn: ${SID}
-description: ${DESC}
-instanceType: 4
-whenCreated: ${LDAPTIME}
-whenChanged: ${LDAPTIME}
-uSNCreated: 1
-uSNChanged: 1
-showInAdvancedViewOnly: TRUE
-name: ${SID}
-objectGUID: ${NEWGUID}
-objectSid: ${SID}
-objectCategory: CN=Foreign-Security-Principal,CN=Schema,CN=Configuration,${BASEDN}
-unixName: ${UNIXNAME}
-";
-       var sub = new Object();
-       sub.SID = sid;
-       sub.DESC = desc;
-       sub.UNIXNAME = unixname;
-       return str + substitute_var(add, sub);
-}
-
-/*
-  return current time as a nt time string
-*/
-function nttime()
-{
-       return "" + sys_nttime();
-}
-
-/*
-  return current time as a ldap time string
-*/
-function ldaptime()
-{
-       return sys_ldaptime(sys_nttime());
-}
-
-function datestring()
-{
-       var t = sys_gmtime(sys_nttime());
-       return sprintf("%04u%02u%02u%02u",
-                      t.tm_year+1900, t.tm_mon+1, t.tm_mday, t.tm_hour);
-}
-
-/*
-  return current time as a ldap time string
-*/
-function nextusn()
-{
-       next_usn = next_usn+1;
-       return next_usn;
-}
-
-/*
-  return first part of hostname
-*/
-function hostname()
-{
-       var s = split(".", sys_hostname());
-       return s[0];
-}
-
-
-/*
-  setup a ldb in the private dir
- */
-function setup_ldb(ldif, dbname, subobj)
-{
-       var extra = "";
-       if (arguments.length == 4) {
-               extra = arguments[3];
+               print(vsprintf(arguments));
        }
-       printVars(lpGet("setup directory"));
-
-       var db = lpGet("private dir") + "/" + dbname;
-       var src = lpGet("setup directory") + "/" + ldif;
-
-       sys_unlink(db);
-
-       var data = sys_file_load(src);
-       data = data + extra;
-       data = substitute_var(data, subobj);
-
-       message("Creating " + db + "\n from " + src);
-       ok = ldbAdd(db, data);
-       assert(ok);
-}
-
-/*
-  setup a file in the private dir
- */
-function setup_file(template, fname, subobj)
-{
-       var f = lpGet("private dir") + "/" + fname;
-       var src = lpGet("setup directory") + "/" + template;
-
-       sys_unlink(f);
-
-       var data = sys_file_load(src);
-       data = substitute_var(data, subobj);
-
-       message("Creating " + f + "\n from " + src);
-       ok = sys_file_save(f, data);
-       assert(ok);
 }
 
 /*
@@ -192,7 +64,7 @@ function ShowHelp()
        print("
 Samba4 provisioning
 
-provision.pl [options]
+provision [options]
  --realm       REALM           set realm
  --domain      DOMAIN          set domain
  --domain-guid GUID            set domainguid (otherwise random)
@@ -200,8 +72,8 @@ provision.pl [options]
  --host-name   HOSTNAME        set hostname
  --host-ip     IPADDRESS       set ipaddress
  --host-guid   GUID            set hostguid (otherwise random)
+ --policy-guid  GUID            set group policy guid (otherwise random)
  --invocationid        GUID            set invocationid (otherwise random)
- --outputdir   OUTPUTDIR       set output directory
  --adminpass   PASSWORD        choose admin password (otherwise random)
  --krbtgtpass  PASSWORD        choose krbtgt password (otherwise random)
  --machinepass PASSWORD        choose machine password (otherwise random)
@@ -211,7 +83,13 @@ provision.pl [options]
  --wheel       GROUPNAME       choose 'wheel' privileged group
  --users       GROUPNAME       choose 'users' group
  --quiet                       Be quiet
-
+ --blank                       do not add users or groups, just the structure
+ --server-role  ROLE            Set server role to provision for (default standalone)
+ --partitions-only              Configure Samba's partitions, but do not modify them (ie, join a BDC)
+ --ldap-base                   output only an LDIF file, suitable for creating an LDAP baseDN
+ --ldap-backend LDAPSERVER      LDAP server to use for this provision
+ --ldap-backend-type  TYPE      OpenLDAP or Fedora DS
+ --aci          ACI             An arbitary LDIF fragment, particularly useful to loading a backend ACI value into a target LDAP server
 You must provide at least a realm and domain
 
 ");
@@ -231,66 +109,90 @@ if (options["realm"] == undefined ||
        ShowHelp();
 }
 
-options.realm        = strlower(options.realm);
-options['host-name'] = strlower(options['host-name']);
-options.domain       = strupper(options.domain);
-options.netbiosname  = strupper(options['host-name']);
+/* cope with an initially blank smb.conf */
+var lp = loadparm_init();
+lp.set("realm", options.realm);
+lp.set("workgroup", options.domain);
+lp.set("server role", options["server-role"]);
+lp.reload();
 
-if (options.hostip == undefined) {
-       var list = sys_interfaces();
-       options.hostip = list[0];
-}
-
-message("Provisioning for " + options.domain + " in realm " + options.realm);
-
-options.root    = findnss(getpwnam, "root", "root");
-options.nobody  = findnss(getpwnam, "nobody", "nobody");
-options.nogroup = findnss(getgrnam, "nogroup", "nogroup", "nobody");
-options.wheel   = findnss(getgrnam, "wheel", "wheel", "root");
-options.users   = findnss(getgrnam, "users", "users", "guest", "other");
-
-
-options.dnsdomain = strlower(options.realm);
-options.dnsname   = strlower(options['host-name']) + "." + options.dnsdomain;
-options.basedn    = "DC=" + join(",DC=", split(".", options.realm));
-
-/*
-  setup the substitution object
-*/
-var subobj = new Object();
-subobj.DOMAINGUID   = randguid();
-subobj.DOMAINSID    = randsid();
-subobj.HOSTGUID     = randguid();
-subobj.INVOCATIONID = randguid();
-subobj.KRBTGTPASS   = randpass(12);
-subobj.MACHINEPASS  = randpass(12);
-subobj.ADMINPASS    = randpass(12);
-subobj.DEFAULTSITE  = "Default-First-Site-Name";
-subobj.NEWGUID      = randguid;
-subobj.NTTIME       = nttime;
-subobj.LDAPTIME     = ldaptime;
-subobj.DATESTRING   = datestring;
-subobj.USN          = nextusn;
+var subobj = provision_guess();
 for (r in options) {
        var key = strupper(join("", split("-", r)));
        subobj[key] = options[r];
 }
 
+var blank = (options["blank"] != undefined);
+var ldapbackend = (options["ldap-backend"] != undefined);
+var ldapbackendtype = options["ldap-backend-type"];
+var partitions_only = (options["partitions-only"] != undefined);
+var paths = provision_default_paths(subobj);
+if (options["aci"] != undefined) {
+       message("set ACI: %s\n", subobj["ACI"]);
+}
+
+message("set DOMAIN SID: %s\n", subobj["DOMAINSID"]);
 
-var extradata = "";
-extradata = add_foreign(extradata, "S-1-5-7",  "Anonymous",           "${NOBODY}");
-extradata = add_foreign(extradata, "S-1-1-0",  "World",               "${NOGROUP}");
-extradata = add_foreign(extradata, "S-1-5-2",  "Network",             "${NOGROUP}");
-extradata = add_foreign(extradata, "S-1-5-18", "System",              "${ROOT}");
-extradata = add_foreign(extradata, "S-1-5-11", "Authenticated Users", "${USERS}");
+provision_fix_subobj(subobj, paths);
 
-message("Using administrator password: " + subobj.ADMINPASS);
+if (ldapbackend) {
+       if (options["ldap-backend"] == "ldapi") {
+               subobj.LDAPBACKEND = subobj.LDAPI_URI;
+       }
+       if (ldapbackendtype == undefined) {
+              
+       } else if (ldapbackendtype == "openldap") {
+               subobj.LDAPMODULE = "normalise,entryuuid";
+               subobj.TDB_MODULES_LIST = "";
+       } else if (ldapbackendtype == "fedora-ds") {
+               subobj.LDAPMODULE = "nsuniqueid";
+       }
+       subobj.BACKEND_MOD = subobj.LDAPMODULE + ",paged_searches";
+       subobj.DOMAINDN_LDB = subobj.LDAPBACKEND;
+       subobj.CONFIGDN_LDB = subobj.LDAPBACKEND;
+       subobj.SCHEMADN_LDB = subobj.LDAPBACKEND;
+       message("LDAP module: %s on backend: %s\n", subobj.LDAPMODULE, subobj.LDAPBACKEND);
+}
+
+if (!provision_validate(subobj, message)) {
+       return -1;
+}
+
+var system_session = system_session();
+var creds = options.get_credentials();
+message("Provisioning for %s in realm %s\n", subobj.DOMAIN, subobj.REALM);
+message("Using administrator password: %s\n", subobj.ADMINPASS);
+if (partitions_only) {
+       provision_become_dc(subobj, message, false, paths, system_session);
+} else {
+       provision(subobj, message, blank, paths, system_session, creds, ldapbackend);
+       provision_dns(subobj, message, paths, system_session, creds);
+       message("To reproduce this provision, run with:\n");
+/*     There has to be a better way than this... */
+       message("--realm='%s' --domain='%s' \\\n", subobj.REALM_CONF, subobj.DOMAIN_CONF);
+       if (subobj.DOMAINGUID != undefined) {
+                message("--domain-guid='%s' \\\n", subobj.DOMAINGUID);
+       }
+       if (subobj.HOSTGUID != undefined) {
+                message("--host-guid='%s' \\\n", subobj.HOSTGUID);
+       }
+       message("--policy-guid='%s' --host-name='%s' --host-ip='%s' \\\n", subobj.POLICYGUID, subobj.HOSTNAME, subobj.HOSTIP);
+       if (subobj.INVOCATIONID != undefined) {
+               message("--invocationid='%s' \\\n", subobj.INVOCATIONID);
+       }
+       message("--adminpass='%s' --krbtgtpass='%s' \\\n", subobj.ADMINPASS, subobj.KRBTGTPASS);
+       message("--machinepass='%s' --dnspass='%s' \\\n", subobj.MACHINEPASS, subobj.DNSPASS);
+       message("--root='%s' --nobody='%s' --nogroup='%s' \\\n", subobj.ROOT, subobj.NOBODY, subobj.NOGROUP);
+       message("--wheel='%s' --users='%s' --server-role='%s' \\\n", subobj.WHEEL, subobj.USERS, subobj.SERVERROLE);
+       if (ldapbackend) {
+               message("--ldap-backend='%s' \\\n", subobj.LDAPBACKEND);
+       }
+       if (ldapbackendtype != undefined) {
+               message("--ldap-backend-type='%s' \\\n", + ldapbackendtype);
+       }
+       message("--aci='" + subobj.ACI + "' \\\n")
+}
 
-setup_ldb("hklm.ldif", "hklm.ldb", subobj);
-setup_ldb("provision.ldif", "sam.ldb", subobj, extradata);
-setup_ldb("rootdse.ldif", "rootdse.ldb", subobj);
-setup_ldb("secrets.ldif", "secrets.ldb", subobj);
-setup_file("provision.zone", subobj.DNSDOMAIN + ".zone", subobj);
 
-message("All OK");
+message("All OK\n");
 return 0;