summaryrefslogtreecommitdiffstats
path: root/xlators
diff options
context:
space:
mode:
authorvmallika <vmallika@redhat.com>2015-04-15 17:35:07 +0530
committerVijay Bellur <vbellur@redhat.com>2015-05-04 03:46:08 -0700
commit821b1fdc893c0dd603d4c43a0b31f1ea495a46c9 (patch)
treea8593c6bc0b1ecbd58350b071b7ae4b5658ea57d /xlators
parent40df2ed4d098d4cd2c6abbed23e497ac3e2e5804 (diff)
quota: support for inode quota in quota.conf
Currently when quota limit is set, corresponding gfid is set in quota.conf. This patch supports storing inode-quota limits in quota.conf and also stores additional byte for each gfid to differentiate between usage quota limit and inode quota limit. Change-Id: I444d7399407594edd280e640681679a784d4c46a BUG: 1202244 Signed-off-by: vmallika <vmallika@redhat.com> Signed-off-by: Sachin Pandit <spandit@redhat.com> Reviewed-on: http://review.gluster.org/10069 Tested-by: NetBSD Build System Tested-by: Gluster Build System <jenkins@build.gluster.com> Reviewed-by: Vijay Bellur <vbellur@redhat.com>
Diffstat (limited to 'xlators')
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-quota.c167
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-utils.c118
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-utils.h6
3 files changed, 180 insertions, 111 deletions
diff --git a/xlators/mgmt/glusterd/src/glusterd-quota.c b/xlators/mgmt/glusterd/src/glusterd-quota.c
index 97fa4380656..9f2aa8ec9de 100644
--- a/xlators/mgmt/glusterd/src/glusterd-quota.c
+++ b/xlators/mgmt/glusterd/src/glusterd-quota.c
@@ -578,28 +578,33 @@ glusterd_update_quota_conf_version (glusterd_volinfo_t *volinfo)
* and continue the search.
*/
static gf_boolean_t
-glusterd_find_gfid_match (uuid_t gfid, unsigned char *buf, size_t bytes_read,
- int opcode, size_t *write_byte_count)
+glusterd_find_gfid_match (uuid_t gfid, char gfid_type, unsigned char *buf,
+ size_t bytes_read, int opcode,
+ size_t *write_byte_count)
{
int gfid_index = 0;
int shift_count = 0;
unsigned char tmp_buf[17] = {0,};
+ char type = 0;
while (gfid_index != bytes_read) {
memcpy ((void *)tmp_buf, (void *)&buf[gfid_index], 16);
- if (!gf_uuid_compare (gfid, tmp_buf)) {
- if (opcode == GF_QUOTA_OPTION_TYPE_REMOVE) {
- shift_count = bytes_read - (gfid_index + 16);
+ type = buf[gfid_index + 16];
+
+ if (!gf_uuid_compare (gfid, tmp_buf) && type == gfid_type) {
+ if (opcode == GF_QUOTA_OPTION_TYPE_REMOVE ||
+ opcode == GF_QUOTA_OPTION_TYPE_REMOVE_OBJECTS) {
+ shift_count = bytes_read - (gfid_index + 17);
memmove ((void *)&buf[gfid_index],
- (void *)&buf[gfid_index+16],
+ (void *)&buf[gfid_index + 17],
shift_count);
- *write_byte_count = bytes_read - 16;
+ *write_byte_count = bytes_read - 17;
} else {
*write_byte_count = bytes_read;
}
return _gf_true;
} else {
- gfid_index+=16;
+ gfid_index += 17;
}
}
if (gfid_index == bytes_read)
@@ -647,15 +652,91 @@ out:
}
int
+glusterd_store_quota_conf_upgrade (glusterd_volinfo_t *volinfo)
+{
+ int ret = -1;
+ int fd = -1;
+ int conf_fd = -1;
+ unsigned char gfid[17] = {0,};
+ xlator_t *this = NULL;
+ char type = 0;
+
+ this = THIS;
+ GF_ASSERT (this);
+
+ fd = gf_store_mkstemp (volinfo->quota_conf_shandle);
+ if (fd < 0) {
+ ret = -1;
+ goto out;
+ }
+
+ conf_fd = open (volinfo->quota_conf_shandle->path, O_RDONLY);
+ if (conf_fd == -1) {
+ ret = -1;
+ goto out;
+ }
+
+ ret = quota_conf_skip_header (conf_fd);
+ if (ret)
+ goto out;
+
+ ret = quota_conf_write_header (fd);
+ if (ret)
+ goto out;
+
+ while (1) {
+ ret = quota_conf_read_gfid (conf_fd, gfid, &type, 1.1);
+ if (ret == 0)
+ break;
+ else if (ret < 0)
+ goto out;
+
+ ret = quota_conf_write_gfid (fd, gfid,
+ GF_QUOTA_CONF_TYPE_USAGE);
+ if (ret < 0)
+ goto out;
+ }
+
+out:
+ if (conf_fd != -1)
+ close (conf_fd);
+
+ if (ret && (fd > 0)) {
+ gf_store_unlink_tmppath (volinfo->quota_conf_shandle);
+ } else if (!ret) {
+ ret = gf_store_rename_tmppath (volinfo->quota_conf_shandle);
+ if (ret) {
+ gf_log (this->name, GF_LOG_ERROR, "Failed to rename "
+ "quota conf file");
+ return ret;
+ }
+
+ ret = glusterd_compute_cksum (volinfo, _gf_true);
+ if (ret) {
+ gf_log (this->name, GF_LOG_ERROR, "Failed to "
+ "compute cksum for quota conf file");
+ return ret;
+ }
+
+ ret = glusterd_store_save_quota_version_and_cksum (volinfo);
+ if (ret)
+ gf_log (this->name, GF_LOG_ERROR, "Failed to "
+ "store quota version and cksum");
+ }
+
+ return ret;
+}
+
+int
glusterd_store_quota_config (glusterd_volinfo_t *volinfo, char *path,
char *gfid_str, int opcode, char **op_errstr)
{
int ret = -1;
int fd = -1;
int conf_fd = -1;
- size_t entry_sz = 131072;
+ size_t entry_sz = 139264;
ssize_t bytes_read = 0;
- size_t bytes_to_write = 0;
+ size_t bytes_to_write = 0;
unsigned char buf[131072] = {0,};
uuid_t gfid = {0,};
xlator_t *this = NULL;
@@ -664,6 +745,8 @@ glusterd_store_quota_config (glusterd_volinfo_t *volinfo, char *path,
gf_boolean_t is_file_empty = _gf_false;
gf_boolean_t is_first_read = _gf_true;
glusterd_conf_t *conf = NULL;
+ float version = 0.0f;
+ char type = 0;
this = THIS;
GF_ASSERT (this);
@@ -672,30 +755,43 @@ glusterd_store_quota_config (glusterd_volinfo_t *volinfo, char *path,
glusterd_store_create_quota_conf_sh_on_absence (volinfo);
- fd = gf_store_mkstemp (volinfo->quota_conf_shandle);
- if (fd < 0) {
- ret = -1;
- goto out;
- }
-
conf_fd = open (volinfo->quota_conf_shandle->path, O_RDONLY);
if (conf_fd == -1) {
ret = -1;
goto out;
}
- ret = glusterd_store_quota_conf_skip_header (this, conf_fd);
- if (ret) {
+ ret = quota_conf_read_version (conf_fd, &version);
+ if (ret)
goto out;
+
+ if (version < 1.2f) {
+ close (conf_fd);
+ ret = glusterd_store_quota_conf_upgrade(volinfo);
+ if (ret)
+ goto out;
+
+ conf_fd = open (volinfo->quota_conf_shandle->path, O_RDONLY);
+ if (conf_fd == -1) {
+ ret = -1;
+ goto out;
+ }
+
+ ret = quota_conf_skip_header (conf_fd);
+ if (ret)
+ goto out;
}
- ret = glusterd_store_quota_conf_stamp_header (this, fd);
- if (ret) {
- gf_log (this->name, GF_LOG_ERROR, "Failed to add header to tmp "
- "file.");
+ fd = gf_store_mkstemp (volinfo->quota_conf_shandle);
+ if (fd < 0) {
+ ret = -1;
goto out;
}
+ ret = quota_conf_write_header (fd);
+ if (ret)
+ goto out;
+
/* Just create empty quota.conf file if create */
if (GF_QUOTA_OPTION_TYPE_ENABLE == opcode) {
modified = _gf_true;
@@ -709,6 +805,11 @@ glusterd_store_quota_config (glusterd_volinfo_t *volinfo, char *path,
}
gf_uuid_parse (gfid_str, gfid);
+ if (opcode > GF_QUOTA_OPTION_TYPE_VERSION_OBJECTS)
+ type = GF_QUOTA_CONF_TYPE_OBJECTS;
+ else
+ type = GF_QUOTA_CONF_TYPE_USAGE;
+
for (;;) {
bytes_read = read (conf_fd, (void*)&buf, entry_sz);
if (bytes_read <= 0) {
@@ -724,14 +825,14 @@ glusterd_store_quota_config (glusterd_volinfo_t *volinfo, char *path,
is_file_empty = _gf_true;
break;
}
- if ((bytes_read % 16) != 0) {
+ if ((bytes_read % 17) != 0) {
gf_log (this->name, GF_LOG_ERROR, "quota.conf "
"corrupted");
ret = -1;
goto out;
}
- found = glusterd_find_gfid_match (gfid, buf, bytes_read, opcode,
- &bytes_to_write);
+ found = glusterd_find_gfid_match (gfid, type, buf, bytes_read,
+ opcode, &bytes_to_write);
ret = write (fd, (void *) buf, bytes_to_write);
if (ret == -1) {
@@ -756,9 +857,23 @@ glusterd_store_quota_config (glusterd_volinfo_t *volinfo, char *path,
switch (opcode) {
case GF_QUOTA_OPTION_TYPE_LIMIT_USAGE:
+ if (!found) {
+ ret = quota_conf_write_gfid (fd, gfid,
+ GF_QUOTA_CONF_TYPE_USAGE);
+ if (ret == -1) {
+ gf_log (this->name, GF_LOG_ERROR,
+ "write into quota.conf failed. "
+ "Reason : %s",
+ strerror (errno));
+ goto out;
+ }
+ modified = _gf_true;
+ }
+ break;
case GF_QUOTA_OPTION_TYPE_LIMIT_OBJECTS:
if (!found) {
- ret = write (fd, gfid, 16);
+ ret = quota_conf_write_gfid (fd, gfid,
+ GF_QUOTA_CONF_TYPE_OBJECTS);
if (ret == -1) {
gf_log (this->name, GF_LOG_ERROR,
"write into quota.conf failed. "
diff --git a/xlators/mgmt/glusterd/src/glusterd-utils.c b/xlators/mgmt/glusterd/src/glusterd-utils.c
index c72c7266f16..31aabaf41d0 100644
--- a/xlators/mgmt/glusterd/src/glusterd-utils.c
+++ b/xlators/mgmt/glusterd/src/glusterd-utils.c
@@ -61,6 +61,7 @@
#include "glusterd-quotad-svc.h"
#include "glusterd-snapd-svc.h"
#include "glusterd-bitd-svc.h"
+#include "quota-common-utils.h"
#include "xdr-generic.h"
#include <sys/resource.h>
@@ -2396,13 +2397,14 @@ int
glusterd_vol_add_quota_conf_to_dict (glusterd_volinfo_t *volinfo, dict_t* load,
int vol_idx, char *prefix)
{
- int fd = -1;
- char *gfid_str = NULL;
- unsigned char buf[16] = {0};
- char key[PATH_MAX] = {0};
- int gfid_idx = 0;
- int ret = -1;
- xlator_t *this = NULL;
+ int fd = -1;
+ unsigned char buf[16] = {0};
+ char key[PATH_MAX] = {0};
+ int gfid_idx = 0;
+ int ret = -1;
+ xlator_t *this = NULL;
+ char type = 0;
+ float version = 0.0f;
this = THIS;
GF_ASSERT (this);
@@ -2418,40 +2420,31 @@ glusterd_vol_add_quota_conf_to_dict (glusterd_volinfo_t *volinfo, dict_t* load,
goto out;
}
- ret = glusterd_store_quota_conf_skip_header (this, fd);
+ ret = quota_conf_read_version (fd, &version);
if (ret)
goto out;
for (gfid_idx=0; ; gfid_idx++) {
-
- ret = read (fd, (void*)&buf, 16) ;
- if (ret <= 0) {
- //Finished reading all entries in the conf file
+ ret = quota_conf_read_gfid (fd, buf, &type, version);
+ if (ret == 0) {
break;
- }
- if (ret != 16) {
- //This should never happen. We must have a multiple of
- //entry_sz bytes in our configuration file.
+ } else if (ret < 0) {
gf_log (this->name, GF_LOG_CRITICAL, "Quota "
"configuration store may be corrupt.");
goto out;
}
- gfid_str = gf_strdup (uuid_utoa (buf));
- if (!gfid_str) {
- ret = -1;
- goto out;
- }
-
snprintf (key, sizeof(key)-1, "%s%d.gfid%d", prefix,
vol_idx, gfid_idx);
- key[sizeof(key)-1] = '\0';
- ret = dict_set_dynstr (load, key, gfid_str);
- if (ret) {
+ ret = dict_set_dynstr_with_alloc (load, key, uuid_utoa (buf));
+ if (ret)
goto out;
- }
- gfid_str = NULL;
+ snprintf (key, sizeof(key)-1, "%s%d.gfid-type%d", prefix,
+ vol_idx, gfid_idx);
+ ret = dict_set_int8 (load, key, type);
+ if (ret)
+ goto out;
}
snprintf (key, sizeof(key)-1, "%s%d.gfid-count", prefix, vol_idx);
@@ -2476,7 +2469,6 @@ glusterd_vol_add_quota_conf_to_dict (glusterd_volinfo_t *volinfo, dict_t* load,
out:
if (fd != -1)
close (fd);
- GF_FREE (gfid_str);
return ret;
}
@@ -2935,14 +2927,15 @@ glusterd_import_quota_conf (dict_t *peer_data, int vol_idx,
glusterd_volinfo_t *new_volinfo,
char *prefix)
{
- int gfid_idx = 0;
- int gfid_count = 0;
- int ret = -1;
- int fd = -1;
- char key[PATH_MAX] = {0};
- char *gfid_str = NULL;
- uuid_t gfid = {0,};
- xlator_t *this = NULL;
+ int gfid_idx = 0;
+ int gfid_count = 0;
+ int ret = -1;
+ int fd = -1;
+ char key[PATH_MAX] = {0};
+ char *gfid_str = NULL;
+ uuid_t gfid = {0,};
+ xlator_t *this = NULL;
+ int8_t gfid_type = 0;
this = THIS;
GF_ASSERT (this);
@@ -2984,33 +2977,34 @@ glusterd_import_quota_conf (dict_t *peer_data, int vol_idx,
if (ret)
goto out;
- ret = glusterd_store_quota_conf_stamp_header (this, fd);
- if (ret) {
- gf_log (this->name, GF_LOG_ERROR, "Failed to add header to tmp "
- "file");
+ ret = quota_conf_write_header (fd);
+ if (ret)
goto out;
- }
gfid_idx = 0;
for (gfid_idx = 0; gfid_idx < gfid_count; gfid_idx++) {
snprintf (key, sizeof (key)-1, "%s%d.gfid%d",
prefix, vol_idx, gfid_idx);
- key[sizeof(key)-1] = '\0';
ret = dict_get_str (peer_data, key, &gfid_str);
if (ret)
goto out;
+ snprintf (key, sizeof (key)-1, "%s%d.gfid-type%d",
+ prefix, vol_idx, gfid_idx);
+ ret = dict_get_int8 (peer_data, key, &gfid_type);
+ if (ret)
+ gfid_type = GF_QUOTA_CONF_TYPE_USAGE;
+
gf_uuid_parse (gfid_str, gfid);
- ret = write (fd, (void*)gfid, 16);
- if (ret != 16) {
+ ret = quota_conf_write_gfid (fd, gfid, (char)gfid_type);
+ if (ret < 0) {
gf_log (this->name, GF_LOG_CRITICAL, "Unable to write "
"gfid %s into quota.conf for %s", gfid_str,
new_volinfo->volname);
ret = -1;
goto out;
}
-
}
ret = gf_store_rename_tmppath (new_volinfo->quota_conf_shandle);
@@ -8952,40 +8946,6 @@ glusterd_clean_up_quota_store (glusterd_volinfo_t *volinfo)
}
-#define QUOTA_CONF_HEADER \
- "GlusterFS Quota conf | version: v%d.%d\n"
-
-int
-glusterd_store_quota_conf_skip_header (xlator_t *this, int fd)
-{
- char buf[PATH_MAX] = {0,};
-
- snprintf (buf, sizeof(buf)-1, QUOTA_CONF_HEADER, 1, 1);
- return gf_skip_header_section (fd, strlen (buf));
-}
-
-int
-glusterd_store_quota_conf_stamp_header (xlator_t *this, int fd)
-{
- char buf[PATH_MAX] = {0,};
- int buf_len = 0;
- ssize_t ret = -1;
- ssize_t written = 0;
-
- snprintf (buf, sizeof(buf)-1, QUOTA_CONF_HEADER, 1, 1);
- buf_len = strlen (buf);
- for (written = 0; written != buf_len; written += ret) {
- ret = write (fd, buf + written, buf_len - written);
- if (ret == -1) {
- goto out;
- }
- }
-
- ret = 0;
-out:
- return ret;
-}
-
int
glusterd_remove_auxiliary_mount (char *volname)
{
diff --git a/xlators/mgmt/glusterd/src/glusterd-utils.h b/xlators/mgmt/glusterd/src/glusterd-utils.h
index 59a07bacc1c..39c4442b72b 100644
--- a/xlators/mgmt/glusterd/src/glusterd-utils.h
+++ b/xlators/mgmt/glusterd/src/glusterd-utils.h
@@ -536,12 +536,6 @@ void
glusterd_clean_up_quota_store (glusterd_volinfo_t *volinfo);
int
-glusterd_store_quota_conf_skip_header (xlator_t *this, int fd);
-
-int
-glusterd_store_quota_conf_stamp_header (xlator_t *this, int fd);
-
-int
glusterd_remove_auxiliary_mount (char *volname);
gf_boolean_t