summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--api/src/glfs-fops.c24
-rw-r--r--cli/src/cli-rpc-ops.c44
-rw-r--r--cli/src/cli-xml-output.c56
-rw-r--r--libglusterfs/src/common-utils.h11
-rw-r--r--libglusterfs/src/dict.c46
-rw-r--r--libglusterfs/src/dict.h5
-rw-r--r--xlators/features/index/src/index.c4
-rw-r--r--xlators/mount/fuse/src/fuse-bridge.c35
-rw-r--r--xlators/protocol/server/src/authenticate.c45
-rw-r--r--xlators/protocol/server/src/server-helpers.c10
-rw-r--r--xlators/protocol/server/src/server-rpc-fops.c76
-rw-r--r--xlators/protocol/server/src/server.c134
-rw-r--r--xlators/storage/posix/src/posix-helpers.c58
-rw-r--r--xlators/storage/posix/src/posix.c389
-rw-r--r--xlators/storage/posix/src/posix.h12
15 files changed, 529 insertions, 420 deletions
diff --git a/api/src/glfs-fops.c b/api/src/glfs-fops.c
index c9897243e..be26dc121 100644
--- a/api/src/glfs-fops.c
+++ b/api/src/glfs-fops.c
@@ -1856,32 +1856,12 @@ out:
}
-static int
-dict_keys_join (void *value, int size, dict_t *dict)
-{
- int len = 0;
-
- int add_key_len (dict_t *d, char *k, data_t *v, void *o)
- {
- if (value && size > len)
- strncpy (value + len, k, size - len);
-
- len += (strlen (k) + 1);
-
- return 0;
- }
-
- dict_foreach (dict, add_key_len, 0);
-
- return len;
-}
-
int
glfs_listxattr_process (void *value, size_t size, dict_t *xattr)
{
int ret = -1;
- ret = dict_keys_join (NULL, 0, xattr);
+ ret = dict_keys_join (NULL, 0, xattr, NULL);
if (!value || !size)
goto out;
@@ -1892,7 +1872,7 @@ glfs_listxattr_process (void *value, size_t size, dict_t *xattr)
goto out;
}
- dict_keys_join (value, size, xattr);
+ dict_keys_join (value, size, xattr, NULL);
out:
if (xattr)
dict_unref (xattr);
diff --git a/cli/src/cli-rpc-ops.c b/cli/src/cli-rpc-ops.c
index 22a69da73..c5a0fffb8 100644
--- a/cli/src/cli-rpc-ops.c
+++ b/cli/src/cli-rpc-ops.c
@@ -474,6 +474,30 @@ cli_out_options ( char *substr, char *optstr, char *valstr)
cli_out ("%s: %s",ptr2 , valstr);
}
+static int
+_gf_cli_output_volinfo_opts (dict_t *d, char *k,
+ data_t *v, void *tmp)
+{
+ int ret = 0;
+ char *key = NULL;
+ char *ptr = NULL;
+ data_t *value = NULL;
+
+ key = tmp;
+
+ ptr = strstr (k, "option.");
+ if (ptr) {
+ value = v;
+ if (!value) {
+ ret = -1;
+ goto out;
+ }
+ cli_out_options (key, k, v->data);
+ }
+out:
+ return ret;
+}
+
int
gf_cli_get_volume_cbk (struct rpc_req *req, struct iovec *iov,
@@ -491,12 +515,10 @@ gf_cli_get_volume_cbk (struct rpc_req *req, struct iovec *iov,
int32_t replica_count = 0;
int32_t vol_type = 0;
int32_t transport = 0;
- char *ptr = NULL;
char *volume_id_str = NULL;
char *brick = NULL;
char *volname = NULL;
dict_t *dict = NULL;
- data_t *value = NULL;
cli_local_t *local = NULL;
char key[1024] = {0};
char err_str[2048] = {0};
@@ -724,22 +746,8 @@ next:
cli_out ("Options Reconfigured:");
snprintf (key, 256, "volume%d.option.",i);
- int _output_volinfo_opts (dict_t *d, char *k,
- data_t *v, void *tmp)
- {
- ptr = strstr (k, "option.");
- if (ptr) {
- value = v;
- if (!value) {
- ret = -1;
- goto internal_out;
- }
- cli_out_options (key, k, v->data);
- }
- internal_out:
- return ret;
- }
- ret = dict_foreach (dict, _output_volinfo_opts, NULL);
+
+ ret = dict_foreach (dict, _gf_cli_output_volinfo_opts, key);
if (ret)
goto out;
diff --git a/cli/src/cli-xml-output.c b/cli/src/cli-xml-output.c
index 88410ef57..7155ef539 100644
--- a/cli/src/cli-xml-output.c
+++ b/cli/src/cli-xml-output.c
@@ -2265,15 +2265,44 @@ out:
return ret;
}
+struct tmp_xml_option_logger {
+ char *key;
+ xmlTextWriterPtr writer;
+};
+
+static int
+_output_vol_info_option (dict_t *d, char *k, data_t *v,
+ void *data)
+{
+ int ret = 0;
+ char *ptr = NULL;
+ struct tmp_xml_option_logger *tmp = NULL;
+
+ tmp = data;
+
+ ptr = strstr (k, "option.");
+ if (!ptr)
+ goto out;
+
+ if (!v) {
+ ret = -1;
+ goto out;
+ }
+ ret = cli_xml_output_vol_info_option (tmp->writer, tmp->key, k,
+ v->data);
+
+out:
+ return ret;
+}
+
int
cli_xml_output_vol_info_options (xmlTextWriterPtr writer, dict_t *dict,
char *prefix)
{
int ret = -1;
int opt_count = 0;
- data_t *value = 0;
- char *ptr = NULL;
char key[1024] = {0,};
+ struct tmp_xml_option_logger tmp = {0,};
snprintf (key, sizeof (key), "%s.opt_count", prefix);
ret = dict_get_int32 (dict, key, &opt_count);
@@ -2288,26 +2317,9 @@ cli_xml_output_vol_info_options (xmlTextWriterPtr writer, dict_t *dict,
XML_RET_CHECK_AND_GOTO (ret, out);
snprintf (key, sizeof (key), "%s.option.", prefix);
- int _output_vol_info_option (dict_t *d, char *k, data_t *v,
- void *data)
- {
- int ret = 0;
- ptr = strstr (k, "option.");
- if (!ptr)
- goto internal_out;
-
- value = v;
- if (!value) {
- ret = -1;
- goto internal_out;
- }
- ret = cli_xml_output_vol_info_option (writer, key, k,
- v->data);
-
- internal_out:
- return ret;
- }
- ret = dict_foreach (dict, _output_vol_info_option, NULL);
+ tmp.key = key;
+ tmp.writer = writer;
+ ret = dict_foreach (dict, _output_vol_info_option, &tmp);
if (ret)
goto out;
diff --git a/libglusterfs/src/common-utils.h b/libglusterfs/src/common-utils.h
index 75692309e..d9d3082c0 100644
--- a/libglusterfs/src/common-utils.h
+++ b/libglusterfs/src/common-utils.h
@@ -172,7 +172,6 @@ void gf_print_trace (int32_t signal, glusterfs_ctx_t *ctx);
} \
} while (0)
-
#define GF_IF_INTERNAL_XATTR_GOTO(pattern, dict, op_errno, label) \
do { \
if (!dict) { \
@@ -180,13 +179,9 @@ void gf_print_trace (int32_t signal, glusterfs_ctx_t *ctx);
"setxattr dict is null"); \
goto label; \
} \
- int _handle_keyvalue_pair (dict_t *d, char *k, \
- data_t *v, void *tmp) \
- { \
- return 0; \
- } \
- if (dict_foreach_fnmatch (dict, pattern, \
- _handle_keyvalue_pair, NULL) > 0) { \
+ if (dict_foreach_fnmatch (dict, pattern, \
+ dict_null_foreach_fn, \
+ NULL) > 0) { \
op_errno = EPERM; \
gf_log (this->name, GF_LOG_ERROR, \
"attempt to set internal" \
diff --git a/libglusterfs/src/dict.c b/libglusterfs/src/dict.c
index e9b8da1c4..a8cdeaf28 100644
--- a/libglusterfs/src/dict.c
+++ b/libglusterfs/src/dict.c
@@ -1079,6 +1079,13 @@ data_to_bin (data_t *data)
}
int
+dict_null_foreach_fn (dict_t *d, char *k,
+ data_t *v, void *tmp)
+{
+ return 0;
+}
+
+int
dict_foreach (dict_t *dict,
int (*fn)(dict_t *this,
char *key,
@@ -1148,6 +1155,45 @@ dict_foreach_fnmatch (dict_t *dict, char *pattern,
}
+/**
+ * dict_keys_join - pack the keys of the dictionary in a buffer.
+ *
+ * @value : buffer in which the keys will be packed (can be NULL)
+ * @size : size of the buffer which is sent (can be 0, in which case buffer
+ * is not packed but only length is returned)
+ * @dict : dictionary of which all the keys will be packed
+ * @filter_fn : keys matched in filter_fn() is counted.
+ *
+ * @return : @length of string after joining keys.
+ *
+ */
+
+int
+dict_keys_join (void *value, int size, dict_t *dict,
+ int (*filter_fn)(char *k))
+{
+ int len = 0;
+ data_pair_t *pairs = NULL;
+ data_pair_t *next = NULL;
+
+ pairs = dict->members_list;
+ while (pairs) {
+ next = pairs->next;
+
+ if (filter_fn && filter_fn (pairs->key))
+ continue;
+
+ if (value && (size > len))
+ strncpy (value + len, pairs->key, size - len);
+
+ len += (strlen (pairs->key) + 1);
+
+ pairs = next;
+ }
+
+ return len;
+}
+
static int
_copy (dict_t *unused,
char *key,
diff --git a/libglusterfs/src/dict.h b/libglusterfs/src/dict.h
index dbf98046f..c7606352c 100644
--- a/libglusterfs/src/dict.h
+++ b/libglusterfs/src/dict.h
@@ -177,7 +177,12 @@ int dict_foreach_fnmatch (dict_t *dict, char *pattern,
void *data),
void *data);
+int dict_null_foreach_fn (dict_t *d, char *k,
+ data_t *v, void *tmp);
+
dict_t *dict_copy (dict_t *this, dict_t *new);
+int dict_keys_join (void *value, int size, dict_t *dict,
+ int (*filter_fn)(char *key));
/* CLEANED UP FUNCTIONS DECLARATIONS */
GF_MUST_CHECK dict_t *dict_new (void);
diff --git a/xlators/features/index/src/index.c b/xlators/features/index/src/index.c
index d1eb763de..d061c4103 100644
--- a/xlators/features/index/src/index.c
+++ b/xlators/features/index/src/index.c
@@ -430,7 +430,8 @@ index_del (xlator_t *this, uuid_t gfid, const char *subdir)
out:
return ret;
}
-int
+
+static int
_check_key_is_zero_filled (dict_t *d, char *k, data_t *v,
void *tmp)
{
@@ -441,6 +442,7 @@ _check_key_is_zero_filled (dict_t *d, char *k, data_t *v,
return 0;
}
+
void
_xattrop_index_action (xlator_t *this, inode_t *inode, dict_t *xattr)
{
diff --git a/xlators/mount/fuse/src/fuse-bridge.c b/xlators/mount/fuse/src/fuse-bridge.c
index a6d022103..214923dec 100644
--- a/xlators/mount/fuse/src/fuse-bridge.c
+++ b/xlators/mount/fuse/src/fuse-bridge.c
@@ -2868,10 +2868,10 @@ send_fuse_xattr (xlator_t *this, fuse_in_header_t *finh, const char *value,
* when it tries to setxattr() for selinux xattrs
*/
static int
-fuse_filter_xattr(xlator_t *this, char *key)
+fuse_filter_xattr(char *key)
{
int need_filter = 0;
- struct fuse_private *priv = this->private;
+ struct fuse_private *priv = THIS->private;
if ((priv->client_pid == GF_CLIENT_PID_GSYNCD)
&& fnmatch ("*.selinux*", key, FNM_PERIOD) == 0)
@@ -2892,6 +2892,7 @@ fuse_xattr_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
data_t *value_data = NULL;
int ret = -1;
int32_t len = 0;
+ int32_t len_next = 0;
state = frame->root->state;
finh = state->finh;
@@ -2922,32 +2923,20 @@ fuse_xattr_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
/* we need to invoke fuse_filter_xattr() twice. Once
* while counting size and then while filling buffer
*/
- int _get_total_len (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- if (!fuse_filter_xattr (this, k))
- len += strlen (k) + 1;
- return 0;
- }
- dict_foreach (dict, _get_total_len, NULL);
+ len = dict_keys_join (NULL, 0, dict, fuse_filter_xattr);
+ if (len < 0)
+ goto out;
value = alloca (len + 1);
if (!value)
goto out;
- len = 0;
-
- int _set_listxattr_keys (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- if (!fuse_filter_xattr (this, k)) {
- strcpy (value + len, k);
- value[len + strlen (k)] = '\0';
- len += strlen (k) + 1;
- }
- return 0;
- }
- dict_foreach (dict, _set_listxattr_keys, NULL);
+ len_next = dict_keys_join (value, len, dict,
+ fuse_filter_xattr);
+ if (len_next != len)
+ gf_log (THIS->name, GF_LOG_ERROR,
+ "sizes not equal %d != %d",
+ len, len_next);
send_fuse_xattr (this, finh, value, len, state->size);
} /* if(state->name)...else */
diff --git a/xlators/protocol/server/src/authenticate.c b/xlators/protocol/server/src/authenticate.c
index 9c843d0bb..eb6deb801 100644
--- a/xlators/protocol/server/src/authenticate.c
+++ b/xlators/protocol/server/src/authenticate.c
@@ -124,34 +124,41 @@ fini (dict_t *this, char *key, data_t *value, void *data)
return 0;
}
+static int
+_gf_auth_option_validate (dict_t *d, char *k, data_t *v, void *tmp)
+{
+ auth_handle_t *handle = NULL;
+ xlator_t *xl = NULL;
+ int ret = 0;
+
+ xl = tmp;
+
+ handle = data_to_ptr (v);
+ if (!handle)
+ return 0;
+
+ list_add_tail (&(handle->vol_opt->list), &(xl->volume_options));
+
+ ret = xlator_options_validate_list (xl, xl->options,
+ handle->vol_opt, NULL);
+ if (ret) {
+ gf_log ("authenticate", GF_LOG_ERROR,
+ "volume option validation failed");
+ return -1;
+ }
+ return 0;
+}
+
int32_t
gf_auth_init (xlator_t *xl, dict_t *auth_modules)
{
int ret = 0;
- auth_handle_t *handle = NULL;
dict_foreach (auth_modules, init, &ret);
if (ret)
goto out;
- int _auth_option_validate (dict_t *d, char *k, data_t *v, void *tmp)
- {
- handle = data_to_ptr (v);
- if (!handle)
- return 0;
-
- list_add_tail (&(handle->vol_opt->list),
- &(xl->volume_options));
- ret = xlator_options_validate_list (xl, xl->options,
- handle->vol_opt, NULL);
- if (ret) {
- gf_log ("authenticate", GF_LOG_ERROR,
- "volume option validation failed");
- return -1;
- }
- return 0;
- }
- ret = dict_foreach (auth_modules, _auth_option_validate, NULL);
+ ret = dict_foreach (auth_modules, _gf_auth_option_validate, xl);
out:
if (ret) {
diff --git a/xlators/protocol/server/src/server-helpers.c b/xlators/protocol/server/src/server-helpers.c
index 0adcd1cf1..28b912eec 100644
--- a/xlators/protocol/server/src/server-helpers.c
+++ b/xlators/protocol/server/src/server-helpers.c
@@ -1397,16 +1397,8 @@ gf_server_check_setxattr_cmd (call_frame_t *frame, dict_t *dict)
if (!conf || !dict)
return 0;
- /* this exact key is used in 'io-stats' too.
- * But this is better place for this information dump.
- */
- int _handle_keyvalue_pair (dict_t *d, char *k,
- data_t *v, void *tmp)
- {
- return 0;
- }
if (dict_foreach_fnmatch (dict, "*io*stat*dump",
- _handle_keyvalue_pair, NULL ) > 0) {
+ dict_null_foreach_fn, NULL ) > 0) {
list_for_each_entry (xprt, &conf->xprt_list, list) {
total_read += xprt->total_bytes_read;
total_write += xprt->total_bytes_write;
diff --git a/xlators/protocol/server/src/server-rpc-fops.c b/xlators/protocol/server/src/server-rpc-fops.c
index 286befc4e..f44ced41d 100644
--- a/xlators/protocol/server/src/server-rpc-fops.c
+++ b/xlators/protocol/server/src/server-rpc-fops.c
@@ -890,6 +890,24 @@ out:
return 0;
}
+/* print every key */
+static int
+_gf_server_log_setxattr_failure (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ server_state_t *state = NULL;
+ call_frame_t *frame = NULL;
+
+ frame = tmp;
+ state = CALL_STATE(frame);
+
+ gf_log (THIS->name, GF_LOG_INFO,
+ "%"PRId64": SETXATTR %s (%s) ==> %s",
+ frame->root->unique, state->loc.path,
+ uuid_utoa (state->resolve.gfid), k);
+ return 0;
+}
+
int
server_setxattr_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
int32_t op_ret, int32_t op_errno, dict_t *xdata)
@@ -905,19 +923,14 @@ server_setxattr_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
rsp.xdata.xdata_len, op_errno, out);
if (op_ret == -1) {
- /* print every key */
- int _log_setxattr_failure (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- gf_log (this->name, ((op_errno == ENOTSUP) ?
- GF_LOG_DEBUG : GF_LOG_INFO),
- "%"PRId64": SETXATTR %s (%s) ==> %s (%s)",
- frame->root->unique, state->loc.path,
- uuid_utoa (state->resolve.gfid), k,
- strerror (op_errno));
- return 0;
- }
- dict_foreach (state->dict, _log_setxattr_failure, NULL);
+ if (op_errno != ENOTSUP)
+ dict_foreach (state->dict,
+ _gf_server_log_setxattr_failure,
+ frame);
+
+ gf_log (THIS->name, ((op_errno == ENOTSUP) ?
+ GF_LOG_DEBUG : GF_LOG_INFO),
+ "%s", strerror (op_errno));
goto out;
}
@@ -933,6 +946,24 @@ out:
return 0;
}
+/* print every key here */
+static int
+_gf_server_log_fsetxattr_failure (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ call_frame_t *frame = NULL;
+ server_state_t *state = NULL;
+
+ frame = tmp;
+ state = CALL_STATE(frame);
+
+ gf_log (THIS->name, GF_LOG_INFO,
+ "%"PRId64": FSETXATTR %"PRId64" (%s) ==> %s",
+ frame->root->unique, state->resolve.fd_no,
+ uuid_utoa (state->resolve.gfid), k);
+
+ return 0;
+}
int
server_fsetxattr_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
@@ -949,19 +980,14 @@ server_fsetxattr_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
rsp.xdata.xdata_len, op_errno, out);
if (op_ret == -1) {
- /* print every key here */
- int _log_setxattr_failure (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- gf_log (this->name, ((op_errno == ENOTSUP) ?
- GF_LOG_DEBUG : GF_LOG_INFO),
- "%"PRId64": FSETXATTR %"PRId64" (%s) ==> %s (%s)",
- frame->root->unique, state->resolve.fd_no,
- uuid_utoa (state->resolve.gfid), k,
- strerror (op_errno));
- return 0;
+ if (op_errno != ENOTSUP) {
+ dict_foreach (state->dict,
+ _gf_server_log_fsetxattr_failure,
+ frame);
}
- dict_foreach (state->dict, _log_setxattr_failure, NULL);
+ gf_log (THIS->name, ((op_errno == ENOTSUP) ?
+ GF_LOG_DEBUG : GF_LOG_INFO),
+ "%s", strerror (op_errno));
goto out;
}
diff --git a/xlators/protocol/server/src/server.c b/xlators/protocol/server/src/server.c
index 19f09a82f..d2bc4876c 100644
--- a/xlators/protocol/server/src/server.c
+++ b/xlators/protocol/server/src/server.c
@@ -616,84 +616,85 @@ out:
return 0;
}
+int
+_check_for_auth_option (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ int ret = 0;
+ xlator_t *xl = NULL;
+ char *tail = NULL;
+ char *tmp_addr_list = NULL;
+ char *addr = NULL;
+ char *tmp_str = NULL;
+
+ xl = tmp;
+
+ tail = strtail (k, "auth.");
+ if (!tail)
+ goto out;
+
+ /* fast fwd thru module type */
+ tail = strchr (tail, '.');
+ if (!tail)
+ goto out;
+ tail++;
+
+ tail = strtail (tail, xl->name);
+ if (!tail)
+ goto out;
+
+ if (*tail == '.') {
+ /* when we are here, the key is checked for
+ * valid auth.allow.<xlator>
+ * Now we verify the ip address
+ */
+ if (!strcmp (v->data, "*")) {
+ ret = 0;
+ goto out;
+ }
+
+ tmp_addr_list = gf_strdup (v->data);
+ addr = strtok_r (tmp_addr_list, ",", &tmp_str);
+ if (!addr)
+ addr = v->data;
+
+ while (addr) {
+ if (valid_internet_address (addr, _gf_true)) {
+ ret = 0;
+ } else {
+ ret = -1;
+ gf_log (xl->name, GF_LOG_ERROR,
+ "internet address '%s'"
+ " does not conform to"
+ " standards.", addr);
+ goto out;
+ }
+ if (tmp_str)
+ addr = strtok_r (NULL, ",", &tmp_str);
+ else
+ addr = NULL;
+ }
+
+ GF_FREE (tmp_addr_list);
+ tmp_addr_list = NULL;
+ }
+out:
+ return ret;
+}
int
validate_auth_options (xlator_t *this, dict_t *dict)
{
int error = -1;
xlator_list_t *trav = NULL;
- char *tail = NULL;
- char *tmp_addr_list = NULL;
- char *addr = NULL;
- char *tmp_str = NULL;
GF_VALIDATE_OR_GOTO ("server", this, out);
GF_VALIDATE_OR_GOTO ("server", dict, out);
trav = this->children;
while (trav) {
- int _check_for_auth_option (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- int ret = 0;
- tail = strtail (k, "auth.");
- if (!tail)
- goto internal_out;
-
- /* fast fwd thru module type */
- tail = strchr (tail, '.');
- if (!tail)
- goto internal_out;
- tail++;
-
- tail = strtail (tail, trav->xlator->name);
- if (!tail)
- goto internal_out;
-
- if (*tail == '.') {
-
- /* when we are here, the key is checked for
- * valid auth.allow.<xlator>
- * Now we verify the ip address
- */
- if (!strcmp (v->data, "*")) {
- ret = 0;
- goto internal_out;
- }
-
- tmp_addr_list = gf_strdup (v->data);
- addr = strtok_r (tmp_addr_list, ",", &tmp_str);
- if (!addr)
- addr = v->data;
-
- while (addr) {
-
- if (valid_internet_address (addr,
- _gf_true)) {
- ret = 0;
- } else {
- ret = -1;
- gf_log (this->name, GF_LOG_ERROR,
- "internet address '%s'"
- " does not conform to"
- " standards.", addr);
- goto internal_out;
-
- }
- if (tmp_str)
- addr = strtok_r (NULL, ",",
- &tmp_str);
- else
- addr = NULL;
- }
-
- GF_FREE (tmp_addr_list);
- tmp_addr_list = NULL;
- }
- internal_out:
- return ret;
- }
- error = dict_foreach (dict, _check_for_auth_option, NULL);
+ error = dict_foreach (dict, _check_for_auth_option,
+ trav->xlator);
if (-1 == error) {
gf_log (this->name, GF_LOG_ERROR,
@@ -706,7 +707,6 @@ validate_auth_options (xlator_t *this, dict_t *dict)
}
out:
- GF_FREE (tmp_addr_list);
return error;
}
diff --git a/xlators/storage/posix/src/posix-helpers.c b/xlators/storage/posix/src/posix-helpers.c
index 58708a347..7e8d5838c 100644
--- a/xlators/storage/posix/src/posix-helpers.c
+++ b/xlators/storage/posix/src/posix-helpers.c
@@ -46,14 +46,6 @@
#include "hashfn.h"
#include <fnmatch.h>
-typedef struct {
- xlator_t *this;
- const char *real_path;
- dict_t *xattr;
- struct iatt *stbuf;
- loc_t *loc;
-} posix_xattr_filler_t;
-
char *marker_xattrs[] = {"trusted.glusterfs.quota.*",
"trusted.glusterfs.*.xtime",
NULL};
@@ -946,35 +938,47 @@ out:
return ret;
}
+static int
+_handle_entry_create_keyvalue_pair (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ int ret = -1;
+ posix_xattr_filler_t *filler = NULL;
+
+ filler = tmp;
+
+ if (!strcmp (GFID_XATTR_KEY, k) ||
+ !strcmp ("gfid-req", k) ||
+ !strcmp ("system.posix_acl_default", k) ||
+ !strcmp ("system.posix_acl_access", k) ||
+ ZR_FILE_CONTENT_REQUEST(k)) {
+ return 0;
+ }
+
+ ret = posix_handle_pair (filler->this, filler->real_path, k, v,
+ XATTR_CREATE);
+ if (ret < 0) {
+ errno = -ret;
+ return -1;
+ }
+ return 0;
+}
+
int
posix_entry_create_xattr_set (xlator_t *this, const char *path,
dict_t *dict)
{
int ret = -1;
+ posix_xattr_filler_t filler = {0,};
+
if (!dict)
goto out;
- int _handle_keyvalue_pair (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- if (!strcmp (GFID_XATTR_KEY, k) ||
- !strcmp ("gfid-req", k) ||
- !strcmp ("system.posix_acl_default", k) ||
- !strcmp ("system.posix_acl_access", k) ||
- ZR_FILE_CONTENT_REQUEST(k)) {
- return 0;
- }
-
- ret = posix_handle_pair (this, path, k, v, XATTR_CREATE);
- if (ret < 0) {
- errno = -ret;
- return -1;
- }
- return 0;
- }
+ filler.this = this;
+ filler.real_path = path;
- ret = dict_foreach (dict, _handle_keyvalue_pair, NULL);
+ ret = dict_foreach (dict, _handle_entry_create_keyvalue_pair, &filler);
out:
return ret;
diff --git a/xlators/storage/posix/src/posix.c b/xlators/storage/posix/src/posix.c
index 816011542..258ce5241 100644
--- a/xlators/storage/posix/src/posix.c
+++ b/xlators/storage/posix/src/posix.c
@@ -2382,6 +2382,17 @@ out:
}
static int gf_posix_xattr_enotsup_log;
+static int
+_handle_setxattr_keyvalue_pair (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ posix_xattr_filler_t *filler = NULL;
+
+ filler = tmp;
+
+ return posix_handle_pair (filler->this, filler->real_path, k, v,
+ filler->flags);
+}
int32_t
posix_setxattr (call_frame_t *frame, xlator_t *this,
@@ -2390,7 +2401,8 @@ posix_setxattr (call_frame_t *frame, xlator_t *this,
int32_t op_ret = -1;
int32_t op_errno = 0;
char * real_path = NULL;
- int ret = -1;
+
+ posix_xattr_filler_t filler = {0,};
DECLARE_OLD_FS_ID_VAR;
SET_FS_ID (frame->root->uid, frame->root->gid);
@@ -2405,17 +2417,13 @@ posix_setxattr (call_frame_t *frame, xlator_t *this,
op_ret = -1;
dict_del (dict, GFID_XATTR_KEY);
-
- int _handle_every_keyvalue_pair (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- ret = posix_handle_pair (this, real_path, k, v, flags);
- if (ret < 0) {
- op_errno = -ret;
- }
- return ret;
- }
- op_ret = dict_foreach (dict, _handle_every_keyvalue_pair, NULL);
+ filler.real_path = real_path;
+ filler.this = this;
+ filler.flags = flags;
+ op_ret = dict_foreach (dict, _handle_setxattr_keyvalue_pair,
+ &filler);
+ if (op_ret < 0)
+ op_errno = -op_ret;
out:
SET_TO_OLD_FS_ID ();
@@ -2899,6 +2907,17 @@ out:
return 0;
}
+static int
+_handle_fsetxattr_keyvalue_pair (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ posix_xattr_filler_t *filler = NULL;
+
+ filler = tmp;
+
+ return posix_fhandle_pair (filler->this, filler->fd, k, v,
+ filler->flags);
+}
int32_t
posix_fsetxattr (call_frame_t *frame, xlator_t *this,
@@ -2908,7 +2927,9 @@ posix_fsetxattr (call_frame_t *frame, xlator_t *this,
int32_t op_errno = 0;
struct posix_fd * pfd = NULL;
int _fd = -1;
- int ret = -1;
+ int ret = -1;
+
+ posix_xattr_filler_t filler = {0,};
DECLARE_OLD_FS_ID_VAR;
SET_FS_ID (frame->root->uid, frame->root->gid);
@@ -2929,17 +2950,13 @@ posix_fsetxattr (call_frame_t *frame, xlator_t *this,
dict_del (dict, GFID_XATTR_KEY);
- int _handle_every_keyvalue_pair (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
- ret = posix_fhandle_pair (this, _fd, k, v, flags);
- if (ret < 0) {
- op_errno = -ret;
- }
- return ret;
- }
-
- op_ret = dict_foreach (dict, _handle_every_keyvalue_pair, NULL);
+ filler.fd = _fd;
+ filler.this = this;
+ filler.flags = flags;
+ op_ret = dict_foreach (dict, _handle_fsetxattr_keyvalue_pair,
+ &filler);
+ if (op_ret < 0)
+ op_errno = -op_ret;
out:
SET_TO_OLD_FS_ID ();
@@ -3130,6 +3147,159 @@ __add_long_array (int64_t *dest, int64_t *src, int count)
}
}
+static int
+_posix_handle_xattr_keyvalue_pair (dict_t *d, char *k, data_t *v,
+ void *tmp)
+{
+ int size = 0;
+ int count = 0;
+ int op_ret = 0;
+ int op_errno = 0;
+ gf_xattrop_flags_t optype = 0;
+ char *array = NULL;
+ inode_t *inode = NULL;
+ xlator_t *this = NULL;
+ posix_xattr_filler_t *filler = NULL;
+
+ filler = tmp;
+
+ optype = (gf_xattrop_flags_t)(filler->flags);
+ this = filler->this;
+ inode = filler->inode;
+
+ count = v->len;
+ array = GF_CALLOC (count, sizeof (char), gf_posix_mt_char);
+
+ LOCK (&inode->lock);
+ {
+ if (filler->real_path) {
+ size = sys_lgetxattr (filler->real_path, k,
+ (char *)array, v->len);
+ } else {
+ size = sys_fgetxattr (filler->fd, k, (char *)array,
+ v->len);
+ }
+
+ op_errno = errno;
+ if ((size == -1) && (op_errno != ENODATA) &&
+ (op_errno != ENOATTR)) {
+ if (op_errno == ENOTSUP) {
+ GF_LOG_OCCASIONALLY(gf_posix_xattr_enotsup_log,
+ this->name, GF_LOG_WARNING,
+ "Extended attributes not "
+ "supported by filesystem");
+ } else if (op_errno != ENOENT ||
+ !posix_special_xattr (marker_xattrs,
+ k)) {
+ if (filler->real_path)
+ gf_log (this->name, GF_LOG_ERROR,
+ "getxattr failed on %s while doing "
+ "xattrop: Key:%s (%s)",
+ filler->real_path,
+ k, strerror (op_errno));
+ else
+ gf_log (this->name, GF_LOG_ERROR,
+ "fgetxattr failed on fd=%d while doing "
+ "xattrop: Key:%s (%s)",
+ filler->fd,
+ k, strerror (op_errno));
+ }
+
+ op_ret = -1;
+ goto unlock;
+ }
+
+ switch (optype) {
+
+ case GF_XATTROP_ADD_ARRAY:
+ __add_array ((int32_t *) array, (int32_t *) v->data,
+ v->len / 4);
+ break;
+
+ case GF_XATTROP_ADD_ARRAY64:
+ __add_long_array ((int64_t *) array, (int64_t *) v->data,
+ v->len / 8);
+ break;
+
+ case GF_XATTROP_OR_ARRAY:
+ __or_array ((int32_t *) array,
+ (int32_t *) v->data,
+ v->len / 4);
+ break;
+
+ case GF_XATTROP_AND_ARRAY:
+ __and_array ((int32_t *) array,
+ (int32_t *) v->data,
+ v->len / 4);
+ break;
+
+ default:
+ gf_log (this->name, GF_LOG_ERROR,
+ "Unknown xattrop type (%d) on %s. Please send "
+ "a bug report to gluster-devel@nongnu.org",
+ optype, filler->real_path);
+ op_ret = -1;
+ op_errno = EINVAL;
+ goto unlock;
+ }
+
+ if (filler->real_path) {
+ size = sys_lsetxattr (filler->real_path, k, array,
+ v->len, 0);
+ } else {
+ size = sys_fsetxattr (filler->fd, k, (char *)array,
+ v->len, 0);
+ }
+ }
+unlock:
+ UNLOCK (&inode->lock);
+
+ if (op_ret == -1)
+ goto out;
+
+ op_errno = errno;
+ if (size == -1) {
+ if (filler->real_path)
+ gf_log (this->name, GF_LOG_ERROR,
+ "setxattr failed on %s while doing xattrop: "
+ "key=%s (%s)", filler->real_path,
+ k, strerror (op_errno));
+ else
+ gf_log (this->name, GF_LOG_ERROR,
+ "fsetxattr failed on fd=%d while doing xattrop: "
+ "key=%s (%s)", filler->fd,
+ k, strerror (op_errno));
+
+ op_ret = -1;
+ goto out;
+ } else {
+ size = dict_set_bin (d, k, array, v->len);
+
+ if (size != 0) {
+ if (filler->real_path)
+ gf_log (this->name, GF_LOG_DEBUG,
+ "dict_set_bin failed (path=%s): "
+ "key=%s (%s)", filler->real_path,
+ k, strerror (-size));
+ else
+ gf_log (this->name, GF_LOG_DEBUG,
+ "dict_set_bin failed (fd=%d): "
+ "key=%s (%s)", filler->fd,
+ k, strerror (-size));
+
+ op_ret = -1;
+ op_errno = EINVAL;
+ goto out;
+ }
+ array = NULL;
+ }
+
+ array = NULL;
+
+out:
+ return op_ret;
+}
+
/**
* xattrop - xattr operations - for internal use by GlusterFS
* @optype: ADD_ARRAY:
@@ -3141,32 +3311,24 @@ int
do_xattrop (call_frame_t *frame, xlator_t *this, loc_t *loc, fd_t *fd,
gf_xattrop_flags_t optype, dict_t *xattr)
{
- char *real_path = NULL;
- char *array = NULL;
- int size = 0;
- int count = 0;
-
- int op_ret = 0;
- int op_errno = 0;
-
- int ret = 0;
- int _fd = -1;
- struct posix_fd *pfd = NULL;
-
- char * path = NULL;
- inode_t * inode = NULL;
+ int op_ret = 0;
+ int op_errno = 0;
+ int _fd = -1;
+ char *real_path = NULL;
+ struct posix_fd *pfd = NULL;
+ inode_t *inode = NULL;
+ posix_xattr_filler_t filler = {0,};
VALIDATE_OR_GOTO (frame, out);
VALIDATE_OR_GOTO (xattr, out);
VALIDATE_OR_GOTO (this, out);
if (fd) {
- ret = posix_fd_ctx_get (fd, this, &pfd);
- if (ret < 0) {
+ op_ret = posix_fd_ctx_get (fd, this, &pfd);
+ if (op_ret < 0) {
gf_log (this->name, GF_LOG_WARNING,
"failed to get pfd from fd=%p",
fd);
- op_ret = -1;
op_errno = EBADFD;
goto out;
}
@@ -3177,152 +3339,21 @@ do_xattrop (call_frame_t *frame, xlator_t *this, loc_t *loc, fd_t *fd,
MAKE_INODE_HANDLE (real_path, this, loc, NULL);
if (real_path) {
- path = gf_strdup (real_path);
inode = loc->inode;
} else if (fd) {
inode = fd->inode;
}
- int _handle_every_keyvalue_pair (dict_t *d, char *k, data_t *v,
- void *tmp)
- {
-
- count = v->len;
- array = GF_CALLOC (count, sizeof (char), gf_posix_mt_char);
-
- LOCK (&inode->lock);
- {
- if (loc) {
- size = sys_lgetxattr (real_path, k,
- (char *)array, v->len);
- } else {
- size = sys_fgetxattr (_fd, k, (char *)array,
- v->len);
- }
-
- op_errno = errno;
- if ((size == -1) && (op_errno != ENODATA) &&
- (op_errno != ENOATTR)) {
- if (op_errno == ENOTSUP) {
- GF_LOG_OCCASIONALLY(gf_posix_xattr_enotsup_log,
- this->name,GF_LOG_WARNING,
- "Extended attributes not "
- "supported by filesystem");
- } else if (op_errno != ENOENT ||
- !posix_special_xattr (marker_xattrs,
- k)) {
- if (loc)
- gf_log (this->name, GF_LOG_ERROR,
- "getxattr failed on %s while doing "
- "xattrop: Key:%s (%s)", path,
- k, strerror (op_errno));
- else
- gf_log (this->name, GF_LOG_ERROR,
- "fgetxattr failed on fd=%d while doing "
- "xattrop: Key:%s (%s)", _fd,
- k, strerror (op_errno));
- }
-
- op_ret = -1;
- goto unlock;
- }
-
- switch (optype) {
-
- case GF_XATTROP_ADD_ARRAY:
- __add_array ((int32_t *) array, (int32_t *) v->data,
- v->len / 4);
- break;
+ filler.this = this;
+ filler.fd = _fd;
+ filler.real_path = real_path;
+ filler.flags = (int)optype;
+ filler.inode = inode;
- case GF_XATTROP_ADD_ARRAY64:
- __add_long_array ((int64_t *) array, (int64_t *) v->data,
- v->len / 8);
- break;
-
- case GF_XATTROP_OR_ARRAY:
- __or_array ((int32_t *) array,
- (int32_t *) v->data,
- v->len / 4);
- break;
-
- case GF_XATTROP_AND_ARRAY:
- __and_array ((int32_t *) array,
- (int32_t *) v->data,
- v->len / 4);
- break;
-
- default:
- gf_log (this->name, GF_LOG_ERROR,
- "Unknown xattrop type (%d) on %s. Please send "
- "a bug report to gluster-devel@nongnu.org",
- optype, path);
- op_ret = -1;
- op_errno = EINVAL;
- goto unlock;
- }
-
- if (loc) {
- size = sys_lsetxattr (real_path, k, array,
- v->len, 0);
- } else {
- size = sys_fsetxattr (_fd, k, (char *)array,
- v->len, 0);
- }
- }
- unlock:
- UNLOCK (&inode->lock);
-
- if (op_ret == -1)
- goto out;
-
- op_errno = errno;
- if (size == -1) {
- if (loc)
- gf_log (this->name, GF_LOG_ERROR,
- "setxattr failed on %s while doing xattrop: "
- "key=%s (%s)", path,
- k, strerror (op_errno));
- else
- gf_log (this->name, GF_LOG_ERROR,
- "fsetxattr failed on fd=%d while doing xattrop: "
- "key=%s (%s)", _fd,
- k, strerror (op_errno));
-
- op_ret = -1;
- goto out;
- } else {
- size = dict_set_bin (xattr, k, array, v->len);
-
- if (size != 0) {
- if (loc)
- gf_log (this->name, GF_LOG_DEBUG,
- "dict_set_bin failed (path=%s): "
- "key=%s (%s)", path,
- k, strerror (-size));
- else
- gf_log (this->name, GF_LOG_DEBUG,
- "dict_set_bin failed (fd=%d): "
- "key=%s (%s)", _fd,
- k, strerror (-size));
-
- op_ret = -1;
- op_errno = EINVAL;
- goto out;
- }
- array = NULL;
- }
-
- array = NULL;
-
- out:
- return op_ret;
- }
- op_ret = dict_foreach (xattr, _handle_every_keyvalue_pair, NULL);
+ op_ret = dict_foreach (xattr, _posix_handle_xattr_keyvalue_pair,
+ &filler);
out:
- GF_FREE (array);
-
- GF_FREE (path);
STACK_UNWIND_STRICT (xattrop, frame, op_ret, op_errno, xattr, NULL);
return 0;
diff --git a/xlators/storage/posix/src/posix.h b/xlators/storage/posix/src/posix.h
index 45ee35963..4703a1fd4 100644
--- a/xlators/storage/posix/src/posix.h
+++ b/xlators/storage/posix/src/posix.h
@@ -127,6 +127,18 @@ struct posix_private {
#endif
};
+typedef struct {
+ xlator_t *this;
+ const char *real_path;
+ dict_t *xattr;
+ struct iatt *stbuf;
+ loc_t *loc;
+ inode_t *inode; /* for all do_xattrop() key handling */
+ int fd;
+ int flags;
+} posix_xattr_filler_t;
+
+
#define POSIX_BASE_PATH(this) (((struct posix_private *)this->private)->base_path)
#define POSIX_BASE_PATH_LEN(this) (((struct posix_private *)this->private)->base_path_length)