static NTSTATUS init_registry_data_action(struct db_context *db, void *private_data) { NTSTATUS status; TALLOC_CTX *frame = talloc_stackframe(); struct regval_ctr *values; int i; /* loop over all of the predefined paths and add each component */ for (i=0; builtin_registry_paths[i] != NULL; i++) { if (regdb_key_exists(db, builtin_registry_paths[i])) { continue; } status = werror_to_ntstatus(init_registry_key_internal(db, builtin_registry_paths[i])); if (!NT_STATUS_IS_OK(status)) { goto done; } } /* loop over all of the predefined values and add each component */ for (i=0; builtin_registry_values[i].path != NULL; i++) { WERROR werr; werr = regval_ctr_init(frame, &values); if (!W_ERROR_IS_OK(werr)) { status = werror_to_ntstatus(werr); goto done; } regdb_fetch_values_internal(db, builtin_registry_values[i].path, values); /* preserve existing values across restarts. Only add new ones */ if (!regval_ctr_key_exists(values, builtin_registry_values[i].valuename)) { regdb_ctr_add_value(values, &builtin_registry_values[i]); status = regdb_store_values_internal(db, builtin_registry_values[i].path, values); if (!NT_STATUS_IS_OK(status)) { goto done; } } TALLOC_FREE(values); } status = NT_STATUS_OK; done: TALLOC_FREE(frame); return status; }
WERROR init_registry_data(void) { WERROR werr; TALLOC_CTX *frame = talloc_stackframe(); struct regval_ctr *values; int i; /* * First, check for the existence of the needed keys and values. * If all do already exist, we can save the writes. */ for (i=0; builtin_registry_paths[i] != NULL; i++) { if (!regdb_key_exists(regdb, builtin_registry_paths[i])) { goto do_init; } } for (i=0; builtin_registry_values[i].path != NULL; i++) { werr = regval_ctr_init(frame, &values); W_ERROR_NOT_OK_GOTO_DONE(werr); regdb_fetch_values_internal(regdb, builtin_registry_values[i].path, values); if (!regval_ctr_key_exists(values, builtin_registry_values[i].valuename)) { TALLOC_FREE(values); goto do_init; } TALLOC_FREE(values); } werr = WERR_OK; goto done; do_init: /* * There are potentially quite a few store operations which are all * indiviually wrapped in tdb transactions. Wrapping them in a single * transaction gives just a single transaction_commit() to actually do * its fsync()s. See tdb/common/transaction.c for info about nested * transaction behaviour. */ werr = regdb_trans_do(regdb, init_registry_data_action, NULL); done: TALLOC_FREE(frame); return werr; }
/** * Initialize a key in the registry: * create each component key of the specified path, * wrapped in one db transaction. */ WERROR init_registry_key(const char *add_path) { struct init_registry_key_context init_ctx; if (regdb_key_exists(regdb, add_path)) { return WERR_OK; } init_ctx.add_path = add_path; return regdb_trans_do(regdb, init_registry_key_action, &init_ctx); }
/** * Initialize a key in the registry: * create each component key of the specified path, * wrapped in one db transaction. */ WERROR init_registry_key(const char *add_path) { struct init_registry_key_context init_ctx; if (regdb_key_exists(regdb, add_path)) { return WERR_OK; } init_ctx.add_path = add_path; return ntstatus_to_werror(dbwrap_trans_do(regdb, init_registry_key_action, &init_ctx)); }