]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
client: use thread local data to track fuse request
authorYan, Zheng <zyan@redhat.com>
Tue, 29 Sep 2015 07:11:24 +0000 (15:11 +0800)
committerYan, Zheng <zyan@redhat.com>
Thu, 3 Mar 2016 12:30:07 +0000 (20:30 +0800)
When handling an operation, libcephfs code may want to access fuse
request for extra information. by tracking fuse request in thread
local data, we can avoid adding extra parameter to Client::ll_foo
functions.

Signed-off-by: Yan, Zheng <zyan@redhat.com>
(cherry picked from commit a9f91d7d70893cdc5f832a26a5be298941d00315)

src/client/fuse_ll.cc

index f9c380c9cb4fde8556fad576baa754bc7654fec3..a83e5a698c3c673a2f8d2d30bc8ffc774fbfb91b 100644 (file)
@@ -90,12 +90,23 @@ public:
   ceph::unordered_map<uint64_t,int> snap_stag_map;
   ceph::unordered_map<int,uint64_t> stag_snap_map;
 
+  pthread_key_t fuse_req_key;
+  void set_fuse_req(fuse_req_t);
+  fuse_req_t get_fuse_req();
+
   struct fuse_args args;
 };
 
-static void fuse_ll_lookup(fuse_req_t req, fuse_ino_t parent, const char *name)
+static CephFuse::Handle *fuse_ll_req_prepare(fuse_req_t req)
 {
   CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  cfuse->set_fuse_req(req);
+  return cfuse;
+}
+
+static void fuse_ll_lookup(fuse_req_t req, fuse_ino_t parent, const char *name)
+{
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   struct fuse_entry_param fe;
   Inode *i2, *i1 = cfuse->iget(parent); // see below
@@ -119,7 +130,7 @@ static void fuse_ll_lookup(fuse_req_t req, fuse_ino_t parent, const char *name)
 static void fuse_ll_forget(fuse_req_t req, fuse_ino_t ino,
                           long unsigned nlookup)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   cfuse->client->ll_forget(cfuse->iget(ino), nlookup+1);
   fuse_reply_none(req);
 }
