diff options
Diffstat (limited to 'xlators/features/changelog/src/changelog-encoders.c')
| -rw-r--r-- | xlators/features/changelog/src/changelog-encoders.c | 156 | 
1 files changed, 156 insertions, 0 deletions
diff --git a/xlators/features/changelog/src/changelog-encoders.c b/xlators/features/changelog/src/changelog-encoders.c new file mode 100644 index 00000000000..c71ea9270b0 --- /dev/null +++ b/xlators/features/changelog/src/changelog-encoders.c @@ -0,0 +1,156 @@ +/* +   Copyright (c) 2013 Red Hat, Inc. <http://www.redhat.com> +   This file is part of GlusterFS. + +   This file is licensed to you under your choice of the GNU Lesser +   General Public License, version 3 or any later version (LGPLv3 or +   later), or the GNU General Public License, version 2 (GPLv2), in all +   cases as published by the Free Software Foundation. +*/ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include "changelog-encoders.h" + +size_t +entry_fn (void *data, char *buffer, gf_boolean_t encode) +{ +        char    *tmpbuf = NULL; +        size_t  bufsz  = 0; +        struct changelog_entry_fields *ce = NULL; + +        ce = (struct changelog_entry_fields *) data; + +        if (encode) { +                tmpbuf = uuid_utoa (ce->cef_uuid); +                CHANGELOG_FILL_BUFFER (buffer, bufsz, tmpbuf, strlen (tmpbuf)); +        } else { +                CHANGELOG_FILL_BUFFER (buffer, bufsz, +                                       ce->cef_uuid, sizeof (uuid_t)); +        } + +        CHANGELOG_FILL_BUFFER (buffer, bufsz, "/", 1); +        CHANGELOG_FILL_BUFFER (buffer, bufsz, +                               ce->cef_bname, strlen (ce->cef_bname)); +        return bufsz; +} + +size_t +fop_fn (void *data, char *buffer, gf_boolean_t encode) +{ +        char buf[10]          = {0,}; +        size_t         bufsz = 0; +        glusterfs_fop_t fop   = 0; + +        fop = *(glusterfs_fop_t *) data; + +        if (encode) { +                (void) snprintf (buf, sizeof (buf), "%d", fop); +                CHANGELOG_FILL_BUFFER (buffer, bufsz, buf, strlen (buf)); +        } else +                CHANGELOG_FILL_BUFFER (buffer, bufsz, &fop, sizeof (fop)); + +        return bufsz; +} + +void +entry_free_fn (void *data) +{ +        changelog_opt_t *co = data; + +        if (!co) +                return; + +        GF_FREE (co->co_entry.cef_bname); +} + +/** + * try to write all data in one shot + */ + +static inline void +changelog_encode_write_xtra (changelog_log_data_t *cld, +                             char *buffer, size_t *off, gf_boolean_t encode) +{ +        int              i      = 0; +        size_t           offset = 0; +        void            *data   = NULL; +        changelog_opt_t *co     = NULL; + +        offset = *off; + +        co = (changelog_opt_t *) cld->cld_ptr; + +        for (; i < cld->cld_xtra_records; i++, co++) { +                CHANGELOG_FILL_BUFFER (buffer, offset, "\0", 1); + +                switch (co->co_type) { +                case CHANGELOG_OPT_REC_FOP: +                        data = &co->co_fop; +                        break; +                case CHANGELOG_OPT_REC_ENTRY: +                        data = &co->co_entry; +                        break; +                } + +                if (co->co_convert) +                        offset += co->co_convert (data, +                                                  buffer + offset, encode); +                else /* no coversion: write it out as it is */ +                        CHANGELOG_FILL_BUFFER (buffer, offset, +                                               data, co->co_len); +        } + +        *off = offset; +} + +int +changelog_encode_ascii (xlator_t *this, changelog_log_data_t *cld) +{ +        size_t            off      = 0; +        size_t            gfid_len = 0; +        char             *gfid_str = NULL; +        char             *buffer   = NULL; +        changelog_priv_t *priv     = NULL; + +        priv = this->private; + +        gfid_str = uuid_utoa (cld->cld_gfid); +        gfid_len = strlen (gfid_str); + +        /* extra bytes for decorations */ +        buffer = alloca (gfid_len + cld->cld_ptr_len + 10); +        CHANGELOG_STORE_ASCII (priv, buffer, +                               off, gfid_str, gfid_len, cld); + +        if (cld->cld_xtra_records) +                changelog_encode_write_xtra (cld, buffer, &off, _gf_true); + +        CHANGELOG_FILL_BUFFER (buffer, off, "\0", 1); + +        return changelog_write_change (priv, buffer, off); +} + +int +changelog_encode_binary (xlator_t *this, changelog_log_data_t *cld) +{ +        size_t            off    = 0; +        char             *buffer = NULL; +        changelog_priv_t *priv   = NULL; + +        priv = this->private; + +        /* extra bytes for decorations */ +        buffer = alloca (sizeof (uuid_t) + cld->cld_ptr_len + 10); +        CHANGELOG_STORE_BINARY (priv, buffer, off, cld->cld_gfid, cld); + +        if (cld->cld_xtra_records) +                changelog_encode_write_xtra (cld, buffer, &off, _gf_false); + +        CHANGELOG_FILL_BUFFER (buffer, off, "\0", 1); + +        return changelog_write_change (priv, buffer, off); +}  | 
