summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/ldb/ldb_tdb/ldb_tdb.c30
-rw-r--r--lib/ldb/ldb_tdb/ldb_tdb.h2
2 files changed, 32 insertions, 0 deletions
diff --git a/lib/ldb/ldb_tdb/ldb_tdb.c b/lib/ldb/ldb_tdb/ldb_tdb.c
index 16e4b8ea26e..a530a454b29 100644
--- a/lib/ldb/ldb_tdb/ldb_tdb.c
+++ b/lib/ldb/ldb_tdb/ldb_tdb.c
@@ -410,6 +410,10 @@ static int ltdb_modified(struct ldb_module *module, struct ldb_dn *dn)
ret = ltdb_cache_reload(module);
}
+ if (ret != LDB_SUCCESS) {
+ ltdb->reindex_failed = true;
+ }
+
return ret;
}
@@ -1404,9 +1408,17 @@ static int ltdb_start_trans(struct ldb_module *module)
ltdb_index_transaction_start(module);
+ ltdb->reindex_failed = false;
+
return LDB_SUCCESS;
}
+/*
+ * Forward declaration to allow prepare_commit to in fact abort the
+ * transaction
+ */
+static int ltdb_del_trans(struct ldb_module *module);
+
static int ltdb_prepare_commit(struct ldb_module *module)
{
int ret;
@@ -1417,6 +1429,24 @@ static int ltdb_prepare_commit(struct ldb_module *module)
return LDB_SUCCESS;
}
+ /*
+ * Check if the last re-index failed.
+ *
+ * This can happen if for example a duplicate value was marked
+ * unique. We must not write a partial re-index into the DB.
+ */
+ if (ltdb->reindex_failed) {
+ /*
+ * We must instead abort the transaction so we get the
+ * old values and old index back
+ */
+ ltdb_del_trans(module);
+ ldb_set_errstring(ldb_module_get_ctx(module),
+ "Failure during re-index, so "
+ "transaction must be aborted.");
+ return LDB_ERR_OPERATIONS_ERROR;
+ }
+
ret = ltdb_index_transaction_commit(module);
if (ret != LDB_SUCCESS) {
tdb_transaction_cancel(ltdb->tdb);
diff --git a/lib/ldb/ldb_tdb/ldb_tdb.h b/lib/ldb/ldb_tdb/ldb_tdb.h
index 7e182495928..9591ee59bf1 100644
--- a/lib/ldb/ldb_tdb/ldb_tdb.h
+++ b/lib/ldb/ldb_tdb/ldb_tdb.h
@@ -37,6 +37,8 @@ struct ltdb_private {
bool read_only;
+ bool reindex_failed;
+
const struct ldb_schema_syntax *GUID_index_syntax;
};