The branch, v3-2-test has been updated
       via  f673bbd300d972dd7ae2d092b3b1e642ed29cfd2 (commit)
      from  9a966e5593ae4474014aec5d8c68c489ac8ce0c9 (commit)

http://gitweb.samba.org/?samba.git;a=shortlog;h=v3-2-test


- Log -----------------------------------------------------------------
commit f673bbd300d972dd7ae2d092b3b1e642ed29cfd2
Author: Günther Deschner <[EMAIL PROTECTED]>
Date:   Fri Feb 29 15:46:14 2008 +0100

    Add infrastructure for reading/storing Group Policy state and control data 
in the registry.
    
    Guenther

-----------------------------------------------------------------------

Summary of changes:
 source/Makefile.in           |    3 +-
 source/include/gpo.h         |   60 +++-
 source/include/reg_objects.h |    7 +
 source/libgpo/gpo_reg.c      | 1058 ++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 1126 insertions(+), 2 deletions(-)
 create mode 100644 source/libgpo/gpo_reg.c


Changeset truncated at 500 lines:

diff --git a/source/Makefile.in b/source/Makefile.in
index c6815e9..baa9177 100644
--- a/source/Makefile.in
+++ b/source/Makefile.in
@@ -377,7 +377,8 @@ LIBWBCLIENT_OBJ0 = nsswitch/libwbclient/wbclient.o \
 LIBWBCLIENT_OBJ = $(LIBWBCLIENT_OBJ0) $(WBCOMMON_OBJ) @LIBTALLOC_STATIC@ 
$(LIBREPLACE_OBJ)
 
 LIBGPO_OBJ0 = libgpo/gpo_ldap.o libgpo/gpo_ini.o libgpo/gpo_util.o \
-             libgpo/gpo_fetch.o libgpo/gpo_filesync.o libgpo/gpo_sec.o
+             libgpo/gpo_fetch.o libgpo/gpo_filesync.o libgpo/gpo_sec.o \
+             libgpo/gpo_reg.o
 LIBGPO_OBJ = $(LIBGPO_OBJ0)
 
 LIBADS_OBJ = libads/ldap.o libads/ldap_printer.o \
diff --git a/source/include/gpo.h b/source/include/gpo.h
index 9b1a672..d8d9e8e 100644
--- a/source/include/gpo.h
+++ b/source/include/gpo.h
@@ -22,7 +22,8 @@ enum GPO_LINK_TYPE {
        GP_LINK_MACHINE = 1,
        GP_LINK_SITE    = 2,
        GP_LINK_DOMAIN  = 3,
-       GP_LINK_OU      = 4
+       GP_LINK_OU      = 4,
+       GP_LINK_LOCAL   = 5 /* for convenience */
 };
 
 /* GPO_OPTIONS */
