summaryrefslogtreecommitdiff
path: root/source3/libnet/libnet_samsync.c
diff options
context:
space:
mode:
authorAndrew Tridgell <tridge@samba.org>2008-12-03 17:47:39 +1100
committerAndrew Tridgell <tridge@samba.org>2008-12-03 17:47:39 +1100
commita226d86dcec393b2cd657d5441c3041dfdf5cd8f (patch)
tree03ef7f3207607a4e5351bf50892b0a39dcf6f219 /source3/libnet/libnet_samsync.c
parent30eff4f31b497ac94d8ee02ee2ec24bc8865ce0d (diff)
parent85b8cccab072bab263061654b677bc84826646c9 (diff)
downloadsamba-a226d86dcec393b2cd657d5441c3041dfdf5cd8f.tar.gz
samba-a226d86dcec393b2cd657d5441c3041dfdf5cd8f.tar.bz2
samba-a226d86dcec393b2cd657d5441c3041dfdf5cd8f.zip
Merge branch 'master' of ssh://git.samba.org/data/git/samba
Diffstat (limited to 'source3/libnet/libnet_samsync.c')
-rw-r--r--source3/libnet/libnet_samsync.c200
1 files changed, 169 insertions, 31 deletions
diff --git a/source3/libnet/libnet_samsync.c b/source3/libnet/libnet_samsync.c
index 00caf2b8c1..4351810169 100644
--- a/source3/libnet/libnet_samsync.c
+++ b/source3/libnet/libnet_samsync.c
@@ -282,47 +282,112 @@ static const char *samsync_debug_str(TALLOC_CTX *mem_ctx,
* libnet_samsync
*/
-NTSTATUS libnet_samsync(enum netr_SamDatabaseID database_id,
- struct samsync_context *ctx)
+void libnet_init_netr_ChangeLogEntry(struct samsync_object *o,
+ struct netr_ChangeLogEntry *e)
+{
+ ZERO_STRUCTP(e);
+
+ e->db_index = o->database_id;
+ e->delta_type = o->object_type;
+
+ switch (e->delta_type) {
+ case NETR_DELTA_DOMAIN:
+ case NETR_DELTA_DELETE_GROUP:
+ case NETR_DELTA_RENAME_GROUP:
+ case NETR_DELTA_DELETE_USER:
+ case NETR_DELTA_RENAME_USER:
+ case NETR_DELTA_DELETE_ALIAS:
+ case NETR_DELTA_RENAME_ALIAS:
+ case NETR_DELTA_DELETE_TRUST:
+ case NETR_DELTA_DELETE_ACCOUNT:
+ case NETR_DELTA_DELETE_SECRET:
+ case NETR_DELTA_DELETE_GROUP2:
+ case NETR_DELTA_DELETE_USER2:
+ case NETR_DELTA_MODIFY_COUNT:
+ break;
+ case NETR_DELTA_USER:
+ case NETR_DELTA_GROUP:
+ case NETR_DELTA_GROUP_MEMBER:
+ case NETR_DELTA_ALIAS:
+ case NETR_DELTA_ALIAS_MEMBER:
+ e->object_rid = o->object_identifier.rid;
+ break;
+ case NETR_DELTA_SECRET:
+ e->object.object_name = o->object_identifier.name;
+ e->flags = NETR_CHANGELOG_NAME_INCLUDED;
+ break;
+ case NETR_DELTA_TRUSTED_DOMAIN:
+ case NETR_DELTA_ACCOUNT:
+ case NETR_DELTA_POLICY:
+ e->object.object_sid = o->object_identifier.sid;
+ e->flags = NETR_CHANGELOG_SID_INCLUDED;
+ break;
+ default:
+ break;
+ }
+}
+
+/**
+ * libnet_samsync_delta
+ */
+
+static NTSTATUS libnet_samsync_delta(TALLOC_CTX *mem_ctx,
+ enum netr_SamDatabaseID database_id,
+ uint64_t *sequence_num,
+ struct samsync_context *ctx,
+ struct netr_ChangeLogEntry *e)
{
NTSTATUS result;
- TALLOC_CTX *mem_ctx;
+ NTSTATUS callback_status;
const char *logon_server = ctx->cli->desthost;
const char *computername = global_myname();
struct netr_Authenticator credential;
struct netr_Authenticator return_authenticator;
uint16_t restart_state = 0;
uint32_t sync_context = 0;
- const char *debug_str;
DATA_BLOB session_key;
ZERO_STRUCT(return_authenticator);
- if (!(mem_ctx = talloc_init("libnet_samsync"))) {
- return NT_STATUS_NO_MEMORY;
- }
-
- debug_str = samsync_debug_str(mem_ctx, ctx->mode, database_id);
- if (debug_str) {
- d_fprintf(stderr, "%s\n", debug_str);
- }
-
do {
struct netr_DELTA_ENUM_ARRAY *delta_enum_array = NULL;
- NTSTATUS callback_status;
netlogon_creds_client_step(ctx->cli->dc, &credential);
- result = rpccli_netr_DatabaseSync2(ctx->cli, mem_ctx,
- logon_server,
- computername,
- &credential,
- &return_authenticator,
- database_id,
- restart_state,
- &sync_context,
- &delta_enum_array,
- 0xffff);
+ if (ctx->single_object_replication &&
+ !ctx->force_full_replication) {
+ result = rpccli_netr_DatabaseRedo(ctx->cli, mem_ctx,
+ logon_server,
+ computername,
+ &credential,
+ &return_authenticator,
+ *e,
+ 0,
+ &delta_enum_array);
+ } else if (!ctx->force_full_replication &&
+ sequence_num && (*sequence_num > 0)) {
+ result = rpccli_netr_DatabaseDeltas(ctx->cli, mem_ctx,
+ logon_server,
+ computername,
+ &credential,
+ &return_authenticator,
+ database_id,
+ sequence_num,
+ &delta_enum_array,
+ 0xffff);
+ } else {
+ result = rpccli_netr_DatabaseSync2(ctx->cli, mem_ctx,
+ logon_server,
+ computername,
+ &credential,
+ &return_authenticator,
+ database_id,
+ restart_state,
+ &sync_context,
+ &delta_enum_array,
+ 0xffff);
+ }
+
if (NT_STATUS_EQUAL(result, NT_STATUS_NOT_SUPPORTED)) {
return result;
}
@@ -346,9 +411,10 @@ NTSTATUS libnet_samsync(enum netr_SamDatabaseID database_id,
delta_enum_array);
/* Process results */
- callback_status = ctx->delta_fn(mem_ctx, database_id,
- delta_enum_array,
- NT_STATUS_IS_OK(result), ctx);
+ callback_status = ctx->ops->process_objects(mem_ctx, database_id,
+ delta_enum_array,
+ sequence_num,
+ ctx);
if (!NT_STATUS_IS_OK(callback_status)) {
result = callback_status;
goto out;
@@ -362,14 +428,86 @@ NTSTATUS libnet_samsync(enum netr_SamDatabaseID database_id,
} while (NT_STATUS_EQUAL(result, STATUS_MORE_ENTRIES));
out:
- if (NT_STATUS_IS_ERR(result) && !ctx->error_message) {
+
+ return result;
+}
+
+/**
+ * libnet_samsync
+ */
+
+NTSTATUS libnet_samsync(enum netr_SamDatabaseID database_id,
+ struct samsync_context *ctx)
+{
+ NTSTATUS status = NT_STATUS_OK;
+ NTSTATUS callback_status;
+ TALLOC_CTX *mem_ctx;
+ const char *debug_str;
+ uint64_t sequence_num = 0;
+ int i = 0;
+
+ if (!(mem_ctx = talloc_new(ctx))) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ if (!ctx->ops) {
+ return NT_STATUS_INVALID_PARAMETER;
+ }
+
+ if (ctx->ops->startup) {
+ status = ctx->ops->startup(mem_ctx, ctx,
+ database_id, &sequence_num);
+ if (!NT_STATUS_IS_OK(status)) {
+ goto done;
+ }
+ }
+
+ debug_str = samsync_debug_str(mem_ctx, ctx->mode, database_id);
+ if (debug_str) {
+ d_fprintf(stderr, "%s\n", debug_str);
+ }
+
+ if (!ctx->single_object_replication) {
+ status = libnet_samsync_delta(mem_ctx, database_id,
+ &sequence_num, ctx, NULL);
+ goto done;
+ }
+
+ for (i=0; i<ctx->num_objects; i++) {
+
+ struct netr_ChangeLogEntry e;
+
+ if (ctx->objects[i].database_id != database_id) {
+ continue;
+ }
+
+ libnet_init_netr_ChangeLogEntry(&ctx->objects[i], &e);
+
+ status = libnet_samsync_delta(mem_ctx, database_id,
+ &sequence_num, ctx, &e);
+ if (!NT_STATUS_IS_OK(status)) {
+ goto done;
+ }
+ }
+
+ done:
+
+ if (NT_STATUS_IS_OK(status) && ctx->ops->finish) {
+ callback_status = ctx->ops->finish(mem_ctx, ctx,
+ database_id, sequence_num);
+ if (!NT_STATUS_IS_OK(callback_status)) {
+ status = callback_status;
+ }
+ }
+
+ if (NT_STATUS_IS_ERR(status) && !ctx->error_message) {
ctx->error_message = talloc_asprintf(ctx,
"Failed to fetch %s database: %s",
samsync_database_str(database_id),
- nt_errstr(result));
+ nt_errstr(status));
- if (NT_STATUS_EQUAL(result, NT_STATUS_NOT_SUPPORTED)) {
+ if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_SUPPORTED)) {
ctx->error_message =
talloc_asprintf_append(ctx->error_message,
@@ -380,7 +518,7 @@ NTSTATUS libnet_samsync(enum netr_SamDatabaseID database_id,
talloc_destroy(mem_ctx);
- return result;
+ return status;
}
/**