Commit 9382d28c authored by Marc Vef's avatar Marc Vef
Browse files

rpc_create fix. Added remove file rpc (untested)

parent 05278495
Loading
Loading
Loading
Loading
+16 −0
Original line number Diff line number Diff line
@@ -129,6 +129,22 @@ void RPCData::rpc_srv_lookup_id(hg_id_t rpc_srv_lookup_id) {
    RPCData::rpc_srv_lookup_id_ = rpc_srv_lookup_id;
}

hg_id_t RPCData::rpc_srv_remove_dentry_id() const {
    return rpc_srv_remove_dentry_id_;
}

void RPCData::rpc_srv_remove_dentry_id(hg_id_t rpc_srv_remove_dentry_id) {
    RPCData::rpc_srv_remove_dentry_id_ = rpc_srv_remove_dentry_id;
}

hg_id_t RPCData::rpc_srv_remove_mdata_id() const {
    return rpc_srv_remove_mdata_id_;
}

void RPCData::rpc_srv_remove_mdata_id(hg_id_t rpc_srv_remove_mdata_id) {
    RPCData::rpc_srv_remove_mdata_id_ = rpc_srv_remove_mdata_id;
}




+9 −0
Original line number Diff line number Diff line
@@ -36,6 +36,8 @@ private:
    hg_id_t rpc_srv_create_mdata_id_;
    hg_id_t rpc_srv_attr_id_;
    hg_id_t rpc_srv_lookup_id_;
    hg_id_t rpc_srv_remove_dentry_id_;
    hg_id_t rpc_srv_remove_mdata_id_;


public:
@@ -106,6 +108,13 @@ public:

    void rpc_srv_lookup_id(hg_id_t rpc_srv_lookup_id);

    hg_id_t rpc_srv_remove_dentry_id() const;

    void rpc_srv_remove_dentry_id(hg_id_t rpc_srv_remove_dentry_id);

    hg_id_t rpc_srv_remove_mdata_id() const;

    void rpc_srv_remove_mdata_id(hg_id_t rpc_srv_remove_mdata_id);
};


+34 −17
Original line number Diff line number Diff line
@@ -9,6 +9,7 @@
#include "../adafs_ops/access.hpp"
#include "../adafs_ops/io.hpp"
#include "../rpc/client/c_metadata.hpp"
#include "../rpc/client/c_dentry.hpp"

using namespace std;

