/*
 *  xen backend driver infrastructure
 *  (c) 2008 Gerd Hoffmann <kraxel@redhat.com>
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; under version 2 of the License.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License along
 *  with this program; if not, write to the Free Software Foundation, Inc.,
 *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
 */

/*
 * TODO: add some xenbus / xenstore concepts overview here.
 */

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <inttypes.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <sys/signal.h>

#include <xs.h>
#include <xenctrl.h>
#include <xen/grant_table.h>

#include "hw.h"
#include "qemu-char.h"
#include "qemu-log.h"
#include "xen_backend.h"

/* ------------------------------------------------------------- */

/* public */
int xen_xc;
struct xs_handle *xenstore = NULL;
const char *xen_protocol;

/* private */
static TAILQ_HEAD(XenDeviceHead, XenDevice) xendevs = TAILQ_HEAD_INITIALIZER(xendevs);
static int debug = 0;

/* ------------------------------------------------------------- */

int xenstore_write_str(const char *base, const char *node, const char *val)
{
    char abspath[XEN_BUFSIZE];

    snprintf(abspath, sizeof(abspath), "%s/%s", base, node);
    if (!xs_write(xenstore, 0, abspath, val, strlen(val)))
	return -1;
    return 0;
}

char *xenstore_read_str(const char *base, const char *node)
{
    char abspath[XEN_BUFSIZE];
    unsigned int len;
    char *str, *ret = NULL;

    snprintf(abspath, sizeof(abspath), "%s/%s", base, node);
    str = xs_read(xenstore, 0, abspath, &len);
    if (str != NULL) {
        /* move to qemu-allocated memory to make sure
         * callers can savely qemu_free() stuff. */
        ret = qemu_strdup(str);
        free(str);
    }
    return ret;
}

int xenstore_write_int(const char *base, const char *node, int ival)
{
    char val[32];

    snprintf(val, sizeof(val), "%d", ival);
    return xenstore_write_str(base, node, val);
}

int xenstore_read_int(const char *base, const char *node, int *ival)
{
    char *val;
    int rc = -1;

    val = xenstore_read_str(base, node);
    if (val && 1 == sscanf(val, "%d", ival))
	rc = 0;
    qemu_free(val);
    return rc;
}

int xenstore_write_be_str(struct XenDevice *xendev, const char *node, const char *val)
{
    return xenstore_write_str(xendev->be, node, val);
}

int xenstore_write_be_int(struct XenDevice *xendev, const char *node, int ival)
{
    return xenstore_write_int(xendev->be, node, ival);
}

char *xenstore_read_be_str(struct XenDevice *xendev, const char *node)
{
    return xenstore_read_str(xendev->be, node);
}

int xenstore_read_be_int(struct XenDevice *xendev, const char *node, int *ival)
{
    return xenstore_read_int(xendev->be, node, ival);
}

char *xenstore_read_fe_str(struct XenDevice *xendev, const char *node)
{
    return xenstore_read_str(xendev->fe, node);
}

int xenstore_read_fe_int(struct XenDevice *xendev, const char *node, int *ival)
{
    return xenstore_read_int(xendev->fe, node, ival);
}

/* ------------------------------------------------------------- */

const char *xenbus_strstate(enum xenbus_state state)
{
	static const char *const name[] = {
		[ XenbusStateUnknown      ] = "Unknown",
		[ XenbusStateInitialising ] = "Initialising",
		[ XenbusStateInitWait     ] = "InitWait",
		[ XenbusStateInitialised  ] = "Initialised",
		[ XenbusStateConnected    ] = "Connected",
		[ XenbusStateClosing      ] = "Closing",
		[ XenbusStateClosed	  ] = "Closed",
	};
	return (state < ARRAY_SIZE(name)) ? name[state] : "INVALID";
}

int xen_be_set_state(struct XenDevice *xendev, enum xenbus_state state)
{
    int rc;

    rc = xenstore_write_be_int(xendev, "state", state);
    if (rc < 0)
	return rc;
    xen_be_printf(xendev, 1, "backend state: %s -> %s\n",
		  xenbus_strstate(xendev->be_state), xenbus_strstate(state));
    xendev->be_state = state;
    return 0;
}

/* ------------------------------------------------------------- */

struct XenDevice *xen_be_find_xendev(const char *type, int dom, int dev)
{
    struct XenDevice *xendev;