@@ -33,6 +34,17 @@ enum GPO_LINK_TYPE {
 #define GPO_LIST_FLAG_MACHINE  0x00000001
 #define GPO_LIST_FLAG_SITEONLY 0x00000002
 
+/* following flags from http://support.microsoft.com/kb/312164/EN-US/ */
+#define GPO_INFO_FLAG_MACHINE                  0x00000001
+#define GPO_INFO_FLAG_BACKGROUND               0x00000010
+#define GPO_INFO_FLAG_SLOWLINK                 0x00000020
+#define GPO_INFO_FLAG_VERBOSE                  0x00000040
+#define GPO_INFO_FLAG_NOCHANGES                        0x00000080
+#define GPO_INFO_FLAG_LINKTRANSITION           0x00000100
+#define GPO_INFO_FLAG_LOGRSOP_TRANSITION       0x00000200
+#define GPO_INFO_FLAG_FORCED_REFRESH           0x00000400
+#define GPO_INFO_FLAG_SAFEMODE_BOOT            0x00000800
+
 #define GPO_VERSION_USER(x) (x >> 16)
 #define GPO_VERSION_MACHINE(x) (x & 0xffff)
 
@@ -88,10 +100,56 @@ struct GP_EXT {
        char **extensions_guid;
        char **snapins;
        char **snapins_guid;
+       struct GP_EXT *next, *prev;
 };
 
 #define GPO_CACHE_DIR "gpo_cache"
 #define GPT_INI "GPT.INI"
+#define GPO_REFRESH_INTERVAL 60*90
+
+#define GPO_REG_STATE_MACHINE "State\\Machine"
+
+enum gp_reg_action {
+       GP_REG_ACTION_NONE = 0,
+       GP_REG_ACTION_ADD_VALUE = 1,
+       GP_REG_ACTION_ADD_KEY = 2,
+       GP_REG_ACTION_DEL_VALUES = 3,
+       GP_REG_ACTION_DEL_VALUE = 4,
+       GP_REG_ACTION_DEL_ALL_VALUES = 5,
+       GP_REG_ACTION_DEL_KEYS = 6,
+       GP_REG_ACTION_SEC_KEY_SET = 7,
+       GP_REG_ACTION_SEC_KEY_RESET = 8
+};
+
+struct gp_registry_entry {
+       enum gp_reg_action action;
+       const char *key;
+       const char *value;
+       struct registry_value *data;
+};
+
+struct gp_registry_value {
+       const char *value;
+       struct registry_value *data;
+};
+
+struct gp_registry_entry2 {
+       enum gp_reg_action action;
+       const char *key;
+       size_t num_values;
+       struct gp_registry_value **values;
+};
+
+struct gp_registry_entries {
+       size_t num_entries;
+       struct gp_registry_entry **entries;
+};
+
+struct gp_registry_context {
+       const struct nt_user_token *token;
+       const char *path;
+       struct registry_key *curr_key;
+};
 
 #define GP_EXT_GUID_SECURITY "827D319E-6EAC-11D2-A4EA-00C04F79F83A"
 #define GP_EXT_GUID_REGISTRY "35378EAC-683F-11D2-A89A-00C04FBBCFA2"
diff --git a/source/include/reg_objects.h b/source/include/reg_objects.h
index 3df701f..1d0d0d4 100644
--- a/source/include/reg_objects.h
+++ b/source/include/reg_objects.h
@@ -105,9 +105,16 @@ typedef struct {
 #define KEY_CURRENT_VERSION    "HKLM\\SOFTWARE\\Microsoft\\Windows 
NT\\CurrentVersion"
 #define KEY_PERFLIB            "HKLM\\SOFTWARE\\Microsoft\\Windows 
NT\\CurrentVersion\\Perflib"
 #define KEY_PERFLIB_009                "HKLM\\SOFTWARE\\Microsoft\\Windows 
NT\\CurrentVersion\\Perflib\\009"
+#define KEY_GROUP_POLICY       "HKLM\\SOFTWARE\\Microsoft\\Windows 
NT\\CurrentVersion\\Group Policy"
+#define KEY_WINLOGON           "HKLM\\SOFTWARE\\Microsoft\\Windows 
NT\\CurrentVersion\\Winlogon"
 #define KEY_SMBCONF            "HKLM\\SOFTWARE\\Samba\\smbconf"
+#define KEY_SAMBA_GROUP_POLICY "HKLM\\SOFTWARE\\Samba\\Group Policy"
 #define KEY_TREE_ROOT          ""
 
+#define KEY_GP_MACHINE_POLICY          "HKLM\\Software\\Policies"
+#define KEY_GP_MACHINE_WIN_POLICY      
"HKLM\\Software\\Microsoft\\Windows\\CurrentVersion\\Policies"
+#define KEY_GP_USER_POLICY             "HKCU\\Software\\Policies"
+#define KEY_GP_USER_WIN_POLICY         
"HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Policies"
 /*
  * Registry key types
  *     Most keys are going to be GENERIC -- may need a better name?
diff --git a/source/libgpo/gpo_reg.c b/source/libgpo/gpo_reg.c
new file mode 100644
index 0000000..2a27a7e
--- /dev/null
+++ b/source/libgpo/gpo_reg.c
@@ -0,0 +1,1058 @@
+/*
+ *  Unix SMB/CIFS implementation.
+ *  Group Policy Object Support
+ *  Copyright (C) Guenther Deschner 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"
+
+
+extern REGISTRY_OPS regdb_ops;
+
+static int gp_reg_fetch_keys(const char *key, REGSUBKEY_CTR *subkey_ctr)
+{
+       return regdb_ops.fetch_subkeys(key, subkey_ctr);
+}
+
+static bool gp_reg_store_keys(const char *key, REGSUBKEY_CTR *subkeys)
+{
+       return regdb_ops.store_subkeys(key, subkeys);
+}
+
+static int gp_reg_fetch_values(const char *key, REGVAL_CTR *val)
+{
+       return regdb_ops.fetch_values(key, val);
+}
+
+static bool gp_reg_store_values(const char *key, REGVAL_CTR *val)
+{
+       return regdb_ops.store_values(key, val);
+}
+
+static WERROR gp_reg_get_secdesc(TALLOC_CTX *mem_ctx, const char *key,
+                                struct security_descriptor **psecdesc)
+{
+       return regdb_ops.get_secdesc(mem_ctx, key, psecdesc);
+}
+
+static WERROR gp_reg_set_secdesc(const char *key,
+                                struct security_descriptor *secdesc)
+{
+       return regdb_ops.set_secdesc(key, secdesc);
+}
+
+/****************************************************************
+****************************************************************/
+
+static REGISTRY_OPS gp_reg_ops = {
+       .fetch_subkeys          = gp_reg_fetch_keys,
+       .fetch_values           = gp_reg_fetch_values,
+       .store_subkeys          = gp_reg_store_keys,
+       .store_values           = gp_reg_store_values,
+/*     .reg_access_check       = gp_reg_reg_access_check, */
+       .get_secdesc            = gp_reg_get_secdesc,
+       .set_secdesc            = gp_reg_set_secdesc
+};
+
+/****************************************************************
+****************************************************************/
+
+struct nt_user_token *registry_create_system_token(TALLOC_CTX *mem_ctx)
+{
+       struct nt_user_token *token = NULL;
+
+       token = TALLOC_ZERO_P(mem_ctx, struct nt_user_token);
+       if (!token) {
+               DEBUG(1,("talloc failed\n"));
+               return NULL;
+       }
+
+       token->privileges = se_priv_all;
+
+       if (!NT_STATUS_IS_OK(add_sid_to_array(token, &global_sid_System,
+                        &token->user_sids, &token->num_sids))) {
+               DEBUG(1,("Error adding nt-authority system sid to token\n"));
+               return NULL;
+       }
+
+       return token;
+}
+
+/****************************************************************
+****************************************************************/
+
+WERROR gp_init_reg_ctx(TALLOC_CTX *mem_ctx,
+                      const char *initial_path,
+                      uint32_t desired_access,
+                      const struct nt_user_token *token,
+                      struct gp_registry_context **reg_ctx)
+{
+       struct gp_registry_context *tmp_ctx;
+       static REGISTRY_HOOK gp_reg_hook;
+       WERROR werr;
+
+       if (!reg_ctx) {
+               return WERR_INVALID_PARAM;
+       }
+
+       if (!regdb_init()) {
+               return WERR_CAN_NOT_COMPLETE;
+       }
+
+       gp_reg_hook.keyname = initial_path; /* KEY_SAMBA_GROUP_POLICY */
+       gp_reg_hook.ops = &gp_reg_ops;
+
+       /* not sure about the cache hook */
+       reghook_cache_init();
+
+       if (!reghook_cache_add(&gp_reg_hook)) {
+               return WERR_CAN_NOT_COMPLETE;
+       }
+
+       tmp_ctx = TALLOC_ZERO_P(mem_ctx, struct gp_registry_context);
+       W_ERROR_HAVE_NO_MEMORY(tmp_ctx);
+
+       if (token) {
+               tmp_ctx->token = token;
+       } else {
+               tmp_ctx->token = registry_create_system_token(mem_ctx);
+       }
+       if (!tmp_ctx->token) {
+               TALLOC_FREE(tmp_ctx);
+               return WERR_NOMEM;
+       }
+
+       if (initial_path) {
+               tmp_ctx->path = talloc_strdup(mem_ctx, initial_path);
+               if (!tmp_ctx->path) {
+                       TALLOC_FREE(tmp_ctx);
+                       return WERR_NOMEM;
+               }
+
+               werr = reg_open_path(mem_ctx, tmp_ctx->path, desired_access,
+                                    tmp_ctx->token, &tmp_ctx->curr_key);
+               if (!W_ERROR_IS_OK(werr)) {
+                       TALLOC_FREE(tmp_ctx);
+                       return werr;
+               }
+       }
+
+       *reg_ctx = tmp_ctx;
+
+       return WERR_OK;
+}
+
+/****************************************************************
+****************************************************************/
+
+void gp_free_reg_ctx(struct gp_registry_context *reg_ctx)
+{
+       TALLOC_FREE(reg_ctx);
+}
+
+/****************************************************************
+****************************************************************/
+
+WERROR gp_store_reg_subkey(TALLOC_CTX *mem_ctx,
+                          const char *subkeyname,
+                          struct registry_key *curr_key,
+                          struct registry_key **new_key)
+{
+       enum winreg_CreateAction action = REG_ACTION_NONE;
+       WERROR werr;
+
+       werr = reg_createkey(mem_ctx, curr_key, subkeyname,
+                            REG_KEY_WRITE, new_key, &action);
+       if (W_ERROR_IS_OK(werr) && (action != REG_CREATED_NEW_KEY)) {
+               return WERR_OK;
+       }
+
+       return werr;
+}
+
+/****************************************************************
+****************************************************************/
+
+WERROR gp_read_reg_subkey(TALLOC_CTX *mem_ctx,
+                         struct gp_registry_context *reg_ctx,
+                         const char *subkeyname,
+                         struct registry_key **key)
+{
+       const char *tmp = NULL;
+
+       if (!reg_ctx || !subkeyname || !key) {
+               return WERR_INVALID_PARAM;
+       }
+
+       tmp = talloc_asprintf(mem_ctx, "%s\\%s", reg_ctx->path, subkeyname);
+       W_ERROR_HAVE_NO_MEMORY(tmp);
+
+       return reg_open_path(mem_ctx, tmp, REG_KEY_READ,
+                            reg_ctx->token, key);
+}
+
+/****************************************************************
+****************************************************************/
+
+WERROR gp_store_reg_val_sz(TALLOC_CTX *mem_ctx,
+                          struct registry_key *key,
+                          const char *val_name,
+                          const char *val)
+{
+       struct registry_value reg_val;
+       ZERO_STRUCT(reg_val);
+
+       /* FIXME: hack */
+       val = val ? val : " ";
+
+       reg_val.type = REG_SZ;
+       reg_val.v.sz.len = strlen(val);
+       reg_val.v.sz.str = talloc_strdup(mem_ctx, val);
+       W_ERROR_HAVE_NO_MEMORY(reg_val.v.sz.str);
+
+       return reg_setvalue(key, val_name, &reg_val);
+}
+
+/****************************************************************
+****************************************************************/
+
+static WERROR gp_store_reg_val_dword(TALLOC_CTX *mem_ctx,
+                                    struct registry_key *key,
+                                    const char *val_name,
+                                    uint32_t val)
+{
+       struct registry_value reg_val;
+       ZERO_STRUCT(reg_val);
+
+       reg_val.type = REG_DWORD;
+       reg_val.v.dword = val;
+
+       return reg_setvalue(key, val_name, &reg_val);
+}
+
+/****************************************************************
+****************************************************************/
+
+WERROR gp_read_reg_val_sz(TALLOC_CTX *mem_ctx,
+                         struct registry_key *key,
+                         const char *val_name,
+                         const char **val)
+{
+       WERROR werr;
+       struct registry_value *reg_val = NULL;
+
+       werr = reg_queryvalue(mem_ctx, key, val_name, &reg_val);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       if (reg_val->type != REG_SZ) {
+               return WERR_INVALID_DATATYPE;
+       }
+
+       *val = talloc_strdup(mem_ctx, reg_val->v.sz.str);
+       W_ERROR_HAVE_NO_MEMORY(*val);
+
+       return WERR_OK;
+}
+
+/****************************************************************
+****************************************************************/
+
+static WERROR gp_read_reg_val_dword(TALLOC_CTX *mem_ctx,
+                                   struct registry_key *key,
+                                   const char *val_name,
+                                   uint32_t *val)
+{
+       WERROR werr;
+       struct registry_value *reg_val = NULL;
+
+       werr = reg_queryvalue(mem_ctx, key, val_name, &reg_val);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       if (reg_val->type != REG_DWORD) {
+               return WERR_INVALID_DATATYPE;
+       }
+
+       *val = reg_val->v.dword;
+
+       return WERR_OK;
+}
+
+/****************************************************************
+****************************************************************/
+
+static WERROR gp_store_reg_gpovals(TALLOC_CTX *mem_ctx,
+                                  struct registry_key *key,
+                                  struct GROUP_POLICY_OBJECT *gpo)
+{
+       WERROR werr;
+
+       if (!key || !gpo) {
+               return WERR_INVALID_PARAM;
+       }
+
+       werr = gp_store_reg_val_dword(mem_ctx, key, "Version",
+                                     gpo->version);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_dword(mem_ctx, key, "WQLFilterPass",
+                                     true); /* fake */
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_dword(mem_ctx, key, "AccessDenied",
+                                     false); /* fake */
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_dword(mem_ctx, key, "GPO-Disabled",
+                                     (gpo->options & GPO_FLAG_DISABLE));
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_dword(mem_ctx, key, "Options",
+                                     gpo->options);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_sz(mem_ctx, key, "GPOID",
+                                  gpo->name);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_sz(mem_ctx, key, "SOM",
+                                  gpo->link);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_sz(mem_ctx, key, "DisplayName",
+                                  gpo->display_name);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       werr = gp_store_reg_val_sz(mem_ctx, key, "WQL-Id",
+                                  NULL);
+       W_ERROR_NOT_OK_RETURN(werr);
+
+       return werr;
+}
+
+/****************************************************************
+****************************************************************/
+
+static const char *gp_reg_groupmembership_path(TALLOC_CTX *mem_ctx,
+                                              const DOM_SID *sid,
+                                              uint32_t flags)
+{
+       if (flags & GPO_LIST_FLAG_MACHINE) {
+               return "GroupMembership";
+       }
+
+       return talloc_asprintf(mem_ctx, "%s\\%s", sid_string_tos(sid),
+                              "GroupMembership");
+}
+
+/****************************************************************
+****************************************************************/
+
+static WERROR gp_reg_del_groupmembership(TALLOC_CTX *mem_ctx,
+                                        struct registry_key *key,
+                                        const struct nt_user_token *token,
+                                        uint32_t flags)
+{
+       const char *path = NULL;
+
+       path = gp_reg_groupmembership_path(mem_ctx, &token->user_sids[0],


-- 
Samba Shared Repository

Reply via email to