[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-devel] [RFC] VirtFS support on Xen

[RFC] VirtFS support on Xen

# Introduction

QEMU/KVM supports file system passthrough via an interface called
VirtFS [0]. VirtFS is in turn implemented with 9pfs protocol [1] and
VirtIO transport.

Xen used to have its own implementation of file system passthrough
called XenFS, but that has been inactive for a few years. The latest
update was in 2009 [2].

This project aims to add VirtFS support on Xen. This is more
sustainable than inventing our own wheel.


Some preliminary work has been done. The original code made a lot of
assumptions that VirtFS was tied to VirtIO, which wasn't true. Patches
to disentangle VirtFS generic code and VirtIO transport have been
upstreamed. What we now need to do is to implement a Xen transport
inside QEMU.

# Linux kernel

Linux kernel has a better shape than QEMU. The generic code and
transport layers are separated cleanly. We need to add a new transport
for Xen.

# Xen toolstack

New interfaces will be added to exposed relevant configuration options
to users. In essence it is just plumbing the right options to QEMU.

# Security

Xen transport will utilise grant table to limit access from backend to
frontend. Users can use several security modes provided by QEMU.

By and large the security of VirtFS on Xen depends on the quality of
QEMU VirtFS code (this is in line with our expectation of other PV
backends in QEMU) and the particular setup of VirtFS (whether a chroot
fs-proxy is used, which security model is picked etc).

# Device type and wire format

I propose to use "virtfs" as device type. A header file named virtfs.h
shall be committed to xen.git as reference for future implementation.

The design of wire format is limited by two factors: 1) 9pfs protocol
is based on transaction -- client sends out request and expects
response, 2) the arrangement of Linux kernel 9pfs places request
buffer and response buffer on the wire at the same time.

Linux seems to be the only one among several popular UNIX / UNIX-like
systems that has in-kernel 9p protocol implementation (correct me if
I'm wrong), so I couldn't fathom what other OSes such as FreeBSD and
NetBSD would need from this wire format. But it would be safe to bet
that they would like to reuse as much code as possible and follow the
same path as Linux does.

So the conclusion so far is that it would make sense for us to follow
the Linux approach (putting two buffers on wire at the same time) to
minimise our work. Other opinions are welcome.

As for the wire format itself, I've attached a draft from my
code. It's far from complete, but it contains the wire format I

# Optimisation

The Xen trasnport can be easily extended to use multiple-page ring
should the need arise. A more sophisticated optimisation is to support
"indirect-descriptor" like interface to boost bandwidth.


[0] http://www.linux-kvm.org/page/VirtFS
[1] https://en.wikipedia.org/wiki/9P_(protocol)
[2] https://blog.xenproject.org/2009/03/26/status-of-xenfs/
[3] http://wiki.qemu.org/Documentation/9psetup
[4] http://man.cat-v.org/plan_9/5/intro


 * virtfs.h
 * Copyright (c) 2016, Wei Liu <wei.liu2@xxxxxxxxxx>


#include <xen/interface/io/ring.h>
#include <xen/interface/grant_table.h>

struct xen_virtfsif_request {
        grant_ref_t gref;      /* Reference to buffer page */
        uint16_t offset;       /* Offset within buffer page */
        uint16_t flags;        /* XEN_VIRTFSF_* */
        uint16_t id;           /* Echoed in response message. */

struct xen_virtfsif_response {
        uint16_t id;
        int16_t  status;        /* Indicate whether backend successfully copy / 
map */

/* TODO: RFC style diagrams go in here */

/* TODO: document xenstore path */
 * /local/domain/$guest/device/virtfs/$x/tag
 * /local/domain/$guest/device/virtfs/$x/ring-ref
 * /local/domain/$guest/device/virtfs/$x/event-channel

 * This is wire format for virtfs requests:
 *   Request 1: xen_virtfsif_request -- XEN_VIRTFSF_* (any flag)
 *   Request 2: xen_virtfsif_request -- if request 1 has XEN_VIRTFSF_MORE
 *   Request 3: xen_virtfsif_request -- if request 2 has XEN_VIRTFSF_MORE
 *   ...
 *   Request N: xen_virtfsif_request -- if request (N-1) has XEN_VIRTFSF_MORE,
 *                                      while itself doesn't contain
 *                                      XEN_VIRTFSF_MORE
 *  | slot 0 | slot 1 | ... | slot m | ... | slot n       |
 *  |       9p request buffer        | 9p response buffer |
 *  Grefs for 9p requests (if any) go in first half of wire format,
 *  grefs for 9p responses (if any) go in second half.

/* If this bit is set, the next slot if part of the request. */
#define _XEN_VIRTFSF_MORE (0)

 * If this bit is set, this gref is for backend to write data (9p
 * response buffer); otherwise it is for backend to read (9p request
 * buffer).
#define _XEN_VIRTFSF_WRITE (1)

                  struct xen_virtfsif_request,
                  struct xen_virtfsif_response);

#endif /* virtfs.h */

Xen-devel mailing list



Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.