    TAILQ_FOREACH(xendev, &xendevs, next) {
	if (xendev->dom != dom)
	    continue;
	if (xendev->dev != dev)
	    continue;
	if (strcmp(xendev->type, type) != 0)
	    continue;
	return xendev;
    }
    return NULL;
}

/*
 * get xen backend device, allocate a new one if it doesn't exist.
 */
static struct XenDevice *xen_be_get_xendev(const char *type, int dom, int dev,
                                           struct XenDevOps *ops)
{
    struct XenDevice *xendev;
    char *dom0;

    xendev = xen_be_find_xendev(type, dom, dev);
    if (xendev)
	return xendev;

    /* init new xendev */
    xendev = qemu_mallocz(ops->size);
    xendev->type  = type;
    xendev->dom   = dom;
    xendev->dev   = dev;
    xendev->ops   = ops;

    dom0 = xs_get_domain_path(xenstore, 0);
    snprintf(xendev->be, sizeof(xendev->be), "%s/backend/%s/%d/%d",
	     dom0, xendev->type, xendev->dom, xendev->dev);
    snprintf(xendev->name, sizeof(xendev->name), "%s-%d",
	     xendev->type, xendev->dev);
    free(dom0);

    xendev->debug      = debug;
    xendev->local_port = -1;

    xendev->evtchndev = xc_evtchn_open();
    if (xendev->evtchndev < 0) {
	xen_be_printf(NULL, 0, "can't open evtchn device\n");
	qemu_free(xendev);
	return NULL;
    }
    fcntl(xc_evtchn_fd(xendev->evtchndev), F_SETFD, FD_CLOEXEC);

    if (ops->flags & DEVOPS_FLAG_NEED_GNTDEV) {
	xendev->gnttabdev = xc_gnttab_open();
	if (xendev->gnttabdev < 0) {
	    xen_be_printf(NULL, 0, "can't open gnttab device\n");
	    xc_evtchn_close(xendev->evtchndev);
	    qemu_free(xendev);
	    return NULL;
	}
    } else {
	xendev->gnttabdev = -1;
    }

    TAILQ_INSERT_TAIL(&xendevs, xendev, next);

    if (xendev->ops->alloc)
	xendev->ops->alloc(xendev);

    return xendev;
}

/*
 * release xen backend device.
 */
static struct XenDevice *xen_be_del_xendev(int dom, int dev)
{
    struct XenDevice *xendev, *xnext;

    /*
     * This is pretty much like TAILQ_FOREACH(xendev, &xendevs, next) but
     * we save the next pointer in xnext because we might free xendev.
     */
    xnext = xendevs.tqh_first;
    while (xnext) {
        xendev = xnext;
        xnext = xendev->next.tqe_next;

	if (xendev->dom != dom)
	    continue;
	if (xendev->dev != dev && dev != -1)
	    continue;

	if (xendev->ops->free)
	    xendev->ops->free(xendev);

	if (xendev->fe) {
	    char token[XEN_BUFSIZE];
	    snprintf(token, sizeof(token), "fe:%p", xendev);
	    xs_unwatch(xenstore, xendev->fe, token);
	    qemu_free(xendev->fe);
	}

	if (xendev->evtchndev >= 0)
	    xc_evtchn_close(xendev->evtchndev);
	if (xendev->gnttabdev >= 0)
	    xc_gnttab_close(xendev->gnttabdev);

	TAILQ_REMOVE(&xendevs, xendev, next);
	qemu_free(xendev);
    }
    return NULL;
}

/*
 * Sync internal data structures on xenstore updates.
 * Node specifies the changed field.  node = NULL means
 * update all fields (used for initialization).
 */
static void xen_be_backend_changed(struct XenDevice *xendev, const char *node)
{
    if (node == NULL  ||  strcmp(node, "online") == 0) {
	if (xenstore_read_be_int(xendev, "online", &xendev->online) == -1)
	    xendev->online = 0;
    }

    if (node) {
	xen_be_printf(xendev, 2, "backend update: %s\n", node);
	if (xendev->ops->backend_changed)
	    xendev->ops->backend_changed(xendev, node);
    }
}

