aboutsummaryrefslogtreecommitdiff
path: root/tools/virtiofsd/passthrough_ll.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/virtiofsd/passthrough_ll.c')
-rw-r--r--tools/virtiofsd/passthrough_ll.c84
1 files changed, 8 insertions, 76 deletions
diff --git a/tools/virtiofsd/passthrough_ll.c b/tools/virtiofsd/passthrough_ll.c
index 4db50046d4..a0beb986f3 100644
--- a/tools/virtiofsd/passthrough_ll.c
+++ b/tools/virtiofsd/passthrough_ll.c
@@ -40,7 +40,6 @@
#include "fuse_virtio.h"
#include "fuse_log.h"
#include "fuse_lowlevel.h"
-#include "standard-headers/linux/fuse.h"
#include <assert.h>
#include <cap-ng.h>
#include <dirent.h>
@@ -126,14 +125,6 @@ struct lo_inode {
GHashTable *posix_locks; /* protected by lo_inode->plock_mutex */
mode_t filetype;
-
- /*
- * So we can detect crossmount roots
- * (As such, this only needs to be valid for directories. Note
- * that files can have multiple parents due to hard links, and so
- * their parent_dev may fluctuate.)
- */
- dev_t parent_dev;
};
struct lo_cred {
@@ -174,7 +165,6 @@ struct lo_data {
int timeout_set;
int readdirplus_set;
int readdirplus_clear;
- int announce_submounts;
int allow_direct_io;
struct lo_inode root;
GHashTable *inodes; /* protected by lo->mutex */
@@ -213,7 +203,6 @@ static const struct fuse_opt lo_opts[] = {
{ "cache=always", offsetof(struct lo_data, cache), CACHE_ALWAYS },
{ "readdirplus", offsetof(struct lo_data, readdirplus_set), 1 },
{ "no_readdirplus", offsetof(struct lo_data, readdirplus_clear), 1 },
- { "announce_submounts", offsetof(struct lo_data, announce_submounts), 1 },
{ "allow_direct_io", offsetof(struct lo_data, allow_direct_io), 1 },
{ "no_allow_direct_io", offsetof(struct lo_data, allow_direct_io), 0 },
FUSE_OPT_END
@@ -611,52 +600,22 @@ static void lo_init(void *userdata, struct fuse_conn_info *conn)
}
}
-/**
- * Call fstatat() and set st_rdev whenever a directory's st_dev
- * differs from the rparent's st_dev (@parent_dev). This will
- * announce submounts to the FUSE client (unless @announce_submounts
- * is false).
- */
-static int do_fstatat(int dirfd, const char *pathname, struct stat *statbuf,
- int flags, dev_t parent_dev, uint32_t *fuse_attr_flags)
-{
- int res = fstatat(dirfd, pathname, statbuf, flags);
- if (res == -1) {
- return res;
- }
-
- if (statbuf->st_dev != parent_dev && S_ISDIR(statbuf->st_mode) &&
- fuse_attr_flags)
- {
- *fuse_attr_flags |= FUSE_ATTR_SUBMOUNT;
- }
-
- return 0;
-}
-
static void lo_getattr(fuse_req_t req, fuse_ino_t ino,
struct fuse_file_info *fi)
{
int res;
struct stat buf;
struct lo_data *lo = lo_data(req);
- struct lo_inode *inode = lo_inode(req, ino);
- uint32_t fuse_attr_flags = 0;
(void)fi;
- res = do_fstatat(inode->fd, "", &buf, AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW,
- inode->parent_dev, &fuse_attr_flags);
- lo_inode_put(lo, &inode);
+ res =
+ fstatat(lo_fd(req, ino), "", &buf, AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW);
if (res == -1) {
return (void)fuse_reply_err(req, errno);
}
- if (!lo->announce_submounts) {
- fuse_attr_flags &= ~FUSE_ATTR_SUBMOUNT;
- }
-
- fuse_reply_attr_with_flags(req, &buf, lo->timeout, fuse_attr_flags);
+ fuse_reply_attr(req, &buf, lo->timeout);
}
static int lo_fi_fd(fuse_req_t req, struct fuse_file_info *fi)
@@ -852,16 +811,11 @@ static int lo_do_lookup(fuse_req_t req, fuse_ino_t parent, const char *name,
goto out_err;
}
- res = do_fstatat(newfd, "", &e->attr, AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW,
- dir->key.dev, &e->attr_flags);
+ res = fstatat(newfd, "", &e->attr, AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW);
if (res == -1) {
goto out_err;
}
- if (!lo->announce_submounts) {
- e->attr_flags &= ~FUSE_ATTR_SUBMOUNT;
- }
-
inode = lo_find(lo, &e->attr);
if (inode) {
close(newfd);
@@ -893,7 +847,6 @@ static int lo_do_lookup(fuse_req_t req, fuse_ino_t parent, const char *name,
g_hash_table_insert(lo->inodes, &inode->key, inode);
pthread_mutex_unlock(&lo->mutex);
}
- inode->parent_dev = dir->key.dev;
e->ino = inode->fuse_ino;
lo_inode_put(lo, &inode);
lo_inode_put(lo, &dir);
@@ -1107,17 +1060,11 @@ static void lo_link(fuse_req_t req, fuse_ino_t ino, fuse_ino_t parent,
goto out_err;
}
- res = do_fstatat(inode->fd, "", &e.attr,
- AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW,
- parent_inode->key.dev, &e.attr_flags);
+ res = fstatat(inode->fd, "", &e.attr, AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW);
if (res == -1) {
goto out_err;
}
- if (!lo->announce_submounts) {
- e.attr_flags &= ~FUSE_ATTR_SUBMOUNT;
- }
-
pthread_mutex_lock(&lo->mutex);
inode->nlookup++;
pthread_mutex_unlock(&lo->mutex);
@@ -1126,14 +1073,6 @@ static void lo_link(fuse_req_t req, fuse_ino_t ino, fuse_ino_t parent,
fuse_log(FUSE_LOG_DEBUG, " %lli/%s -> %lli\n", (unsigned long long)parent,
name, (unsigned long long)e.ino);
- /*
- * No need to update inode->parent_dev, because
- * (1) We cannot, the inode now has more than one parent,
- * (2) Directories cannot have more than one parent, so link()
- * does not work for them; but parent_dev only needs to be
- * valid for directories.
- */
-
fuse_reply_entry(req, &e);
lo_inode_put(lo, &parent_inode);
lo_inode_put(lo, &inode);
@@ -1152,21 +1091,14 @@ static struct lo_inode *lookup_name(fuse_req_t req, fuse_ino_t parent,
{
int res;
struct stat attr;
- struct lo_data *lo = lo_data(req);
- struct lo_inode *dir = lo_inode(req, parent);
- if (!dir) {
- return NULL;
- }
-
- res = do_fstatat(dir->fd, name, &attr,
- AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW, dir->key.dev, NULL);
- lo_inode_put(lo, &dir);
+ res = fstatat(lo_fd(req, parent), name, &attr,
+ AT_EMPTY_PATH | AT_SYMLINK_NOFOLLOW);
if (res == -1) {
return NULL;
}
- return lo_find(lo, &attr);
+ return lo_find(lo_data(req), &attr);
}
static void lo_rmdir(fuse_req_t req, fuse_ino_t parent, const char *name)