diff options
Diffstat (limited to 'xlators/nfs/server/src/nfs-fops.h')
| -rw-r--r-- | xlators/nfs/server/src/nfs-fops.h | 259 | 
1 files changed, 259 insertions, 0 deletions
diff --git a/xlators/nfs/server/src/nfs-fops.h b/xlators/nfs/server/src/nfs-fops.h new file mode 100644 index 00000000000..8b12777d7b4 --- /dev/null +++ b/xlators/nfs/server/src/nfs-fops.h @@ -0,0 +1,259 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS is free software; you can redistribute it and/or modify +  it under the terms of the GNU General Public License as published +  by the Free Software Foundation; either version 3 of the License, +  or (at your option) any later version. + +  GlusterFS is distributed in the hope that it will be useful, but +  WITHOUT ANY WARRANTY; without even the implied warranty of +  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +  General Public License for more details. + +  You should have received a copy of the GNU General Public License +  along with this program.  If not, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _NFS_FOPS_H_ +#define _NFS_FOPS_H_ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include "dict.h" +#include "xlator.h" +#include "iobuf.h" +#include "call-stub.h" +#include "stack.h" +#include "nfs.h" +#include "nfs-common.h" +#include <semaphore.h> + +/* This structure used to communicate state between a fop and its callback. + * The problem is, when we're calling a fop in the nfs op handler, the callback + * is the NFS protocol's callback and we have to perform all GlusterFS + * inode, inode table, fd_ts and fd table operations in the NFS callback. That + * approach soon gets extremely complicated and confusing because, then we have + * to try and separate in our heads which source lines in those callbacks are + * required for serving the NFS op and which ones are needed for satisfying + * GlusterFS requirements. This structure allows us avoid performing GlusterFS + * state maintenance operations inside the fops layer itself. Now, before + * we call the callback registered by the NFS operation, a hidden fops-layer + * specific callback is called which performs the state maintenance and then + * calls the NFS callback. + * + * These are allocated from a mem-pool stored in the nfs xlator's state. + * i.e. struct nfs_state. + * That is initiated in nfs_init_subvolumes in nfs.c. + */ +struct nfs_fop_local { +        /* The local sent along by the user of the fop. */ +        void            *proglocal; + +        /* The address of the callback supplied by the user. After our +         * callback is executed this one is called. +         * The exact cast destination of this pointer will depend on the +         * fop that is being called. +         */ +        void            *progcbk; + +        /* Used only for write requests. */ +        struct iobref   *iobref; + +        inode_t         *parent; +        inode_t         *newparent; +        inode_t         *inode; + +        /* Set to 1 by nfs-inodes layer, which uses this to decide whether to +         * link the newly allocated inode into the itable, in case the fop was +         * successful. +         */ +        int             newinode; + +        /* Used by nfs-fops layer in order to determine whether to funge the +         * ino in a dir's stbuf. This funging of root ino is needed to ensure +         * that the root ino remains 1 even when the NFS server has been +         * restarted. Note that in distribute, a fresh lookup and a revalidate +         * on the root inode returns two different inode numbers and this we +         * need to handle by ourself. +         */ +        int             rootinode; + +        /* This member is used to determine whether the new parent of a file +         * being renamed is the root directory. If yes, the ino is funged. +         */ +        int             newrootinode; +        int             newrootparentinode; + +        /* Determines whether to funge the ino in the post and pre parent +         * stbufs for a file/dir where the parent directory could be the root +         * dir. Needed here because of the same reason as above. +         */ +        int             rootparentinode; + +        char            path[NFS_NAME_MAX]; +        char            newpath[NFS_NAME_MAX]; +}; + +extern struct nfs_fop_local * +nfs_fop_local_init (xlator_t *xl); + +extern void +nfs_fop_local_wipe (xlator_t *xl, struct nfs_fop_local *l); + +#define xlator_top_private(xl)  ((struct nfs_state *)((xlator_t *)(xl)->ctx->top)->private) + +#define prog_data_to_nfl(xla, nflocal, fram, pcbk, plocal)              \ +        do {                                                            \ +                nflocal = nfs_fop_local_init (xla);                     \ +                if (nflocal) {                                          \ +                        nflocal->proglocal = plocal;                    \ +                        nflocal->progcbk = pcbk;                        \ +                        if (fram)                                       \ +                                ((call_frame_t *)fram)->local = nflocal;                \ +                }                                                       \ +        } while (0)                                                     \ + + + +#define nfl_to_prog_data(xla, nflocal, pcbk, fram)                      \ +        do {                                                            \ +                nflocal = fram->local;                                  \ +                fram->local = nflocal->proglocal;                       \ +                pcbk = nflocal->progcbk;                                \ +                nfs_fop_local_wipe (xla, nflocal);                      \ +        } while (0)                                                     \ + +#define nfs_fop_handle_local_init(fram, xla, nfloc, cbck,prgloc,retval,lab) \ +        do {                                                                \ +                prog_data_to_nfl (xla, nfloc, fram, cbck, prgloc);          \ +                if (!nfloc) {                                               \ +                        gf_log (GF_NFS,GF_LOG_ERROR,"Failed to init local");\ +                        retval = -ENOMEM;                                   \ +                        goto lab;                                           \ +                }                                                           \ +        } while (0)                                                         \ + +extern int +nfs_fop_fstat (xlator_t *xl, nfs_user_t *nfu, fd_t *fd, +               fop_stat_cbk_t cbk, void *local); + +extern int +nfs_fop_readdirp (xlator_t *xl, nfs_user_t *nfu, fd_t *dirfd, +                  size_t bufsize, off_t offset, fop_readdir_cbk_t cbk, +                  void *local); +extern int +nfs_fop_lookup (xlator_t *xl, nfs_user_t *nfu, loc_t *loc, +                fop_lookup_cbk_t cbk, void *local); + +extern int +nfs_fop_create (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, int flags, +                mode_t mode, fd_t *fd, fop_create_cbk_t cbk, void *local); +extern int +nfs_fop_flush (xlator_t *xl, nfs_user_t *nfu, fd_t *fd, +               fop_flush_cbk_t cbk, void *local); + +extern int +nfs_fop_mkdir (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, mode_t mode, +               fop_mkdir_cbk_t cbk, void *local); + +extern int +nfs_fop_truncate (xlator_t *xl, nfs_user_t *nfu, loc_t *loc, off_t offset, +                  fop_truncate_cbk_t cbk, void *local); + +extern int +nfs_fop_read (xlator_t *xl, nfs_user_t *nfu, fd_t *fd, size_t size, +              off_t offset, fop_readv_cbk_t cbk, void *local); + +extern int +nfs_fop_fsync (xlator_t *xl, nfs_user_t *nfu, fd_t *fd, int32_t datasync, +               fop_fsync_cbk_t cbk, void *local); + +extern int +nfs_fop_write (xlator_t *xl, nfs_user_t *nfu, fd_t *fd, struct iobuf *srciob, +               struct iovec *vector, int32_t count, off_t offset, +               fop_writev_cbk_t cbk, void *local); + +extern int +nfs_fop_open (xlator_t *xl, nfs_user_t *nfu, loc_t *loc, int32_t flags, +              fd_t *fd, int32_t wbflags, fop_open_cbk_t cbk, void *local); + +extern int +nfs_fop_rename (xlator_t *xl, nfs_user_t *nfu, loc_t *oldloc, +                loc_t *newloc, fop_rename_cbk_t cbk, void *local); + +extern int +nfs_fop_link (xlator_t *xl, nfs_user_t *nfu, loc_t *oldloc, loc_t *newloc, +              fop_link_cbk_t cbk, void *local); + +extern int +nfs_fop_unlink (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, +                fop_unlink_cbk_t cbk, void *local); + +extern int +nfs_fop_rmdir (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, +               fop_rmdir_cbk_t cbk, void *local); + +extern int +nfs_fop_mknod (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, mode_t mode, +               dev_t dev, fop_mknod_cbk_t cbk, void *local); + +extern int +nfs_fop_readlink (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, +                  size_t size, fop_readlink_cbk_t cbk, void *local); + +extern int +nfs_fop_symlink (xlator_t *xl, nfs_user_t *nfu, char *target, +                 loc_t *pathloc, fop_symlink_cbk_t cbk, void *local); + +extern int +nfs_fop_setattr (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, +                 struct iatt *buf, int32_t valid, fop_setattr_cbk_t cbk, +                 void *local); + +extern int +nfs_fop_statfs (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc, +                fop_statfs_cbk_t cbk, void *local); + +extern int +nfs_fop_opendir (xlator_t *xl, nfs_user_t *nfu, loc_t *pathloc,fd_t *dirfd, +                 fop_opendir_cbk_t cbk, void *local); + +extern int +nfs_fop_stat (xlator_t *xl, nfs_user_t *nfu, loc_t *loc, +              fop_stat_cbk_t cbk, void *local); + +/* Synchronous equivalents of some of the fops above. + */ + +/* sfl = sync fop local + * Structure used to turn async fops into sync calls for certain NFS ops + * that need blocking operations. + */ +typedef struct nfs_syncfop { +        sem_t           replysig; +        call_stub_t     *replystub; +} nfs_syncfop_t; + +extern nfs_syncfop_t * +nfs_syncfop_init (); + +extern call_stub_t * +nfs_syncfop_wait (nfs_syncfop_t *s); + +extern void +nfs_syncfop_notify (nfs_syncfop_t *s); + +extern call_stub_t * +nfs_fop_lookup_sync (xlator_t *xl, nfs_user_t *nfu, loc_t *loc); + +extern call_stub_t * +nfs_fop_readdirp_sync (xlator_t *fopxl, nfs_user_t *nfu, fd_t *dirfd, +                       off_t offset, size_t bufsize); + +#endif  | 