static void xen_be_frontend_changed(struct XenDevice *xendev, const char *node)
{
    int fe_state;

    if (node == NULL  ||  strcmp(node, "state") == 0) {
	if (xenstore_read_fe_int(xendev, "state", &fe_state) == -1)
	    fe_state = XenbusStateUnknown;
	if (xendev->fe_state != fe_state)
	    xen_be_printf(xendev, 1, "frontend state: %s -> %s\n",
			  xenbus_strstate(xendev->fe_state),
			  xenbus_strstate(fe_state));
	xendev->fe_state = fe_state;
    }
    if (node == NULL  ||  strcmp(node, "protocol") == 0) {
	qemu_free(xendev->protocol);
	xendev->protocol = xenstore_read_fe_str(xendev, "protocol");
	if (xendev->protocol)
	    xen_be_printf(xendev, 1, "frontend protocol: %s\n", xendev->protocol);
    }

    if (node) {
	xen_be_printf(xendev, 2, "frontend update: %s\n", node);
	if (xendev->ops->frontend_changed)
	    xendev->ops->frontend_changed(xendev, node);
    }
}

/* ------------------------------------------------------------- */
/* Check for possible state transitions and perform them.        */

/*
 * Initial xendev setup.  Read frontend path, register watch for it.
 * Should succeed once xend finished setting up the backend device.
 *
 * Also sets initial state (-> Initializing) when done.  Which
 * only affects the xendev->be_state variable as xenbus should
 * already be put into that state by xend.
 */
static int xen_be_try_setup(struct XenDevice *xendev)
{
    char token[XEN_BUFSIZE];
    int be_state;

    if (xenstore_read_be_int(xendev, "state", &be_state) == -1) {
	xen_be_printf(xendev, 0, "reading backend state failed\n");
	return -1;
    }

    if (be_state != XenbusStateInitialising) {
	xen_be_printf(xendev, 0, "initial backend state is wrong (%s)\n",
		      xenbus_strstate(be_state));
	return -1;
    }

    xendev->fe = xenstore_read_be_str(xendev, "frontend");
    if (xendev->fe == NULL) {
	xen_be_printf(xendev, 0, "reading frontend path failed\n");
	return -1;
    }

    /* setup frontend watch */
    snprintf(token, sizeof(token), "fe:%p", xendev);
    if (!xs_watch(xenstore, xendev->fe, token)) {
	xen_be_printf(xendev, 0, "watching frontend path (%s) failed\n",
		      xendev->fe);
	return -1;
    }
    xen_be_set_state(xendev, XenbusStateInitialising);

    xen_be_backend_changed(xendev, NULL);
    xen_be_frontend_changed(xendev, NULL);
    return 0;
}

/*
 * Try initialize xendev.  Prepare everything the backend can do
 * without synchronizing with the frontend.  Fakes hotplug-status.  No
 * hotplug involved here because this is about userspace drivers, thus
 * there are kernel backend devices which could invoke hotplug.
 *
 * Goes to InitWait on success.
 */
static int xen_be_try_init(struct XenDevice *xendev)
{
    int rc = 0;

    if (!xendev->online) {
	xen_be_printf(xendev, 1, "not online\n");
	return -1;
    }

    if (xendev->ops->init)
	rc = xendev->ops->init(xendev);
    if (rc != 0) {
	xen_be_printf(xendev, 1, "init() failed\n");
	return rc;
    }

    xenstore_write_be_str(xendev, "hotplug-status", "connected");
    xen_be_set_state(xendev, XenbusStateInitWait);
    return 0;
}

/*
 * Try to connect xendev.  Depends on the frontend being ready
 * for it (shared ring and evtchn info in xenstore, state being
 * Initialised or Connected).
 *
 * Goes to Connected on success.
 */
static int xen_be_try_connect(struct XenDevice *xendev)
{
    int rc = 0;

    if (xendev->fe_state != XenbusStateInitialised  &&
	xendev->fe_state != XenbusStateConnected) {
	if (xendev->ops->flags & DEVOPS_FLAG_IGNORE_STATE) {
	    xen_be_printf(xendev, 2, "frontend not ready, ignoring\n");
	} else {
	    xen_be_printf(xendev, 2, "frontend not ready (yet)\n");
	    return -1;
	}
    }

    if (xendev->ops->connect)
	rc = xendev->ops->connect(xendev);
    if (rc != 0) {
	xen_be_printf(xendev, 0, "connect() failed\n");
	return rc;
    }

    xen_be_set_state(xendev, XenbusStateConnected);
    return 0;
}

/*
 * Teardown connection.
 *
 * Goes to Closed when done.
 */
