mirror of
https://github.com/samba-team/samba.git
synced 2025-01-11 05:18:09 +03:00
s3-registry: move regf based reg_api calls into own file.
Guenther
This commit is contained in:
parent
323f729df0
commit
91e8f8ded2
@ -620,6 +620,8 @@ REG_INIT_FULL_OBJ = registry/reg_init_full.o
|
||||
REGFIO_OBJ = registry/regfio.o \
|
||||
$(REG_PARSE_PRS_OBJ)
|
||||
|
||||
REG_API_REGF_OBJ = registry/reg_api_regf.o
|
||||
|
||||
REGOBJS_OBJ = registry/reg_objects.o
|
||||
|
||||
REG_BACKENDS_BASE_OBJ = registry/reg_backend_db.o
|
||||
@ -638,7 +640,6 @@ REG_BACKENDS_EXTRA_OBJ = registry/reg_backend_printing.o \
|
||||
REG_BASE_OBJ = registry/reg_api.o \
|
||||
registry/reg_dispatcher.o \
|
||||
registry/reg_cachehook.o \
|
||||
$(REGFIO_OBJ) \
|
||||
$(REGOBJS_OBJ) \
|
||||
registry/reg_util_internal.o \
|
||||
lib/util_nttoken.o \
|
||||
@ -756,7 +757,8 @@ PROFILES_OBJ = utils/profiles.o \
|
||||
$(LIBSMB_ERR_OBJ) \
|
||||
$(PARAM_OBJ) \
|
||||
$(LIB_OBJ) $(LIB_DUMMY_OBJ) \
|
||||
$(POPT_LIB_OBJ)
|
||||
$(POPT_LIB_OBJ) \
|
||||
$(REGFIO_OBJ)
|
||||
|
||||
OPLOCK_OBJ = smbd/oplock.o smbd/oplock_irix.o smbd/oplock_linux.o \
|
||||
smbd/oplock_onefs.o
|
||||
@ -904,6 +906,8 @@ SMBD_OBJ_BASE = $(PARAM_WITHOUT_REG_OBJ) $(SMBD_OBJ_SRV) $(LIBSMB_OBJ) \
|
||||
$(SMBLDAP_OBJ) $(LIBNET_OBJ) \
|
||||
$(LIBSMBCONF_OBJ) \
|
||||
$(PRIVILEGES_BASIC_OBJ) \
|
||||
$(REGFIO_OBJ) \
|
||||
$(REG_API_REGF_OBJ) \
|
||||
$(LIBNDR_XATTR_OBJ)
|
||||
|
||||
PRINTING_OBJ = printing/pcap.o printing/print_svid.o printing/print_aix.o \
|
||||
@ -1164,6 +1168,7 @@ NET_OBJ = $(NET_OBJ1) \
|
||||
$(REG_SMBCONF_OBJ) \
|
||||
$(LIBNET_OBJ) $(LIBNET_DSSYNC_OBJ) $(LIBNET_SAMSYNC_OBJ) \
|
||||
$(LIBSMBCONF_OBJ) \
|
||||
$(REGFIO_OBJ) \
|
||||
$(PRIVILEGES_BASIC_OBJ) \
|
||||
$(LIB_EVENTLOG_OBJ) localedir.o
|
||||
|
||||
|
@ -169,8 +169,6 @@ WERROR reg_getkeysecurity(TALLOC_CTX *mem_ctx, struct registry_key *key,
|
||||
WERROR reg_setkeysecurity(struct registry_key *key,
|
||||
struct security_descriptor *psecdesc);
|
||||
WERROR reg_getversion(uint32_t *version);
|
||||
WERROR reg_restorekey(struct registry_key *key, const char *fname);
|
||||
WERROR reg_savekey(struct registry_key *key, const char *fname);
|
||||
WERROR reg_deleteallvalues(struct registry_key *key);
|
||||
WERROR reg_open_path(TALLOC_CTX *mem_ctx, const char *orig_path,
|
||||
uint32 desired_access, const struct security_token *token,
|
||||
@ -189,6 +187,11 @@ WERROR reg_create_path(TALLOC_CTX *mem_ctx, const char *orig_path,
|
||||
WERROR reg_delete_path(const struct security_token *token,
|
||||
const char *orig_path);
|
||||
|
||||
/* The following definitions come from registry/reg_api_regf.c */
|
||||
|
||||
WERROR reg_restorekey(struct registry_key *key, const char *fname);
|
||||
WERROR reg_savekey(struct registry_key *key, const char *fname);
|
||||
|
||||
/* The following definitions come from registry/reg_init_basic.c */
|
||||
|
||||
WERROR registry_init_common(void);
|
||||
|
@ -65,7 +65,6 @@
|
||||
#include "includes.h"
|
||||
#include "registry.h"
|
||||
#include "reg_cachehook.h"
|
||||
#include "regfio.h"
|
||||
#include "reg_util_internal.h"
|
||||
#include "reg_backend_db.h"
|
||||
#include "reg_dispatcher.h"
|
||||
@ -748,277 +747,6 @@ WERROR reg_getversion(uint32_t *version)
|
||||
return WERR_OK;
|
||||
}
|
||||
|
||||
/*******************************************************************
|
||||
Note: topkeypat is the *full* path that this *key will be
|
||||
loaded into (including the name of the key)
|
||||
********************************************************************/
|
||||
|
||||
static WERROR reg_load_tree(REGF_FILE *regfile, const char *topkeypath,
|
||||
REGF_NK_REC *key)
|
||||
{
|
||||
REGF_NK_REC *subkey;
|
||||
struct registry_key_handle registry_key;
|
||||
struct regval_ctr *values;
|
||||
struct regsubkey_ctr *subkeys;
|
||||
int i;
|
||||
char *path = NULL;
|
||||
WERROR result = WERR_OK;
|
||||
|
||||
/* initialize the struct registry_key_handle structure */
|
||||
|
||||
registry_key.ops = reghook_cache_find(topkeypath);
|
||||
if (!registry_key.ops) {
|
||||
DEBUG(0, ("reg_load_tree: Failed to assign registry_ops "
|
||||
"to [%s]\n", topkeypath));
|
||||
return WERR_BADFILE;
|
||||
}
|
||||
|
||||
registry_key.name = talloc_strdup(regfile->mem_ctx, topkeypath);
|
||||
if (!registry_key.name) {
|
||||
DEBUG(0, ("reg_load_tree: Talloc failed for reg_key.name!\n"));
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
|
||||
/* now start parsing the values and subkeys */
|
||||
|
||||
result = regsubkey_ctr_init(regfile->mem_ctx, &subkeys);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
result = regval_ctr_init(subkeys, &values);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
/* copy values into the struct regval_ctr */
|
||||
|
||||
for (i=0; i<key->num_values; i++) {
|
||||
regval_ctr_addvalue(values, key->values[i].valuename,
|
||||
key->values[i].type,
|
||||
key->values[i].data,
|
||||
(key->values[i].data_size & ~VK_DATA_IN_OFFSET));
|
||||
}
|
||||
|
||||
/* copy subkeys into the struct regsubkey_ctr */
|
||||
|
||||
key->subkey_index = 0;
|
||||
while ((subkey = regfio_fetch_subkey( regfile, key ))) {
|
||||
result = regsubkey_ctr_addkey(subkeys, subkey->keyname);
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
TALLOC_FREE(subkeys);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
/* write this key and values out */
|
||||
|
||||
if (!store_reg_values(®istry_key, values)
|
||||
|| !store_reg_keys(®istry_key, subkeys))
|
||||
{
|
||||
DEBUG(0,("reg_load_tree: Failed to load %s!\n", topkeypath));
|
||||
result = WERR_REG_IO_FAILURE;
|
||||
}
|
||||
|
||||
TALLOC_FREE(subkeys);
|
||||
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
return result;
|
||||
}
|
||||
|
||||
/* now continue to load each subkey registry tree */
|
||||
|
||||
key->subkey_index = 0;
|
||||
while ((subkey = regfio_fetch_subkey(regfile, key))) {
|
||||
path = talloc_asprintf(regfile->mem_ctx,
|
||||
"%s\\%s",
|
||||
topkeypath,
|
||||
subkey->keyname);
|
||||
if (path == NULL) {
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
result = reg_load_tree(regfile, path, subkey);
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/*******************************************************************
|
||||
********************************************************************/
|
||||
|
||||
static WERROR restore_registry_key(struct registry_key_handle *krecord,
|
||||
const char *fname)
|
||||
{
|
||||
REGF_FILE *regfile;
|
||||
REGF_NK_REC *rootkey;
|
||||
WERROR result;
|
||||
|
||||
/* open the registry file....fail if the file already exists */
|
||||
|
||||
regfile = regfio_open(fname, (O_RDONLY), 0);
|
||||
if (regfile == NULL) {
|
||||
DEBUG(0, ("restore_registry_key: failed to open \"%s\" (%s)\n",
|
||||
fname, strerror(errno)));
|
||||
return ntstatus_to_werror(map_nt_error_from_unix(errno));
|
||||
}
|
||||
|
||||
/* get the rootkey from the regf file and then load the tree
|
||||
via recursive calls */
|
||||
|
||||
if (!(rootkey = regfio_rootkey(regfile))) {
|
||||
regfio_close(regfile);
|
||||
return WERR_REG_FILE_INVALID;
|
||||
}
|
||||
|
||||
result = reg_load_tree(regfile, krecord->name, rootkey);
|
||||
|
||||
/* cleanup */
|
||||
|
||||
regfio_close(regfile);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
WERROR reg_restorekey(struct registry_key *key, const char *fname)
|
||||
{
|
||||
return restore_registry_key(key->key, fname);
|
||||
}
|
||||
|
||||
/********************************************************************
|
||||
********************************************************************/
|
||||
|
||||
static WERROR reg_write_tree(REGF_FILE *regfile, const char *keypath,
|
||||
REGF_NK_REC *parent)
|
||||
{
|
||||
REGF_NK_REC *key;
|
||||
struct regval_ctr *values;
|
||||
struct regsubkey_ctr *subkeys;
|
||||
int i, num_subkeys;
|
||||
char *key_tmp = NULL;
|
||||
char *keyname, *parentpath;
|
||||
char *subkeypath = NULL;
|
||||
char *subkeyname;
|
||||
struct registry_key_handle registry_key;
|
||||
WERROR result = WERR_OK;
|
||||
struct security_descriptor *sec_desc = NULL;
|
||||
|
||||
if (!regfile) {
|
||||
return WERR_GENERAL_FAILURE;
|
||||
}
|
||||
|
||||
if (!keypath) {
|
||||
return WERR_OBJECT_PATH_INVALID;
|
||||
}
|
||||
|
||||
/* split up the registry key path */
|
||||
|
||||
key_tmp = talloc_strdup(regfile->mem_ctx, keypath);
|
||||
if (!key_tmp) {
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
if (!reg_split_key(key_tmp, &parentpath, &keyname)) {
|
||||
return WERR_OBJECT_PATH_INVALID;
|
||||
}
|
||||
|
||||
if (!keyname) {
|
||||
keyname = parentpath;
|
||||
}
|
||||
|
||||
/* we need a registry_key_handle object here to enumerate subkeys and values */
|
||||
|
||||
ZERO_STRUCT(registry_key);
|
||||
|
||||
registry_key.name = talloc_strdup(regfile->mem_ctx, keypath);
|
||||
if (registry_key.name == NULL) {
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
|
||||
registry_key.ops = reghook_cache_find(registry_key.name);
|
||||
if (registry_key.ops == NULL) {
|
||||
return WERR_BADFILE;
|
||||
}
|
||||
|
||||
/* lookup the values and subkeys */
|
||||
|
||||
result = regsubkey_ctr_init(regfile->mem_ctx, &subkeys);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
result = regval_ctr_init(subkeys, &values);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
fetch_reg_keys(®istry_key, subkeys);
|
||||
fetch_reg_values(®istry_key, values);
|
||||
|
||||
result = regkey_get_secdesc(regfile->mem_ctx, ®istry_key, &sec_desc);
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
goto done;
|
||||
}
|
||||
|
||||
/* write out this key */
|
||||
|
||||
key = regfio_write_key(regfile, keyname, values, subkeys, sec_desc,
|
||||
parent);
|
||||
if (key == NULL) {
|
||||
result = WERR_CAN_NOT_COMPLETE;
|
||||
goto done;
|
||||
}
|
||||
|
||||
/* write each one of the subkeys out */
|
||||
|
||||
num_subkeys = regsubkey_ctr_numkeys(subkeys);
|
||||
for (i=0; i<num_subkeys; i++) {
|
||||
subkeyname = regsubkey_ctr_specific_key(subkeys, i);
|
||||
subkeypath = talloc_asprintf(regfile->mem_ctx, "%s\\%s",
|
||||
keypath, subkeyname);
|
||||
if (subkeypath == NULL) {
|
||||
result = WERR_NOMEM;
|
||||
goto done;
|
||||
}
|
||||
result = reg_write_tree(regfile, subkeypath, key);
|
||||
if (!W_ERROR_IS_OK(result))
|
||||
goto done;
|
||||
}
|
||||
|
||||
DEBUG(6, ("reg_write_tree: wrote key [%s]\n", keypath));
|
||||
|
||||
done:
|
||||
TALLOC_FREE(subkeys);
|
||||
TALLOC_FREE(registry_key.name);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static WERROR backup_registry_key(struct registry_key_handle *krecord,
|
||||
const char *fname)
|
||||
{
|
||||
REGF_FILE *regfile;
|
||||
WERROR result;
|
||||
|
||||
/* open the registry file....fail if the file already exists */
|
||||
|
||||
regfile = regfio_open(fname, (O_RDWR|O_CREAT|O_EXCL),
|
||||
(S_IREAD|S_IWRITE));
|
||||
if (regfile == NULL) {
|
||||
DEBUG(0,("backup_registry_key: failed to open \"%s\" (%s)\n",
|
||||
fname, strerror(errno) ));
|
||||
return ntstatus_to_werror(map_nt_error_from_unix(errno));
|
||||
}
|
||||
|
||||
/* write the registry tree to the file */
|
||||
|
||||
result = reg_write_tree(regfile, krecord->name, NULL);
|
||||
|
||||
/* cleanup */
|
||||
|
||||
regfio_close(regfile);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
WERROR reg_savekey(struct registry_key *key, const char *fname)
|
||||
{
|
||||
return backup_registry_key(key->key, fname);
|
||||
}
|
||||
|
||||
/**********************************************************************
|
||||
* Higher level utility functions
|
||||
**********************************************************************/
|
||||
|
301
source3/registry/reg_api_regf.c
Normal file
301
source3/registry/reg_api_regf.c
Normal file
@ -0,0 +1,301 @@
|
||||
/*
|
||||
* Unix SMB/CIFS implementation.
|
||||
* Virtual Windows Registry Layer
|
||||
* Copyright (C) Volker Lendecke 2006
|
||||
* Copyright (C) Michael Adam 2007-2008
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "includes.h"
|
||||
#include "registry.h"
|
||||
#include "reg_cachehook.h"
|
||||
#include "regfio.h"
|
||||
#include "reg_util_internal.h"
|
||||
#include "reg_dispatcher.h"
|
||||
#include "reg_objects.h"
|
||||
|
||||
#undef DBGC_CLASS
|
||||
#define DBGC_CLASS DBGC_REGISTRY
|
||||
|
||||
/*******************************************************************
|
||||
Note: topkeypat is the *full* path that this *key will be
|
||||
loaded into (including the name of the key)
|
||||
********************************************************************/
|
||||
|
||||
static WERROR reg_load_tree(REGF_FILE *regfile, const char *topkeypath,
|
||||
REGF_NK_REC *key)
|
||||
{
|
||||
REGF_NK_REC *subkey;
|
||||
struct registry_key_handle registry_key;
|
||||
struct regval_ctr *values;
|
||||
struct regsubkey_ctr *subkeys;
|
||||
int i;
|
||||
char *path = NULL;
|
||||
WERROR result = WERR_OK;
|
||||
|
||||
/* initialize the struct registry_key_handle structure */
|
||||
|
||||
registry_key.ops = reghook_cache_find(topkeypath);
|
||||
if (!registry_key.ops) {
|
||||
DEBUG(0, ("reg_load_tree: Failed to assign registry_ops "
|
||||
"to [%s]\n", topkeypath));
|
||||
return WERR_BADFILE;
|
||||
}
|
||||
|
||||
registry_key.name = talloc_strdup(regfile->mem_ctx, topkeypath);
|
||||
if (!registry_key.name) {
|
||||
DEBUG(0, ("reg_load_tree: Talloc failed for reg_key.name!\n"));
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
|
||||
/* now start parsing the values and subkeys */
|
||||
|
||||
result = regsubkey_ctr_init(regfile->mem_ctx, &subkeys);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
result = regval_ctr_init(subkeys, &values);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
/* copy values into the struct regval_ctr */
|
||||
|
||||
for (i=0; i<key->num_values; i++) {
|
||||
regval_ctr_addvalue(values, key->values[i].valuename,
|
||||
key->values[i].type,
|
||||
key->values[i].data,
|
||||
(key->values[i].data_size & ~VK_DATA_IN_OFFSET));
|
||||
}
|
||||
|
||||
/* copy subkeys into the struct regsubkey_ctr */
|
||||
|
||||
key->subkey_index = 0;
|
||||
while ((subkey = regfio_fetch_subkey( regfile, key ))) {
|
||||
result = regsubkey_ctr_addkey(subkeys, subkey->keyname);
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
TALLOC_FREE(subkeys);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
/* write this key and values out */
|
||||
|
||||
if (!store_reg_values(®istry_key, values)
|
||||
|| !store_reg_keys(®istry_key, subkeys))
|
||||
{
|
||||
DEBUG(0,("reg_load_tree: Failed to load %s!\n", topkeypath));
|
||||
result = WERR_REG_IO_FAILURE;
|
||||
}
|
||||
|
||||
TALLOC_FREE(subkeys);
|
||||
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
return result;
|
||||
}
|
||||
|
||||
/* now continue to load each subkey registry tree */
|
||||
|
||||
key->subkey_index = 0;
|
||||
while ((subkey = regfio_fetch_subkey(regfile, key))) {
|
||||
path = talloc_asprintf(regfile->mem_ctx,
|
||||
"%s\\%s",
|
||||
topkeypath,
|
||||
subkey->keyname);
|
||||
if (path == NULL) {
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
result = reg_load_tree(regfile, path, subkey);
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/*******************************************************************
|
||||
********************************************************************/
|
||||
|
||||
static WERROR restore_registry_key(struct registry_key_handle *krecord,
|
||||
const char *fname)
|
||||
{
|
||||
REGF_FILE *regfile;
|
||||
REGF_NK_REC *rootkey;
|
||||
WERROR result;
|
||||
|
||||
/* open the registry file....fail if the file already exists */
|
||||
|
||||
regfile = regfio_open(fname, (O_RDONLY), 0);
|
||||
if (regfile == NULL) {
|
||||
DEBUG(0, ("restore_registry_key: failed to open \"%s\" (%s)\n",
|
||||
fname, strerror(errno)));
|
||||
return ntstatus_to_werror(map_nt_error_from_unix(errno));
|
||||
}
|
||||
|
||||
/* get the rootkey from the regf file and then load the tree
|
||||
via recursive calls */
|
||||
|
||||
if (!(rootkey = regfio_rootkey(regfile))) {
|
||||
regfio_close(regfile);
|
||||
return WERR_REG_FILE_INVALID;
|
||||
}
|
||||
|
||||
result = reg_load_tree(regfile, krecord->name, rootkey);
|
||||
|
||||
/* cleanup */
|
||||
|
||||
regfio_close(regfile);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
WERROR reg_restorekey(struct registry_key *key, const char *fname)
|
||||
{
|
||||
return restore_registry_key(key->key, fname);
|
||||
}
|
||||
|
||||
/********************************************************************
|
||||
********************************************************************/
|
||||
|
||||
static WERROR reg_write_tree(REGF_FILE *regfile, const char *keypath,
|
||||
REGF_NK_REC *parent)
|
||||
{
|
||||
REGF_NK_REC *key;
|
||||
struct regval_ctr *values;
|
||||
struct regsubkey_ctr *subkeys;
|
||||
int i, num_subkeys;
|
||||
char *key_tmp = NULL;
|
||||
char *keyname, *parentpath;
|
||||
char *subkeypath = NULL;
|
||||
char *subkeyname;
|
||||
struct registry_key_handle registry_key;
|
||||
WERROR result = WERR_OK;
|
||||
struct security_descriptor *sec_desc = NULL;
|
||||
|
||||
if (!regfile) {
|
||||
return WERR_GENERAL_FAILURE;
|
||||
}
|
||||
|
||||
if (!keypath) {
|
||||
return WERR_OBJECT_PATH_INVALID;
|
||||
}
|
||||
|
||||
/* split up the registry key path */
|
||||
|
||||
key_tmp = talloc_strdup(regfile->mem_ctx, keypath);
|
||||
if (!key_tmp) {
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
if (!reg_split_key(key_tmp, &parentpath, &keyname)) {
|
||||
return WERR_OBJECT_PATH_INVALID;
|
||||
}
|
||||
|
||||
if (!keyname) {
|
||||
keyname = parentpath;
|
||||
}
|
||||
|
||||
/* we need a registry_key_handle object here to enumerate subkeys and values */
|
||||
|
||||
ZERO_STRUCT(registry_key);
|
||||
|
||||
registry_key.name = talloc_strdup(regfile->mem_ctx, keypath);
|
||||
if (registry_key.name == NULL) {
|
||||
return WERR_NOMEM;
|
||||
}
|
||||
|
||||
registry_key.ops = reghook_cache_find(registry_key.name);
|
||||
if (registry_key.ops == NULL) {
|
||||
return WERR_BADFILE;
|
||||
}
|
||||
|
||||
/* lookup the values and subkeys */
|
||||
|
||||
result = regsubkey_ctr_init(regfile->mem_ctx, &subkeys);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
result = regval_ctr_init(subkeys, &values);
|
||||
W_ERROR_NOT_OK_RETURN(result);
|
||||
|
||||
fetch_reg_keys(®istry_key, subkeys);
|
||||
fetch_reg_values(®istry_key, values);
|
||||
|
||||
result = regkey_get_secdesc(regfile->mem_ctx, ®istry_key, &sec_desc);
|
||||
if (!W_ERROR_IS_OK(result)) {
|
||||
goto done;
|
||||
}
|
||||
|
||||
/* write out this key */
|
||||
|
||||
key = regfio_write_key(regfile, keyname, values, subkeys, sec_desc,
|
||||
parent);
|
||||
if (key == NULL) {
|
||||
result = WERR_CAN_NOT_COMPLETE;
|
||||
goto done;
|
||||
}
|
||||
|
||||
/* write each one of the subkeys out */
|
||||
|
||||
num_subkeys = regsubkey_ctr_numkeys(subkeys);
|
||||
for (i=0; i<num_subkeys; i++) {
|
||||
subkeyname = regsubkey_ctr_specific_key(subkeys, i);
|
||||
subkeypath = talloc_asprintf(regfile->mem_ctx, "%s\\%s",
|
||||
keypath, subkeyname);
|
||||
if (subkeypath == NULL) {
|
||||
result = WERR_NOMEM;
|
||||
goto done;
|
||||
}
|
||||
result = reg_write_tree(regfile, subkeypath, key);
|
||||
if (!W_ERROR_IS_OK(result))
|
||||
goto done;
|
||||
}
|
||||
|
||||
DEBUG(6, ("reg_write_tree: wrote key [%s]\n", keypath));
|
||||
|
||||
done:
|
||||
TALLOC_FREE(subkeys);
|
||||
TALLOC_FREE(registry_key.name);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static WERROR backup_registry_key(struct registry_key_handle *krecord,
|
||||
const char *fname)
|
||||
{
|
||||
REGF_FILE *regfile;
|
||||
WERROR result;
|
||||
|
||||
/* open the registry file....fail if the file already exists */
|
||||
|
||||
regfile = regfio_open(fname, (O_RDWR|O_CREAT|O_EXCL),
|
||||
(S_IREAD|S_IWRITE));
|
||||
if (regfile == NULL) {
|
||||
DEBUG(0,("backup_registry_key: failed to open \"%s\" (%s)\n",
|
||||
fname, strerror(errno) ));
|
||||
return ntstatus_to_werror(map_nt_error_from_unix(errno));
|
||||
}
|
||||
|
||||
/* write the registry tree to the file */
|
||||
|
||||
result = reg_write_tree(regfile, krecord->name, NULL);
|
||||
|
||||
/* cleanup */
|
||||
|
||||
regfio_close(regfile);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
WERROR reg_savekey(struct registry_key *key, const char *fname)
|
||||
{
|
||||
return backup_registry_key(key->key, fname);
|
||||
}
|
Loading…
Reference in New Issue
Block a user