diff options
Diffstat (limited to 'hw/9pfs')
-rw-r--r-- | hw/9pfs/9p-local.c | 7 | ||||
-rw-r--r-- | hw/9pfs/9p-xattr.c | 1 | ||||
-rw-r--r-- | hw/9pfs/9p.c | 25 |
3 files changed, 25 insertions, 8 deletions
diff --git a/hw/9pfs/9p-local.c b/hw/9pfs/9p-local.c index 45e9a1f9b0..f3ebca4f7a 100644 --- a/hw/9pfs/9p-local.c +++ b/hw/9pfs/9p-local.c @@ -1098,8 +1098,13 @@ static int local_name_to_path(FsContext *ctx, V9fsPath *dir_path, { if (dir_path) { v9fs_path_sprintf(target, "%s/%s", dir_path->data, name); - } else { + } else if (strcmp(name, "/")) { v9fs_path_sprintf(target, "%s", name); + } else { + /* We want the path of the export root to be relative, otherwise + * "*at()" syscalls would treat it as "/" in the host. + */ + v9fs_path_sprintf(target, "%s", "."); } return 0; } diff --git a/hw/9pfs/9p-xattr.c b/hw/9pfs/9p-xattr.c index eec160b3c2..d05c1a1c1d 100644 --- a/hw/9pfs/9p-xattr.c +++ b/hw/9pfs/9p-xattr.c @@ -108,6 +108,7 @@ ssize_t v9fs_list_xattr(FsContext *ctx, const char *path, g_free(name); close_preserve_errno(dirfd); if (xattr_len < 0) { + g_free(orig_value); return -1; } diff --git a/hw/9pfs/9p.c b/hw/9pfs/9p.c index b8c0b99358..c80ba67389 100644 --- a/hw/9pfs/9p.c +++ b/hw/9pfs/9p.c @@ -539,14 +539,15 @@ static void coroutine_fn virtfs_reset(V9fsPDU *pdu) /* Free all fids */ while (s->fid_list) { + /* Get fid */ fidp = s->fid_list; + fidp->ref++; + + /* Clunk fid */ s->fid_list = fidp->next; + fidp->clunked = 1; - if (fidp->ref) { - fidp->clunked = 1; - } else { - free_fid(pdu, fidp); - } + put_fid(pdu, fidp); } } @@ -1550,6 +1551,10 @@ static void coroutine_fn v9fs_lcreate(void *opaque) err = -ENOENT; goto out_nofid; } + if (fidp->fid_type != P9_FID_NONE) { + err = -EINVAL; + goto out; + } flags = get_dotl_openflags(pdu->s, flags); err = v9fs_co_open2(pdu, fidp, &name, gid, @@ -2153,6 +2158,10 @@ static void coroutine_fn v9fs_create(void *opaque) err = -EINVAL; goto out_nofid; } + if (fidp->fid_type != P9_FID_NONE) { + err = -EINVAL; + goto out; + } if (perm & P9_STAT_MODE_DIR) { err = v9fs_co_mkdir(pdu, fidp, &name, perm & 0777, fidp->uid, -1, &stbuf); @@ -2379,8 +2388,10 @@ static void coroutine_fn v9fs_flush(void *opaque) * Wait for pdu to complete. */ qemu_co_queue_wait(&cancel_pdu->complete, NULL); - cancel_pdu->cancelled = 0; - pdu_free(cancel_pdu); + if (!qemu_co_queue_next(&cancel_pdu->complete)) { + cancel_pdu->cancelled = 0; + pdu_free(cancel_pdu); + } } pdu_complete(pdu, 7); } |