2 * Unix SMB/CIFS implementation.
4 * WINREG client routines
6 * Copyright (c) 2011 Andreas Schneider <asn@samba.org>
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 3 of the License, or
11 * (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, see <http://www.gnu.org/licenses/>.
23 #include "../librpc/gen_ndr/ndr_winreg_c.h"
24 #include "../librpc/gen_ndr/ndr_security.h"
25 #include "rpc_client/cli_winreg.h"
27 NTSTATUS dcerpc_winreg_query_dword(TALLOC_CTX *mem_ctx,
28 struct dcerpc_binding_handle *h,
29 struct policy_handle *key_handle,
34 struct winreg_String wvalue;
35 enum winreg_Type type;
36 uint32_t value_len = 0;
37 uint32_t data_size = 0;
38 WERROR result = WERR_OK;
44 status = dcerpc_winreg_QueryValue(h,
53 if (!NT_STATUS_IS_OK(status)) {
56 if (!W_ERROR_IS_OK(result)) {
61 if (type != REG_DWORD) {
62 *pwerr = WERR_INVALID_DATATYPE;
67 *pwerr = WERR_INVALID_DATA;
71 blob = data_blob_talloc(mem_ctx, NULL, data_size);
72 if (blob.data == NULL) {
78 status = dcerpc_winreg_QueryValue(h,
87 if (!NT_STATUS_IS_OK(status)) {
90 if (!W_ERROR_IS_OK(result)) {
96 *data = IVAL(blob.data, 0);
102 NTSTATUS dcerpc_winreg_query_binary(TALLOC_CTX *mem_ctx,
103 struct dcerpc_binding_handle *h,
104 struct policy_handle *key_handle,
109 struct winreg_String wvalue;
110 enum winreg_Type type;
111 WERROR result = WERR_OK;
112 uint32_t value_len = 0;
113 uint32_t data_size = 0;
119 status = dcerpc_winreg_QueryValue(h,
128 if (!NT_STATUS_IS_OK(status)) {
131 if (!W_ERROR_IS_OK(result)) {
136 if (type != REG_BINARY) {
137 *pwerr = WERR_INVALID_DATATYPE;
141 blob = data_blob_talloc(mem_ctx, NULL, data_size);
142 if (blob.data == NULL) {
148 status = dcerpc_winreg_QueryValue(h,
157 if (!NT_STATUS_IS_OK(status)) {
160 if (!W_ERROR_IS_OK(result)) {
166 data->data = blob.data;
167 data->length = blob.length;
173 NTSTATUS dcerpc_winreg_query_multi_sz(TALLOC_CTX *mem_ctx,
174 struct dcerpc_binding_handle *h,
175 struct policy_handle *key_handle,
180 struct winreg_String wvalue;
181 enum winreg_Type type;
182 WERROR result = WERR_OK;
183 uint32_t value_len = 0;
184 uint32_t data_size = 0;
190 status = dcerpc_winreg_QueryValue(h,
199 if (!NT_STATUS_IS_OK(status)) {
202 if (!W_ERROR_IS_OK(result)) {
207 if (type != REG_MULTI_SZ) {
208 *pwerr = WERR_INVALID_DATATYPE;
212 blob = data_blob_talloc(mem_ctx, NULL, data_size);
213 if (blob.data == NULL) {
219 status = dcerpc_winreg_QueryValue(h,
228 if (!NT_STATUS_IS_OK(status)) {
231 if (!W_ERROR_IS_OK(result)) {
239 ok = pull_reg_multi_sz(mem_ctx, &blob, data);
248 NTSTATUS dcerpc_winreg_query_sz(TALLOC_CTX *mem_ctx,
249 struct dcerpc_binding_handle *h,
250 struct policy_handle *key_handle,
255 struct winreg_String wvalue;
256 enum winreg_Type type;
257 WERROR result = WERR_OK;
258 uint32_t value_len = 0;
259 uint32_t data_size = 0;
265 status = dcerpc_winreg_QueryValue(h,
274 if (!NT_STATUS_IS_OK(status)) {
277 if (!W_ERROR_IS_OK(result)) {
282 if (type != REG_SZ) {
283 *pwerr = WERR_INVALID_DATATYPE;
287 blob = data_blob_talloc(mem_ctx, NULL, data_size);
288 if (blob.data == NULL) {
294 status = dcerpc_winreg_QueryValue(h,
303 if (!NT_STATUS_IS_OK(status)) {
306 if (!W_ERROR_IS_OK(result)) {
314 ok = pull_reg_sz(mem_ctx, &blob, data);
323 NTSTATUS dcerpc_winreg_query_sd(TALLOC_CTX *mem_ctx,
324 struct dcerpc_binding_handle *h,
325 struct policy_handle *key_handle,
327 struct security_descriptor **data,
330 WERROR result = WERR_OK;
334 status = dcerpc_winreg_query_binary(mem_ctx,
340 if (!NT_STATUS_IS_OK(status)) {
343 if (!W_ERROR_IS_OK(result)) {
349 struct security_descriptor *sd;
350 enum ndr_err_code ndr_err;
352 sd = talloc_zero(mem_ctx, struct security_descriptor);
358 ndr_err = ndr_pull_struct_blob(&blob,
361 (ndr_pull_flags_fn_t) ndr_pull_security_descriptor);
362 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
363 DEBUG(2, ("dcerpc_winreg_query_sd: Failed to marshall "
364 "security descriptor\n"));
375 NTSTATUS dcerpc_winreg_set_dword(TALLOC_CTX *mem_ctx,
376 struct dcerpc_binding_handle *h,
377 struct policy_handle *key_handle,
382 struct winreg_String wvalue = { 0, };
384 WERROR result = WERR_OK;
388 blob = data_blob_talloc(mem_ctx, NULL, 4);
389 SIVAL(blob.data, 0, data);
391 status = dcerpc_winreg_SetValue(h,
399 if (!NT_STATUS_IS_OK(status)) {
402 if (!W_ERROR_IS_OK(result)) {
409 NTSTATUS dcerpc_winreg_set_sz(TALLOC_CTX *mem_ctx,
410 struct dcerpc_binding_handle *h,
411 struct policy_handle *key_handle,
416 struct winreg_String wvalue = { 0, };
418 WERROR result = WERR_OK;
423 blob = data_blob_string_const("");
425 if (!push_reg_sz(mem_ctx, &blob, data)) {
426 DEBUG(2, ("dcerpc_winreg_set_sz: Could not marshall "
427 "string %s for %s\n",
434 status = dcerpc_winreg_SetValue(h,
442 if (!NT_STATUS_IS_OK(status)) {
445 if (!W_ERROR_IS_OK(result)) {
452 NTSTATUS dcerpc_winreg_set_expand_sz(TALLOC_CTX *mem_ctx,
453 struct dcerpc_binding_handle *h,
454 struct policy_handle *key_handle,
459 struct winreg_String wvalue = { 0, };
461 WERROR result = WERR_OK;
466 blob = data_blob_string_const("");
468 if (!push_reg_sz(mem_ctx, &blob, data)) {
469 DEBUG(2, ("dcerpc_winreg_set_expand_sz: Could not marshall "
470 "string %s for %s\n",
477 status = dcerpc_winreg_SetValue(h,
485 if (!NT_STATUS_IS_OK(status)) {
488 if (!W_ERROR_IS_OK(result)) {
495 NTSTATUS dcerpc_winreg_set_multi_sz(TALLOC_CTX *mem_ctx,
496 struct dcerpc_binding_handle *h,
497 struct policy_handle *key_handle,
502 struct winreg_String wvalue = { 0, };
504 WERROR result = WERR_OK;
508 if (!push_reg_multi_sz(mem_ctx, &blob, data)) {
509 DEBUG(2, ("dcerpc_winreg_set_multi_sz: Could not marshall "
510 "string multi sz for %s\n",
516 status = dcerpc_winreg_SetValue(h,
524 if (!NT_STATUS_IS_OK(status)) {
527 if (!W_ERROR_IS_OK(result)) {
534 NTSTATUS dcerpc_winreg_set_binary(TALLOC_CTX *mem_ctx,
535 struct dcerpc_binding_handle *h,
536 struct policy_handle *key_handle,
541 struct winreg_String wvalue = { 0, };
542 WERROR result = WERR_OK;
547 status = dcerpc_winreg_SetValue(h,
555 if (!NT_STATUS_IS_OK(status)) {
558 if (!W_ERROR_IS_OK(result)) {
565 NTSTATUS dcerpc_winreg_set_sd(TALLOC_CTX *mem_ctx,
566 struct dcerpc_binding_handle *h,
567 struct policy_handle *key_handle,
569 const struct security_descriptor *data,
572 enum ndr_err_code ndr_err;
575 ndr_err = ndr_push_struct_blob(&blob,
578 (ndr_push_flags_fn_t) ndr_push_security_descriptor);
579 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
580 DEBUG(2, ("dcerpc_winreg_set_sd: Failed to marshall security "
586 return dcerpc_winreg_set_binary(mem_ctx,
594 NTSTATUS dcerpc_winreg_add_multi_sz(TALLOC_CTX *mem_ctx,
595 struct dcerpc_binding_handle *h,
596 struct policy_handle *key_handle,
601 const char **a = NULL;
604 WERROR result = WERR_OK;
607 status = dcerpc_winreg_query_multi_sz(mem_ctx,
614 /* count the elements */
615 for (p = a, i = 0; p && *p; p++, i++);
617 p = TALLOC_REALLOC_ARRAY(mem_ctx, a, const char *, i + 2);
626 status = dcerpc_winreg_set_multi_sz(mem_ctx,
636 NTSTATUS dcerpc_winreg_enum_keys(TALLOC_CTX *mem_ctx,
637 struct dcerpc_binding_handle *h,
638 struct policy_handle *key_hnd,
639 uint32_t *pnum_subkeys,
640 const char ***psubkeys,
643 const char **subkeys;
644 uint32_t num_subkeys, max_subkeylen, max_classlen;
645 uint32_t num_values, max_valnamelen, max_valbufsize;
647 NTTIME last_changed_time;
648 uint32_t secdescsize;
649 struct winreg_String classname;
650 WERROR result = WERR_OK;
654 tmp_ctx = talloc_stackframe();
655 if (tmp_ctx == NULL) {
656 return NT_STATUS_NO_MEMORY;
659 ZERO_STRUCT(classname);
661 status = dcerpc_winreg_QueryInfoKey(h,
674 if (!NT_STATUS_IS_OK(status)) {
677 if (!W_ERROR_IS_OK(result)) {
682 subkeys = talloc_zero_array(tmp_ctx, const char *, num_subkeys + 2);
683 if (subkeys == NULL) {
688 if (num_subkeys == 0) {
689 subkeys[0] = talloc_strdup(subkeys, "");
690 if (subkeys[0] == NULL) {
696 *psubkeys = talloc_move(mem_ctx, &subkeys);
699 TALLOC_FREE(tmp_ctx);
703 for (i = 0; i < num_subkeys; i++) {
707 struct winreg_StringBuf class_buf;
708 struct winreg_StringBuf name_buf;
712 class_buf.size = max_classlen + 2;
713 class_buf.length = 0;
716 name_buf.size = max_subkeylen + 2;
719 ZERO_STRUCT(modtime);
721 status = dcerpc_winreg_EnumKey(h,
729 if (!NT_STATUS_IS_OK(status)) {
730 DEBUG(5, ("dcerpc_winreg_enum_keys: Could not enumerate keys: %s\n",
735 if (W_ERROR_EQUAL(result, WERR_NO_MORE_ITEMS) ) {
739 if (!W_ERROR_IS_OK(result)) {
740 DEBUG(5, ("dcerpc_winreg_enum_keys: Could not enumerate keys: %s\n",
741 win_errstr(result)));
746 if (name_buf.name == NULL) {
747 *pwerr = WERR_INVALID_PARAMETER;
751 name = talloc_strdup(subkeys, name_buf.name);
760 *pnum_subkeys = num_subkeys;
762 *psubkeys = talloc_move(mem_ctx, &subkeys);
766 TALLOC_FREE(tmp_ctx);
771 /* vim: set ts=8 sw=8 noet cindent syntax=c.doxygen: */