[SCM] Samba Shared Repository - branch master updated

Andrew Tridgell tridge at samba.org
Mon Feb 15 03:57:56 MST 2010


The branch, master has been updated
       via  2dff1f4... s4-test: use local ldb for urgent_replication test
       via  3035c7c... s4-ldb: fixed permissions on urgent_replication.py
       via  1ca2bd7... s4-test: minor fixes to urgent_replication.py
       via  f5de126... s4-drs: Test situations for Urgent Replication
       via  cf1ed06... s4-drs: Function for accessing dsdb_load_partition_usn from Python
       via  5aa42f8... s4-drs: Fixes bugs regarding Urgent Replication on wrong situations
      from  ddbda92... spoolss: disable GetPrinterDriver level 101 (as called by XP).

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 2dff1f45f72f77dd94fcab6552e2c957df9aac5f
Author: Andrew Tridgell <tridge at samba.org>
Date:   Mon Feb 15 21:21:55 2010 +1100

    s4-test: use local ldb for urgent_replication test
    
    This test only currently works on a local ldb, as it needs system
    access.

commit 3035c7c2ad2cb41ca01405ea7b2566fcc058fbe7
Author: Andrew Tridgell <tridge at samba.org>
Date:   Mon Feb 15 21:18:13 2010 +1100

    s4-ldb: fixed permissions on urgent_replication.py

commit 1ca2bd78b95ad5a0852620ba56481f19a9d3a084
Author: Andrew Tridgell <tridge at samba.org>
Date:   Mon Feb 15 21:14:42 2010 +1100

    s4-test: minor fixes to urgent_replication.py
    
    - fix usage name
    - remove unnecessary python functions
    - remote unused gc ldb

commit f5de126b858cdfed5c763662dce270a7c4e42e57
Author: Fernando J V da Silva <fernandojvsilva at yahoo.com.br>
Date:   Thu Feb 4 17:03:41 2010 -0200

    s4-drs: Test situations for Urgent Replication
    
    Checks if the partition's uSNUrgent is updated or not, depending
    on the class of the object which is created, modified or deleted.
    
    Signed-off-by: Andrew Tridgell <tridge at samba.org>

commit cf1ed0678acaf1a802d4b90c464edb638ab1364f
Author: Fernando J V da Silva <fernandojvsilva at yahoo.com.br>
Date:   Thu Feb 4 16:58:31 2010 -0200

    s4-drs: Function for accessing dsdb_load_partition_usn from Python
    
    Returns both uSNHighest and uSNUrgent as a dict object in Python
    from a given partition dn.
    
    Signed-off-by: Andrew Tridgell <tridge at samba.org>

commit 5aa42f8010d0895b5bc5018567c431f79c40f8f6
Author: Fernando J V da Silva <fernandojvsilva at yahoo.com.br>
Date:   Thu Feb 4 16:46:52 2010 -0200

    s4-drs: Fixes bugs regarding Urgent Replication on wrong situations
    
    It fixes the bug which causes an urgent replication to be enabled
    incorrectly when an object is modified, but it should happen only
    when it was created. This patch also fixes the bug that enable an
    urgent replication when an object is deleted, but it should happen
    only when it was modified and fixes the bug that does not enable
    an urgent replication when an object is deleted and it should happen
    only when it is deleted (not when it is modified).
    
    Signed-off-by: Andrew Tridgell <tridge at samba.org>

-----------------------------------------------------------------------

Summary of changes:
 source4/dsdb/samdb/ldb_modules/repl_meta_data.c    |   23 +-
 source4/lib/ldb/tests/python/urgent_replication.py |  391 ++++++++++++++++++++
 source4/scripting/python/pyglue.c                  |   50 +++
 source4/selftest/tests.sh                          |    1 +
 4 files changed, 458 insertions(+), 7 deletions(-)
 create mode 100755 source4/lib/ldb/tests/python/urgent_replication.py


Changeset truncated at 500 lines:

