[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 10/25] 9pfs: handle walk of ".." in the root directo
From: |
Michael Roth |
Subject: |
[Qemu-devel] [PATCH 10/25] 9pfs: handle walk of ".." in the root directory |
Date: |
Tue, 20 Sep 2016 12:05:26 -0500 |
From: Greg Kurz <address@hidden>
The 9P spec at http://man.cat-v.org/plan_9/5/intro says:
All directories must support walks to the directory .. (dot-dot) meaning
parent directory, although by convention directories contain no explicit
entry for .. or . (dot). The parent of the root directory of a server's
tree is itself.
This means that a client cannot walk further than the root directory
exported by the server. In other words, if the client wants to walk
"/.." or "/foo/../..", the server should answer like the request was
to walk "/".
This patch just does that:
- we cache the QID of the root directory at attach time
- during the walk we compare the QID of each path component with the root
QID to detect if we're in a "/.." situation
- if so, we skip the current component and go to the next one
Signed-off-by: Greg Kurz <address@hidden>
Reviewed-by: Eric Blake <address@hidden>
Signed-off-by: Peter Maydell <address@hidden>
(cherry picked from commit 56f101ecce0eafd09e2daf1c4eeb1377d6959261)
Signed-off-by: Michael Roth <address@hidden>
---
hw/9pfs/9p.c | 40 +++++++++++++++++++++++++++++++---------
hw/9pfs/9p.h | 1 +
2 files changed, 32 insertions(+), 9 deletions(-)
diff --git a/hw/9pfs/9p.c b/hw/9pfs/9p.c
index 1e96427..1ac05b2 100644
--- a/hw/9pfs/9p.c
+++ b/hw/9pfs/9p.c
@@ -1008,6 +1008,7 @@ static void v9fs_attach(void *opaque)
goto out;
}
err += offset;
+ memcpy(&s->root_qid, &qid, sizeof(qid));
trace_v9fs_attach_return(pdu->tag, pdu->id,
qid.type, qid.version, qid.path);
/*
@@ -1259,6 +1260,14 @@ static bool name_is_illegal(const char *name)
return !*name || strchr(name, '/') != NULL;
}
+static bool not_same_qid(const V9fsQID *qid1, const V9fsQID *qid2)
+{
+ return
+ qid1->type != qid2->type ||
+ qid1->version != qid2->version ||
+ qid1->path != qid2->path;
+}
+
static void v9fs_walk(void *opaque)
{
int name_idx;
@@ -1274,6 +1283,7 @@ static void v9fs_walk(void *opaque)
V9fsFidState *newfidp = NULL;
V9fsPDU *pdu = opaque;
V9fsState *s = pdu->s;
+ V9fsQID qid;
err = pdu_unmarshal(pdu, offset, "ddw", &fid, &newfid, &nwnames);
if (err < 0) {
@@ -1307,6 +1317,12 @@ static void v9fs_walk(void *opaque)
err = -ENOENT;
goto out_nofid;
}
+
+ err = fid_to_qid(pdu, fidp, &qid);
+ if (err < 0) {
+ goto out;
+ }
+
v9fs_path_init(&dpath);
v9fs_path_init(&path);
/*
@@ -1316,16 +1332,22 @@ static void v9fs_walk(void *opaque)
v9fs_path_copy(&dpath, &fidp->path);
v9fs_path_copy(&path, &fidp->path);
for (name_idx = 0; name_idx < nwnames; name_idx++) {
- err = v9fs_co_name_to_path(pdu, &dpath, wnames[name_idx].data, &path);
- if (err < 0) {
- goto out;
- }
- err = v9fs_co_lstat(pdu, &path, &stbuf);
- if (err < 0) {
- goto out;
+ if (not_same_qid(&pdu->s->root_qid, &qid) ||
+ strcmp("..", wnames[name_idx].data)) {
+ err = v9fs_co_name_to_path(pdu, &dpath, wnames[name_idx].data,
+ &path);
+ if (err < 0) {
+ goto out;
+ }
+
+ err = v9fs_co_lstat(pdu, &path, &stbuf);
+ if (err < 0) {
+ goto out;
+ }
+ stat_to_qid(&stbuf, &qid);
+ v9fs_path_copy(&dpath, &path);
}
- stat_to_qid(&stbuf, &qids[name_idx]);
- v9fs_path_copy(&dpath, &path);
+ memcpy(&qids[name_idx], &qid, sizeof(qid));
}
if (fid == newfid) {
BUG_ON(fidp->fid_type != P9_FID_NONE);
diff --git a/hw/9pfs/9p.h b/hw/9pfs/9p.h
index 1a19418..589b3a5 100644
--- a/hw/9pfs/9p.h
+++ b/hw/9pfs/9p.h
@@ -219,6 +219,7 @@ typedef struct V9fsState
int32_t root_fid;
Error *migration_blocker;
V9fsConf fsconf;
+ V9fsQID root_qid;
} V9fsState;
/* 9p2000.L open flags */
--
1.9.1
- [Qemu-devel] [PATCH 00/25] Patch Round-up for stable 2.6.2, freeze on 2016-08-26, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 11/25] virtio: zero vq->inuse in virtio_reset(), Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 09/25] 9pfs: forbid . and .. in file names, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 10/25] 9pfs: handle walk of ".." in the root directory,
Michael Roth <=
- [Qemu-devel] [PATCH 12/25] virtio-balloon: discard virtqueue element on reset, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 13/25] vnc: fix qemu crash because of SIGSEGV, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 14/25] 9pfs: fix potential segfault during walk, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 15/25] scsi: mptsas: use g_new0 to allocate MPTSASRequest object, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 22/25] crypto: ensure XTS is only used with ciphers with 16 byte blocks, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 16/25] scsi: pvscsi: limit process IO loop to ring size, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 18/25] scsi-disk: change disk serial length from 20 to 36, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 17/25] qemu-char: avoid segfault if user lacks of permisson of a given logfile, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 20/25] scsi: mptconfig: fix an assert expression, Michael Roth, 2016/09/20
- [Qemu-devel] [PATCH 02/25] ui: fix refresh of VNC server surface, Michael Roth, 2016/09/20