r23798: updated old Temple Place FSF addresses to new URL
[samba.git] / source4 / dsdb / samdb / ldb_modules / objectguid.c
index 7e475d1ef44df051315b4e78c9952c03bb4c1d5f..d7e74cf38d8b8a56d43a01b46d2a896584a78d04 100644 (file)
@@ -3,6 +3,7 @@
 
    Copyright (C) Simo Sorce  2004-2006
    Copyright (C) Andrew Bartlett <abartlet@samba.org> 2005
+   Copyright (C) Andrew Tridgell 2005
 
      ** NOTE! The following LGPL license applies to the ldb
      ** library. This does NOT imply that all of Samba is released
@@ -11,7 +12,7 @@
    This library is free software; you can redistribute it and/or
    modify it under the terms of the GNU Lesser General Public
    License as published by the Free Software Foundation; either
-   version 2 of the License, or (at your option) any later version.
+   version 3 of the License, or (at your option) any later version.
 
    This library is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
@@ -19,8 +20,7 @@
    Lesser General Public License for more details.
 
    You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, write to the Free Software
-   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+   License along with this library; if not, see <http://www.gnu.org/licenses/>.
 */
 
 /*
@@ -34,7 +34,7 @@
  */
 
 #include "includes.h"
-#include "ldb/include/includes.h"
+#include "ldb/include/ldb_includes.h"
 #include "librpc/gen_ndr/ndr_misc.h"
 
 static struct ldb_message_element *objectguid_find_attribute(const struct ldb_message *msg, const char *name)
@@ -79,6 +79,29 @@ static int add_time_element(struct ldb_message *msg, const char *attr, time_t t)
        return 0;
 }
 
+/*
+  add a uint64_t element to a record
+*/
+static int add_uint64_element(struct ldb_message *msg, const char *attr, uint64_t v)
+{
+       struct ldb_message_element *el;
+
+       if (ldb_msg_find_element(msg, attr) != NULL) {
+               return 0;
+       }
+
+       if (ldb_msg_add_fmt(msg, attr, "%llu", (unsigned long long)v) != 0) {
+               return -1;
+       }
+
+       el = ldb_msg_find_element(msg, attr);
+       /* always set as replace. This works because on add ops, the flag
+          is ignored */
+       el->flags = LDB_FLAG_MOD_REPLACE;
+
+       return 0;
+}
+
 /* add_record: add objectGUID attribute */
 static int objectguid_add(struct ldb_module *module, struct ldb_request *req)
 {
@@ -87,6 +110,7 @@ static int objectguid_add(struct ldb_module *module, struct ldb_request *req)
        struct ldb_message *msg;
        struct ldb_val v;
        struct GUID guid;
+       uint64_t seq_num;
        NTSTATUS nt_status;
        int ret;
        time_t t = time(NULL);
@@ -126,7 +150,7 @@ static int objectguid_add(struct ldb_module *module, struct ldb_request *req)
                return LDB_ERR_OPERATIONS_ERROR;
        }
 
-       ret = ldb_msg_add_value(msg, "objectGUID", &v);
+       ret = ldb_msg_add_value(msg, "objectGUID", &v, NULL);
        if (ret) {
                talloc_free(down_req);
                return ret;
@@ -138,6 +162,16 @@ static int objectguid_add(struct ldb_module *module, struct ldb_request *req)
                return LDB_ERR_OPERATIONS_ERROR;
        }
 
+       /* Get a sequence number from the backend */
+       ret = ldb_sequence_number(module->ldb, LDB_SEQ_NEXT, &seq_num);
+       if (ret == LDB_SUCCESS) {
+               if (add_uint64_element(msg, "uSNCreated", seq_num) != 0 ||
+                   add_uint64_element(msg, "uSNChanged", seq_num) != 0) {
+                       talloc_free(down_req);
+                       return LDB_ERR_OPERATIONS_ERROR;
+               }
+       }
+
        ldb_set_timeout_from_prev_req(module->ldb, req, down_req);
 
        /* go on with the call chain */
@@ -159,6 +193,7 @@ static int objectguid_modify(struct ldb_module *module, struct ldb_request *req)
        struct ldb_message *msg;
        int ret;
        time_t t = time(NULL);
+       uint64_t seq_num;
 
        ldb_debug(module->ldb, LDB_DEBUG_TRACE, "objectguid_add_record\n");
 
@@ -186,6 +221,15 @@ static int objectguid_modify(struct ldb_module *module, struct ldb_request *req)
                return LDB_ERR_OPERATIONS_ERROR;
        }
 
+       /* Get a sequence number from the backend */
+       ret = ldb_sequence_number(module->ldb, LDB_SEQ_NEXT, &seq_num);
+       if (ret == LDB_SUCCESS) {
+               if (add_uint64_element(msg, "uSNChanged", seq_num) != 0) {
+                       talloc_free(down_req);
+                       return LDB_ERR_OPERATIONS_ERROR;
+               }
+       }
+
        ldb_set_timeout_from_prev_req(module->ldb, req, down_req);
 
        /* go on with the call chain */