@@ -127,7 +138,7 @@ static void fuse_ll_forget(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_getattr(fuse_req_t req, fuse_ino_t ino,
                            struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   struct stat stbuf;
@@ -148,7 +159,7 @@ static void fuse_ll_getattr(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_setattr(fuse_req_t req, fuse_ino_t ino, struct stat *attr,
                            int to_set, struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
 
@@ -174,7 +185,7 @@ static void fuse_ll_setattr(fuse_req_t req, fuse_ino_t ino, struct stat *attr,
 static void fuse_ll_setxattr(fuse_req_t req, fuse_ino_t ino, const char *name,
                             const char *value, size_t size, int flags)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
 
@@ -187,7 +198,7 @@ static void fuse_ll_setxattr(fuse_req_t req, fuse_ino_t ino, const char *name,
 
 static void fuse_ll_listxattr(fuse_req_t req, fuse_ino_t ino, size_t size)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   char buf[size];
@@ -206,7 +217,7 @@ static void fuse_ll_listxattr(fuse_req_t req, fuse_ino_t ino, size_t size)
 static void fuse_ll_getxattr(fuse_req_t req, fuse_ino_t ino, const char *name,
                             size_t size)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   char buf[size];
@@ -225,7 +236,7 @@ static void fuse_ll_getxattr(fuse_req_t req, fuse_ino_t ino, const char *name,
 static void fuse_ll_removexattr(fuse_req_t req, fuse_ino_t ino,
                                const char *name)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
 
@@ -239,13 +250,13 @@ static void fuse_ll_removexattr(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_opendir(fuse_req_t req, fuse_ino_t ino,
                            struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   void *dirp;
 
-  int r = cfuse->client->ll_opendir(in, (dir_result_t **) &dirp, ctx->uid,
-                                   ctx->gid);
+  int r = cfuse->client->ll_opendir(in, (dir_result_t **)&dirp,
+                                   ctx->uid, ctx->gid);
   if (r >= 0) {
     fi->fh = (long)dirp;
     fuse_reply_open(req, fi);
@@ -258,7 +269,7 @@ static void fuse_ll_opendir(fuse_req_t req, fuse_ino_t ino,
 
 static void fuse_ll_readlink(fuse_req_t req, fuse_ino_t ino)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   char buf[PATH_MAX + 1];  // leave room for a null terminator
@@ -277,7 +288,7 @@ static void fuse_ll_readlink(fuse_req_t req, fuse_ino_t ino)
 static void fuse_ll_mknod(fuse_req_t req, fuse_ino_t parent, const char *name,
                          mode_t mode, dev_t rdev)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *i2, *i1 = cfuse->iget(parent);
   struct fuse_entry_param fe;
@@ -302,7 +313,7 @@ static void fuse_ll_mknod(fuse_req_t req, fuse_ino_t parent, const char *name,
 static void fuse_ll_mkdir(fuse_req_t req, fuse_ino_t parent, const char *name,
                          mode_t mode)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *i2, *i1 = cfuse->iget(parent);
   struct fuse_entry_param fe;
@@ -326,7 +337,7 @@ static void fuse_ll_mkdir(fuse_req_t req, fuse_ino_t parent, const char *name,
 
 static void fuse_ll_unlink(fuse_req_t req, fuse_ino_t parent, const char *name)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(parent);
 
@@ -338,7 +349,7 @@ static void fuse_ll_unlink(fuse_req_t req, fuse_ino_t parent, const char *name)
 
 static void fuse_ll_rmdir(fuse_req_t req, fuse_ino_t parent, const char *name)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(parent);
 
@@ -351,7 +362,7 @@ static void fuse_ll_rmdir(fuse_req_t req, fuse_ino_t parent, const char *name)
 static void fuse_ll_symlink(fuse_req_t req, const char *existing,
                            fuse_ino_t parent, const char *name)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *i2, *i1 = cfuse->iget(parent);
   struct fuse_entry_param fe;
@@ -376,7 +387,7 @@ static void fuse_ll_symlink(fuse_req_t req, const char *existing,
 static void fuse_ll_rename(fuse_req_t req, fuse_ino_t parent, const char *name,
                           fuse_ino_t newparent, const char *newname)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(parent);
   Inode *nin = cfuse->iget(newparent);
@@ -391,7 +402,7 @@ static void fuse_ll_rename(fuse_req_t req, fuse_ino_t parent, const char *name,
 static void fuse_ll_link(fuse_req_t req, fuse_ino_t ino, fuse_ino_t newparent,
                         const char *newname)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   Inode *nin = cfuse->iget(newparent);
@@ -416,7 +427,7 @@ static void fuse_ll_link(fuse_req_t req, fuse_ino_t ino, fuse_ino_t newparent,
 static void fuse_ll_open(fuse_req_t req, fuse_ino_t ino,
                         struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *in = cfuse->iget(ino);
   Fh *fh = NULL;
@@ -439,7 +450,7 @@ static void fuse_ll_open(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_read(fuse_req_t req, fuse_ino_t ino, size_t size, off_t off,
                         struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
   bufferlist bl;
   int r = cfuse->client->ll_read(fh, off, size, &bl);
@@ -452,7 +463,7 @@ static void fuse_ll_read(fuse_req_t req, fuse_ino_t ino, size_t size, off_t off,
 static void fuse_ll_write(fuse_req_t req, fuse_ino_t ino, const char *buf,
                           size_t size, off_t off, struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
   int r = cfuse->client->ll_write(fh, off, size, buf);
   if (r >= 0)
@@ -464,7 +475,7 @@ static void fuse_ll_write(fuse_req_t req, fuse_ino_t ino, const char *buf,
 static void fuse_ll_flush(fuse_req_t req, fuse_ino_t ino,
                          struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
   int r = cfuse->client->ll_flush(fh);
   fuse_reply_err(req, -r);
@@ -474,7 +485,7 @@ static void fuse_ll_flush(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_ioctl(fuse_req_t req, fuse_ino_t ino, int cmd, void *arg, struct fuse_file_info *fi,
                           unsigned flags, const void *in_buf, size_t in_bufsz, size_t out_bufsz)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
 
   if (flags & FUSE_IOCTL_COMPAT) {
     fuse_reply_err(req, ENOSYS);
@@ -506,7 +517,7 @@ static void fuse_ll_fallocate(fuse_req_t req, fuse_ino_t ino, int mode,
                               off_t offset, off_t length,
                               struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = (Fh*)fi->fh;
   int r = cfuse->client->ll_fallocate(fh, mode, offset, length);
   fuse_reply_err(req, -r);
@@ -517,7 +528,7 @@ static void fuse_ll_fallocate(fuse_req_t req, fuse_ino_t ino, int mode,
 static void fuse_ll_release(fuse_req_t req, fuse_ino_t ino,
                            struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
   int r = cfuse->client->ll_release(fh);
   fuse_reply_err(req, -r);
@@ -526,7 +537,7 @@ static void fuse_ll_release(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_fsync(fuse_req_t req, fuse_ino_t ino, int datasync,
                          struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
   int r = cfuse->client->ll_fsync(fh, datasync);
   fuse_reply_err(req, -r);
@@ -567,7 +578,7 @@ static int fuse_ll_add_dirent(void *p, struct dirent *de, struct stat *st,
 static void fuse_ll_readdir(fuse_req_t req, fuse_ino_t ino, size_t size,
                            off_t off, struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
 
   dir_result_t *dirp = reinterpret_cast<dir_result_t*>(fi->fh);
   cfuse->client->seekdir(dirp, off);
@@ -590,7 +601,7 @@ static void fuse_ll_readdir(fuse_req_t req, fuse_ino_t ino, size_t size,
 static void fuse_ll_releasedir(fuse_req_t req, fuse_ino_t ino,
                               struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   dir_result_t *dirp = reinterpret_cast<dir_result_t*>(fi->fh);
   cfuse->client->ll_releasedir(dirp);
   fuse_reply_err(req, 0);
@@ -604,7 +615,7 @@ static void fuse_ll_access(fuse_req_t req, fuse_ino_t ino, int mask)
 static void fuse_ll_create(fuse_req_t req, fuse_ino_t parent, const char *name,
                           mode_t mode, struct fuse_file_info *fi)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   const struct fuse_ctx *ctx = fuse_req_ctx(req);
   Inode *i1 = cfuse->iget(parent), *i2;
   struct fuse_entry_param fe;
@@ -629,7 +640,7 @@ static void fuse_ll_create(fuse_req_t req, fuse_ino_t parent, const char *name,
 static void fuse_ll_statfs(fuse_req_t req, fuse_ino_t ino)
 {
   struct statvfs stbuf;
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Inode *in = cfuse->iget(ino);
 
   int r = cfuse->client->ll_statfs(in, &stbuf);
@@ -644,7 +655,7 @@ static void fuse_ll_statfs(fuse_req_t req, fuse_ino_t ino)
 static void fuse_ll_getlk(fuse_req_t req, fuse_ino_t ino,
                          struct fuse_file_info *fi, struct flock *lock)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
 
   int r = cfuse->client->ll_getlk(fh, lock, fi->lock_owner);
@@ -657,7 +668,7 @@ static void fuse_ll_getlk(fuse_req_t req, fuse_ino_t ino,
 static void fuse_ll_setlk(fuse_req_t req, fuse_ino_t ino,
                          struct fuse_file_info *fi, struct flock *lock, int sleep)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = reinterpret_cast<Fh*>(fi->fh);
 
   // must use multithread if operation may block
@@ -673,7 +684,7 @@ static void fuse_ll_setlk(fuse_req_t req, fuse_ino_t ino,
 
 static void fuse_ll_interrupt(fuse_req_t req, void* data)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   cfuse->client->ll_interrupt(data);
 }
 
@@ -689,7 +700,7 @@ static void switch_interrupt_cb(void *req, void* data)
 static void fuse_ll_flock(fuse_req_t req, fuse_ino_t ino,
                          struct fuse_file_info *fi, int cmd)
 {
-  CephFuse::Handle *cfuse = (CephFuse::Handle *)fuse_req_userdata(req);
+  CephFuse::Handle *cfuse = fuse_ll_req_prepare(req);
   Fh *fh = (Fh*)fi->fh;
 
   // must use multithread if operation may block
@@ -878,10 +889,18 @@ void CephFuse::Handle::finalize()
   if (ch)
     fuse_unmount(mountpoint, ch);
 
+  pthread_key_delete(fuse_req_key);
 }
 
 int CephFuse::Handle::init(int argc, const char *argv[])
 {
+
+  int r = pthread_key_create(&fuse_req_key, NULL);
+  if (r) {
+    derr << "pthread_key_create failed." << dendl;
+    return r;
+  }
+
   // set up fuse argc/argv
   int newargc = 0;
   const char **newargv = (const char **) malloc((argc + 10) * sizeof(char *));
@@ -1031,6 +1050,17 @@ uint64_t CephFuse::Handle::make_fake_ino(inodeno_t ino, snapid_t snapid)
   return fino;
 }
 
+void CephFuse::Handle::set_fuse_req(fuse_req_t req)
+{
+  pthread_setspecific(fuse_req_key, (void*)req);
+}
+
+fuse_req_t CephFuse::Handle::get_fuse_req()
+{
+  return (fuse_req_t) pthread_getspecific(fuse_req_key);
+}
+
+
 CephFuse::CephFuse(Client *c, int fd) : _handle(new CephFuse::Handle(c, fd))
 {
 }