s4:libnet/py_net.c: "py_net_finddc" - add an "address" parameter
authorMatthias Dieter Wallnöfer <mdw@samba.org>
Tue, 22 Nov 2011 21:26:06 +0000 (22:26 +0100)
committerStefan Metzmacher <metze@samba.org>
Sat, 26 Nov 2011 09:34:58 +0000 (10:34 +0100)
This is useful for a new "samba-tool domain info" command.

Patch inspired by Matthieu Patou.

Signed-off-by: Stefan Metzmacher <metze@samba.org>
source4/libnet/py_net.c
source4/scripting/bin/samba_spnupdate
source4/scripting/python/samba/join.py
source4/scripting/python/samba/netcmd/common.py

index a8db2976a665555631c3d0922eec4b2a2035cc76..7c90572e1268be5af4bf2618be2575863ac91751 100644 (file)
@@ -580,23 +580,31 @@ static PyObject *py_net_replicate_chunk(py_net_Object *self, PyObject *args, PyO
 /*
   find a DC given a domain name and server type
  */
-static PyObject *py_net_finddc(py_net_Object *self, PyObject *args)
+static PyObject *py_net_finddc(py_net_Object *self, PyObject *args, PyObject *kwargs)
 {
-       const char *domain_name;
+       const char *domain = NULL, *address = NULL;
        unsigned server_type;
        NTSTATUS status;
        struct finddcs *io;
        TALLOC_CTX *mem_ctx;
        PyObject *ret;
+       const char * const kwnames[] = { "flags", "domain", "address", NULL };
 
-       if (!PyArg_ParseTuple(args, "sI", &domain_name, &server_type)) {
+       if (!PyArg_ParseTupleAndKeywords(args, kwargs, "I|ss",
+                                        discard_const_p(char *, kwnames),
+                                        &server_type, &domain, &address)) {
                return NULL;
        }
 
        mem_ctx = talloc_new(self->mem_ctx);
 
        io = talloc_zero(mem_ctx, struct finddcs);
-       io->in.domain_name = domain_name;
+       if (domain != NULL) {
+               io->in.domain_name = domain;
+       }
+       if (address != NULL) {
+               io->in.server_address = address;
+       }
        io->in.minimum_dc_flags = server_type;
 
        status = finddcs_cldap(io, io,
@@ -624,8 +632,8 @@ static const char py_net_replicate_init_doc[] = "replicate_init(samdb, lp, drspi
 static const char py_net_replicate_chunk_doc[] = "replicate_chunk(state, level, ctr, schema)\n"
                                         "Process replication for one chunk";
 
-static const char py_net_finddc_doc[] = "finddc(domain, server_type)\n"
-                                        "find a DC with the specified server_type bits. Return the DNS name";
+static const char py_net_finddc_doc[] = "finddc(flags=server_type, domain=None, address=None)\n"
+                                        "Find a DC with the specified 'server_type' bits. The 'domain' and/or 'address' have to be used as additional search criteria. Returns the whole netlogon struct";
 
 static PyMethodDef net_obj_methods[] = {
        {"join_member", (PyCFunction)py_net_join_member, METH_VARARGS|METH_KEYWORDS, py_net_join_member_doc},
@@ -638,7 +646,7 @@ static PyMethodDef net_obj_methods[] = {
        {"vampire", (PyCFunction)py_net_vampire, METH_VARARGS|METH_KEYWORDS, py_net_vampire_doc},
        {"replicate_init", (PyCFunction)py_net_replicate_init, METH_VARARGS|METH_KEYWORDS, py_net_replicate_init_doc},
        {"replicate_chunk", (PyCFunction)py_net_replicate_chunk, METH_VARARGS|METH_KEYWORDS, py_net_replicate_chunk_doc},
-       {"finddc", (PyCFunction)py_net_finddc, METH_VARARGS, py_net_finddc_doc},
+       {"finddc", (PyCFunction)py_net_finddc, METH_KEYWORDS, py_net_finddc_doc},
        { NULL }
 };
 
index 10da1d917b651bbda47bae6f8427dfdb9a87b8cf..52a51d8b81ceda46e18bae1690346fa96c0660ee 100755 (executable)
@@ -190,7 +190,7 @@ def call_rodc_update(d):
 
     net = Net(creds=creds, lp=lp)
     try:
-        cldap_ret = net.finddc(domainnbt.NBT_SERVER_DS | nbt.NBT_SERVER_WRITABLE)
+        cldap_ret = net.finddc(domain=domain, flags=nbt.NBT_SERVER_DS | nbt.NBT_SERVER_WRITABLE)
     except Exception, reason:
         print("Unable to find writeable DC for domain '%s' to send DRS writeSPN to : %s" % (domain, reason))
         sys.exit(1)
index 4252a2d7d428799bb695834584951365e6504a4b..3ae1a2c81d77511e4557baae06fec6729bf82da3 100644 (file)
@@ -195,7 +195,7 @@ class dc_join(object):
     def find_dc(ctx, domain):
         '''find a writeable DC for the given domain'''
         try:
-            ctx.cldap_ret = ctx.net.finddc(domainnbt.NBT_SERVER_LDAP | nbt.NBT_SERVER_DS | nbt.NBT_SERVER_WRITABLE)
+            ctx.cldap_ret = ctx.net.finddc(domain=domain, flags=nbt.NBT_SERVER_LDAP | nbt.NBT_SERVER_DS | nbt.NBT_SERVER_WRITABLE)
         except Exception:
             raise Exception("Failed to find a writeable DC for domain '%s'" % domain)
         if ctx.cldap_ret.client_site is not None and ctx.cldap_ret.client_site != "":
index 234fad3c03251a80ee908c1ed6373b0c5f9fac99..cc97fc523fb7f0580c7876d7bc82de612acea023 100644 (file)
@@ -52,10 +52,13 @@ def netcmd_dnsname(lp):
     return lp.get('netbios name').lower() + "." + lp.get('realm').lower()
 
 
-def netcmd_finddc(lp, creds):
-    '''return domain-name of a writable/ldap-capable DC for the domain.'''
+def netcmd_finddc(lp, creds, realm=None):
+    '''Return domain-name of a writable/ldap-capable DC for the default
+       domain (parameter "realm" in smb.conf) unless another realm has been
+       specified as argument'''
     net = Net(creds=creds, lp=lp)
-    realm = lp.get('realm')
-    cldap_ret = net.finddc(realm,
-                nbt.NBT_SERVER_LDAP | nbt.NBT_SERVER_DS | nbt.NBT_SERVER_WRITABLE)
+    if realm is None:
+        realm = lp.get('realm')
+    cldap_ret = net.finddc(domain=realm,
+                flags=nbt.NBT_SERVER_LDAP | nbt.NBT_SERVER_DS | nbt.NBT_SERVER_WRITABLE)
     return cldap_ret.pdc_dns_name