diff options
author | Stefan Metzmacher <metze@samba.org> | 2014-01-23 12:13:14 +0100 |
---|---|---|
committer | Günther Deschner <gd@samba.org> | 2014-02-13 11:54:14 +0100 |
commit | 017338a180c87e938af5215720bf59610f4ddbb1 (patch) | |
tree | bb26b97f92077f6e1bd32cb2077c22754155b3df /librpc | |
parent | 05b54f5a3376735a84cc1c6f1427e3045aa8024d (diff) | |
download | samba-017338a180c87e938af5215720bf59610f4ddbb1.tar.gz samba-017338a180c87e938af5215720bf59610f4ddbb1.tar.xz samba-017338a180c87e938af5215720bf59610f4ddbb1.zip |
librpc/rpc: set more things via dcerpc_binding_set_string_option()
Signed-off-by: Stefan Metzmacher <metze@samba.org>
Reviewed-by: Guenther Deschner <gd@samba.org>
Diffstat (limited to 'librpc')
-rw-r--r-- | librpc/rpc/binding.c | 121 | ||||
-rw-r--r-- | librpc/rpc/rpc_common.h | 1 |
2 files changed, 122 insertions, 0 deletions
diff --git a/librpc/rpc/binding.c b/librpc/rpc/binding.c index 15c1bca3f28..8c17b226a1e 100644 --- a/librpc/rpc/binding.c +++ b/librpc/rpc/binding.c @@ -447,9 +447,35 @@ _PUBLIC_ NTSTATUS dcerpc_parse_binding(TALLOC_CTX *mem_ctx, const char *s, struc _PUBLIC_ const char *dcerpc_binding_get_string_option(const struct dcerpc_binding *b, const char *name) { + struct { + const char *name; + const char *value; +#define _SPECIAL(x) { .name = #x, .value = b->x, } + } specials[] = { + { .name = "object", .value = b->object_string, }, + _SPECIAL(host), + _SPECIAL(endpoint), + _SPECIAL(target_hostname), + _SPECIAL(target_principal), +#undef _SPECIAL + }; size_t i; int ret; + ret = strcmp(name, "transport"); + if (ret == 0) { + return derpc_transport_string_by_transport(b->transport); + } + + for (i=0; i < ARRAY_SIZE(specials); i++) { + ret = strcmp(specials[i].name, name); + if (ret != 0) { + continue; + } + + return specials[i].value; + } + if (b->options == NULL) { return NULL; } @@ -501,6 +527,17 @@ _PUBLIC_ NTSTATUS dcerpc_binding_set_string_option(struct dcerpc_binding *b, const char *name, const char *value) { + struct { + const char *name; + const char **ptr; +#define _SPECIAL(x) { .name = #x, .ptr = &b->x, } + } specials[] = { + _SPECIAL(host), + _SPECIAL(endpoint), + _SPECIAL(target_hostname), + _SPECIAL(target_principal), +#undef _SPECIAL + }; const char *opt = NULL; char *tmp; size_t name_len = strlen(name); @@ -512,6 +549,83 @@ _PUBLIC_ NTSTATUS dcerpc_binding_set_string_option(struct dcerpc_binding *b, * value != NULL means add or reset. */ + ret = strcmp(name, "transport"); + if (ret == 0) { + enum dcerpc_transport_t t = dcerpc_transport_by_name(value); + + if (t == NCA_UNKNOWN && value != NULL) { + return NT_STATUS_INVALID_PARAMETER_MIX; + } + + b->transport = t; + return NT_STATUS_OK; + } + + ret = strcmp(name, "object"); + if (ret == 0) { + DATA_BLOB blob; + NTSTATUS status; + struct GUID uuid; + + tmp = discard_const_p(char, b->object_string); + + if (value == NULL) { + talloc_free(tmp); + b->object_string = NULL; + ZERO_STRUCT(b->object); + return NT_STATUS_OK; + } + + blob = data_blob_string_const(value); + if (blob.length != 36) { + return NT_STATUS_INVALID_PARAMETER_MIX; + } + + status = GUID_from_data_blob(&blob, &uuid); + if (!NT_STATUS_IS_OK(status)) { + return status; + } + + b->object_string = GUID_string(b, &uuid); + if (b->object_string == NULL) { + b->object_string = tmp; + return NT_STATUS_NO_MEMORY; + } + talloc_free(tmp); + + ZERO_STRUCT(b->object); + b->object.uuid = uuid; + return NT_STATUS_OK; + } + + for (i=0; i < ARRAY_SIZE(specials); i++) { + ret = strcmp(specials[i].name, name); + if (ret != 0) { + continue; + } + + tmp = discard_const_p(char, *specials[i].ptr); + + if (value == NULL) { + talloc_free(tmp); + *specials[i].ptr = NULL; + return NT_STATUS_OK; + } + + if (value[0] == '\0') { + return NT_STATUS_INVALID_PARAMETER_MIX; + } + + *specials[i].ptr = talloc_strdup(b, value); + if (*specials[i].ptr == NULL) { + *specials[i].ptr = tmp; + return NT_STATUS_NO_MEMORY; + } + talloc_free(tmp); + + return NT_STATUS_OK; + } + for (i=0; b->options && b->options[i]; i++) { const char *o = b->options[i]; @@ -959,6 +1073,13 @@ _PUBLIC_ struct dcerpc_binding *dcerpc_binding_dup(TALLOC_CTX *mem_ctx, n->flags = b->flags; n->assoc_group_id = b->assoc_group_id; + if (b->object_string != NULL) { + n->object_string = talloc_strdup(n, b->object_string); + if (n->object_string == NULL) { + talloc_free(n); + return NULL; + } + } if (b->host != NULL) { n->host = talloc_strdup(n, b->host); if (n->host == NULL) { diff --git a/librpc/rpc/rpc_common.h b/librpc/rpc/rpc_common.h index 0fd9933d230..a7a081c1b1c 100644 --- a/librpc/rpc/rpc_common.h +++ b/librpc/rpc/rpc_common.h @@ -43,6 +43,7 @@ enum dcerpc_transport_t { struct dcerpc_binding { enum dcerpc_transport_t transport; struct ndr_syntax_id object; + const char *object_string; const char *host; const char *target_hostname; const char *target_principal; |