diff --git a/source4/dsdb/samdb/ldb_modules/repl_meta_data.c b/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
index 725ba2a..51611ac 100644
--- a/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
+++ b/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
@@ -92,7 +92,7 @@ struct replmd_replicated_request {
 
 enum urgent_situation {
 	REPL_URGENT_ON_CREATE = 1,
-	REPL_URGENT_ON_UPDATE = 3, /* activated on creating as well*/
+	REPL_URGENT_ON_UPDATE = 2,
 	REPL_URGENT_ON_DELETE = 4
 };
 
@@ -103,10 +103,10 @@ static const struct {
 } urgent_objects[] = {
 		{"nTDSDSA", (REPL_URGENT_ON_CREATE | REPL_URGENT_ON_DELETE)},
 		{"crossRef", (REPL_URGENT_ON_CREATE | REPL_URGENT_ON_DELETE)},
-		{"attributeSchema", REPL_URGENT_ON_UPDATE},
-		{"classSchema", REPL_URGENT_ON_UPDATE},
-		{"secret", REPL_URGENT_ON_UPDATE},
-		{"rIDManager", REPL_URGENT_ON_UPDATE},
+		{"attributeSchema", (REPL_URGENT_ON_CREATE | REPL_URGENT_ON_UPDATE)},
+		{"classSchema", (REPL_URGENT_ON_CREATE | REPL_URGENT_ON_UPDATE)},
+		{"secret", (REPL_URGENT_ON_CREATE | REPL_URGENT_ON_UPDATE)},
+		{"rIDManager", (REPL_URGENT_ON_CREATE | REPL_URGENT_ON_UPDATE)},
 		{NULL, 0}
 };
 
@@ -1077,6 +1077,7 @@ static int replmd_update_rpmd(struct ldb_module *module,
 	struct ldb_result *res;
 	struct ldb_context *ldb;
 	struct ldb_message_element *objectclass_el;
+	enum urgent_situation situation;
 
 	ldb = ldb_module_get_ctx(module);
 
@@ -1098,9 +1099,17 @@ static int replmd_update_rpmd(struct ldb_module *module,
 		return LDB_ERR_OPERATIONS_ERROR;
 	}
 
+	/* if isDeleted is present and is TRUE, then we consider we are deleting,
+	 * otherwise we consider we are updating */
+	if (ldb_msg_check_string_attribute(msg, "isDeleted", "TRUE")) {
+		situation = REPL_URGENT_ON_DELETE;
+	} else {
+		situation = REPL_URGENT_ON_UPDATE;
+	}
+
 	objectclass_el = ldb_msg_find_element(res->msgs[0], "objectClass");
 	if (is_urgent && replmd_check_urgent_objectclass(objectclass_el,
-							REPL_URGENT_ON_UPDATE)) {
+							situation)) {
 		*is_urgent = true;
 	}
 
@@ -1133,7 +1142,7 @@ static int replmd_update_rpmd(struct ldb_module *module,
 			return ret;
 		}
 
-		if (is_urgent && !*is_urgent) {
+		if (is_urgent && !*is_urgent && (situation == REPL_URGENT_ON_UPDATE)) {
 			*is_urgent = replmd_check_urgent_attribute(&msg->elements[i]);
 		}
 
diff --git a/source4/lib/ldb/tests/python/urgent_replication.py b/source4/lib/ldb/tests/python/urgent_replication.py
new file mode 100755
index 0000000..752a95e
--- /dev/null
+++ b/source4/lib/ldb/tests/python/urgent_replication.py
@@ -0,0 +1,391 @@
+#!/usr/bin/python
+# -*- coding: utf-8 -*-
+# This is a port of the original in testprogs/ejs/ldap.js
+
+import getopt
+import optparse
+import sys
+import time
+import random
+import base64
+import os
+
+sys.path.append("bin/python")
+sys.path.append("../lib/subunit/python")
+
+import samba.getopt as options
+
+from samba.auth import system_session
+from ldb import SCOPE_BASE, LdbError
+from ldb import ERR_NO_SUCH_OBJECT
+from ldb import Message, MessageElement, Dn
+from ldb import FLAG_MOD_REPLACE
+from samba import Ldb
+from samba import glue
+
+from subunit.run import SubunitTestRunner
+import unittest
+
+from samba.ndr import ndr_pack, ndr_unpack
+from samba.dcerpc import security
+
+parser = optparse.OptionParser("urgent_replication [options] <host>")
+sambaopts = options.SambaOptions(parser)
+parser.add_option_group(sambaopts)
+parser.add_option_group(options.VersionOptions(parser))
+# use command line creds if available
+credopts = options.CredentialsOptions(parser)
+parser.add_option_group(credopts)
+opts, args = parser.parse_args()
+
+if len(args) < 1:
+    parser.print_usage()
+    sys.exit(1)
+
+host = args[0]
+
+lp = sambaopts.get_loadparm()
+creds = credopts.get_credentials(lp)
+
+class UrgentReplicationTests(unittest.TestCase):
+
+    def delete_force(self, ldb, dn):
+        try:
+            ldb.delete(dn)
+        except LdbError, (num, _):
+            self.assertEquals(num, ERR_NO_SUCH_OBJECT)
+
+    def find_basedn(self, ldb):
+        res = ldb.search(base="", expression="", scope=SCOPE_BASE,
+                         attrs=["defaultNamingContext"])
+        self.assertEquals(len(res), 1)
+        return res[0]["defaultNamingContext"][0]
+
+    def setUp(self):
+        self.ldb = ldb
+        self.base_dn = self.find_basedn(ldb)
+
+        print "baseDN: %s\n" % self.base_dn
+
+    def test_nonurgent_object(self):
+        '''Test if the urgent replication is not activated
+           when handling a non urgent object'''
+        self.ldb.add({
+            "dn": "cn=nonurgenttest,cn=users," + self.base_dn,
+            "objectclass":"user",
+            "samaccountname":"nonurgenttest",
+            "description":"nonurgenttest description"});
+
+        ''' urgent replication should not be enabled when creating '''
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should not be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=nonurgenttest,cn=users," + self.base_dn)
+        m["description"] = MessageElement("new description", FLAG_MOD_REPLACE,
+          "description")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should not be enabled when deleting '''
+        self.delete_force(self.ldb, "cn=nonurgenttest,cn=users," + self.base_dn)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+    def test_nTDSDSA_object(self):
+        '''Test if the urgent replication is activated
+           when handling a nTDSDSA object'''
+        self.ldb.add({
+            "dn": "cn=test server,cn=Servers,cn=Default-First-Site-Name,cn=Sites,cn=Configuration," + self.base_dn,
+            "objectclass":"server",
+            "cn":"test server",
+            "name":"test server",
+            "systemFlags":"50000000"});
+
+        self.ldb.add_ldif(
+            """dn: cn=NTDS Settings test,cn=test server,cn=Servers,cn=Default-First-Site-Name,cn=Sites,cn=Configuration,%s""" % (self.base_dn) + """
+objectclass: nTDSDSA
+cn: NTDS Settings test
+options: 1
+instanceType: 4
+systemFlags: 33554432""", ["relax:0"]);
+
+        ''' urgent replication should be enabled when creation '''
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Configuration," + self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should NOT be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=NTDS Settings test,cn=test server,cn=Servers,cn=Default-First-Site-Name,cn=Sites,cn=Configuration," + self.base_dn)
+        m["options"] = MessageElement("0", FLAG_MOD_REPLACE,
+          "options")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Configuration," + self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should be enabled when deleting '''
+        self.delete_force(self.ldb, "cn=NTDS Settings test,cn=test server,cn=Servers,cn=Default-First-Site-Name,cn=Sites,cn=Configuration," + self.base_dn)
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Configuration," + self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        self.delete_force(self.ldb, "cn=test server,cn=Servers,cn=Default-First-Site-Name,cn=Sites,cn=Configuration," + self.base_dn)
+
+
+    def test_crossRef_object(self):
+        '''Test if the urgent replication is activated
+           when handling a crossRef object'''
+        self.ldb.add({
+                      "dn": "CN=test crossRef,CN=Partitions,CN=Configuration,"+ self.base_dn,
+                      "objectClass": "crossRef",
+                      "cn": "test crossRef",
+                      "instanceType": "4",
+                      "nCName": self.base_dn,
+                      "showInAdvancedViewOnly": "TRUE",
+                      "name": "test crossRef",
+                      "systemFlags": "1"});
+
+        ''' urgent replication should be enabled when creating '''
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Configuration," + self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should NOT be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=test crossRef,CN=Partitions,CN=Configuration," + self.base_dn)
+        m["systemFlags"] = MessageElement("0", FLAG_MOD_REPLACE,
+          "systemFlags")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Configuration," + self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+        ''' urgent replication should be enabled when deleting '''
+        self.delete_force(self.ldb, "cn=test crossRef,CN=Partitions,CN=Configuration," + self.base_dn)
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Configuration," + self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+
+    def test_attributeSchema_object(self):
+        '''Test if the urgent replication is activated
+           when handling an attributeSchema object'''
+
+        try:
+            self.ldb.add_ldif(
+                              """dn: CN=test attributeSchema,cn=Schema,CN=Configuration,%s""" % self.base_dn + """
+objectClass: attributeSchema
+cn: test attributeSchema
+instanceType: 4
+isSingleValued: FALSE
+showInAdvancedViewOnly: FALSE
+attributeID: 0.9.2342.19200300.100.1.1
+attributeSyntax: 2.5.5.12
+adminDisplayName: test attributeSchema
+adminDescription: test attributeSchema
+oMSyntax: 64
+systemOnly: FALSE
+searchFlags: 8
+lDAPDisplayName: test attributeSchema
+name: test attributeSchema
+systemFlags: 0""", ["relax:0"]);
+
+            ''' urgent replication should be enabled when creating '''
+            res = glue.dsdb_load_partition_usn(self.ldb, "cn=Schema,cn=Configuration," + self.base_dn)
+            self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        except LdbError:
+            print "Not testing urgent replication when creating attributeSchema object ...\n"
+
+        ''' urgent replication should be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "CN=test attributeSchema,CN=Schema,CN=Configuration," + self.base_dn)
+        m["lDAPDisplayName"] = MessageElement("updated test attributeSchema", FLAG_MOD_REPLACE,
+          "lDAPDisplayName")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Schema,cn=Configuration," + self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+    def test_classSchema_object(self):
+        '''Test if the urgent replication is activated
+           when handling a classSchema object'''
+        try:
+            self.ldb.add_ldif(
+                            """dn: CN=test classSchema,CN=Schema,CN=Configuration,%s""" % self.base_dn + """
+objectClass: classSchema
+cn: test classSchema
+instanceType: 4
+subClassOf: top
+governsID: 1.2.840.113556.1.5.999
+rDNAttID: cn
+showInAdvancedViewOnly: TRUE
+adminDisplayName: test classSchema
+adminDescription: test classSchema
+objectClassCategory: 1
+lDAPDisplayName: test classSchema
+name: test classSchema
+systemOnly: FALSE
+systemPossSuperiors: dfsConfiguration
+systemMustContain: msDFS-SchemaMajorVersion
+defaultSecurityDescriptor: D:(A;;RPWPCRCCDCLCLORCWOWDSDDTSW;;;DA)(A;;RPWPCRCCD
+ CLCLORCWOWDSDDTSW;;;SY)(A;;RPLCLORC;;;AU)(A;;RPWPCRCCDCLCLORCWOWDSDDTSW;;;CO)
+systemFlags: 16
+defaultHidingValue: TRUE""", ["relax:0"]);
+
+            ''' urgent replication should be enabled when creating '''
+            res = glue.dsdb_load_partition_usn(self.ldb, "cn=Schema,cn=Configuration," + self.base_dn)
+            self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        except LdbError:
+            print "Not testing urgent replication when creating classSchema object ...\n"
+
+        ''' urgent replication should be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "CN=test classSchema,CN=Schema,CN=Configuration," + self.base_dn)
+        m["lDAPDisplayName"] = MessageElement("updated test classSchema", FLAG_MOD_REPLACE,
+          "lDAPDisplayName")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, "cn=Schema,cn=Configuration," + self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+    def test_secret_object(self):
+
+        '''Test if the urgent replication is activated
+           when handling a secret object'''
+
+        self.ldb.add({
+            "dn": "cn=test secret,cn=System," + self.base_dn,
+            "objectClass":"secret",
+            "cn":"test secret",
+            "name":"test secret",
+            "currentValue":"xxxxxxx"});
+
+
+        ''' urgent replication should be enabled when creationg '''
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=test secret,cn=System," + self.base_dn)
+        m["currentValue"] = MessageElement("yyyyyyyy", FLAG_MOD_REPLACE,
+          "currentValue")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should NOT be enabled when deleting '''
+        self.delete_force(self.ldb, "cn=test secret,cn=System," + self.base_dn)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+    def test_rIDManager_object(self):
+        '''Test if the urgent replication is activated
+            when handling a rIDManager object'''
+        self.ldb.add_ldif(
+            """dn: CN=RID Manager test,CN=System,%s""" % self.base_dn + """
+objectClass: rIDManager
+cn: RID Manager test
+instanceType: 4
+showInAdvancedViewOnly: TRUE
+name: RID Manager test
+systemFlags: -1946157056
+isCriticalSystemObject: TRUE
+rIDAvailablePool: 133001-1073741823""", ["relax:0"])
+
+        ''' urgent replication should be enabled when creating '''
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should be enabled when modifying '''
+        m = Message()
+        m.dn = Dn(ldb, "CN=RID Manager test,CN=System," + self.base_dn)
+        m["systemFlags"] = MessageElement("0", FLAG_MOD_REPLACE,
+          "systemFlags")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should NOT be enabled when deleting '''
+        self.delete_force(self.ldb, "CN=RID Manager test,CN=System," + self.base_dn)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+    def test_urgent_attributes(self):
+        '''Test if the urgent replication is activated
+            when handling urgent attributes of an object'''
+
+        self.ldb.add({
+            "dn": "cn=user UrgAttr test,cn=users," + self.base_dn,
+            "objectclass":"user",
+            "samaccountname":"user UrgAttr test",
+            "userAccountControl":"1",
+            "lockoutTime":"0",
+            "pwdLastSet":"0",
+            "description":"urgent attributes test description"});
+
+        ''' urgent replication should NOT be enabled when creating '''
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should be enabled when modifying userAccountControl '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=user UrgAttr test,cn=users," + self.base_dn)
+        m["userAccountControl"] = MessageElement("0", FLAG_MOD_REPLACE,
+          "userAccountControl")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should be enabled when modifying lockoutTime '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=user UrgAttr test,cn=users," + self.base_dn)
+        m["lockoutTime"] = MessageElement("1", FLAG_MOD_REPLACE,
+          "lockoutTime")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should be enabled when modifying pwdLastSet '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=user UrgAttr test,cn=users," + self.base_dn)
+        m["pwdLastSet"] = MessageElement("1", FLAG_MOD_REPLACE,
+          "pwdLastSet")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should NOT be enabled when modifying a not-urgent attribute '''
+        m = Message()
+        m.dn = Dn(ldb, "cn=user UrgAttr test,cn=users," + self.base_dn)
+        m["description"] = MessageElement("updated urgent attributes test description",
+                                          FLAG_MOD_REPLACE, "description")
+        ldb.modify(m)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+        ''' urgent replication should NOT be enabled when deleting '''
+        self.delete_force(self.ldb, "cn=user UrgAttr test,cn=users," + self.base_dn)
+        res = glue.dsdb_load_partition_usn(self.ldb, self.base_dn)
+        self.assertNotEquals(res["uSNHighest"], res["uSNUrgent"]);
+
+
+if not "://" in host:
+    if os.path.isfile(host):
+        host = "tdb://%s" % host
+    else:
+        host = "ldap://%s" % host
+
+
+ldb = Ldb(host, credentials=creds, session_info=system_session(), lp=lp)
+
+runner = SubunitTestRunner()
+rc = 0
+if not runner.run(unittest.makeSuite(UrgentReplicationTests)).wasSuccessful():
+    rc = 1
+sys.exit(rc)
diff --git a/source4/scripting/python/pyglue.c b/source4/scripting/python/pyglue.c
index 5279a0b..57e6043 100644
--- a/source4/scripting/python/pyglue.c
+++ b/source4/scripting/python/pyglue.c
@@ -438,6 +438,54 @@ static PyObject *py_dsdb_make_schema_global(PyObject *self, PyObject *args)
 	Py_RETURN_NONE;
 }
 