static void xen_be_disconnect(struct XenDevice *xendev, enum xenbus_state state)
{
    if (xendev->be_state != XenbusStateClosing &&
        xendev->be_state != XenbusStateClosed  &&
        xendev->ops->disconnect)
	xendev->ops->disconnect(xendev);
    if (xendev->be_state != state)
        xen_be_set_state(xendev, state);
}

/*
 * Try to reset xendev, for reconnection by another frontend instance.
 */
static int xen_be_try_reset(struct XenDevice *xendev)
{
    if (xendev->fe_state != XenbusStateInitialising)
        return -1;

    xen_be_printf(xendev, 1, "device reset (for re-connect)\n");
    xen_be_set_state(xendev, XenbusStateInitialising);
    return 0;
}

/*
 * state change dispatcher function
 */
void xen_be_check_state(struct XenDevice *xendev)
{
    int rc = 0;

    /* frontend may request shutdown from almost anywhere */
    if (xendev->fe_state == XenbusStateClosing ||
	xendev->fe_state == XenbusStateClosed) {
	xen_be_disconnect(xendev, xendev->fe_state);
	return;
    }

    /* check for possible backend state transitions */
    for (;;) {
	switch (xendev->be_state) {
	case XenbusStateUnknown:
	    rc = xen_be_try_setup(xendev);
	    break;
	case XenbusStateInitialising:
	    rc = xen_be_try_init(xendev);
	    break;
	case XenbusStateInitWait:
	    rc = xen_be_try_connect(xendev);
	    break;
        case XenbusStateClosed:
            rc = xen_be_try_reset(xendev);
            break;
	default:
	    rc = -1;
	}
	if (rc != 0)
	    break;
    }
}

/* ------------------------------------------------------------- */

static int xenstore_scan(const char *type, int dom, struct XenDevOps *ops)
{
    struct XenDevice *xendev;
    char path[XEN_BUFSIZE], token[XEN_BUFSIZE];
    char **dev = NULL, *dom0;
    unsigned int cdev, j;

    /* setup watch */
    dom0 = xs_get_domain_path(xenstore, 0);
    snprintf(token, sizeof(token), "be:%p:%d:%p", type, dom, ops);
    snprintf(path, sizeof(path), "%s/backend/%s/%d", dom0, type, dom);
    free(dom0);
    if (!xs_watch(xenstore, path, token)) {
	xen_be_printf(NULL, 0, "xen be: watching backend path (%s) failed\n", path);
	return -1;
    }

    /* look for backends */
    dev = xs_directory(xenstore, 0, path, &cdev);
    if (!dev)
	return 0;
    for (j = 0; j < cdev; j++) {
	xendev = xen_be_get_xendev(type, dom, atoi(dev[j]), ops);
	if (xendev == NULL)
	    continue;
	xen_be_check_state(xendev);
    }
    free(dev);
    return 0;
}

static void xenstore_update_be(char *watch, char *type, int dom,
			       struct XenDevOps *ops)
{
    struct XenDevice *xendev;
    char path[XEN_BUFSIZE], *dom0;
    unsigned int len, dev;

    dom0 = xs_get_domain_path(xenstore, 0);
    len = snprintf(path, sizeof(path), "%s/backend/%s/%d", dom0, type, dom);
    free(dom0);
    if (strncmp(path, watch, len) != 0)
	return;
    if (sscanf(watch+len, "/%u/%255s", &dev, path) != 2) {
	strcpy(path, "");
	if (sscanf(watch+len, "/%u", &dev) != 1)
	    dev = -1;
    }
    if (dev == -1)
	return;

    if (0) {
	/* FIXME: detect devices being deleted from xenstore ... */
	xen_be_del_xendev(dom, dev);
    }

    xendev = xen_be_get_xendev(type, dom, dev, ops);
    if (xendev != NULL) {
	xen_be_backend_changed(xendev, path);
	xen_be_check_state(xendev);
    }
}

static void xenstore_update_fe(char *watch, struct XenDevice *xendev)
{
    char *node;
    unsigned int len;

    len = strlen(xendev->fe);
    if (strncmp(xendev->fe, watch, len) != 0)
	return;
    if (watch[len] != '/')
	return;
    node = watch + len + 1;

    xen_be_frontend_changed(xendev, node);
    xen_be_check_state(xendev);
}

