summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rwxr-xr-xtests/basic/geo-replication/marker-xattrs.t108
-rw-r--r--tests/volume.rc6
-rw-r--r--xlators/cluster/afr/src/afr-inode-read.c90
-rw-r--r--xlators/cluster/afr/src/afr.h2
-rw-r--r--xlators/cluster/dht/src/dht-common.c70
-rw-r--r--xlators/cluster/dht/src/dht-common.h3
-rw-r--r--xlators/cluster/ec/src/ec.c23
-rw-r--r--xlators/cluster/ec/src/ec.h2
-rw-r--r--xlators/cluster/stripe/src/stripe.c84
-rw-r--r--xlators/cluster/stripe/src/stripe.h2
-rw-r--r--xlators/lib/src/libxlator.c310
-rw-r--r--xlators/lib/src/libxlator.h14
12 files changed, 352 insertions, 362 deletions
diff --git a/tests/basic/geo-replication/marker-xattrs.t b/tests/basic/geo-replication/marker-xattrs.t
new file mode 100755
index 00000000000..a7dcb50aa78
--- /dev/null
+++ b/tests/basic/geo-replication/marker-xattrs.t
@@ -0,0 +1,108 @@
+#!/bin/bash
+
+. $(dirname $0)/../../include.rc
+. $(dirname $0)/../../volume.rc
+
+TEST glusterd
+TEST pidof glusterd
+
+## Start and create a replicated volume
+TEST $CLI volume create $V0 replica 2 $H0:$B0/${V0}-{0,1,2,3}
+
+TEST $CLI volume set $V0 indexing on
+
+TEST $CLI volume start $V0;
+
+## Mount native
+TEST glusterfs --volfile-server=$H0 --volfile-id=$V0 $M0
+
+## Mount client-pid=-1
+TEST glusterfs --volfile-server=$H0 --volfile-id=$V0 --client-pid=-1 $M1
+
+TEST touch $M0
+
+vol_uuid=$(get_volume_mark $M1)
+xtime=trusted.glusterfs.$vol_uuid.xtime
+
+TEST "getfattr -n $xtime $M1 | grep -q ${xtime}="
+
+TEST kill_brick $V0 $H0 $B0/${V0}-0
+
+TEST "getfattr -n $xtime $M1 | grep -q ${xtime}="
+
+EXPECT_WITHIN $UMOUNT_TIMEOUT "Y" force_umount $M0
+EXPECT_WITHIN $UMOUNT_TIMEOUT "Y" force_umount $M1
+
+TEST $CLI volume stop $V0;
+TEST $CLI volume delete $V0;
+
+cleanup
+TEST glusterd
+TEST pidof glusterd
+## Start and create a disperse volume
+TEST $CLI volume create $V0 disperse 3 redundancy 1 $H0:$B0/${V0}-{0,1,2}
+
+TEST $CLI volume set $V0 indexing on
+
+TEST $CLI volume start $V0;
+
+## Mount native
+TEST glusterfs --volfile-server=$H0 --volfile-id=$V0 $M0
+EXPECT_WITHIN $CHILD_UP_TIMEOUT "3" mount_get_option_value $M0 $V0-disperse-0 childs_up
+
+## Mount client-pid=-1
+TEST glusterfs --volfile-server=$H0 --volfile-id=$V0 --client-pid=-1 $M1
+EXPECT_WITHIN $CHILD_UP_TIMEOUT "3" mount_get_option_value $M1 $V0-disperse-0 childs_up
+
+TEST touch $M0
+
+vol_uuid=$(get_volume_mark $M1)
+xtime=trusted.glusterfs.$vol_uuid.xtime
+
+TEST "getfattr -n $xtime $M1 | grep -q ${xtime}="
+
+TEST kill_brick $V0 $H0 $B0/${V0}-0
+
+TEST "getfattr -n $xtime $M1 | grep -q ${xtime}="
+
+EXPECT_WITHIN $UMOUNT_TIMEOUT "Y" force_umount $M0
+EXPECT_WITHIN $UMOUNT_TIMEOUT "Y" force_umount $M1
+
+TEST $CLI volume stop $V0;
+TEST $CLI volume delete $V0;
+
+cleanup
+TEST glusterd
+TEST pidof glusterd
+## Start and create a stripe volume
+TEST $CLI volume create $V0 stripe 2 $H0:$B0/${V0}-{0,1}
+
+TEST $CLI volume set $V0 indexing on
+
+TEST $CLI volume start $V0;
+
+## Mount native
+TEST glusterfs --volfile-server=$H0 --volfile-id=$V0 $M0
+
+## Mount client-pid=-1
+TEST glusterfs --volfile-server=$H0 --volfile-id=$V0 --client-pid=-1 $M1
+
+TEST touch $M0
+
+vol_uuid=$(get_volume_mark $M1)
+xtime=trusted.glusterfs.$vol_uuid.xtime
+
+TEST "getfattr -n $xtime $M1 | grep -q ${xtime}="
+
+TEST kill_brick $V0 $H0 $B0/${V0}-0
+
+#Stripe doesn't tolerate ENOTCONN
+TEST ! "getfattr -n $xtime $M1 | grep -q ${xtime}="
+
+EXPECT_WITHIN $UMOUNT_TIMEOUT "Y" force_umount $M0
+EXPECT_WITHIN $UMOUNT_TIMEOUT "Y" force_umount $M1
+
+TEST $CLI volume stop $V0;
+TEST $CLI volume delete $V0;
+
+cleanup
diff --git a/tests/volume.rc b/tests/volume.rc
index 1276dccdbae..ac078e2bcce 100644
--- a/tests/volume.rc
+++ b/tests/volume.rc
@@ -469,5 +469,9 @@ function mount_get_option_value {
local subvol=$2
local key=$3
- grep "$3" $m/.meta/graphs/active/$subvol/private | awk '{print $3}'
+ grep -w "$3" $m/.meta/graphs/active/$subvol/private | awk '{print $3}'
+}
+
+function get_volume_mark {
+ getfattr -n trusted.glusterfs.volume-mark -ehex $1 | sed -n 's/^trusted.glusterfs.volume-mark=0x//p' | cut -b5-36 | sed 's/\([a-f0-9]\{8\}\)\([a-f0-9]\{4\}\)\([a-f0-9]\{4\}\)\([a-f0-9]\{4\}\)/\1-\2-\3-\4-/'
}
diff --git a/xlators/cluster/afr/src/afr-inode-read.c b/xlators/cluster/afr/src/afr-inode-read.c
index 77acf0b25b9..afa40fbad2a 100644
--- a/xlators/cluster/afr/src/afr-inode-read.c
+++ b/xlators/cluster/afr/src/afr-inode-read.c
@@ -1408,6 +1408,23 @@ afr_getxattr_all_subvols (xlator_t *this, call_frame_t *frame,
return;
}
+int
+afr_marker_populate_args (call_frame_t *frame, int type, int *gauge,
+ xlator_t **subvols)
+{
+ xlator_t *this = frame->this;
+ afr_private_t *priv = this->private;
+
+ memcpy (subvols, priv->children, sizeof (*subvols) * priv->child_count);
+
+ if (type == MARKER_XTIME_TYPE) {
+ /*Don't error out on ENOENT/ENOTCONN */
+ gauge[MCNT_NOTFOUND] = 0;
+ gauge[MCNT_ENOTCONN] = 0;
+ }
+ return priv->child_count;
+}
+
int32_t
afr_getxattr (call_frame_t *frame, xlator_t *this,
loc_t *loc, const char *name, dict_t *xdata)
@@ -1415,13 +1432,10 @@ afr_getxattr (call_frame_t *frame, xlator_t *this,
afr_private_t *priv = NULL;
xlator_t **children = NULL;
afr_local_t *local = NULL;
- xlator_list_t *trav = NULL;
- xlator_t **sub_volumes = NULL;
int i = 0;
int32_t op_errno = 0;
int ret = -1;
fop_getxattr_cbk_t cbk = NULL;
- int afr_xtime_gauge[MCNT_MAX] = {0,};
local = AFR_FRAME_INIT (frame, op_errno);
@@ -1457,35 +1471,11 @@ afr_getxattr (call_frame_t *frame, xlator_t *this,
op_errno = ENODATA;
goto out;
}
- if ((strcmp (GF_XATTR_MARKER_KEY, name) == 0)
- && (GF_CLIENT_PID_GSYNCD == frame->root->pid)) {
-
- local->marker.call_count = priv->child_count;
-
- sub_volumes = alloca ( priv->child_count * sizeof (xlator_t *));
- for (i = 0, trav = this->children; trav ;
- trav = trav->next, i++) {
-
- *(sub_volumes + i) = trav->xlator;
- }
-
- if (cluster_getmarkerattr (frame, this, loc, name,
- local, afr_getxattr_unwind,
- sub_volumes,
- priv->child_count,
- MARKER_UUID_TYPE,
- marker_uuid_default_gauge,
- priv->vol_uuid)) {
-
- gf_log (this->name, GF_LOG_INFO,
- "%s: failed to get marker attr (%s)",
- loc->path, name);
- op_errno = EINVAL;
- goto out;
- }
+ if (cluster_handle_marker_getxattr (frame, loc, name, priv->vol_uuid,
+ afr_getxattr_unwind,
+ afr_marker_populate_args) == 0)
return 0;
- }
if (!strcmp (name, GF_AFR_HEAL_INFO)) {
afr_get_heal_info (frame, this, loc, xdata);
@@ -1519,46 +1509,6 @@ afr_getxattr (call_frame_t *frame, xlator_t *this,
return 0;
}
- if (*priv->vol_uuid) {
- if ((match_uuid_local (name, priv->vol_uuid) == 0)
- && (GF_CLIENT_PID_GSYNCD == frame->root->pid)) {
- local->marker.call_count = priv->child_count;
-
- sub_volumes = alloca ( priv->child_count
- * sizeof (xlator_t *));
- for (i = 0, trav = this->children; trav ;
- trav = trav->next, i++) {
-
- *(sub_volumes + i) = trav->xlator;
-
- }
-
- /* don't err out on getting ENOTCONN (brick down)
- * from a subset of the bricks
- */
- memcpy (afr_xtime_gauge, marker_xtime_default_gauge,
- sizeof (afr_xtime_gauge));
- afr_xtime_gauge[MCNT_NOTFOUND] = 0;
- afr_xtime_gauge[MCNT_ENOTCONN] = 0;
- if (cluster_getmarkerattr (frame, this, loc,
- name, local,
- afr_getxattr_unwind,
- sub_volumes,
- priv->child_count,
- MARKER_XTIME_TYPE,
- afr_xtime_gauge,
- priv->vol_uuid)) {
- gf_log (this->name, GF_LOG_INFO,
- "%s: failed to get marker attr (%s)",
- loc->path, name);
- op_errno = EINVAL;
- goto out;
- }
-
- return 0;
- }
- }
-
no_name:
afr_read_txn (frame, this, local->loc.inode, afr_getxattr_wind,
diff --git a/xlators/cluster/afr/src/afr.h b/xlators/cluster/afr/src/afr.h
index 0885b582d77..de000e765ea 100644
--- a/xlators/cluster/afr/src/afr.h
+++ b/xlators/cluster/afr/src/afr.h
@@ -720,8 +720,6 @@ typedef struct _afr_local {
syncbarrier_t barrier;
- struct marker_str marker;
-
/* extra data for fops */
dict_t *xdata_req;
dict_t *xdata_rsp;
diff --git a/xlators/cluster/dht/src/dht-common.c b/xlators/cluster/dht/src/dht-common.c
index 3a196e07be9..b7df1f4da4b 100644
--- a/xlators/cluster/dht/src/dht-common.c
+++ b/xlators/cluster/dht/src/dht-common.c
@@ -2791,6 +2791,22 @@ dht_getxattr_get_real_filename (call_frame_t *frame, xlator_t *this,
return 0;
}
+int
+dht_marker_populate_args (call_frame_t *frame, int type, int *gauge,
+ xlator_t **subvols)
+{
+ dht_local_t *local = NULL;
+ int i = 0;
+ dht_layout_t *layout = NULL;
+
+ local = frame->local;
+ layout = local->layout;
+
+ for (i = 0; i < layout->cnt; i++)
+ subvols[i] = layout->list[i].xlator;
+
+ return layout->cnt;
+}
int
dht_getxattr (call_frame_t *frame, xlator_t *this,
@@ -2804,7 +2820,6 @@ dht_getxattr (call_frame_t *frame, xlator_t *this,
dht_conf_t *conf = NULL;
dht_local_t *local = NULL;
dht_layout_t *layout = NULL;
- xlator_t **sub_volumes = NULL;
int op_errno = -1;
int i = 0;
int cnt = 0;
@@ -2918,30 +2933,6 @@ dht_getxattr (call_frame_t *frame, xlator_t *this,
return 0;
}
- if (key && (!strcmp (GF_XATTR_MARKER_KEY, key))
- && (GF_CLIENT_PID_GSYNCD == frame->root->pid)) {
- if (DHT_IS_DIR(layout)) {
- cnt = layout->cnt;
- } else {
- cnt = 1;
- }
-
- sub_volumes = alloca ( cnt * sizeof (xlator_t *));
- for (i = 0; i < cnt; i++)
- *(sub_volumes + i) = layout->list[i].xlator;
-
- if (cluster_getmarkerattr (frame, this, loc, key,
- local, dht_getxattr_unwind,
- sub_volumes, cnt,
- MARKER_UUID_TYPE, marker_uuid_default_gauge,
- conf->vol_uuid)) {
- op_errno = EINVAL;
- goto err;
- }
-
- return 0;
- }
-
if (key && (!strcmp (GF_XATTR_QUOTA_LIMIT_LIST, key) ||
!strcmp (GF_XATTR_QUOTA_LIMIT_LIST_OBJECT, key))) {
/* quota hardlimit and aggregated size of a directory is stored
@@ -2955,31 +2946,10 @@ dht_getxattr (call_frame_t *frame, xlator_t *this,
return 0;
}
- if (key && *conf->vol_uuid) {
- if ((match_uuid_local (key, conf->vol_uuid) == 0) &&
- (GF_CLIENT_PID_GSYNCD == frame->root->pid)) {
- if (DHT_IS_DIR(layout)) {
- cnt = layout->cnt;
- } else {
- cnt = 1;
- }
- sub_volumes = alloca ( cnt * sizeof (xlator_t *));
- for (i = 0; i < cnt; i++)
- sub_volumes[i] = layout->list[i].xlator;
-
- if (cluster_getmarkerattr (frame, this, loc, key,
- local, dht_getxattr_unwind,
- sub_volumes, cnt,
- MARKER_XTIME_TYPE,
- marker_xtime_default_gauge,
- conf->vol_uuid)) {
- op_errno = EINVAL;
- goto err;
- }
-
- return 0;
- }
- }
+ if (cluster_handle_marker_getxattr (frame, loc, key, conf->vol_uuid,
+ dht_getxattr_unwind,
+ dht_marker_populate_args) == 0)
+ return 0;
if (DHT_IS_DIR(layout)) {
cnt = local->call_cnt = layout->cnt;
diff --git a/xlators/cluster/dht/src/dht-common.h b/xlators/cluster/dht/src/dht-common.h
index 9145f336d7c..9d505c1e601 100644
--- a/xlators/cluster/dht/src/dht-common.h
+++ b/xlators/cluster/dht/src/dht-common.h
@@ -216,9 +216,6 @@ struct dht_local {
/* gfid related */
uuid_t gfid;
- /*Marker Related*/
- struct marker_str marker;
-
/* flag used to make sure we need to return estale in
{lookup,revalidate}_cbk */
char return_estale;
diff --git a/xlators/cluster/ec/src/ec.c b/xlators/cluster/ec/src/ec.c
index 9fecde4c495..9b8251a5403 100644
--- a/xlators/cluster/ec/src/ec.c
+++ b/xlators/cluster/ec/src/ec.c
@@ -576,16 +576,39 @@ int32_t ec_gf_fsyncdir(call_frame_t * frame, xlator_t * this, fd_t * fd,
return 0;
}
+int
+ec_marker_populate_args (call_frame_t *frame, int type, int *gauge,
+ xlator_t **subvols)
+{
+ xlator_t *this = frame->this;
+ ec_t *ec = this->private;
+
+ memcpy (subvols, ec->xl_list, sizeof (*subvols) * ec->nodes);
+
+ if (type == MARKER_XTIME_TYPE) {
+ /*Don't error out on ENOENT/ENOTCONN */
+ gauge[MCNT_NOTFOUND] = 0;
+ gauge[MCNT_ENOTCONN] = 0;
+ }
+
+ return ec->nodes;
+}
+
int32_t
ec_gf_getxattr (call_frame_t *frame, xlator_t *this, loc_t *loc,
const char *name, dict_t *xdata)
{
int error = 0;
+ ec_t *ec = this->private;
if (name && strcmp (name, EC_XATTR_HEAL) != 0) {
EC_INTERNAL_XATTR_OR_GOTO(name, NULL, error, out);
}
+ if (cluster_handle_marker_getxattr (frame, loc, name, ec->vol_uuid,
+ NULL, ec_marker_populate_args) == 0)
+ return 0;
+
ec_getxattr (frame, this, -1, EC_MINIMUM_MIN, default_getxattr_cbk,
NULL, loc, name, xdata);
diff --git a/xlators/cluster/ec/src/ec.h b/xlators/cluster/ec/src/ec.h
index 1c740187757..d565bf8fcb4 100644
--- a/xlators/cluster/ec/src/ec.h
+++ b/xlators/cluster/ec/src/ec.h
@@ -14,6 +14,7 @@
#include "xlator.h"
#include "timer.h"
#include "ec-heald.h"
+#include "libxlator.h"
#define EC_XATTR_PREFIX "trusted.ec."
#define EC_XATTR_CONFIG EC_XATTR_PREFIX"config"
@@ -45,5 +46,6 @@ struct _ec
struct mem_pool * cbk_pool;
struct mem_pool * lock_pool;
ec_self_heald_t shd;
+ char vol_uuid[UUID_SIZE + 1];
};
#endif /* __EC_H__ */
diff --git a/xlators/cluster/stripe/src/stripe.c b/xlators/cluster/stripe/src/stripe.c
index 7af9442a7ff..8896d7a2ad2 100644
--- a/xlators/cluster/stripe/src/stripe.c
+++ b/xlators/cluster/stripe/src/stripe.c
@@ -5454,6 +5454,25 @@ stripe_vgetxattr_cbk (call_frame_t *frame, void *cookie,
return ret;
}
+int
+stripe_marker_populate_args (call_frame_t *frame, int type, int *gauge,
+ xlator_t **subvols)
+{
+ xlator_t *this = frame->this;
+ stripe_private_t *priv = this->private;
+ stripe_local_t *local = frame->local;
+ int count = 0;
+
+ count = priv->child_count;
+ if (MARKER_XTIME_TYPE == type) {
+ if (!IA_FILE_OR_DIR (local->loc.inode->ia_type))
+ count = 1;
+ }
+ memcpy (subvols, priv->xl_array, sizeof (*subvols) * count);
+
+ return count;
+}
+
int32_t
stripe_getxattr (call_frame_t *frame, xlator_t *this,
loc_t *loc, const char *name, dict_t *xdata)
@@ -5463,7 +5482,6 @@ stripe_getxattr (call_frame_t *frame, xlator_t *this,
stripe_private_t *priv = NULL;
int32_t op_errno = EINVAL;
int i = 0;
- xlator_t **sub_volumes;
int ret = 0;
VALIDATE_OR_GOTO (frame, err);
@@ -5486,31 +5504,6 @@ stripe_getxattr (call_frame_t *frame, xlator_t *this,
loc_copy (&local->loc, loc);
- if (name && (strcmp (GF_XATTR_MARKER_KEY, name) == 0)
- && (GF_CLIENT_PID_GSYNCD == frame->root->pid)) {
- local->marker.call_count = priv->child_count;
-
- sub_volumes = alloca ( priv->child_count *
- sizeof (xlator_t *));
- for (i = 0, trav = this->children; trav ;
- trav = trav->next, i++) {
-
- *(sub_volumes + i) = trav->xlator;
-
- }
-
- if (cluster_getmarkerattr (frame, this, loc, name,
- local, stripe_getxattr_unwind,
- sub_volumes, priv->child_count,
- MARKER_UUID_TYPE, marker_uuid_default_gauge,
- priv->vol_uuid)) {
- op_errno = EINVAL;
- goto err;
- }
-
- return 0;
- }
-
if (name && strncmp (name, GF_XATTR_QUOTA_SIZE_KEY,
strlen (GF_XATTR_QUOTA_SIZE_KEY)) == 0) {
local->wind_count = priv->child_count;
@@ -5555,41 +5548,10 @@ stripe_getxattr (call_frame_t *frame, xlator_t *this,
return 0;
}
- if (name &&(*priv->vol_uuid)) {
- if ((match_uuid_local (name, priv->vol_uuid) == 0)
- && (GF_CLIENT_PID_GSYNCD == frame->root->pid)) {
-
- if (!IA_FILE_OR_DIR (loc->inode->ia_type))
- local->marker.call_count = 1;
- else
- local->marker.call_count = priv->child_count;
-
- sub_volumes = alloca (local->marker.call_count *
- sizeof (xlator_t *));
-
- for (i = 0, trav = this->children;
- i < local->marker.call_count;
- i++, trav = trav->next) {
- *(sub_volumes + i) = trav->xlator;
-
- }
-
- if (cluster_getmarkerattr (frame, this, loc, name,
- local,
- stripe_getxattr_unwind,
- sub_volumes,
- local->marker.call_count,
- MARKER_XTIME_TYPE,
- marker_xtime_default_gauge,
- priv->vol_uuid)) {
- op_errno = EINVAL;
- goto err;
- }
-
- return 0;
- }
- }
-
+ if (cluster_handle_marker_getxattr (frame, loc, name, priv->vol_uuid,
+ stripe_getxattr_unwind,
+ stripe_marker_populate_args) == 0)
+ return 0;
STACK_WIND (frame, stripe_internal_getxattr_cbk, FIRST_CHILD(this),
FIRST_CHILD(this)->fops->getxattr, loc, name, xdata);
diff --git a/xlators/cluster/stripe/src/stripe.h b/xlators/cluster/stripe/src/stripe.h
index 5673d18f390..150d9e49f93 100644
--- a/xlators/cluster/stripe/src/stripe.h
+++ b/xlators/cluster/stripe/src/stripe.h
@@ -190,8 +190,6 @@ struct stripe_local {
int32_t nallocs;
char xsel[256];
- struct marker_str marker;
-
/* General usage */
off_t offset;
off_t stripe_size;
diff --git a/xlators/lib/src/libxlator.c b/xlators/lib/src/libxlator.c
index 0b5036c8ba8..30436131b6b 100644
--- a/xlators/lib/src/libxlator.c
+++ b/xlators/lib/src/libxlator.c
@@ -61,6 +61,9 @@ get_hosttime (uint32_t *oldtimbuf, uint32_t *newtimebuf)
int
match_uuid_local (const char *name, char *uuid)
{
+ if (!uuid || !*uuid)
+ return -1;
+
name = strtail ((char *)name, MARKER_XATTR_PREFIX);
if (!name || name++[0] != '.')
return -1;
@@ -132,6 +135,57 @@ evaluate_marker_results (int *gauge, int *count)
return op_errno;
}
+static void
+cluster_marker_unwind (call_frame_t *frame, char *key, void *value, size_t size,
+ dict_t *dict)
+{
+ xl_marker_local_t *local = frame->local;
+ int ret = 0;
+ int32_t op_ret = 0;
+ int32_t op_errno = 0;
+ gf_boolean_t unref = _gf_false;
+
+ frame->local = local->xl_local;
+
+ if (local->count[MCNT_FOUND]) {
+ if (!dict) {
+ dict = dict_new();
+ if (dict) {
+ unref = _gf_true;
+ } else {
+ op_ret = -1;
+ op_errno = ENOMEM;
+ goto out;
+ }
+ }
+
+ ret = dict_set_static_bin (dict, key, value, size);
+ if (ret) {
+ op_ret = -1;
+ op_errno = ENOMEM;
+ goto out;
+ }
+ }
+
+ op_errno = evaluate_marker_results (local->gauge, local->count);
+ if (op_errno)
+ op_ret = -1;
+
+out:
+ if (local->xl_specf_unwind) {
+ local->xl_specf_unwind (frame, op_ret,
+ op_errno, dict, NULL);
+ } else {
+ STACK_UNWIND_STRICT (getxattr, frame, op_ret, op_errno,
+ dict, NULL);
+ }
+
+ GF_FREE (local);
+ if (unref)
+ dict_unref (dict);
+
+}
+
/* Aggregate all the <volid>.xtime attrs of the cluster and send the max*/
int32_t
cluster_markerxtime_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
@@ -140,26 +194,12 @@ cluster_markerxtime_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
{
int32_t callcnt = 0;
- int ret = -1;
uint32_t *net_timebuf = NULL;
uint32_t host_timebuf[2] = {0,};
char marker_xattr[128] = {0};
xl_marker_local_t *local = NULL;
- char need_unwind = 0;
- gf_boolean_t unref = _gf_false;
-
- if (!this || !frame || !frame->local || !cookie) {
- gf_log ("", GF_LOG_DEBUG, "possible NULL deref");
- need_unwind = 1;
- goto out;
- }
local = frame->local;
- if (!local || !local->vol_uuid) {
- gf_log (this->name, GF_LOG_DEBUG, "possible NULL deref");
- need_unwind = 1;
- goto out;
- }
snprintf (marker_xattr, sizeof (marker_xattr), "%s.%s.%s",
MARKER_XATTR_PREFIX, local->vol_uuid, XTIME);
@@ -199,50 +239,9 @@ cluster_markerxtime_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
unlock:
UNLOCK (&frame->lock);
- if (!callcnt) {
- op_ret = 0;
- op_errno = 0;
- need_unwind = 1;
-
- if (local->count[MCNT_FOUND]) {
- if (!dict) {
- dict = dict_new();
- if (dict) {
- unref = _gf_true;
- } else {
- op_ret = -1;
- op_errno = ENOMEM;
- goto out;
- }
- }
-
- ret = dict_set_static_bin (dict, marker_xattr,
- (void *)local->net_timebuf, 8);
- if (ret) {
- op_ret = -1;
- op_errno = ENOMEM;
- goto out;
- }
- }
-
- op_errno = evaluate_marker_results (local->gauge, local->count);
- if (op_errno)
- op_ret = -1;
- }
-
-out:
- if (need_unwind && local && local->xl_specf_unwind) {
- frame->local = local->xl_local;
- local->xl_specf_unwind (frame, op_ret,
- op_errno, dict, xdata);
- GF_FREE (local);
- } else if (need_unwind) {
- STACK_UNWIND_STRICT (getxattr, frame, op_ret, op_errno,
- dict, xdata);
- }
-
- if (unref)
- dict_unref (dict);
+ if (callcnt == 0)
+ cluster_marker_unwind (frame, marker_xattr, local->net_timebuf,
+ 8, dict);
return 0;
@@ -256,23 +255,10 @@ cluster_markeruuid_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
struct volume_mark *volmark = NULL;
xl_marker_local_t *local = NULL;
int32_t ret = -1;
- char need_unwind = 0;
char *vol_uuid = NULL;
- if (!this || !frame || !cookie) {
- gf_log ("", GF_LOG_DEBUG, "possible NULL deref");
- need_unwind = 1;
- goto out;
- }
-
local = frame->local;
- if (!local) {
- gf_log (this->name, GF_LOG_DEBUG, "possible NULL deref");
- need_unwind = 1;
- goto out;
- }
-
LOCK (&frame->lock);
{
callcnt = --local->call_count;
@@ -296,9 +282,9 @@ cluster_markeruuid_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
goto unlock;
}
- if (local->retval)
+ if (local->retval) {
goto unlock;
- else if (volmark->retval) {
+ } else if (volmark->retval) {
GF_FREE (local->volmark);
local->volmark =
memdup (volmark, sizeof (*volmark));
@@ -323,103 +309,14 @@ cluster_markeruuid_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
unlock:
UNLOCK (&frame->lock);
- if (!callcnt) {
- op_ret = 0;
- op_errno = 0;
- need_unwind = 1;
+ if (callcnt == 0)
+ cluster_marker_unwind (frame, GF_XATTR_MARKER_KEY,
+ local->volmark, sizeof (*local->volmark),
+ dict);
- if (local->count[MCNT_FOUND]) {
- if (!dict)
- dict = dict_new();
-
- if (dict_set_bin (dict, GF_XATTR_MARKER_KEY,
- local->volmark,
- sizeof (struct volume_mark))) {
- op_ret = -1;
- op_errno = ENOMEM;
- }
- }
- op_errno = evaluate_marker_results (local->gauge, local->count);
- if (op_errno)
- op_ret = -1;
- }
-
- out:
- if (need_unwind && local && local->xl_specf_unwind) {
- frame->local = local->xl_local;
- local->xl_specf_unwind (frame, op_ret,
- op_errno, dict, xdata);
- GF_FREE (local);
- return 0;
- } else if (need_unwind){
- STACK_UNWIND_STRICT (getxattr, frame, op_ret, op_errno,
- dict, xdata);
- }
return 0;
}
-
-int32_t
-cluster_getmarkerattr (call_frame_t *frame,xlator_t *this, loc_t *loc,
- const char *name, void *xl_local,
- xlator_specf_unwind_t xl_specf_getxattr_unwind,
- xlator_t **sub_volumes, int count, int type,
- int *gauge, char *vol_uuid)
-{
- int i = 0;
- xl_marker_local_t *local = NULL;
-
- VALIDATE_OR_GOTO (frame, err);
- VALIDATE_OR_GOTO (this, err);
- VALIDATE_OR_GOTO (loc, err);
- VALIDATE_OR_GOTO (loc->path, err);
- VALIDATE_OR_GOTO (loc->inode, err);
- VALIDATE_OR_GOTO (name, err);
- VALIDATE_OR_GOTO (xl_specf_getxattr_unwind, err);
-
- local = GF_CALLOC (sizeof (struct marker_str), 1,
- gf_common_mt_libxl_marker_local);
-
- if (!local)
- goto err;
-
- local->xl_local = xl_local;
- local->call_count = count;
- local->xl_specf_unwind = xl_specf_getxattr_unwind;
- local->vol_uuid = vol_uuid;
- memcpy (local->gauge, gauge, sizeof (local->gauge));
-
- frame->local = local;
-
- for (i=0; i < count; i++) {
- if (MARKER_UUID_TYPE == type)
- STACK_WIND (frame, cluster_markeruuid_cbk,
- *(sub_volumes + i),
- (*(sub_volumes + i))->fops->getxattr,
- loc, name, NULL);
- else if (MARKER_XTIME_TYPE == type)
- STACK_WIND (frame, cluster_markerxtime_cbk,
- *(sub_volumes + i),
- (*(sub_volumes + i))->fops->getxattr,
- loc, name, NULL);
- else {
- gf_log (this->name, GF_LOG_WARNING,
- "Unrecognized type (%d) of marker attr "
- "received", type);
- STACK_WIND (frame, default_getxattr_cbk,
- *(sub_volumes + i),
- (*(sub_volumes + i))->fops->getxattr,
- loc, name, NULL);
- break;
- }
- }
-
- return 0;
-err:
- return -1;
-
-}
-
int
gf_get_min_stime (xlator_t *this, dict_t *dst, char *key, data_t *value)
{
@@ -529,3 +426,84 @@ error:
return ret;
}
+
+static int
+_get_children_count (xlator_t *xl)
+{
+ int i = 0;
+ xlator_list_t *trav = NULL;
+ for (i = 0, trav = xl->children; trav ; trav = trav->next, i++) {
+ /*'i' will have the value */
+ }
+
+ return i;
+}
+
+int
+cluster_handle_marker_getxattr (call_frame_t *frame, loc_t *loc,
+ const char *name, char *vol_uuid,
+ xlator_specf_unwind_t unwind,
+ int (*populate_args) (call_frame_t *frame,
+ int type, int *gauge,
+ xlator_t **subvols))
+{
+ xlator_t *this = frame->this;
+ xlator_t **subvols = NULL;
+ int num_subvols = 0;
+ int type = 0;
+ int i = 0;
+ int gauge[MCNT_MAX] = {0};
+ xl_marker_local_t *local = NULL;
+
+ if (GF_CLIENT_PID_GSYNCD != frame->root->pid)
+ return -EINVAL;
+
+ if (strcmp (GF_XATTR_MARKER_KEY, name) == 0) {
+ type = MARKER_UUID_TYPE;
+ memcpy (gauge, marker_uuid_default_gauge, sizeof (gauge));
+ } else if (match_uuid_local (name, vol_uuid) == 0) {
+ type = MARKER_XTIME_TYPE;
+ memcpy (gauge, marker_xtime_default_gauge, sizeof (gauge));
+ } else {
+ return -EINVAL;
+ }
+
+ num_subvols = _get_children_count (this);
+ subvols = alloca (num_subvols * sizeof (*subvols));
+ num_subvols = populate_args (frame, type, gauge, subvols);
+
+ local = GF_CALLOC (sizeof (struct marker_str), 1,
+ gf_common_mt_libxl_marker_local);
+
+ if (!local)
+ goto fail;
+
+ local->xl_local = frame->local;
+ local->call_count = num_subvols;
+ local->xl_specf_unwind = unwind;
+ local->vol_uuid = vol_uuid;
+ memcpy (local->gauge, gauge, sizeof (local->gauge));
+
+ frame->local = local;
+
+ for (i = 0; i < num_subvols; i++) {
+ if (MARKER_UUID_TYPE == type)
+ STACK_WIND (frame, cluster_markeruuid_cbk,
+ subvols[i],
+ subvols[i]->fops->getxattr,
+ loc, name, NULL);
+ else if (MARKER_XTIME_TYPE == type)
+ STACK_WIND (frame, cluster_markerxtime_cbk,
+ subvols[i],
+ subvols[i]->fops->getxattr,
+ loc, name, NULL);
+ }
+
+ return 0;
+fail:
+ if (unwind)
+ unwind (frame, -1, ENOMEM, NULL, NULL);
+ else
+ default_getxattr_failure_cbk (frame, ENOMEM);
+ return 0;
+}
diff --git a/xlators/lib/src/libxlator.h b/xlators/lib/src/libxlator.h
index 404124ca7d3..20d5a32f248 100644
--- a/xlators/lib/src/libxlator.h
+++ b/xlators/lib/src/libxlator.h
@@ -139,13 +139,13 @@ int32_t
cluster_markeruuid_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
int op_ret, int op_errno, dict_t *dict, dict_t *xdata);
-int32_t
-cluster_getmarkerattr (call_frame_t *frame,xlator_t *this, loc_t *loc,
- const char *name, void *xl_local,
- xlator_specf_unwind_t xl_specf_getxattr_unwind,
- xlator_t **sub_volumes, int count, int type,
- int *gauge, char *vol_uuid);
-
+int
+cluster_handle_marker_getxattr (call_frame_t *frame, loc_t *loc,
+ const char *name, char *vol_uuid,
+ xlator_specf_unwind_t unwind,
+ int (*populate_args) (call_frame_t *frame,
+ int type, int *gauge,
+ xlator_t **subvols));
int
match_uuid_local (const char *name, char *uuid);