The Samba-Bugzilla – Attachment 10649 Details for
Bug 11055
vfs_snapper incorrectly handles multi-byte DBus strings
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
patchset for 4.2, cherry picked from master
bso11055_vfs_snapper_str_42t.patchset (text/plain), 14.16 KB, created by
David Disseldorp
on 2015-01-22 10:44:49 UTC
(
hide
)
Description:
patchset for 4.2, cherry picked from master
Filename:
MIME Type:
Creator:
David Disseldorp
Created:
2015-01-22 10:44:49 UTC
Size:
14.16 KB
patch
obsolete
>From 372e27d49a5d0f846e5acfa9fec76dfadf76117c Mon Sep 17 00:00:00 2001 >From: David Disseldorp <ddiss@samba.org> >Date: Wed, 21 Jan 2015 18:16:55 +0100 >Subject: [PATCH 1/3] vfs_snapper: free dbus req messages in error paths > >Bug: https://bugzilla.samba.org/show_bug.cgi?id=11055 > >Signed-off-by: David Disseldorp <ddiss@samba.org> >Reviewed-by: Jeremy Allison <jra@samba.org> >(cherry picked from commit f72fa6390b73f47a57033282335786c24664a3f8) >--- > source3/modules/vfs_snapper.c | 4 ++++ > 1 file changed, 4 insertions(+) > >diff --git a/source3/modules/vfs_snapper.c b/source3/modules/vfs_snapper.c >index 12a3b9a..ed6e073 100644 >--- a/source3/modules/vfs_snapper.c >+++ b/source3/modules/vfs_snapper.c >@@ -472,6 +472,7 @@ static NTSTATUS snapper_list_snaps_pack(char *snapper_conf, > dbus_message_iter_init_append(msg, &args); > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_STRING, > &snapper_conf)) { >+ dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } > >@@ -690,16 +691,19 @@ static NTSTATUS snapper_list_snaps_at_time_pack(const char *snapper_conf, > dbus_message_iter_init_append(msg, &args); > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_STRING, > &snapper_conf)) { >+ dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } > > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_INT64, > &time_lower)) { >+ dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } > > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_INT64, > &time_upper)) { >+ dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } > >-- >2.1.2 > > >From ce6934ce448ea895dae0a384e970712d01a18e7b Mon Sep 17 00:00:00 2001 >From: David Disseldorp <ddiss@samba.org> >Date: Wed, 21 Jan 2015 18:16:56 +0100 >Subject: [PATCH 2/3] vfs_snapper: add DBus string encoding and decoding > helpers > >Snapper uses the following mechanism for encoding and decoding strings >used in DBus traffic: >Characters above 127 (0x7F - ASCII DEL) must be encoded hexadecimal as >"\x??". As a consequence "\" must be encoded as "\\". > >This change adds string encoding and decoding helpers to vfs_snapper. > >Bug: https://bugzilla.samba.org/show_bug.cgi?id=11055 > >Signed-off-by: David Disseldorp <ddiss@samba.org> >Reviewed-by: Jeremy Allison <jra@samba.org> >(cherry picked from commit 3d48fc96739bde631f8197aa313a81808481adf3) >--- > source3/modules/vfs_snapper.c | 124 ++++++++++++++++++++++++++++++++++++++++++ > 1 file changed, 124 insertions(+) > >diff --git a/source3/modules/vfs_snapper.c b/source3/modules/vfs_snapper.c >index ed6e073..35f2a82 100644 >--- a/source3/modules/vfs_snapper.c >+++ b/source3/modules/vfs_snapper.c >@@ -91,6 +91,130 @@ static NTSTATUS snapper_err_ntstatus_map(const char *snapper_err_str) > return NT_STATUS_UNSUCCESSFUL; > } > >+/* >+ * Strings are UTF-8. Other characters must be encoded hexadecimal as "\x??". >+ * As a consequence "\" must be encoded as "\\". >+ */ >+static NTSTATUS snapper_dbus_str_encode(TALLOC_CTX *mem_ctx, const char *in_str, >+ char **_out_str) >+{ >+ size_t in_len; >+ char *out_str; >+ int i; >+ int out_off; >+ int out_len; >+ >+ if (in_str == NULL) { >+ return NT_STATUS_INVALID_PARAMETER; >+ } >+ >+ in_len = strlen(in_str); >+ >+ /* output can be max 4 times the length of @in_str, +1 for terminator */ >+ out_len = (in_len * 4) + 1; >+ >+ out_str = talloc_array(mem_ctx, char, out_len); >+ if (out_str == NULL) { >+ return NT_STATUS_NO_MEMORY; >+ } >+ >+ out_off = 0; >+ for (i = 0; i < in_len; i++) { >+ size_t pushed; >+ >+ if (in_str[i] == '\\') { >+ pushed = snprintf(out_str + out_off, out_len - out_off, >+ "\\\\"); >+ } else if ((unsigned char)in_str[i] > 127) { >+ pushed = snprintf(out_str + out_off, out_len - out_off, >+ "\\x%02x", (unsigned char)in_str[i]); >+ } else { >+ /* regular character */ >+ *(out_str + out_off) = in_str[i]; >+ pushed = sizeof(char); >+ } >+ if (pushed >= out_len - out_off) { >+ /* truncated, should never happen */ >+ talloc_free(out_str); >+ return NT_STATUS_INTERNAL_ERROR; >+ } >+ out_off += pushed; >+ } >+ >+ *(out_str + out_off) = '\0'; >+ *_out_str = out_str; >+ >+ return NT_STATUS_OK; >+} >+ >+static NTSTATUS snapper_dbus_str_decode(TALLOC_CTX *mem_ctx, const char *in_str, >+ char **_out_str) >+{ >+ size_t in_len; >+ char *out_str; >+ int i; >+ int out_off; >+ int out_len; >+ >+ if (in_str == NULL) { >+ return NT_STATUS_INVALID_PARAMETER; >+ } >+ >+ in_len = strlen(in_str); >+ >+ /* output cannot be larger than input, +1 for terminator */ >+ out_len = in_len + 1; >+ >+ out_str = talloc_array(mem_ctx, char, out_len); >+ if (out_str == NULL) { >+ return NT_STATUS_NO_MEMORY; >+ } >+ >+ out_off = 0; >+ for (i = 0; i < in_len; i++) { >+ int j; >+ char hex_buf[3]; >+ unsigned int non_ascii_byte; >+ >+ if (in_str[i] != '\\') { >+ out_str[out_off] = in_str[i]; >+ out_off++; >+ continue; >+ } >+ >+ i++; >+ if (in_str[i] == '\\') { >+ out_str[out_off] = '\\'; >+ out_off++; >+ continue; >+ } else if (in_str[i] != 'x') { >+ goto err_invalid_src_encoding; >+ } >+ >+ /* non-ASCII, encoded as two hex chars */ >+ for (j = 0; j < 2; j++) { >+ i++; >+ if ((in_str[i] == '\0') || !isxdigit(in_str[i])) { >+ goto err_invalid_src_encoding; >+ } >+ hex_buf[j] = in_str[i]; >+ } >+ hex_buf[2] = '\0'; >+ >+ sscanf(hex_buf, "%x", &non_ascii_byte); >+ out_str[out_off] = (unsigned char)non_ascii_byte; >+ out_off++; >+ } >+ >+ out_str[out_off] = '\0'; >+ *_out_str = out_str; >+ >+ return NT_STATUS_OK; >+err_invalid_src_encoding: >+ DEBUG(0, ("invalid encoding %s\n", in_str)); >+ return NT_STATUS_INVALID_PARAMETER; >+} >+ > static DBusConnection *snapper_dbus_conn_create(void) > { > DBusError err; >-- >2.1.2 > > >From 5c590251b8efcc9ccc880099120622d146268742 Mon Sep 17 00:00:00 2001 >From: David Disseldorp <ddiss@samba.org> >Date: Wed, 21 Jan 2015 18:16:57 +0100 >Subject: [PATCH 3/3] vfs_snapper: encode and decode Snapper DBus strings > >Snapper uses a special character encoding for strings used in DBus >requests and responses. This change ensures that Samba packs and unpacks >strings in the corresponding format, using the previously added >encode/decode helper functions. > >Bug: https://bugzilla.samba.org/show_bug.cgi?id=11055 > >Signed-off-by: David Disseldorp <ddiss@samba.org> >Reviewed-by: Jeremy Allison <jra@samba.org> >(cherry picked from commit 32e9d7fa220d05f5ca95ed61cf6c7aa7d0261c03) >--- > source3/modules/vfs_snapper.c | 110 ++++++++++++++++++++++++++++++++++++------ > 1 file changed, 94 insertions(+), 16 deletions(-) > >diff --git a/source3/modules/vfs_snapper.c b/source3/modules/vfs_snapper.c >index 35f2a82..b5e7628 100644 >--- a/source3/modules/vfs_snapper.c >+++ b/source3/modules/vfs_snapper.c >@@ -319,12 +319,15 @@ static NTSTATUS snapper_type_check_get(DBusMessageIter *iter, > return NT_STATUS_OK; > } > >-static NTSTATUS snapper_dict_unpack(DBusMessageIter *iter, >+static NTSTATUS snapper_dict_unpack(TALLOC_CTX *mem_ctx, >+ DBusMessageIter *iter, > struct snapper_dict *dict_out) > > { > NTSTATUS status; > DBusMessageIter dct_iter; >+ char *key_encoded; >+ char *val_encoded; > > status = snapper_type_check(iter, DBUS_TYPE_DICT_ENTRY); > if (!NT_STATUS_IS_OK(status)) { >@@ -333,15 +336,25 @@ static NTSTATUS snapper_dict_unpack(DBusMessageIter *iter, > dbus_message_iter_recurse(iter, &dct_iter); > > status = snapper_type_check_get(&dct_iter, DBUS_TYPE_STRING, >- &dict_out->key); >+ &key_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ return status; >+ } >+ status = snapper_dbus_str_decode(mem_ctx, key_encoded, &dict_out->key); > if (!NT_STATUS_IS_OK(status)) { > return status; > } > > dbus_message_iter_next(&dct_iter); > status = snapper_type_check_get(&dct_iter, DBUS_TYPE_STRING, >- &dict_out->val); >+ &val_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(dict_out->key); >+ return status; >+ } >+ status = snapper_dbus_str_decode(mem_ctx, val_encoded, &dict_out->val); > if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(dict_out->key); > return status; > } > >@@ -384,7 +397,7 @@ static NTSTATUS snapper_dict_array_unpack(TALLOC_CTX *mem_ctx, > if (dicts == NULL) > abort(); > >- status = snapper_dict_unpack(&array_iter, >+ status = snapper_dict_unpack(mem_ctx, &array_iter, > &dicts[num_dicts - 1]); > if (!NT_STATUS_IS_OK(status)) { > talloc_free(dicts); >@@ -424,6 +437,8 @@ static NTSTATUS snapper_conf_unpack(TALLOC_CTX *mem_ctx, > { > NTSTATUS status; > DBusMessageIter st_iter; >+ char *name_encoded; >+ char *mnt_encoded; > > status = snapper_type_check(iter, DBUS_TYPE_STRUCT); > if (!NT_STATUS_IS_OK(status)) { >@@ -432,15 +447,29 @@ static NTSTATUS snapper_conf_unpack(TALLOC_CTX *mem_ctx, > dbus_message_iter_recurse(iter, &st_iter); > > status = snapper_type_check_get(&st_iter, DBUS_TYPE_STRING, >- &conf_out->name); >+ &name_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ return status; >+ } >+ >+ status = snapper_dbus_str_decode(mem_ctx, name_encoded, >+ &conf_out->name); > if (!NT_STATUS_IS_OK(status)) { > return status; > } > > dbus_message_iter_next(&st_iter); > status = snapper_type_check_get(&st_iter, DBUS_TYPE_STRING, >- &conf_out->mnt); >+ &mnt_encoded); > if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(conf_out->name); >+ return status; >+ } >+ >+ status = snapper_dbus_str_decode(mem_ctx, mnt_encoded, >+ &conf_out->mnt); >+ if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(conf_out->name); > return status; > } > >@@ -448,8 +477,13 @@ static NTSTATUS snapper_conf_unpack(TALLOC_CTX *mem_ctx, > status = snapper_dict_array_unpack(mem_ctx, &st_iter, > &conf_out->num_attrs, > &conf_out->attrs); >+ if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(conf_out->mnt); >+ talloc_free(conf_out->name); >+ return status; >+ } > >- return status; >+ return NT_STATUS_OK; > } > > static struct snapper_conf *snapper_conf_array_base_find(int32_t num_confs, >@@ -577,11 +611,14 @@ static NTSTATUS snapper_list_confs_unpack(TALLOC_CTX *mem_ctx, > return NT_STATUS_OK; > } > >-static NTSTATUS snapper_list_snaps_pack(char *snapper_conf, >+static NTSTATUS snapper_list_snaps_pack(TALLOC_CTX *mem_ctx, >+ char *snapper_conf, > DBusMessage **req_msg_out) > { > DBusMessage *msg; > DBusMessageIter args; >+ char *conf_encoded; >+ NTSTATUS status; > > msg = dbus_message_new_method_call("org.opensuse.Snapper", /* target for the method call */ > "/org/opensuse/Snapper", /* object to call on */ >@@ -592,10 +629,17 @@ static NTSTATUS snapper_list_snaps_pack(char *snapper_conf, > return NT_STATUS_NO_MEMORY; > } > >+ status = snapper_dbus_str_encode(mem_ctx, snapper_conf, &conf_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ dbus_message_unref(msg); >+ return status; >+ } >+ > /* append arguments */ > dbus_message_iter_init_append(msg, &args); > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_STRING, >- &snapper_conf)) { >+ &conf_encoded)) { >+ talloc_free(conf_encoded); > dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } >@@ -611,6 +655,8 @@ static NTSTATUS snapper_snap_struct_unpack(TALLOC_CTX *mem_ctx, > { > NTSTATUS status; > DBusMessageIter st_iter; >+ char *desc_encoded; >+ char *cleanup_encoded; > > status = snapper_type_check(iter, DBUS_TYPE_STRUCT); > if (!NT_STATUS_IS_OK(status)) { >@@ -654,15 +700,29 @@ static NTSTATUS snapper_snap_struct_unpack(TALLOC_CTX *mem_ctx, > > dbus_message_iter_next(&st_iter); > status = snapper_type_check_get(&st_iter, DBUS_TYPE_STRING, >- &snap_out->desc); >+ &desc_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ return status; >+ } >+ >+ status = snapper_dbus_str_decode(mem_ctx, desc_encoded, >+ &snap_out->desc); > if (!NT_STATUS_IS_OK(status)) { > return status; > } > > dbus_message_iter_next(&st_iter); > status = snapper_type_check_get(&st_iter, DBUS_TYPE_STRING, >- &snap_out->cleanup); >+ &cleanup_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(snap_out->desc); >+ return status; >+ } >+ >+ status = snapper_dbus_str_decode(mem_ctx, cleanup_encoded, >+ &snap_out->cleanup); > if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(snap_out->desc); > return status; > } > >@@ -670,8 +730,13 @@ static NTSTATUS snapper_snap_struct_unpack(TALLOC_CTX *mem_ctx, > status = snapper_dict_array_unpack(mem_ctx, &st_iter, > &snap_out->num_user_data, > &snap_out->user_data); >+ if (!NT_STATUS_IS_OK(status)) { >+ talloc_free(snap_out->cleanup); >+ talloc_free(snap_out->desc); >+ return status; >+ } > >- return status; >+ return NT_STATUS_OK; > } > > static void snapper_snap_array_print(int32_t num_snaps, >@@ -795,13 +860,16 @@ static NTSTATUS snapper_list_snaps_unpack(TALLOC_CTX *mem_ctx, > return NT_STATUS_OK; > } > >-static NTSTATUS snapper_list_snaps_at_time_pack(const char *snapper_conf, >+static NTSTATUS snapper_list_snaps_at_time_pack(TALLOC_CTX *mem_ctx, >+ const char *snapper_conf, > time_t time_lower, > time_t time_upper, > DBusMessage **req_msg_out) > { > DBusMessage *msg; > DBusMessageIter args; >+ char *conf_encoded; >+ NTSTATUS status; > > msg = dbus_message_new_method_call("org.opensuse.Snapper", > "/org/opensuse/Snapper", >@@ -812,21 +880,30 @@ static NTSTATUS snapper_list_snaps_at_time_pack(const char *snapper_conf, > return NT_STATUS_NO_MEMORY; > } > >+ status = snapper_dbus_str_encode(mem_ctx, snapper_conf, &conf_encoded); >+ if (!NT_STATUS_IS_OK(status)) { >+ dbus_message_unref(msg); >+ return status; >+ } >+ > dbus_message_iter_init_append(msg, &args); > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_STRING, >- &snapper_conf)) { >+ &conf_encoded)) { >+ talloc_free(conf_encoded); > dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } > > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_INT64, > &time_lower)) { >+ talloc_free(conf_encoded); > dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } > > if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_INT64, > &time_upper)) { >+ talloc_free(conf_encoded); > dbus_message_unref(msg); > return NT_STATUS_NO_MEMORY; > } >@@ -975,7 +1052,7 @@ static int snapper_get_shadow_copy_data(struct vfs_handle_struct *handle, > goto err_conn_free; > } > >- status = snapper_list_snaps_pack(conf_name, &req_msg); >+ status = snapper_list_snaps_pack(tmp_ctx, conf_name, &req_msg); > if (!NT_STATUS_IS_OK(status)) { > goto err_conn_free; > } >@@ -1141,7 +1218,8 @@ static NTSTATUS snapper_get_snap_at_time_call(TALLOC_CTX *mem_ctx, > struct snapper_snap *snaps; > char *snap_path; > >- status = snapper_list_snaps_at_time_pack(conf_name, >+ status = snapper_list_snaps_at_time_pack(mem_ctx, >+ conf_name, > snaptime, > snaptime, > &req_msg); >-- >2.1.2 >
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Raw
Flags:
jra
:
review+
Actions:
View
Attachments on
bug 11055
:
10638
|
10639
| 10649