static void xenstore_update(void *unused)
{
    char **vec = NULL;
    intptr_t type, ops, ptr;
    unsigned int dom, count;

    vec = xs_read_watch(xenstore, &count);
    if (vec == NULL)
	goto cleanup;

    if (sscanf(vec[XS_WATCH_TOKEN], "be:%" PRIxPTR ":%d:%" PRIxPTR,
               &type, &dom, &ops) == 3)
	xenstore_update_be(vec[XS_WATCH_PATH], (void*)type, dom, (void*)ops);
    if (sscanf(vec[XS_WATCH_TOKEN], "fe:%" PRIxPTR, &ptr) == 1)
	xenstore_update_fe(vec[XS_WATCH_PATH], (void*)ptr);

cleanup:
    qemu_free(vec);
}

static void xen_be_evtchn_event(void *opaque)
{
    struct XenDevice *xendev = opaque;
    evtchn_port_t port;

    port = xc_evtchn_pending(xendev->evtchndev);
    if (port != xendev->local_port) {
	xen_be_printf(xendev, 0, "xc_evtchn_pending returned %d (expected %d)\n",
		      port, xendev->local_port);
	return;
    }
    xc_evtchn_unmask(xendev->evtchndev, port);

    if (xendev->ops->event)
	xendev->ops->event(xendev);
}

/* -------------------------------------------------------------------- */

int xen_be_init(void)
{
    xenstore = xs_daemon_open();
    if (!xenstore) {
	xen_be_printf(NULL, 0, "can't connect to xenstored\n");
	return -1;
    }

    if (qemu_set_fd_handler(xs_fileno(xenstore), xenstore_update, NULL, NULL) < 0)
	goto err;

    xen_xc = xc_interface_open();
    if (xen_xc == -1) {
	xen_be_printf(NULL, 0, "can't open xen interface\n");
	goto err;
    }
    return 0;

err:
    qemu_set_fd_handler(xs_fileno(xenstore), NULL, NULL, NULL);
    xs_daemon_close(xenstore);
    xenstore = NULL;

    return -1;
}

int xen_be_register(const char *type, struct XenDevOps *ops)
{
    return xenstore_scan(type, xen_domid, ops);
}

int xen_be_bind_evtchn(struct XenDevice *xendev)
{
    if (xendev->local_port != -1)
	return 0;
    xendev->local_port = xc_evtchn_bind_interdomain
	(xendev->evtchndev, xendev->dom, xendev->remote_port);
    if (xendev->local_port == -1) {
	xen_be_printf(xendev, 0, "xc_evtchn_bind_interdomain failed\n");
	return -1;
    }
    xen_be_printf(xendev, 2, "bind evtchn port %d\n", xendev->local_port);
    qemu_set_fd_handler(xc_evtchn_fd(xendev->evtchndev),
			xen_be_evtchn_event, NULL, xendev);
    return 0;
}

void xen_be_unbind_evtchn(struct XenDevice *xendev)
{
    if (xendev->local_port == -1)
	return;
    qemu_set_fd_handler(xc_evtchn_fd(xendev->evtchndev), NULL, NULL, NULL);
    xc_evtchn_unbind(xendev->evtchndev, xendev->local_port);
    xen_be_printf(xendev, 2, "unbind evtchn port %d\n", xendev->local_port);
    xendev->local_port = -1;
}

int xen_be_send_notify(struct XenDevice *xendev)
{
    return xc_evtchn_notify(xendev->evtchndev, xendev->local_port);
}

/*
 * msg_level:
 *  0 == errors (stderr + logfile).
 *  1 == informative debug messages (logfile only).
 *  2 == noisy debug messages (logfile only).
 *  3 == will flood your log (logfile only).
 */
void xen_be_printf(struct XenDevice *xendev, int msg_level, const char *fmt, ...)
{
    va_list args;

    if (xendev) {
        if (msg_level > xendev->debug)
            return;
        qemu_log("xen be: %s: ", xendev->name);
        if (msg_level == 0)
            fprintf(stderr, "xen be: %s: ", xendev->name);
    } else {
        if (msg_level > debug)
            return;
        qemu_log("xen be core: ");
        if (msg_level == 0)
            fprintf(stderr, "xen be core: ");
    }
    va_start(args, fmt);
    qemu_log_vprintf(fmt, args);
    va_end(args);
    if (msg_level == 0) {
        va_start(args, fmt);
        vfprintf(stderr, fmt, args);
        va_end(args);
    }
    qemu_log_flush();
}
