2 * Unix SMB/CIFS implementation.
3 * Group Policy Object Support
4 * Copyright (C) Guenther Deschner 2007-2008
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, see <http://www.gnu.org/licenses/>.
21 #include "../libgpo/gpo.h"
22 #include "libgpo/gpo_proto.h"
26 /****************************************************************
27 ****************************************************************/
29 struct nt_user_token *registry_create_system_token(TALLOC_CTX *mem_ctx)
31 struct nt_user_token *token = NULL;
33 token = TALLOC_ZERO_P(mem_ctx, struct nt_user_token);
35 DEBUG(1,("talloc failed\n"));
39 token->privileges = se_priv_all;
41 if (!NT_STATUS_IS_OK(add_sid_to_array(token, &global_sid_System,
42 &token->user_sids, &token->num_sids))) {
43 DEBUG(1,("Error adding nt-authority system sid to token\n"));
50 /****************************************************************
51 ****************************************************************/
53 WERROR gp_init_reg_ctx(TALLOC_CTX *mem_ctx,
54 const char *initial_path,
55 uint32_t desired_access,
56 const struct nt_user_token *token,
57 struct gp_registry_context **reg_ctx)
59 struct gp_registry_context *tmp_ctx;
63 return WERR_INVALID_PARAM;
66 werr = registry_init_basic();
67 if (!W_ERROR_IS_OK(werr)) {
71 tmp_ctx = TALLOC_ZERO_P(mem_ctx, struct gp_registry_context);
72 W_ERROR_HAVE_NO_MEMORY(tmp_ctx);
75 tmp_ctx->token = token;
77 tmp_ctx->token = registry_create_system_token(mem_ctx);
79 if (!tmp_ctx->token) {
85 if (!W_ERROR_IS_OK(werr)) {
90 tmp_ctx->path = talloc_strdup(mem_ctx, initial_path);
96 werr = reg_open_path(mem_ctx, tmp_ctx->path, desired_access,
97 tmp_ctx->token, &tmp_ctx->curr_key);
98 if (!W_ERROR_IS_OK(werr)) {
109 /****************************************************************
110 ****************************************************************/
112 void gp_free_reg_ctx(struct gp_registry_context *reg_ctx)
114 TALLOC_FREE(reg_ctx);
117 /****************************************************************
118 ****************************************************************/
120 WERROR gp_store_reg_subkey(TALLOC_CTX *mem_ctx,
121 const char *subkeyname,
122 struct registry_key *curr_key,
123 struct registry_key **new_key)
125 enum winreg_CreateAction action = REG_ACTION_NONE;
128 werr = reg_createkey(mem_ctx, curr_key, subkeyname,
129 REG_KEY_WRITE, new_key, &action);
130 if (W_ERROR_IS_OK(werr) && (action != REG_CREATED_NEW_KEY)) {
137 /****************************************************************
138 ****************************************************************/
140 WERROR gp_read_reg_subkey(TALLOC_CTX *mem_ctx,
141 struct gp_registry_context *reg_ctx,
142 const char *subkeyname,
143 struct registry_key **key)
145 const char *tmp = NULL;
147 if (!reg_ctx || !subkeyname || !key) {
148 return WERR_INVALID_PARAM;
151 tmp = talloc_asprintf(mem_ctx, "%s\\%s", reg_ctx->path, subkeyname);
152 W_ERROR_HAVE_NO_MEMORY(tmp);
154 return reg_open_path(mem_ctx, tmp, REG_KEY_READ,
155 reg_ctx->token, key);
158 /****************************************************************
159 ****************************************************************/
161 WERROR gp_store_reg_val_sz(TALLOC_CTX *mem_ctx,
162 struct registry_key *key,
163 const char *val_name,
166 struct registry_value reg_val;
167 ZERO_STRUCT(reg_val);
170 val = val ? val : " ";
172 reg_val.type = REG_SZ;
173 reg_val.v.sz.len = strlen(val);
174 reg_val.v.sz.str = talloc_strdup(mem_ctx, val);
175 W_ERROR_HAVE_NO_MEMORY(reg_val.v.sz.str);
177 return reg_setvalue(key, val_name, ®_val);
180 /****************************************************************
181 ****************************************************************/
183 static WERROR gp_store_reg_val_dword(TALLOC_CTX *mem_ctx,
184 struct registry_key *key,
185 const char *val_name,
188 struct registry_value reg_val;
189 ZERO_STRUCT(reg_val);
191 reg_val.type = REG_DWORD;
192 reg_val.v.dword = val;
194 return reg_setvalue(key, val_name, ®_val);
197 /****************************************************************
198 ****************************************************************/
200 WERROR gp_read_reg_val_sz(TALLOC_CTX *mem_ctx,
201 struct registry_key *key,
202 const char *val_name,
206 struct registry_value *reg_val = NULL;
208 werr = reg_queryvalue(mem_ctx, key, val_name, ®_val);
209 W_ERROR_NOT_OK_RETURN(werr);
211 if (reg_val->type != REG_SZ) {
212 return WERR_INVALID_DATATYPE;
215 *val = talloc_strdup(mem_ctx, reg_val->v.sz.str);
216 W_ERROR_HAVE_NO_MEMORY(*val);
221 /****************************************************************
222 ****************************************************************/
224 static WERROR gp_read_reg_val_dword(TALLOC_CTX *mem_ctx,
225 struct registry_key *key,
226 const char *val_name,
230 struct registry_value *reg_val = NULL;
232 werr = reg_queryvalue(mem_ctx, key, val_name, ®_val);
233 W_ERROR_NOT_OK_RETURN(werr);
235 if (reg_val->type != REG_DWORD) {
236 return WERR_INVALID_DATATYPE;
239 *val = reg_val->v.dword;
244 /****************************************************************
245 ****************************************************************/
247 static WERROR gp_store_reg_gpovals(TALLOC_CTX *mem_ctx,
248 struct registry_key *key,
249 struct GROUP_POLICY_OBJECT *gpo)
254 return WERR_INVALID_PARAM;
257 werr = gp_store_reg_val_dword(mem_ctx, key, "Version",
259 W_ERROR_NOT_OK_RETURN(werr);
261 werr = gp_store_reg_val_dword(mem_ctx, key, "WQLFilterPass",
263 W_ERROR_NOT_OK_RETURN(werr);
265 werr = gp_store_reg_val_dword(mem_ctx, key, "AccessDenied",
267 W_ERROR_NOT_OK_RETURN(werr);
269 werr = gp_store_reg_val_dword(mem_ctx, key, "GPO-Disabled",
270 (gpo->options & GPO_FLAG_DISABLE));
271 W_ERROR_NOT_OK_RETURN(werr);
273 werr = gp_store_reg_val_dword(mem_ctx, key, "Options",
275 W_ERROR_NOT_OK_RETURN(werr);
277 werr = gp_store_reg_val_sz(mem_ctx, key, "GPOID",
279 W_ERROR_NOT_OK_RETURN(werr);
281 werr = gp_store_reg_val_sz(mem_ctx, key, "SOM",
283 W_ERROR_NOT_OK_RETURN(werr);
285 werr = gp_store_reg_val_sz(mem_ctx, key, "DisplayName",
287 W_ERROR_NOT_OK_RETURN(werr);
289 werr = gp_store_reg_val_sz(mem_ctx, key, "WQL-Id",
291 W_ERROR_NOT_OK_RETURN(werr);
296 /****************************************************************
297 ****************************************************************/
299 static const char *gp_reg_groupmembership_path(TALLOC_CTX *mem_ctx,
300 const struct dom_sid *sid,
303 if (flags & GPO_LIST_FLAG_MACHINE) {
304 return "GroupMembership";
307 return talloc_asprintf(mem_ctx, "%s\\%s", sid_string_tos(sid),
311 /****************************************************************
312 ****************************************************************/
314 static WERROR gp_reg_del_groupmembership(TALLOC_CTX *mem_ctx,
315 struct registry_key *key,
316 const struct nt_user_token *token,
319 const char *path = NULL;
321 path = gp_reg_groupmembership_path(mem_ctx, &token->user_sids[0],
323 W_ERROR_HAVE_NO_MEMORY(path);
325 return reg_deletekey_recursive(mem_ctx, key, path);
329 /****************************************************************
330 ****************************************************************/
332 static WERROR gp_reg_store_groupmembership(TALLOC_CTX *mem_ctx,
333 struct gp_registry_context *reg_ctx,
334 const struct nt_user_token *token,
337 struct registry_key *key = NULL;
340 const char *valname = NULL;
341 const char *path = NULL;
342 const char *val = NULL;
345 path = gp_reg_groupmembership_path(mem_ctx, &token->user_sids[0],
347 W_ERROR_HAVE_NO_MEMORY(path);
349 gp_reg_del_groupmembership(mem_ctx, reg_ctx->curr_key, token, flags);
351 werr = gp_store_reg_subkey(mem_ctx, path,
352 reg_ctx->curr_key, &key);
353 W_ERROR_NOT_OK_RETURN(werr);
355 for (i=0; i<token->num_sids; i++) {
357 valname = talloc_asprintf(mem_ctx, "Group%d", count++);
358 W_ERROR_HAVE_NO_MEMORY(valname);
360 val = sid_string_talloc(mem_ctx, &token->user_sids[i]);
361 W_ERROR_HAVE_NO_MEMORY(val);
362 werr = gp_store_reg_val_sz(mem_ctx, key, valname, val);
363 W_ERROR_NOT_OK_RETURN(werr);
366 werr = gp_store_reg_val_dword(mem_ctx, key, "Count", count);
367 W_ERROR_NOT_OK_RETURN(werr);
372 /****************************************************************
373 ****************************************************************/
376 static WERROR gp_reg_read_groupmembership(TALLOC_CTX *mem_ctx,
377 struct gp_registry_context *reg_ctx,
378 const struct dom_sid *object_sid,
379 struct nt_user_token **token,
382 struct registry_key *key = NULL;
385 const char *valname = NULL;
386 const char *val = NULL;
387 const char *path = NULL;
389 int num_token_sids = 0;
390 struct nt_user_token *tmp_token = NULL;
392 tmp_token = TALLOC_ZERO_P(mem_ctx, struct nt_user_token);
393 W_ERROR_HAVE_NO_MEMORY(tmp_token);
395 path = gp_reg_groupmembership_path(mem_ctx, object_sid, flags);
396 W_ERROR_HAVE_NO_MEMORY(path);
398 werr = gp_read_reg_subkey(mem_ctx, reg_ctx, path, &key);
399 W_ERROR_NOT_OK_RETURN(werr);
401 werr = gp_read_reg_val_dword(mem_ctx, key, "Count", &count);
402 W_ERROR_NOT_OK_RETURN(werr);
404 for (i=0; i<count; i++) {
406 valname = talloc_asprintf(mem_ctx, "Group%d", i);
407 W_ERROR_HAVE_NO_MEMORY(valname);
409 werr = gp_read_reg_val_sz(mem_ctx, key, valname, &val);
410 W_ERROR_NOT_OK_RETURN(werr);
412 if (!string_to_sid(&tmp_token->user_sids[num_token_sids++],
414 return WERR_INSUFFICIENT_BUFFER;
418 tmp_token->num_sids = num_token_sids;
425 /****************************************************************
426 ****************************************************************/
428 static const char *gp_req_state_path(TALLOC_CTX *mem_ctx,
429 const struct dom_sid *sid,
432 if (flags & GPO_LIST_FLAG_MACHINE) {
433 return GPO_REG_STATE_MACHINE;
436 return talloc_asprintf(mem_ctx, "%s\\%s", "State", sid_string_tos(sid));
439 /****************************************************************
440 ****************************************************************/
442 static WERROR gp_del_reg_state(TALLOC_CTX *mem_ctx,
443 struct registry_key *key,
446 return reg_deletesubkeys_recursive(mem_ctx, key, path);
449 /****************************************************************
450 ****************************************************************/
452 WERROR gp_reg_state_store(TALLOC_CTX *mem_ctx,
455 const struct nt_user_token *token,
456 struct GROUP_POLICY_OBJECT *gpo_list)
458 struct gp_registry_context *reg_ctx = NULL;
459 WERROR werr = WERR_GENERAL_FAILURE;
460 const char *subkeyname = NULL;
461 struct GROUP_POLICY_OBJECT *gpo;
463 struct registry_key *key;
465 werr = gp_init_reg_ctx(mem_ctx, KEY_GROUP_POLICY, REG_KEY_WRITE,
467 W_ERROR_NOT_OK_RETURN(werr);
469 werr = gp_secure_key(mem_ctx, flags, reg_ctx->curr_key,
470 &token->user_sids[0]);
471 if (!W_ERROR_IS_OK(werr)) {
472 DEBUG(0,("failed to secure key: %s\n", win_errstr(werr)));
476 werr = gp_reg_store_groupmembership(mem_ctx, reg_ctx, token, flags);
477 if (!W_ERROR_IS_OK(werr)) {
478 DEBUG(0,("failed to store group membership: %s\n", win_errstr(werr)));
482 subkeyname = gp_req_state_path(mem_ctx, &token->user_sids[0], flags);
488 werr = gp_del_reg_state(mem_ctx, reg_ctx->curr_key, subkeyname);
489 if (!W_ERROR_IS_OK(werr)) {
490 DEBUG(0,("failed to delete old state: %s\n", win_errstr(werr)));
494 werr = gp_store_reg_subkey(mem_ctx, subkeyname,
495 reg_ctx->curr_key, ®_ctx->curr_key);
496 if (!W_ERROR_IS_OK(werr)) {
500 werr = gp_store_reg_val_sz(mem_ctx, reg_ctx->curr_key,
501 "Distinguished-Name", dn);
502 if (!W_ERROR_IS_OK(werr)) {
506 /* store link list */
508 werr = gp_store_reg_subkey(mem_ctx, "GPLink-List",
509 reg_ctx->curr_key, &key);
510 if (!W_ERROR_IS_OK(werr)) {
516 werr = gp_store_reg_subkey(mem_ctx, "GPO-List",
517 reg_ctx->curr_key, ®_ctx->curr_key);
518 if (!W_ERROR_IS_OK(werr)) {
522 for (gpo = gpo_list; gpo; gpo = gpo->next) {
524 subkeyname = talloc_asprintf(mem_ctx, "%d", count++);
530 werr = gp_store_reg_subkey(mem_ctx, subkeyname,
531 reg_ctx->curr_key, &key);
532 if (!W_ERROR_IS_OK(werr)) {
536 werr = gp_store_reg_gpovals(mem_ctx, key, gpo);
537 if (!W_ERROR_IS_OK(werr)) {
538 DEBUG(0,("gp_reg_state_store: "
539 "gpo_store_reg_gpovals failed for %s: %s\n",
540 gpo->display_name, win_errstr(werr)));
545 gp_free_reg_ctx(reg_ctx);
549 /****************************************************************
550 ****************************************************************/
552 static WERROR gp_read_reg_gpovals(TALLOC_CTX *mem_ctx,
553 struct registry_key *key,
554 struct GROUP_POLICY_OBJECT *gpo)
559 return WERR_INVALID_PARAM;
562 werr = gp_read_reg_val_dword(mem_ctx, key, "Version",
564 W_ERROR_NOT_OK_RETURN(werr);
566 werr = gp_read_reg_val_dword(mem_ctx, key, "Options",
568 W_ERROR_NOT_OK_RETURN(werr);
570 werr = gp_read_reg_val_sz(mem_ctx, key, "GPOID",
572 W_ERROR_NOT_OK_RETURN(werr);
574 werr = gp_read_reg_val_sz(mem_ctx, key, "SOM",
576 W_ERROR_NOT_OK_RETURN(werr);
578 werr = gp_read_reg_val_sz(mem_ctx, key, "DisplayName",
580 W_ERROR_NOT_OK_RETURN(werr);
585 /****************************************************************
586 ****************************************************************/
588 static WERROR gp_read_reg_gpo(TALLOC_CTX *mem_ctx,
589 struct registry_key *key,
590 struct GROUP_POLICY_OBJECT **gpo_ret)
592 struct GROUP_POLICY_OBJECT *gpo = NULL;
595 if (!gpo_ret || !key) {
596 return WERR_INVALID_PARAM;
599 gpo = TALLOC_ZERO_P(mem_ctx, struct GROUP_POLICY_OBJECT);
600 W_ERROR_HAVE_NO_MEMORY(gpo);
602 werr = gp_read_reg_gpovals(mem_ctx, key, gpo);
603 W_ERROR_NOT_OK_RETURN(werr);
610 /****************************************************************
611 ****************************************************************/
613 WERROR gp_reg_state_read(TALLOC_CTX *mem_ctx,
615 const struct dom_sid *sid,
616 struct GROUP_POLICY_OBJECT **gpo_list)
618 struct gp_registry_context *reg_ctx = NULL;
619 WERROR werr = WERR_GENERAL_FAILURE;
620 const char *subkeyname = NULL;
621 struct GROUP_POLICY_OBJECT *gpo = NULL;
623 struct registry_key *key = NULL;
624 const char *path = NULL;
625 const char *gp_state_path = NULL;
628 return WERR_INVALID_PARAM;
631 ZERO_STRUCTP(gpo_list);
633 gp_state_path = gp_req_state_path(mem_ctx, sid, flags);
634 if (!gp_state_path) {
639 path = talloc_asprintf(mem_ctx, "%s\\%s\\%s",
648 werr = gp_init_reg_ctx(mem_ctx, path, REG_KEY_READ, NULL, ®_ctx);
649 if (!W_ERROR_IS_OK(werr)) {
655 subkeyname = talloc_asprintf(mem_ctx, "%d", count++);
661 werr = gp_read_reg_subkey(mem_ctx, reg_ctx, subkeyname, &key);
662 if (W_ERROR_EQUAL(werr, WERR_BADFILE)) {
666 if (!W_ERROR_IS_OK(werr)) {
667 DEBUG(0,("gp_reg_state_read: "
668 "gp_read_reg_subkey gave: %s\n",
673 werr = gp_read_reg_gpo(mem_ctx, key, &gpo);
674 if (!W_ERROR_IS_OK(werr)) {
678 DLIST_ADD(*gpo_list, gpo);
682 gp_free_reg_ctx(reg_ctx);
686 /****************************************************************
687 ****************************************************************/
689 static WERROR gp_reg_generate_sd(TALLOC_CTX *mem_ctx,
690 const struct dom_sid *sid,
691 struct security_descriptor **sd,
694 struct security_ace ace[6];
697 struct security_acl *theacl = NULL;
699 uint8_t inherit_flags;
702 init_sec_ace(&ace[0],
704 SEC_ACE_TYPE_ACCESS_ALLOWED,
708 init_sec_ace(&ace[1],
709 &global_sid_Builtin_Administrators,
710 SEC_ACE_TYPE_ACCESS_ALLOWED,
714 init_sec_ace(&ace[2],
715 sid ? sid : &global_sid_Authenticated_Users,
716 SEC_ACE_TYPE_ACCESS_ALLOWED,
719 inherit_flags = SEC_ACE_FLAG_OBJECT_INHERIT |
720 SEC_ACE_FLAG_CONTAINER_INHERIT |
721 SEC_ACE_FLAG_INHERIT_ONLY;
724 init_sec_ace(&ace[3],
726 SEC_ACE_TYPE_ACCESS_ALLOWED,
727 mask, inherit_flags);
730 init_sec_ace(&ace[4],
731 &global_sid_Builtin_Administrators,
732 SEC_ACE_TYPE_ACCESS_ALLOWED,
733 mask, inherit_flags);
736 init_sec_ace(&ace[5],
737 sid ? sid : &global_sid_Authenticated_Users,
738 SEC_ACE_TYPE_ACCESS_ALLOWED,
739 mask, inherit_flags);
741 theacl = make_sec_acl(mem_ctx, NT4_ACL_REVISION, 6, ace);
742 W_ERROR_HAVE_NO_MEMORY(theacl);
744 *sd = make_sec_desc(mem_ctx, SD_REVISION,
745 SEC_DESC_SELF_RELATIVE |
746 SEC_DESC_DACL_AUTO_INHERITED | /* really ? */
747 SEC_DESC_DACL_AUTO_INHERIT_REQ, /* really ? */
750 W_ERROR_HAVE_NO_MEMORY(*sd);
755 /****************************************************************
756 ****************************************************************/
758 WERROR gp_secure_key(TALLOC_CTX *mem_ctx,
760 struct registry_key *key,
761 const struct dom_sid *sid)
763 struct security_descriptor *sd = NULL;
765 const struct dom_sid *sd_sid = NULL;
768 if (!(flags & GPO_LIST_FLAG_MACHINE)) {
772 werr = gp_reg_generate_sd(mem_ctx, sd_sid, &sd, &sd_size);
773 W_ERROR_NOT_OK_RETURN(werr);
775 return reg_setkeysecurity(key, sd);
778 /****************************************************************
779 ****************************************************************/
781 void dump_reg_val(int lvl, const char *direction,
782 const char *key, const char *subkey,
783 struct registry_value *val)
786 const char *type_str = NULL;
789 DEBUG(lvl,("no val!\n"));
793 type_str = str_regtype(val->type);
795 DEBUG(lvl,("\tdump_reg_val:\t%s '%s'\n\t\t\t'%s' %s: ",
796 direction, key, subkey, type_str));
800 DEBUG(lvl,("%d (0x%08x)\n",
801 (int)val->v.dword, val->v.dword));
804 DEBUG(lvl,("%d (0x%016llx)\n",
806 (unsigned long long)val->v.qword));
809 DEBUG(lvl,("%s (length: %d)\n",
811 (int)val->v.sz.len));
814 DEBUG(lvl,("(num_strings: %d)\n",
815 val->v.multi_sz.num_strings));
816 for (i=0; i < val->v.multi_sz.num_strings; i++) {
817 DEBUGADD(lvl,("\t%s\n",
818 val->v.multi_sz.strings[i]));
825 dump_data(lvl, val->v.binary.data,
826 val->v.binary.length);
829 DEBUG(lvl,("unsupported type: %d\n", val->type));
834 /****************************************************************
835 ****************************************************************/
837 void dump_reg_entry(uint32_t flags,
839 struct gp_registry_entry *entry)
841 if (!(flags & GPO_INFO_FLAG_VERBOSE))
850 /****************************************************************
851 ****************************************************************/
853 void dump_reg_entries(uint32_t flags,
855 struct gp_registry_entry *entries,
860 if (!(flags & GPO_INFO_FLAG_VERBOSE))
863 for (i=0; i < num_entries; i++) {
864 dump_reg_entry(flags, dir, &entries[i]);
868 /****************************************************************
869 ****************************************************************/
871 bool add_gp_registry_entry_to_array(TALLOC_CTX *mem_ctx,
872 struct gp_registry_entry *entry,
873 struct gp_registry_entry **entries,
876 *entries = TALLOC_REALLOC_ARRAY(mem_ctx, *entries,
877 struct gp_registry_entry,
880 if (*entries == NULL) {
885 (*entries)[*num].action = entry->action;
886 (*entries)[*num].key = entry->key;
887 (*entries)[*num].value = entry->value;
888 (*entries)[*num].data = entry->data;
894 /****************************************************************
895 ****************************************************************/
897 static const char *gp_reg_action_str(enum gp_reg_action action)
900 case GP_REG_ACTION_NONE:
901 return "GP_REG_ACTION_NONE";
902 case GP_REG_ACTION_ADD_VALUE:
903 return "GP_REG_ACTION_ADD_VALUE";
904 case GP_REG_ACTION_ADD_KEY:
905 return "GP_REG_ACTION_ADD_KEY";
906 case GP_REG_ACTION_DEL_VALUES:
907 return "GP_REG_ACTION_DEL_VALUES";
908 case GP_REG_ACTION_DEL_VALUE:
909 return "GP_REG_ACTION_DEL_VALUE";
910 case GP_REG_ACTION_DEL_ALL_VALUES:
911 return "GP_REG_ACTION_DEL_ALL_VALUES";
912 case GP_REG_ACTION_DEL_KEYS:
913 return "GP_REG_ACTION_DEL_KEYS";
914 case GP_REG_ACTION_SEC_KEY_SET:
915 return "GP_REG_ACTION_SEC_KEY_SET";
916 case GP_REG_ACTION_SEC_KEY_RESET:
917 return "GP_REG_ACTION_SEC_KEY_RESET";
923 /****************************************************************
924 ****************************************************************/
926 WERROR reg_apply_registry_entry(TALLOC_CTX *mem_ctx,
927 struct registry_key *root_key,
928 struct gp_registry_context *reg_ctx,
929 struct gp_registry_entry *entry,
930 const struct nt_user_token *token,
934 struct registry_key *key = NULL;
936 if (flags & GPO_INFO_FLAG_VERBOSE) {
937 printf("about to store key: [%s]\n", entry->key);
938 printf(" value: [%s]\n", entry->value);
939 printf(" data: [%s]\n", str_regtype(entry->data->type));
940 printf(" action: [%s]\n", gp_reg_action_str(entry->action));
943 werr = gp_store_reg_subkey(mem_ctx, entry->key,
945 /* reg_ctx->curr_key, &key); */
946 if (!W_ERROR_IS_OK(werr)) {
947 DEBUG(0,("gp_store_reg_subkey failed: %s\n", win_errstr(werr)));
951 switch (entry->action) {
952 case GP_REG_ACTION_NONE:
953 case GP_REG_ACTION_ADD_KEY:
956 case GP_REG_ACTION_SEC_KEY_SET:
957 werr = gp_secure_key(mem_ctx, flags,
959 &token->user_sids[0]);
960 if (!W_ERROR_IS_OK(werr)) {
961 DEBUG(0,("reg_apply_registry_entry: "
962 "gp_secure_key failed: %s\n",
967 case GP_REG_ACTION_ADD_VALUE:
968 werr = reg_setvalue(key, entry->value, entry->data);
969 if (!W_ERROR_IS_OK(werr)) {
970 DEBUG(0,("reg_apply_registry_entry: "
971 "reg_setvalue failed: %s\n",
973 dump_reg_entry(flags, "STORE", entry);
977 case GP_REG_ACTION_DEL_VALUE:
978 werr = reg_deletevalue(key, entry->value);
979 if (!W_ERROR_IS_OK(werr)) {
980 DEBUG(0,("reg_apply_registry_entry: "
981 "reg_deletevalue failed: %s\n",
983 dump_reg_entry(flags, "STORE", entry);
987 case GP_REG_ACTION_DEL_ALL_VALUES:
988 werr = reg_deleteallvalues(key);
989 if (!W_ERROR_IS_OK(werr)) {
990 DEBUG(0,("reg_apply_registry_entry: "
991 "reg_deleteallvalues failed: %s\n",
993 dump_reg_entry(flags, "STORE", entry);
997 case GP_REG_ACTION_DEL_VALUES:
998 case GP_REG_ACTION_DEL_KEYS:
999 case GP_REG_ACTION_SEC_KEY_RESET:
1000 DEBUG(0,("reg_apply_registry_entry: "
1001 "not yet supported: %s (%d)\n",
1002 gp_reg_action_str(entry->action),
1004 return WERR_NOT_SUPPORTED;
1006 DEBUG(0,("invalid action: %d\n", entry->action));
1007 return WERR_INVALID_PARAM;