@@ -220,6 +221,7 @@ void adafs_ll_create(fuse_req_t req, fuse_ino_t parent, const char* name, mode_t
            fuse_ino_t new_inode;
            err = rpc_send_create_dentry(recipient, parent, name, f_mode, new_inode);
            if (err == 0) {
                recipient = RPC_DATA->get_rpc_node(fmt::FormatInt(new_inode).str());
                err = rpc_send_create_mdata(recipient, uid, gid, f_mode, new_inode);
                if (err == 0) {
                    fep.ino = new_inode;
@@ -307,33 +309,48 @@ void adafs_ll_mknod(fuse_req_t req, fuse_ino_t parent, const char* name, mode_t
 */
void adafs_ll_unlink(fuse_req_t req, fuse_ino_t parent, const char* name) {
    ADAFS_DATA->spdlogger()->debug("adafs_ll_unlink() enter: parent_inode {} name {}", parent, name);
    fuse_ino_t inode;
    fuse_ino_t del_inode;
    int err;

    // XXX errorhandling
    /*
     * XXX consider the whole lookup count functionality. We need something like a hashtable here, which marks the file
     * for removal. If forget is then called, the file should be really removed. (see forget comments)
     * Any fuse comments that increment the lookup count will show the file as deleted after unlink and before/after forget.
     * symlinks, hardlinks, devices, pipes, etc all work differently with forget and unlink
     */

    if (ADAFS_DATA->host_size() > 1) {
        auto recipient = RPC_DATA->get_rpc_node(RPC_DATA->get_dentry_hashable(parent, name));
        if (recipient == ADAFS_DATA->host_id()) { // local
            // Remove denty returns <err, inode_of_dentry> pair
    tie(err, inode) = remove_dentry(parent, name);
            tie(err, del_inode) = remove_dentry(parent, name);
            if (err != 0) {
                fuse_reply_err(req, err);
                return;
            }
            // Remove inode
    err = remove_all_metadata(inode);
            err = remove_all_metadata(del_inode);
        } else { // remote
            err = rpc_send_remove_dentry(recipient, parent, name, del_inode);
            if (err == 0) {
                recipient = RPC_DATA->get_rpc_node(fmt::FormatInt(del_inode).str());
                err = rpc_send_remove_mdata(recipient, del_inode);
            }
        }
    } else { // local
        // Remove denty returns <err, inode_of_dentry> pair
        tie(err, del_inode) = remove_dentry(parent, name);
        if (err != 0) {
            fuse_reply_err(req, err);
            return;
        }
        // Remove inode
        err = remove_all_metadata(del_inode);
    }

    /* TODO really consider if this is even required in a distributed setup, I'd argue: No
     * XXX consider the whole lookup count functionality. We need something like a hashtable here, which marks the file
     * for removal. If forget is then called, the file should be really removed. (see forget comments)
     * Any fuse comments that increment the lookup count will show the file as deleted after unlink and before/after forget.
     * symlinks, hardlinks, devices, pipes, etc all work differently with forget and unlink
     */

    // XXX delete data blocks (asynchronously)

    fuse_reply_err(req, 0);
    fuse_reply_err(req, err);
}

/**
+101 −1
Original line number Diff line number Diff line
@@ -56,3 +56,103 @@ int rpc_send_lookup(const size_t recipient, const fuse_ino_t parent, const char*
        err = 1;
    return err;
}

int rpc_send_create_dentry(const size_t recipient, const fuse_ino_t parent, const string& name,
                           const mode_t mode, fuse_ino_t& new_inode) {
    hg_handle_t handle;
    hg_addr_t svr_addr = HG_ADDR_NULL;
    rpc_create_dentry_in_t in;
    rpc_create_dentry_out_t out;
    auto err = 0;
    // fill in
    in.parent_inode = static_cast<uint64_t>(parent);
    in.filename = name.c_str();
    in.mode = static_cast<uint32_t>(mode);
    // TODO HG_ADDR_T is never freed atm. Need to change LRUCache
    if (!RPC_DATA->get_addr_by_hostid(recipient, svr_addr)) {
        ADAFS_DATA->spdlogger()->error("server address not resolvable for host id {}", recipient);
        return 1;
    }
    auto ret = HG_Create(RPC_DATA->client_hg_context(), svr_addr, RPC_DATA->rpc_srv_create_dentry_id(), &handle);
    if (ret != HG_SUCCESS) {
        ADAFS_DATA->spdlogger()->error("creating handle FAILED");
        return 1;
    }
    int send_ret = HG_FALSE;
    for (int i = 0; i < max_retries; ++i) {
        send_ret = margo_forward_timed(RPC_DATA->client_mid(), handle, &in, 15000);
        if (send_ret == HG_SUCCESS) {
            break;
        }
    }
    if (send_ret == HG_SUCCESS) {
        /* decode response */
        ret = HG_Get_output(handle, &out);

        ADAFS_DATA->spdlogger()->debug("Got response inode: {}", out.inode);
        new_inode = static_cast<fuse_ino_t>(out.inode);

        /* clean up resources consumed by this rpc */
        HG_Free_output(handle, &out);
    } else {
        ADAFS_DATA->spdlogger()->error("RPC send_create_dentry (timed out)");
    }

    in.filename = nullptr; // XXX temporary. If this is not done free input crashes because of invalid pointer?!
    HG_Free_input(handle, &in);
    HG_Destroy(handle);
    if (new_inode == INVALID_INODE)
        err = 1;

    return err;
}

int rpc_send_remove_dentry(const size_t recipient, const fuse_ino_t parent, const string& name, fuse_ino_t& del_inode) {
    hg_handle_t handle;
    hg_addr_t svr_addr = HG_ADDR_NULL;
    rpc_remove_dentry_in_t in;
    rpc_remove_dentry_out_t out;
    auto err = 0;
    // fill in
    in.parent_inode = static_cast<uint64_t>(parent);
    in.filename = name.c_str();
    // TODO HG_ADDR_T is never freed atm. Need to change LRUCache
    if (!RPC_DATA->get_addr_by_hostid(recipient, svr_addr)) {
        ADAFS_DATA->spdlogger()->error("server address not resolvable for host id {}", recipient);
        return 1;
    }
    auto ret = HG_Create(RPC_DATA->client_hg_context(), svr_addr, RPC_DATA->rpc_srv_remove_dentry_id(), &handle);
    if (ret != HG_SUCCESS) {
        ADAFS_DATA->spdlogger()->error("creating handle FAILED");
        return 1;
    }
    int send_ret = HG_FALSE;
    for (int i = 0; i < max_retries; ++i) {
        send_ret = margo_forward_timed(RPC_DATA->client_mid(), handle, &in, 15000);
        if (send_ret == HG_SUCCESS) {
            break;
        }
    }
    if (send_ret == HG_SUCCESS) {
        /* decode response */
        ret = HG_Get_output(handle, &out);

        ADAFS_DATA->spdlogger()->debug("Got response deleted inode: {}", out.del_inode);
        del_inode = static_cast<fuse_ino_t>(out.del_inode);

        /* clean up resources consumed by this rpc */
        HG_Free_output(handle, &out);
    } else {
        ADAFS_DATA->spdlogger()->error("RPC send_remove_dentry (timed out)");
    }

    in.filename = nullptr; // XXX temporary. If this is not done free input crashes because of invalid pointer?!
    HG_Free_input(handle, &in);
    HG_Destroy(handle);
    if (del_inode == INVALID_INODE)
        err = 1;

    return err;
}

+6 −0
Original line number Diff line number Diff line
@@ -9,5 +9,11 @@

int rpc_send_lookup(const size_t recipient, const fuse_ino_t parent, const char* name, fuse_ino_t& inode);

int rpc_send_create_dentry(const size_t recipient, const fuse_ino_t parent, const std::string& name,
                           const mode_t mode, fuse_ino_t& new_inode);

int
rpc_send_remove_dentry(const size_t recipient, const fuse_ino_t parent, const std::string& name, fuse_ino_t& del_inode);


#endif //LFS_C_DENTRY_HPP
Loading