From mboxrd@z Thu Jan 1 00:00:00 1970 From: "Aneesh Kumar K.V" Subject: Re: [PATCH v2 1/2] kvm tools: Add support for 9p2000.u Date: Wed, 03 Aug 2011 08:21:21 +0530 Message-ID: <877h6vnr6e.fsf@skywalker.in.ibm.com> References: <1312310789-22817-1-git-send-email-levinsasha928@gmail.com> Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii Cc: kvm@vger.kernel.org, mingo@elte.hu, asias.hejun@gmail.com, gorcunov@gmail.com, Sasha Levin To: Sasha Levin , penberg@kernel.org Return-path: Received: from e2.ny.us.ibm.com ([32.97.182.142]:32980 "EHLO e2.ny.us.ibm.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1753327Ab1HCCvc (ORCPT ); Tue, 2 Aug 2011 22:51:32 -0400 Received: from d01relay01.pok.ibm.com (d01relay01.pok.ibm.com [9.56.227.233]) by e2.ny.us.ibm.com (8.14.4/8.13.1) with ESMTP id p732U5XR014429 for ; Tue, 2 Aug 2011 22:30:05 -0400 Received: from d01av04.pok.ibm.com (d01av04.pok.ibm.com [9.56.224.64]) by d01relay01.pok.ibm.com (8.13.8/8.13.8/NCO v10.0) with ESMTP id p732pVrs209396 for ; Tue, 2 Aug 2011 22:51:31 -0400 Received: from d01av04.pok.ibm.com (loopback [127.0.0.1]) by d01av04.pok.ibm.com (8.14.4/8.13.1/NCO v10.0 AVout) with ESMTP id p732pUPT020090 for ; Tue, 2 Aug 2011 22:51:31 -0400 In-Reply-To: <1312310789-22817-1-git-send-email-levinsasha928@gmail.com> Sender: kvm-owner@vger.kernel.org List-ID: On Tue, 2 Aug 2011 21:46:28 +0300, Sasha Levin wrote: > This patch adds support for the UNIX extensions to 9p2000. > > Supporting thses extensions allow us to transperantly mount UNIX directories > without missing features such as symlinks. > > Signed-off-by: Sasha Levin Reviewed-by: Aneesh Kumar K.V > --- > tools/kvm/include/kvm/virtio-9p.h | 4 +- > tools/kvm/virtio/9p-pdu.c | 6 ++- > tools/kvm/virtio/9p.c | 66 ++++++++++++++++++++++++++++++------ > 3 files changed, 61 insertions(+), 15 deletions(-) > > diff --git a/tools/kvm/include/kvm/virtio-9p.h b/tools/kvm/include/kvm/virtio-9p.h > index 8584f49..0e55e5c 100644 > --- a/tools/kvm/include/kvm/virtio-9p.h > +++ b/tools/kvm/include/kvm/virtio-9p.h > @@ -11,8 +11,8 @@ > #define VIRTQUEUE_NUM 128 > #define VIRTIO_P9_DEFAULT_TAG "kvm_9p" > #define VIRTIO_P9_HDR_LEN (sizeof(u32)+sizeof(u8)+sizeof(u16)) > -#define VIRTIO_P9_MAX_FID 128 > -#define VIRTIO_P9_VERSION "9P2000" > +#define VIRTIO_P9_MAX_FID 256 > +#define VIRTIO_P9_VERSION "9P2000.u" > #define MAX_TAG_LEN 32 > > struct p9_msg { > diff --git a/tools/kvm/virtio/9p-pdu.c b/tools/kvm/virtio/9p-pdu.c > index 0c454db..8ed249f 100644 > --- a/tools/kvm/virtio/9p-pdu.c > +++ b/tools/kvm/virtio/9p-pdu.c > @@ -200,13 +200,15 @@ static int virtio_p9_pdu_encode(struct p9_pdu *pdu, const char *fmt, va_list ap) > case 'S': > { > struct p9_wstat *stbuf = va_arg(ap, struct p9_wstat *); > - retval = virtio_p9_pdu_writef(pdu, "wwdQdddqssss", > + retval = virtio_p9_pdu_writef(pdu, "wwdQdddqsssssddd", > stbuf->size, stbuf->type, > stbuf->dev, &stbuf->qid, > stbuf->mode, stbuf->atime, > stbuf->mtime, stbuf->length, > stbuf->name, stbuf->uid, > - stbuf->gid, stbuf->muid); > + stbuf->gid, stbuf->muid, > + stbuf->extension, stbuf->n_uid, > + stbuf->n_gid, stbuf->n_muid); > } > break; > default: > diff --git a/tools/kvm/virtio/9p.c b/tools/kvm/virtio/9p.c > index 3b5555c..965f873 100644 > --- a/tools/kvm/virtio/9p.c > +++ b/tools/kvm/virtio/9p.c > @@ -162,7 +162,7 @@ static void virtio_p9_error_reply(struct p9_dev *p9dev, > > err_str = strerror(err); > pdu->write_offset = VIRTIO_P9_HDR_LEN; > - virtio_p9_pdu_writef(pdu, "s", err_str); > + virtio_p9_pdu_writef(pdu, "sd", err_str, err); > *outlen = pdu->write_offset; > > pdu->read_offset = sizeof(u32) + sizeof(u8); > @@ -204,7 +204,6 @@ static void virtio_p9_open(struct p9_dev *p9dev, > struct p9_qid qid; > struct p9_fid *new_fid; > > - > virtio_p9_pdu_readf(pdu, "db", &fid, &mode); > new_fid = &p9dev->fids[fid]; > > @@ -242,13 +241,14 @@ static void virtio_p9_create(struct p9_dev *p9dev, > u8 mode; > u32 perm; > char *name; > + char *ext = NULL; > u32 fid_val; > struct stat st; > struct p9_qid qid; > struct p9_fid *fid; > char full_path[PATH_MAX]; > > - virtio_p9_pdu_readf(pdu, "dsdb", &fid_val, &name, &perm, &mode); > + virtio_p9_pdu_readf(pdu, "dsdbs", &fid_val, &name, &perm, &mode, &ext); > fid = &p9dev->fids[fid_val]; > > sprintf(full_path, "%s/%s", fid->abs_path, name); > @@ -262,6 +262,14 @@ static void virtio_p9_create(struct p9_dev *p9dev, > close_fid(p9dev, fid_val); > fid->dir = dir; > fid->is_dir = 1; > + } else if (perm & P9_DMSYMLINK) { > + if (symlink(ext, full_path) < 0) > + goto err_out; > + } else if (perm & P9_DMLINK) { > + int ext_fid = atoi(ext); > + > + if (link(p9dev->fids[ext_fid].abs_path, full_path) < 0) > + goto err_out; > } else { > fd = open(full_path, omode2uflags(mode) | O_CREAT, 0777); > if (fd < 0) > @@ -277,9 +285,14 @@ static void virtio_p9_create(struct p9_dev *p9dev, > virtio_p9_pdu_writef(pdu, "Qd", &qid, 0); > *outlen = pdu->write_offset; > virtio_p9_set_reply_header(pdu, *outlen); > + > + free(name); > + free(ext); > return; > err_out: > virtio_p9_error_reply(p9dev, pdu, errno, outlen); > + free(name); > + free(ext); > return; > } > > @@ -294,7 +307,7 @@ static void virtio_p9_walk(struct p9_dev *p9dev, > u32 newfid_val; > struct p9_qid wqid; > struct p9_fid *new_fid; > - > + int ret; > > virtio_p9_pdu_readf(pdu, "ddw", &fid_val, &newfid_val, &nwname); > new_fid = &p9dev->fids[newfid_val]; > @@ -315,7 +328,9 @@ static void virtio_p9_walk(struct p9_dev *p9dev, > /* Format the new path we're 'walk'ing into */ > sprintf(tmp, "%s/%.*s", > fid->path, (int)strlen(str), str); > - if (lstat(rel_to_abs(p9dev, tmp, full_path), &st) < 0) > + > + ret = lstat(rel_to_abs(p9dev, tmp, full_path), &st); > + if (ret < 0) > goto err_out; > > st2qid(&st, &wqid); > @@ -375,12 +390,22 @@ static void virtio_p9_attach(struct p9_dev *p9dev, > virtio_p9_pdu_writef(pdu, "Q", &qid); > *outlen = pdu->write_offset; > virtio_p9_set_reply_header(pdu, *outlen); > + free(uname); > + free(aname); > return; > err_out: > + free(uname); > + free(aname); > virtio_p9_error_reply(p9dev, pdu, errno, outlen); > return; > } > > +static void virtio_p9_free_stat(struct p9_wstat *wstat) > +{ > + free(wstat->extension); > + free(wstat->name); > +} > + > static void virtio_p9_fill_stat(struct p9_dev *p9dev, const char *name, > struct stat *st, struct p9_wstat *wstat) > { > @@ -393,6 +418,17 @@ static void virtio_p9_fill_stat(struct p9_dev *p9dev, const char *name, > wstat->length = 0; > wstat->mode |= P9_DMDIR; > } > + if (S_ISLNK(st->st_mode)) { > + char tmp[PATH_MAX] = {0}, full_path[PATH_MAX] = {0}; > + > + rel_to_abs(p9dev, name, full_path); > + > + if (readlink(full_path, tmp, PATH_MAX) > 0) > + wstat->extension = strdup(tmp); > + wstat->mode |= P9_DMSYMLINK; > + } else { > + wstat->extension = NULL; > + } > > wstat->atime = st->st_atime; > wstat->mtime = st->st_mtime; > @@ -401,14 +437,20 @@ static void virtio_p9_fill_stat(struct p9_dev *p9dev, const char *name, > wstat->uid = NULL; > wstat->gid = NULL; > wstat->muid = NULL; > + wstat->n_uid = wstat->n_gid = wstat->n_muid = 0; > > - /* NOTE: size shouldn't include its own length */ > - /* size[2] type[2] dev[4] qid[13] */ > - /* mode[4] atime[4] mtime[4] length[8]*/ > - /* name[s] uid[s] gid[s] muid[s] */ > - wstat->size = 2+4+13+4+4+4+8+2+2+2+2; > + /* > + * NOTE: size shouldn't include its own length > + * size[2] type[2] dev[4] qid[13] > + * mode[4] atime[4] mtime[4] length[8] > + * name[s] uid[s] gid[s] muid[s] > + * ext[s] uid[4] gid[4] muid[4] > + */ > + wstat->size = 2+4+13+4+4+4+8+2+2+2+2+2+4+4+4; > if (wstat->name) > wstat->size += strlen(wstat->name); > + if (wstat->extension) > + wstat->size += strlen(wstat->extension); > } > > static void virtio_p9_read(struct p9_dev *p9dev, > @@ -440,6 +482,7 @@ static void virtio_p9_read(struct p9_dev *p9dev, > read = pdu->write_offset; > virtio_p9_pdu_writef(pdu, "S", &wstat); > rcount += pdu->write_offset - read; > + virtio_p9_free_stat(&wstat); > > cur = readdir(fid->dir); > } > @@ -486,6 +529,7 @@ static void virtio_p9_stat(struct p9_dev *p9dev, > > virtio_p9_pdu_writef(pdu, "wS", 0, &wstat); > *outlen = pdu->write_offset; > + virtio_p9_free_stat(&wstat); > virtio_p9_set_reply_header(pdu, *outlen); > return; > err_out: > -- > 1.7.6 >