diff options
Diffstat (limited to 'xlators/features/read-only/src')
| -rw-r--r-- | xlators/features/read-only/src/read-only-common.c | 2 | ||||
| -rw-r--r-- | xlators/features/read-only/src/read-only-common.h | 4 | ||||
| -rw-r--r-- | xlators/features/read-only/src/read-only-mem-types.h | 2 | ||||
| -rw-r--r-- | xlators/features/read-only/src/read-only.c | 14 | ||||
| -rw-r--r-- | xlators/features/read-only/src/read-only.h | 15 | ||||
| -rw-r--r-- | xlators/features/read-only/src/worm-helper.c | 24 | ||||
| -rw-r--r-- | xlators/features/read-only/src/worm.c | 144 |
7 files changed, 152 insertions, 53 deletions
diff --git a/xlators/features/read-only/src/read-only-common.c b/xlators/features/read-only/src/read-only-common.c index 39985169991..9640e7e3eee 100644 --- a/xlators/features/read-only/src/read-only-common.c +++ b/xlators/features/read-only/src/read-only-common.c @@ -9,7 +9,7 @@ */ #include "read-only.h" #include "read-only-mem-types.h" -#include "defaults.h" +#include <glusterfs/defaults.h> gf_boolean_t is_readonly_or_worm_enabled(call_frame_t *frame, xlator_t *this) diff --git a/xlators/features/read-only/src/read-only-common.h b/xlators/features/read-only/src/read-only-common.h index 32719da28f1..5561961ffa2 100644 --- a/xlators/features/read-only/src/read-only-common.h +++ b/xlators/features/read-only/src/read-only-common.h @@ -7,8 +7,8 @@ later), or the GNU General Public License, version 2 (GPLv2), in all cases as published by the Free Software Foundation. */ -#include "xlator.h" -#include "defaults.h" +#include <glusterfs/xlator.h> +#include <glusterfs/defaults.h> gf_boolean_t is_readonly_or_worm_enabled(call_frame_t *frame, xlator_t *this); diff --git a/xlators/features/read-only/src/read-only-mem-types.h b/xlators/features/read-only/src/read-only-mem-types.h index 4baaeb41216..c67d6c02cd0 100644 --- a/xlators/features/read-only/src/read-only-mem-types.h +++ b/xlators/features/read-only/src/read-only-mem-types.h @@ -11,7 +11,7 @@ #ifndef __READONLY_MEM_TYPES_H__ #define __READONLY_MEM_TYPES_H__ -#include "mem-types.h" +#include <glusterfs/mem-types.h> enum gf_read_only_mem_types_ { gf_read_only_mt_priv_t = gf_common_mt_end + 1, diff --git a/xlators/features/read-only/src/read-only.c b/xlators/features/read-only/src/read-only.c index c92a9801196..48654998e63 100644 --- a/xlators/features/read-only/src/read-only.c +++ b/xlators/features/read-only/src/read-only.c @@ -7,7 +7,6 @@ later), or the GNU General Public License, version 2 (GPLv2), in all cases as published by the Free Software Foundation. */ -#include "defaults.h" #include "read-only-common.h" #include "read-only-mem-types.h" #include "read-only.h" @@ -130,3 +129,16 @@ struct volume_options options[] = { "\"off\" by default."}, {.key = {NULL}}, }; + +xlator_api_t xlator_api = { + .init = init, + .fini = fini, + .reconfigure = reconfigure, + .mem_acct_init = mem_acct_init, + .op_version = {1}, /* Present from the initial version */ + .fops = &fops, + .cbks = &cbks, + .options = options, + .identifier = "read-only", + .category = GF_TECH_PREVIEW, +}; diff --git a/xlators/features/read-only/src/read-only.h b/xlators/features/read-only/src/read-only.h index d74053a2a8f..aced5d3c577 100644 --- a/xlators/features/read-only/src/read-only.h +++ b/xlators/features/read-only/src/read-only.h @@ -11,25 +11,26 @@ #ifndef __READONLY_H__ #define __READONLY_H__ -#include "read-only-mem-types.h" -#include "xlator.h" +#include <stdint.h> // for uint64_t, uint8_t +#include <sys/time.h> // for time_t +#include "glusterfs/glusterfs.h" // for gf_boolean_t typedef struct { uint8_t worm : 1; uint8_t retain : 1; uint8_t legal_hold : 1; uint8_t ret_mode : 1; - uint64_t ret_period; - uint64_t auto_commit_period; + int64_t ret_period; + int64_t auto_commit_period; } worm_reten_state_t; typedef struct { gf_boolean_t readonly_or_worm_enabled; gf_boolean_t worm_file; gf_boolean_t worm_files_deletable; - uint64_t reten_period; - uint64_t com_period; - char *reten_mode; + int64_t reten_period; + int64_t com_period; + int reten_mode; time_t start_time; } read_only_priv_t; diff --git a/xlators/features/read-only/src/worm-helper.c b/xlators/features/read-only/src/worm-helper.c index 3f882fe08d6..df45f2a940b 100644 --- a/xlators/features/read-only/src/worm-helper.c +++ b/xlators/features/read-only/src/worm-helper.c @@ -9,8 +9,8 @@ */ #include "read-only-mem-types.h" #include "read-only.h" -#include "xlator.h" -#include "syncop.h" +#include <glusterfs/xlator.h> +#include <glusterfs/syncop.h> #include "worm-helper.h" /*Function to check whether file is read-only. @@ -41,7 +41,7 @@ worm_init_state(xlator_t *this, gf_boolean_t fop_with_fd, void *file_ptr) GF_VALIDATE_OR_GOTO("worm", this, out); GF_VALIDATE_OR_GOTO(this->name, file_ptr, out); - start_time = time(NULL); + start_time = gf_time(); dict = dict_new(); if (!dict) { gf_log(this->name, GF_LOG_ERROR, "Error creating the dict"); @@ -84,10 +84,7 @@ worm_set_state(xlator_t *this, gf_boolean_t fop_with_fd, void *file_ptr, retention_state->worm = 1; retention_state->retain = 1; retention_state->legal_hold = 0; - if (strcmp(priv->reten_mode, "relax") == 0) - retention_state->ret_mode = 0; - else - retention_state->ret_mode = 1; + retention_state->ret_mode = priv->reten_mode; retention_state->ret_period = priv->reten_period; retention_state->auto_commit_period = priv->com_period; if (fop_with_fd) @@ -97,7 +94,7 @@ worm_set_state(xlator_t *this, gf_boolean_t fop_with_fd, void *file_ptr, if (ret) goto out; stbuf->ia_mtime = stpre.ia_mtime; - stbuf->ia_atime = time(NULL) + retention_state->ret_period; + stbuf->ia_atime = gf_time() + retention_state->ret_period; if (fop_with_fd) ret = syncop_fsetattr(this, (fd_t *)file_ptr, stbuf, GF_SET_ATTR_ATIME, @@ -289,6 +286,7 @@ gf_worm_state_transition(xlator_t *this, gf_boolean_t fop_with_fd, { int op_errno = EROFS; int ret = -1; + time_t now = 0; uint64_t com_period = 0; uint64_t start_time = 0; dict_t *dict = NULL; @@ -340,8 +338,10 @@ gf_worm_state_transition(xlator_t *this, gf_boolean_t fop_with_fd, goto out; } - if (ret == -1 && (time(NULL) - start_time) >= com_period) { - if ((time(NULL) - stbuf.ia_mtime) >= com_period) { + now = gf_time(); + + if (ret == -1 && (now - start_time) >= com_period) { + if ((now - stbuf.ia_mtime) >= com_period) { ret = worm_set_state(this, fop_with_fd, file_ptr, &reten_state, &stbuf); if (ret) { @@ -355,10 +355,10 @@ gf_worm_state_transition(xlator_t *this, gf_boolean_t fop_with_fd, op_errno = 0; goto out; } - } else if (ret == -1 && (time(NULL) - start_time) < com_period) { + } else if (ret == -1 && (now - start_time) < com_period) { op_errno = 0; goto out; - } else if (reten_state.retain && ((time(NULL) >= stbuf.ia_atime))) { + } else if (reten_state.retain && ((now >= stbuf.ia_atime))) { gf_worm_state_lookup(this, fop_with_fd, file_ptr, &reten_state, &stbuf); } if (reten_state.worm && !reten_state.retain && priv->worm_files_deletable && diff --git a/xlators/features/read-only/src/worm.c b/xlators/features/read-only/src/worm.c index db128b75196..1cc5526d5cd 100644 --- a/xlators/features/read-only/src/worm.c +++ b/xlators/features/read-only/src/worm.c @@ -7,12 +7,12 @@ later), or the GNU General Public License, version 2 (GPLv2), in all cases as published by the Free Software Foundation. */ -#include "xlator.h" -#include "defaults.h" +#include <glusterfs/xlator.h> +#include <glusterfs/defaults.h> #include "read-only-common.h" #include "read-only-mem-types.h" #include "read-only.h" -#include "syncop.h" +#include <glusterfs/syncop.h> #include "worm-helper.h" int32_t @@ -292,6 +292,12 @@ worm_setattr(call_frame_t *frame, xlator_t *this, loc_t *loc, goto out; } } + reten_state.ret_period = reten_state.ret_period + stbuf->ia_atime - + stpre.ia_atime; + ret = gf_worm_set_xattr(this, &reten_state, _gf_false, loc); + if (ret) { + goto out; + } stbuf->ia_mtime = stpre.ia_mtime; } } @@ -372,6 +378,13 @@ worm_fsetattr(call_frame_t *frame, xlator_t *this, fd_t *fd, struct iatt *stbuf, goto out; } } + reten_state.ret_period = reten_state.ret_period + stbuf->ia_atime - + stpre.ia_atime; + ret = gf_worm_set_xattr(this, &reten_state, _gf_true, fd); + if (ret) { + goto out; + } + stbuf->ia_mtime = stpre.ia_mtime; } } @@ -427,29 +440,22 @@ worm_create_cbk(call_frame_t *frame, void *cookie, xlator_t *this, { int ret = 0; read_only_priv_t *priv = NULL; - dict_t *dict = NULL; + // In case of an error exit because fd can be NULL and this would + // cause an segfault when performing fsetxattr . We explicitly + // unwind to avoid future problems + if (op_ret < 0) { + goto out; + } priv = this->private; GF_ASSERT(priv); if (priv->worm_file) { - dict = dict_new(); - if (!dict) { - gf_log(this->name, GF_LOG_ERROR, - "Error creating the " - "dict"); - goto out; - } - ret = dict_set_int8(dict, "trusted.worm_file", 1); + ret = fd_ctx_set(fd, this, 1); if (ret) { gf_log(this->name, GF_LOG_ERROR, - "Error in setting " - "the dict"); - goto out; - } - ret = syncop_fsetxattr(this, fd, dict, 0, NULL, NULL); - if (ret) { - gf_log(this->name, GF_LOG_ERROR, "Error setting xattr"); - goto out; + "Failed to set the fd ctx " + "for gfid:%s . Worm feature may not work for the gfid", + uuid_utoa(inode->gfid)); } ret = worm_init_state(this, _gf_true, fd); if (ret) { @@ -460,8 +466,6 @@ worm_create_cbk(call_frame_t *frame, void *cookie, xlator_t *this, out: STACK_UNWIND_STRICT(create, frame, op_ret, op_errno, fd, inode, buf, preparent, postparent, xdata); - if (dict) - dict_unref(dict); return ret; } @@ -475,11 +479,21 @@ worm_create(call_frame_t *frame, xlator_t *this, loc_t *loc, int32_t flags, return 0; } +static void +set_reten_mode(read_only_priv_t *priv, char *reten_mode) +{ + if (strcmp(reten_mode, "relax") == 0) + priv->reten_mode = 0; + else + priv->reten_mode = 1; +} + int32_t init(xlator_t *this) { int ret = -1; read_only_priv_t *priv = NULL; + char *reten_mode = NULL; if (!this->children || this->children->next) { gf_log(this->name, GF_LOG_ERROR, @@ -509,9 +523,10 @@ init(xlator_t *this) GF_OPTION_INIT("worm", priv->readonly_or_worm_enabled, bool, out); GF_OPTION_INIT("worm-file-level", priv->worm_file, bool, out); - GF_OPTION_INIT("default-retention-period", priv->reten_period, uint64, out); - GF_OPTION_INIT("auto-commit-period", priv->com_period, uint64, out); - GF_OPTION_INIT("retention-mode", priv->reten_mode, str, out); + GF_OPTION_INIT("default-retention-period", priv->reten_period, int64, out); + GF_OPTION_INIT("auto-commit-period", priv->com_period, int64, out); + GF_OPTION_INIT("retention-mode", reten_mode, str, out); + set_reten_mode(priv, reten_mode); GF_OPTION_INIT("worm-files-deletable", priv->worm_files_deletable, bool, out); @@ -524,6 +539,7 @@ int reconfigure(xlator_t *this, dict_t *options) { read_only_priv_t *priv = NULL; + char *reten_mode = NULL; int ret = -1; priv = this->private; @@ -533,9 +549,10 @@ reconfigure(xlator_t *this, dict_t *options) out); GF_OPTION_RECONF("worm-file-level", priv->worm_file, options, bool, out); GF_OPTION_RECONF("default-retention-period", priv->reten_period, options, - uint64, out); - GF_OPTION_RECONF("retention-mode", priv->reten_mode, options, str, out); - GF_OPTION_RECONF("auto-commit-period", priv->com_period, options, uint64, + int64, out); + GF_OPTION_RECONF("retention-mode", reten_mode, options, str, out); + set_reten_mode(priv, reten_mode); + GF_OPTION_RECONF("auto-commit-period", priv->com_period, options, int64, out); GF_OPTION_RECONF("worm-files-deletable", priv->worm_files_deletable, options, bool, out); @@ -556,6 +573,7 @@ fini(xlator_t *this) mem_put(priv); this->private = NULL; mem_pool_destroy(this->local_pool); + this->local_pool = NULL; out: return; } @@ -583,7 +601,62 @@ struct xlator_fops fops = { .lk = ro_lk, }; -struct xlator_cbks cbks; +int32_t +worm_release(xlator_t *this, fd_t *fd) +{ + dict_t *dict = NULL; + int ret = -1; + dict = dict_new(); + uint64_t value = 0; + loc_t loc = { + 0, + }; + read_only_priv_t *priv = NULL; + priv = this->private; + + if (priv->worm_file) { + if (!dict) { + gf_log(this->name, GF_LOG_ERROR, "Error creating the dict"); + goto out; + } + + ret = fd_ctx_get(fd, this, &value); + if (ret) { + gf_log(this->name, GF_LOG_DEBUG, "Failed to get the fd ctx"); + } + if (!value) { + goto out; + } + + ret = dict_set_int8(dict, "trusted.worm_file", 1); + if (ret) { + gf_log(this->name, GF_LOG_ERROR, + "Error in setting " + "the dict"); + goto out; + } + + loc.inode = inode_ref(fd->inode); + gf_uuid_copy(loc.gfid, fd->inode->gfid); + ret = syncop_setxattr(this, &loc, dict, 0, NULL, NULL); + if (ret) { + gf_log(this->name, GF_LOG_ERROR, "Error setting xattr"); + goto out; + } + + gf_worm_state_transition(this, _gf_false, &loc, GF_FOP_WRITE); + } + +out: + loc_wipe(&loc); + if (dict) + dict_unref(dict); + return 0; +} + +struct xlator_cbks cbks = { + .release = worm_release, +}; struct volume_options options[] = { {.key = {"worm"}, @@ -634,3 +707,16 @@ struct volume_options options[] = { .description = "Auto commit period for the files."}, {.key = {NULL}}, }; + +xlator_api_t xlator_api = { + .init = init, + .fini = fini, + .reconfigure = reconfigure, + .mem_acct_init = mem_acct_init, + .op_version = {1}, /* Present from the initial version */ + .fops = &fops, + .cbks = &cbks, + .options = options, + .identifier = "worm", + .category = GF_TECH_PREVIEW, +}; |