+static PyObject *py_dsdb_load_partition_usn(PyObject *self, PyObject *args)
+{
+	PyObject *py_dn, *py_ldb, *result;
+	struct ldb_dn *dn;
+	uint64_t highest_uSN, urgent_uSN;
+	struct ldb_context *ldb;
+	TALLOC_CTX *mem_ctx;
+	int ret;
+
+	mem_ctx = talloc_new(NULL);
+	if (mem_ctx == NULL) {
+	   PyErr_NoMemory();
+	   return NULL;
+	}
+
+	if (!PyArg_ParseTuple(args, "OO", &py_ldb, &py_dn)) {
+	   talloc_free(mem_ctx);
+	   return NULL;
+	}
+
+	PyErr_LDB_OR_RAISE(py_ldb, ldb);
+
+	if (!PyObject_AsDn(mem_ctx, py_dn, ldb, &dn)) {
+	   talloc_free(mem_ctx);
+	   return NULL;
+	}
+
+	ret = dsdb_load_partition_usn(ldb, dn, &highest_uSN, &urgent_uSN);
+	if (ret != LDB_SUCCESS) {
+	   char *errstr = talloc_asprintf(mem_ctx, "Failed to load partition uSN - %s", ldb_errstring(ldb));
+	   PyErr_SetString(PyExc_RuntimeError, errstr);


-- 
Samba Shared Repository


More information about the samba-cvs mailing list