* [PATCH 0/2] libxl: add PV display device driver interface @ 2017-03-23 10:10 Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 1/2] " Oleksandr Grytsov ` (2 more replies) 0 siblings, 3 replies; 11+ messages in thread From: Oleksandr Grytsov @ 2017-03-23 10:10 UTC (permalink / raw) To: xen-devel; +Cc: Oleksandr Grytsov From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> Hi all, We are working on series of PV drivers (display, sound, input etc.) and would like to add their support to libxl and xl. These patches add PV display device. PV display is based on [1] protocol. During implementation I see a lot of code duplication. This problem was mentioned in [2]. One of the solutions was to implement common parts in IDL and make them autogenerated. On my side, to minimize the copy/pasting I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. Existing PV devices implementations can be reworked to use these macros as well. Any other proposals to avoid the duplications are welcome. Thanks. [1] http://marc.info/?l=xen-devel&m=149000029128972&w=2 [2] http://marc.info/?l=xen-devel&m=145372933919792&w=2 Oleksandr Grytsov (2): libxl: add PV display device driver interface xl: add PV display device commands tools/libxl/Makefile | 2 +- tools/libxl/libxl.h | 21 ++++ tools/libxl/libxl_create.c | 1 + tools/libxl/libxl_internal.h | 228 +++++++++++++++++++++++++++++++++++ tools/libxl/libxl_types.idl | 22 +++- tools/libxl/libxl_types_internal.idl | 1 + tools/libxl/libxl_utils.h | 4 + tools/libxl/libxl_vdispl.c | 137 +++++++++++++++++++++ tools/xl/Makefile | 1 + tools/xl/xl.h | 3 + tools/xl/xl_cmdtable.c | 16 +++ tools/xl/xl_parse.c | 44 ++++++- tools/xl/xl_parse.h | 2 +- tools/xl/xl_vdispl.c | 162 +++++++++++++++++++++++++ 14 files changed, 639 insertions(+), 5 deletions(-) create mode 100644 tools/libxl/libxl_vdispl.c create mode 100644 tools/xl/xl_vdispl.c -- 2.7.4 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* [PATCH 1/2] libxl: add PV display device driver interface 2017-03-23 10:10 [PATCH 0/2] libxl: add PV display device driver interface Oleksandr Grytsov @ 2017-03-23 10:10 ` Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 2/2] xl: add PV display device commands Oleksandr Grytsov 2017-03-23 10:21 ` [PATCH 0/2] libxl: add PV display device driver interface Juergen Gross 2 siblings, 0 replies; 11+ messages in thread From: Oleksandr Grytsov @ 2017-03-23 10:10 UTC (permalink / raw) To: xen-devel; +Cc: Oleksandr Grytsov From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> Signed-off-by: Oleksandr Grytsov <oleksandr_grytsov@epam.com> --- tools/libxl/Makefile | 2 +- tools/libxl/libxl.h | 21 ++++ tools/libxl/libxl_create.c | 1 + tools/libxl/libxl_internal.h | 228 +++++++++++++++++++++++++++++++++++ tools/libxl/libxl_types.idl | 22 +++- tools/libxl/libxl_types_internal.idl | 1 + tools/libxl/libxl_utils.h | 4 + tools/libxl/libxl_vdispl.c | 137 +++++++++++++++++++++ 8 files changed, 413 insertions(+), 3 deletions(-) create mode 100644 tools/libxl/libxl_vdispl.c diff --git a/tools/libxl/Makefile b/tools/libxl/Makefile index f00d9ef..cb7c17f 100644 --- a/tools/libxl/Makefile +++ b/tools/libxl/Makefile @@ -138,7 +138,7 @@ LIBXL_OBJS = flexarray.o libxl.o libxl_create.o libxl_dm.o libxl_pci.o \ libxl_dom_suspend.o libxl_dom_save.o libxl_usb.o \ libxl_vtpm.o libxl_nic.o libxl_disk.o libxl_console.o \ libxl_cpupool.o libxl_mem.o libxl_sched.o libxl_tmem.o \ - libxl_domain.o \ + libxl_domain.o libxl_vdispl.o \ $(LIBXL_OBJS-y) LIBXL_OBJS += libxl_genid.o LIBXL_OBJS += _libxl_types.o libxl_flask.o _libxl_types_internal.o diff --git a/tools/libxl/libxl.h b/tools/libxl/libxl.h index 92f1751..a4fc304 100644 --- a/tools/libxl/libxl.h +++ b/tools/libxl/libxl.h @@ -1833,6 +1833,27 @@ libxl_device_vtpm *libxl_device_vtpm_list(libxl_ctx *ctx, uint32_t domid, int *n int libxl_device_vtpm_getinfo(libxl_ctx *ctx, uint32_t domid, libxl_device_vtpm *vtpm, libxl_vtpminfo *vtpminfo); +/* Virtual displays */ +int libxl_device_vdispl_add(libxl_ctx *ctx, uint32_t domid, + libxl_device_vdispl *displ, + const libxl_asyncop_how *ao_how) + LIBXL_EXTERNAL_CALLERS_ONLY; +int libxl_device_vdispl_remove(libxl_ctx *ctx, uint32_t domid, + libxl_device_vdispl *vdispl, + const libxl_asyncop_how *ao_how) + LIBXL_EXTERNAL_CALLERS_ONLY; +int libxl_device_vdispl_destroy(libxl_ctx *ctx, uint32_t domid, + libxl_device_vdispl *vdispl, + const libxl_asyncop_how *ao_how) + LIBXL_EXTERNAL_CALLERS_ONLY; + +libxl_device_vdispl *libxl_device_vdispl_list(libxl_ctx *ctx, uint32_t domid, + int *num); +void libxl_device_vdispl_list_free(libxl_device_vdispl* list, int num); +int libxl_device_vdispl_getinfo(libxl_ctx *ctx, uint32_t domid, + libxl_device_vdispl *vdispl, + libxl_vdisplinfo *vdisplinfo); + /* Keyboard */ int libxl_device_vkb_add(libxl_ctx *ctx, uint32_t domid, libxl_device_vkb *vkb, const libxl_asyncop_how *ao_how) diff --git a/tools/libxl/libxl_create.c b/tools/libxl/libxl_create.c index e741b9a..19e0683 100644 --- a/tools/libxl/libxl_create.c +++ b/tools/libxl/libxl_create.c @@ -1445,6 +1445,7 @@ const struct libxl_device_type *device_type_tbl[] = { &libxl__usbdev_devtype, &libxl__pcidev_devtype, &libxl__dtdev_devtype, + &libxl__vdispl_devtype, NULL }; diff --git a/tools/libxl/libxl_internal.h b/tools/libxl/libxl_internal.h index 5bbede5..787bebb 100644 --- a/tools/libxl/libxl_internal.h +++ b/tools/libxl/libxl_internal.h @@ -3465,6 +3465,233 @@ _hidden void libxl__bootloader_run(libxl__egc*, libxl__bootloader_state *st); LIBXL_DEFINE_DEVICE_REMOVE_EXT(type, type, remove, 0) \ LIBXL_DEFINE_DEVICE_REMOVE_EXT(type, type, destroy, 1) +#define LIBXL_DEFINE_DEVICE_COMMIT(type) \ + static int libxl__device_##type##_commit(libxl__egc *egc, \ + uint32_t domid, libxl_device_##type *type, \ + flexarray_t *front, flexarray_t *back, \ + libxl__ao_device *aodev, int rc) \ + { \ + STATE_AO_GC(aodev->ao); \ + libxl__device *device; \ + xs_transaction_t t = XBT_NULL; \ + libxl_domain_config d_config; \ + libxl__domain_userdata_lock *lock = NULL; \ + \ + libxl_domain_config_init(&d_config); \ + \ + if (rc) goto out; \ + \ + if (aodev->update_json) { \ + lock = libxl__lock_domain_userdata(gc, domid); \ + if (!lock) { rc = ERROR_LOCK_FAIL; goto out; } \ + \ + rc = libxl__get_domain_configuration(gc, domid, &d_config); \ + if (rc) goto out; \ + \ + DEVICE_ADD(type, type##s, domid, type, \ + COMPARE_DEVID, &d_config); \ + \ + rc = libxl__dm_check_start(gc, &d_config, domid); \ + if (rc) goto out; \ + } \ + \ + GCNEW(device); \ + rc = libxl__device_from_##type(gc, domid, type, device); \ + if ( rc != 0 ) goto out; \ + \ + for (;;) { \ + rc = libxl__xs_transaction_start(gc, &t); \ + if (rc) goto out; \ + \ + rc = libxl__device_exists(gc, t, device); \ + if (rc < 0) goto out; \ + if (rc == 1) { \ + LOGD(ERROR, domid, "device already exists in xenstore");\ + aodev->action = LIBXL__DEVICE_ACTION_ADD; \ + rc = ERROR_DEVICE_EXISTS; \ + goto out; \ + } \ + \ + if (aodev->update_json) { \ + rc = libxl__set_domain_configuration(gc, domid, \ + &d_config); \ + if (rc) goto out; \ + } \ + \ + libxl__device_generic_add(gc, t, device, \ + libxl__xs_kvs_of_flexarray(gc, back), \ + libxl__xs_kvs_of_flexarray(gc, front), \ + NULL); \ + \ + rc = libxl__xs_transaction_commit(gc, &t); \ + if (rc < 0) { rc = ERROR_FAIL; goto out; } \ + if (!rc) break; \ + } \ + \ + aodev->dev = device; \ + aodev->action = LIBXL__DEVICE_ACTION_ADD; \ + libxl__wait_device_connection(egc, aodev); \ + rc = 0; \ + \ + out: \ + libxl__xs_transaction_abort(gc, &t); \ + if (lock) libxl__unlock_domain_userdata(lock); \ + libxl_domain_config_dispose(&d_config); \ + aodev->rc = rc; \ + if(rc) aodev->callback(egc, aodev); \ + return rc; \ + } + +#define LIBXL_DEFINE_DEVICE_LIST_GET(type) \ + libxl_device_##type *libxl_device_##type##_list(libxl_ctx *ctx, \ + uint32_t domid, \ + int *num) \ + { \ + GC_INIT(ctx); \ + \ + libxl_device_##type* types = NULL; \ + libxl_device_##type* r = NULL; \ + libxl_device_##type* type; \ + char *libxl_path; \ + char** dir = NULL; \ + unsigned int ndirs = 0; \ + int rc; \ + \ + *num = 0; \ + \ + libxl_path = GCSPRINTF("%s/device/%s", \ + libxl__xs_libxl_path(gc, domid), #type); \ + \ + dir = libxl__xs_directory(gc, XBT_NULL, libxl_path, &ndirs); \ + \ + if (dir && ndirs) { \ + types = malloc(sizeof(*types) * ndirs); \ + libxl_device_##type* end = types + ndirs; \ + \ + for(type = types; type < end; ++type, ++dir) { \ + const char* be_path = libxl__xs_read(gc, XBT_NULL, \ + GCSPRINTF("%s/%s/backend", libxl_path, *dir)); \ + \ + libxl_device_##type##_init(type); \ + \ + type->devid = atoi(*dir); \ + \ + rc = libxl__backendpath_parse_domid(gc, be_path, \ + &type->backend_domid); \ + if (rc) goto out; \ + } \ + } \ + \ + *num = ndirs; \ + r = types; \ + types = NULL; \ + \ + out: \ + if (types) { \ + for(; type >= types; --type) { \ + libxl_device_##type##_dispose(type); \ + } \ + free(types); \ + } \ + \ + GC_FREE; \ + \ + return r; \ + } + +#define LIBXL_DEFINE_DEVICE_LIST_FREE(type) \ + void libxl_device_##type##_list_free(libxl_device_##type* list, \ + int nr) \ + { \ + int i; \ + for (i = 0; i < nr; i++) { \ + libxl_device_##type##_dispose(&list[i]); \ + } \ + free(list); \ + } + +#define LIBXL_DEFINE_DEVID_TO_DEVICE(type) \ + int libxl_devid_to_device_##type(libxl_ctx *ctx, \ + uint32_t domid, \ + int devid, \ + libxl_device_##type *type) \ + { \ + libxl_device_##type *types = NULL; \ + int n, i; \ + int rc; \ + \ + libxl_device_##type##_init(type); \ + \ + types = libxl_device_##type##_list(ctx, domid, &n); \ + if (!types) { rc = ERROR_NOTFOUND; goto out; } \ + \ + for (i = 0; i < n; ++i) { \ + if (devid == types[i].devid) { \ + type->backend_domid = types[i].backend_domid; \ + type->devid = types[i].devid; \ + rc = 0; \ + goto out; \ + } \ + } \ + \ + rc = ERROR_NOTFOUND; \ + \ + out: \ + if (types) { \ + libxl_device_##type##_list_free(types, n); \ + } \ + return rc; \ + } + +#define LIBXL_DEFINE_DEVICE_GETINFO(type) \ + int libxl_device_##type##_getinfo(libxl_ctx *ctx, \ + uint32_t domid, \ + libxl_device_##type *type, \ + libxl_##type##info *info) \ + { \ + GC_INIT(ctx); \ + char *libxl_path, *dompath, *devpath; \ + char *val; \ + int rc; \ + \ + libxl_##type##info_init(info); \ + dompath = libxl__xs_get_dompath(gc, domid); \ + info->devid = type->devid; \ + \ + devpath = GCSPRINTF("%s/device/"#type"/%d", \ + dompath, info->devid); \ + libxl_path = GCSPRINTF("%s/device/"#type"/%d", \ + libxl__xs_libxl_path(gc, domid), \ + info->devid); \ + info->backend = xs_read(ctx->xsh, XBT_NULL, \ + GCSPRINTF("%s/backend", libxl_path), \ + NULL); \ + if (!info->backend) { rc = ERROR_FAIL; goto out; } \ + \ + rc = libxl__backendpath_parse_domid(gc, info->backend, \ + &info->backend_id); \ + if (rc) { goto out; } \ + \ + val = libxl__xs_read(gc, XBT_NULL, \ + GCSPRINTF("%s/state", devpath)); \ + info->state = val ? strtoul(val, NULL, 10) : -1; \ + \ + info->frontend = xs_read(ctx->xsh, XBT_NULL, \ + GCSPRINTF("%s/frontend", libxl_path), \ + NULL); \ + info->frontend_id = domid; \ + \ + rc = libxl__device_##type##_getinfo(gc, ctx->xsh, \ + libxl_path, info); \ + if (rc) { goto out; } \ + \ + rc = 0; \ + \ + out: \ + GC_FREE; \ + return rc; \ + } + struct libxl_device_type { char *type; int skip_attach; /* Skip entry in domcreate_attach_devices() if 1 */ @@ -3524,6 +3751,7 @@ extern const struct libxl_device_type libxl__vtpm_devtype; extern const struct libxl_device_type libxl__usbctrl_devtype; extern const struct libxl_device_type libxl__usbdev_devtype; extern const struct libxl_device_type libxl__pcidev_devtype; +extern const struct libxl_device_type libxl__vdispl_devtype; extern const struct libxl_device_type *device_type_tbl[]; diff --git a/tools/libxl/libxl_types.idl b/tools/libxl/libxl_types.idl index a612d1f..46845f0 100644 --- a/tools/libxl/libxl_types.idl +++ b/tools/libxl/libxl_types.idl @@ -690,7 +690,14 @@ libxl_device_vtpm = Struct("device_vtpm", [ ("backend_domname", string), ("devid", libxl_devid), ("uuid", libxl_uuid), -]) + ]) + +libxl_device_vdispl = Struct("device_vdispl", [ + ("backend_domid", libxl_domid), + ("backend_domname", string), + ("devid", libxl_devid), + ("be_alloc", bool), + ]) libxl_device_channel = Struct("device_channel", [ ("backend_domid", libxl_domid), @@ -702,7 +709,7 @@ libxl_device_channel = Struct("device_channel", [ ("pty", None), ("socket", Struct(None, [("path", string)])), ])), -]) + ]) libxl_domain_config = Struct("domain_config", [ ("c_info", libxl_domain_create_info), @@ -716,6 +723,7 @@ libxl_domain_config = Struct("domain_config", [ ("vfbs", Array(libxl_device_vfb, "num_vfbs")), ("vkbs", Array(libxl_device_vkb, "num_vkbs")), ("vtpms", Array(libxl_device_vtpm, "num_vtpms")), + ("vdispls", Array(libxl_device_vdispl, "num_vdispls")), # a channel manifests as a console with a name, # see docs/misc/channels.txt ("channels", Array(libxl_device_channel, "num_channels")), @@ -812,6 +820,16 @@ libxl_physinfo = Struct("physinfo", [ ("cap_hvm_directio", bool), ], dir=DIR_OUT) +libxl_vdisplinfo = Struct("vdisplinfo", [ + ("backend", string), + ("backend_id", uint32), + ("frontend", string), + ("frontend_id", uint32), + ("devid", libxl_devid), + ("state", integer), + ("be_alloc", bool), + ], dir=DIR_OUT) + # NUMA node characteristics: size and free are how much memory it has, and how # much of it is free, respectively. dists is an array of distances from this # node to each other node. diff --git a/tools/libxl/libxl_types_internal.idl b/tools/libxl/libxl_types_internal.idl index 82e5c07..cdef4d3 100644 --- a/tools/libxl/libxl_types_internal.idl +++ b/tools/libxl/libxl_types_internal.idl @@ -25,6 +25,7 @@ libxl__device_kind = Enumeration("device_kind", [ (8, "VTPM"), (9, "VUSB"), (10, "QUSB"), + (11, "VDISPL") ]) libxl__console_backend = Enumeration("console_backend", [ diff --git a/tools/libxl/libxl_utils.h b/tools/libxl/libxl_utils.h index 25773d8..9e743dc 100644 --- a/tools/libxl/libxl_utils.h +++ b/tools/libxl/libxl_utils.h @@ -78,6 +78,10 @@ int libxl_devid_to_device_vtpm(libxl_ctx *ctx, uint32_t domid, int devid, libxl_device_vtpm *vtpm); int libxl_devid_to_device_usbctrl(libxl_ctx *ctx, uint32_t domid, int devid, libxl_device_usbctrl *usbctrl); + +int libxl_devid_to_device_vdispl(libxl_ctx *ctx, uint32_t domid, + int devid, libxl_device_vdispl *vdispl); + int libxl_ctrlport_to_device_usbdev(libxl_ctx *ctx, uint32_t domid, int ctrl, int port, libxl_device_usbdev *usbdev); diff --git a/tools/libxl/libxl_vdispl.c b/tools/libxl/libxl_vdispl.c new file mode 100644 index 0000000..869aaa1 --- /dev/null +++ b/tools/libxl/libxl_vdispl.c @@ -0,0 +1,137 @@ +/* + * Copyright (C) 2016 EPAM Systems Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published + * by the Free Software Foundation; version 2.1 only. with the special + * exception on linking described in file 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 Lesser General Public License for more details. + */ + +#include "libxl_osdeps.h" + +#include "libxl_internal.h" + +static int libxl__device_vdispl_setdefault(libxl__gc *gc, domid_t domid, + libxl_device_vdispl *vdispl) +{ + int rc; + + rc = libxl__resolve_domid(gc, vdispl->backend_domname, + &vdispl->backend_domid); + + if (vdispl->devid == -1) { + vdispl->devid = libxl__device_nextid(gc, domid, + (char*)libxl__device_kind_to_string(LIBXL__DEVICE_KIND_VDISPL)); + } + + return rc; +} + +static int libxl__device_from_vdispl(libxl__gc *gc, uint32_t domid, + libxl_device_vdispl *vdispl, + libxl__device *device) +{ + device->backend_devid = vdispl->devid; + device->backend_domid = vdispl->backend_domid; + device->backend_kind = LIBXL__DEVICE_KIND_VDISPL; + device->devid = vdispl->devid; + device->domid = domid; + device->kind = LIBXL__DEVICE_KIND_VDISPL; + + return 0; +} + +LIBXL_DEFINE_DEVICE_COMMIT(vdispl) + +static void libxl__device_vdispl_add(libxl__egc *egc, uint32_t domid, + libxl_device_vdispl *vdispl, + libxl__ao_device *aodev) +{ + STATE_AO_GC(aodev->ao); + flexarray_t *front; + flexarray_t *back; + int rc; + + rc = libxl__device_vdispl_setdefault(gc, domid, vdispl); + if (rc) goto out; + + front = flexarray_make(gc, 16, 1); + back = flexarray_make(gc, 16, 1); + + flexarray_append(back, "frontend-id"); + flexarray_append(back, GCSPRINTF("%d", domid)); + flexarray_append(back, "online"); + flexarray_append(back, "1"); + flexarray_append(back, "state"); + flexarray_append(back, GCSPRINTF("%d", XenbusStateInitialising)); + flexarray_append(back, "handle"); + flexarray_append(back, GCSPRINTF("%d", vdispl->devid)); + + flexarray_append(front, "backend-id"); + flexarray_append(front, GCSPRINTF("%d", vdispl->backend_domid)); + flexarray_append(front, "state"); + flexarray_append(front, GCSPRINTF("%d", XenbusStateInitialising)); + flexarray_append(front, "handle"); + flexarray_append(front, GCSPRINTF("%d", vdispl->devid)); + flexarray_append(front, "be_alloc"); + flexarray_append(front, GCSPRINTF("%d", vdispl->be_alloc)); + +out: + libxl__device_vdispl_commit(egc, domid, vdispl, front, back, aodev, rc); +} + +static int libxl__device_vdispl_getinfo(libxl__gc *gc, struct xs_handle *xsh, + const char* libxl_path, + libxl_vdisplinfo *info) +{ + char *val; + + val = libxl__xs_read(gc, XBT_NULL, GCSPRINTF("%s/be_alloc", libxl_path)); + info->be_alloc = val ? strtoul(val, NULL, 10) : 0; + + return 0; +} + +static void libxl__update_config_vdispl(libxl__gc *gc, void *dst, void *src) +{ + libxl_device_vdispl *d, *s; + + d = (libxl_device_vdispl*)dst; + s = (libxl_device_vdispl*)src; + + d->devid = s->devid; + d->be_alloc = s->be_alloc; +} + +static int libxl_device_vdispl_compare(libxl_device_vdispl *d1, + libxl_device_vdispl *d2) +{ + return COMPARE_DEVID(d1, d2); +} + +LIBXL_DEFINE_DEVICE_ADD(vdispl) +static LIBXL_DEFINE_DEVICES_ADD(vdispl) +LIBXL_DEFINE_DEVICE_REMOVE(vdispl) + +LIBXL_DEFINE_DEVICE_LIST_GET(vdispl) +LIBXL_DEFINE_DEVICE_LIST_FREE(vdispl) + +LIBXL_DEFINE_DEVID_TO_DEVICE(vdispl) +LIBXL_DEFINE_DEVICE_GETINFO(vdispl) + +DEFINE_DEVICE_TYPE_STRUCT(vdispl, + .update_config = libxl__update_config_vdispl +); + +/* + * Local variables: + * mode: C + * c-basic-offset: 4 + * indent-tabs-mode: nil + * End: + */ -- 2.7.4 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH 2/2] xl: add PV display device commands 2017-03-23 10:10 [PATCH 0/2] libxl: add PV display device driver interface Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 1/2] " Oleksandr Grytsov @ 2017-03-23 10:10 ` Oleksandr Grytsov 2017-03-23 10:21 ` [PATCH 0/2] libxl: add PV display device driver interface Juergen Gross 2 siblings, 0 replies; 11+ messages in thread From: Oleksandr Grytsov @ 2017-03-23 10:10 UTC (permalink / raw) To: xen-devel; +Cc: Oleksandr Grytsov From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> Signed-off-by: Oleksandr Grytsov <oleksandr_grytsov@epam.com> --- tools/xl/Makefile | 1 + tools/xl/xl.h | 3 + tools/xl/xl_cmdtable.c | 16 +++++ tools/xl/xl_parse.c | 44 +++++++++++++- tools/xl/xl_parse.h | 2 +- tools/xl/xl_vdispl.c | 162 +++++++++++++++++++++++++++++++++++++++++++++++++ 6 files changed, 226 insertions(+), 2 deletions(-) create mode 100644 tools/xl/xl_vdispl.c diff --git a/tools/xl/Makefile b/tools/xl/Makefile index e16f877..5c784b5 100644 --- a/tools/xl/Makefile +++ b/tools/xl/Makefile @@ -21,6 +21,7 @@ XL_OBJS += xl_vtpm.o xl_block.o xl_nic.o xl_usb.o XL_OBJS += xl_sched.o xl_pci.o xl_vcpu.o xl_cdrom.o xl_mem.o XL_OBJS += xl_psr.o xl_info.o xl_console.o xl_misc.o XL_OBJS += xl_vmcontrol.o xl_saverestore.o xl_migrate.o +XL_OBJS += xl_vdispl.o $(XL_OBJS): CFLAGS += $(CFLAGS_libxentoollog) $(XL_OBJS): CFLAGS += $(CFLAGS_XL) diff --git a/tools/xl/xl.h b/tools/xl/xl.h index 1ad0726..370a0d4 100644 --- a/tools/xl/xl.h +++ b/tools/xl/xl.h @@ -165,6 +165,9 @@ int main_blockdetach(int argc, char **argv); int main_vtpmattach(int argc, char **argv); int main_vtpmlist(int argc, char **argv); int main_vtpmdetach(int argc, char **argv); +int main_vdisplattach(int argc, char **argv); +int main_vdispllist(int argc, char **argv); +int main_vdispldetach(int argc, char **argv); int main_usbctrl_attach(int argc, char **argv); int main_usbctrl_detach(int argc, char **argv); int main_usbdev_attach(int argc, char **argv); diff --git a/tools/xl/xl_cmdtable.c b/tools/xl/xl_cmdtable.c index 1219b33..1050dc1 100644 --- a/tools/xl/xl_cmdtable.c +++ b/tools/xl/xl_cmdtable.c @@ -372,6 +372,22 @@ struct cmd_spec cmd_table[] = { "Destroy a domain's virtual TPM device", "<Domain> <DevId|uuid>", }, + { "vdispl-attach", + &main_vdisplattach, 1, 1, + "Create a new virtual display device", + "<Domain> [devId=<Device>] [backend=<BackDomain>] [beAlloc=<BackAlloc>]", + " BackAlloc - set to 1 to allow backend allocated display buffers" + }, + { "vdispl-list", + &main_vdispllist, 0, 0, + "List virtual display devices for a domain", + "<Domain(s)>", + }, + { "vdispl-detach", + &main_vdispldetach, 0, 1, + "Destroy a domain's virtual display device", + "<Domain> <DevId>", + }, { "uptime", &main_uptime, 0, 0, "Print uptime for all/some domains", diff --git a/tools/xl/xl_parse.c b/tools/xl/xl_parse.c index 1ef0c27..6d378ed 100644 --- a/tools/xl/xl_parse.c +++ b/tools/xl/xl_parse.c @@ -707,6 +707,25 @@ int parse_usbdev_config(libxl_device_usbdev *usbdev, char *token) return 0; } +int parse_vdispl_config(libxl_device_vdispl *vdispl, char *token) +{ + char *oparg; + + if (MATCH_OPTION("backend", token, oparg)) { + vdispl->backend_domid = find_domain(oparg); + vdispl->backend_domname = strdup(oparg); + } else if (MATCH_OPTION("devId", token, oparg)) { + vdispl->devid = atoi(oparg); + } else if (MATCH_OPTION("beAlloc", token, oparg)) { + vdispl->be_alloc = strtoul(oparg, NULL, 0); + } else { + fprintf(stderr, "Unknown string `%s' in vdispl spec\n", token); + return 1; + } + + return 0; +} + void parse_config_data(const char *config_source, const char *config_data, int config_len, @@ -716,7 +735,7 @@ void parse_config_data(const char *config_source, long l, vcpus = 0; XLU_Config *config; XLU_ConfigList *cpus, *vbds, *nics, *pcis, *cvfbs, *cpuids, *vtpms, - *usbctrls, *usbdevs; + *usbctrls, *usbdevs, *vdispls; XLU_ConfigList *channels, *ioports, *irqs, *iomem, *viridian, *dtdevs; int num_ioports, num_irqs, num_iomem, num_cpus, num_viridian; int pci_power_mgmt = 0; @@ -1295,6 +1314,29 @@ void parse_config_data(const char *config_source, } } + if (!xlu_cfg_get_list(config, "vdispl", &vdispls, 0, 0)) { + d_config->num_vdispls = 0; + d_config->vdispls = NULL; + while ((buf = xlu_cfg_get_listitem(vdispls, d_config->num_vdispls)) != NULL) { + libxl_device_vdispl *vdispl; + char * buf2 = strdup(buf); + char *p; + vdispl = ARRAY_EXTEND_INIT(d_config->vdispls, + d_config->num_vdispls, + libxl_device_vdispl_init); + p = strtok (buf2, ","); + while (p != NULL) + { + while (*p == ' ') p++; + if (parse_vdispl_config(vdispl, p)) { + exit(1); + } + p = strtok (NULL, ","); + } + free(buf2); + } + } + if (!xlu_cfg_get_list (config, "channel", &channels, 0, 0)) { d_config->num_channels = 0; d_config->channels = NULL; diff --git a/tools/xl/xl_parse.h b/tools/xl/xl_parse.h index db8bc3f..cc459fb 100644 --- a/tools/xl/xl_parse.h +++ b/tools/xl/xl_parse.h @@ -33,7 +33,7 @@ int parse_usbctrl_config(libxl_device_usbctrl *usbctrl, char *token); int parse_usbdev_config(libxl_device_usbdev *usbdev, char *token); int parse_cpurange(const char *cpu, libxl_bitmap *cpumap); int parse_nic_config(libxl_device_nic *nic, XLU_Config **config, char *token); - +int parse_vdispl_config(libxl_device_vdispl *vdispl, char *token); int match_option_size(const char *prefix, size_t len, char *arg, char **argopt); diff --git a/tools/xl/xl_vdispl.c b/tools/xl/xl_vdispl.c new file mode 100644 index 0000000..4df90c9 --- /dev/null +++ b/tools/xl/xl_vdispl.c @@ -0,0 +1,162 @@ +/* + * Copyright (C) 2016 EPAM Systems Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published + * by the Free Software Foundation; version 2.1 only. with the special + * exception on linking described in file 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 Lesser General Public License for more details. + */ + +#include <stdlib.h> + +#include <libxl.h> +#include <libxl_utils.h> +#include <libxlutil.h> + +#include "xl.h" +#include "xl_utils.h" +#include "xl_parse.h" + +int main_vdisplattach(int argc, char **argv) +{ + int opt; + int rc; + char *oparg; + uint32_t domid; + libxl_device_vdispl vdispl; + + SWITCH_FOREACH_OPT(opt, "", NULL, "vdispl-attach", 1) { + /* No options */ + } + + libxl_device_vdispl_init(&vdispl); + domid = find_domain(argv[optind++]); + + for (argv += optind, argc -= optind; argc > 0; ++argv, --argc) { + if (MATCH_OPTION("devId", *argv, oparg)) { + vdispl.devid = atoi(oparg); + } else if (MATCH_OPTION("backend", *argv, oparg)) { + vdispl.backend_domid = find_domain(oparg); + replace_string(&vdispl.backend_domname, oparg); + } else if (MATCH_OPTION("beAlloc", *argv, oparg)) { + vdispl.be_alloc = strtoul(oparg, NULL, 0); + } else { + fprintf(stderr, "unrecognized argument `%s'\n", *argv); + rc = 1; + goto out; + } + } + + if (dryrun_only) { + char *json = libxl_device_vdispl_to_json(ctx, &vdispl); + printf("vdispl: %s\n", json); + free(json); + goto out; + } + + if (libxl_device_vdispl_add(ctx, domid, &vdispl, 0)) { + fprintf(stderr, "libxl_device_vdispl_add failed.\n"); + rc = ERROR_FAIL; + } + + rc = 0; + +out: + libxl_device_vdispl_dispose(&vdispl); + return rc; +} + +int main_vdispllist(int argc, char **argv) +{ + int opt; + int i, n; + libxl_device_vdispl *vdispls; + libxl_vdisplinfo vdisplinfo; + + SWITCH_FOREACH_OPT(opt, "", NULL, "vdispl-list", 1) { + /* No options */ + } + + /* vdisplinfo.uuid should be outputted too */ + printf("%-5s %-3s %-6s %-5s %-8s %-40s %-40s\n", + "Vdev", "BE", "handle", "state", "be-alloc", "BE-path", "FE-path"); + for (argv += optind, argc -= optind; argc > 0; --argc, ++argv) { + uint32_t domid; + + if (libxl_domain_qualifier_to_domid(ctx, *argv, &domid) < 0) { + fprintf(stderr, "%s is an invalid domain identifier\n", *argv); + continue; + } + + vdispls = libxl_device_vdispl_list(ctx, domid, &n); + + if (!vdispls) { + continue; + } + + for (i = 0; i < n; i++) { + libxl_vdisplinfo_init(&vdisplinfo); + if (libxl_device_vdispl_getinfo(ctx, domid, &vdispls[i], + &vdisplinfo) == 0) { + /* Vdev BE hdl st be-alloc BE-path FE-path*/ + printf("%-5d %-3d %-6d %-5d %-8d %-40s %-40s\n", + vdisplinfo.devid, vdisplinfo.backend_id, + vdisplinfo.frontend_id, + vdisplinfo.state, vdisplinfo.be_alloc, + vdisplinfo.backend, vdisplinfo.frontend); + } + libxl_vdisplinfo_dispose(&vdisplinfo); + } + + libxl_device_vdispl_list_free(vdispls, n); + } + return 0; +} + +int main_vdispldetach(int argc, char **argv) +{ + uint32_t domid, devid; + int opt, rc; + libxl_device_vdispl vdispl; + + SWITCH_FOREACH_OPT(opt, "", NULL, "vdispl-detach", 2) { + /* No options */ + } + + domid = find_domain(argv[optind++]); + devid = atoi(argv[optind++]); + + libxl_device_vdispl_init(&vdispl); + + if (libxl_devid_to_device_vdispl(ctx, domid, devid, &vdispl)) { + fprintf(stderr, "Error: Device %d not connected.\n", devid); + rc = ERROR_FAIL; + goto out; + } + + rc = libxl_device_vdispl_remove(ctx, domid, &vdispl, 0); + if (rc) { + fprintf(stderr, "libxl_device_vdispl_remove failed.\n"); + rc = ERROR_FAIL; + goto out; + } + + rc = 0; + +out: + libxl_device_vdispl_dispose(&vdispl); + return rc; +} + +/* + * Local variables: + * mode: C + * c-basic-offset: 4 + * indent-tabs-mode: nil + * End: + */ -- 2.7.4 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply related [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 10:10 [PATCH 0/2] libxl: add PV display device driver interface Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 1/2] " Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 2/2] xl: add PV display device commands Oleksandr Grytsov @ 2017-03-23 10:21 ` Juergen Gross 2017-03-23 11:32 ` al1img . 2 siblings, 1 reply; 11+ messages in thread From: Juergen Gross @ 2017-03-23 10:21 UTC (permalink / raw) To: Oleksandr Grytsov, xen-devel; +Cc: Oleksandr Grytsov On 23/03/17 11:10, Oleksandr Grytsov wrote: > From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> > > Hi all, > > We are working on series of PV drivers (display, sound, input etc.) and > would like to add their support to libxl and xl. These patches add PV display > device. PV display is based on [1] protocol. > > During implementation I see a lot of code duplication. This problem was > mentioned in [2]. One of the solutions was to implement common parts in IDL > and make them autogenerated. On my side, to minimize the copy/pasting > I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, > LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. > Existing PV devices implementations can be reworked to use these macros as > well. Any other proposals to avoid the duplications are welcome. Did you look into the device type framework I introduced with commit 74e857c6c7f9 and some followups? Maybe it is possible to expand this framework by adding more callbacks to struct libxl_device_type and have some common function(s) in libxl_device.c? Juergen _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 10:21 ` [PATCH 0/2] libxl: add PV display device driver interface Juergen Gross @ 2017-03-23 11:32 ` al1img . 2017-03-23 12:08 ` Juergen Gross 0 siblings, 1 reply; 11+ messages in thread From: al1img . @ 2017-03-23 11:32 UTC (permalink / raw) To: Juergen Gross; +Cc: xen-devel, Oleksandr Grytsov Hi Juergen, I've checked the mentioned commits. And I don't see how it can be done. The duplication I see it is in libxl_device_type.add and libxl_device_type.list functions for different PV devices. These functions have a lot of common code which I've tried to move to macros in my patches. 2017-03-23 12:21 GMT+02:00 Juergen Gross <jgross@suse.com>: > On 23/03/17 11:10, Oleksandr Grytsov wrote: >> From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> >> >> Hi all, >> >> We are working on series of PV drivers (display, sound, input etc.) and >> would like to add their support to libxl and xl. These patches add PV display >> device. PV display is based on [1] protocol. >> >> During implementation I see a lot of code duplication. This problem was >> mentioned in [2]. One of the solutions was to implement common parts in IDL >> and make them autogenerated. On my side, to minimize the copy/pasting >> I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, >> LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. >> Existing PV devices implementations can be reworked to use these macros as >> well. Any other proposals to avoid the duplications are welcome. > > Did you look into the device type framework I introduced with commit > 74e857c6c7f9 and some followups? Maybe it is possible to expand this > framework by adding more callbacks to struct libxl_device_type and > have some common function(s) in libxl_device.c? > > Juergen -- Best Regards, Oleksandr Grytsov. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 11:32 ` al1img . @ 2017-03-23 12:08 ` Juergen Gross 2017-03-23 14:23 ` al1img . 0 siblings, 1 reply; 11+ messages in thread From: Juergen Gross @ 2017-03-23 12:08 UTC (permalink / raw) To: al1img .; +Cc: xen-devel, Oleksandr Grytsov On 23/03/17 12:32, al1img . wrote: > Hi Juergen, > > I've checked the mentioned commits. And I don't see how it can be done. > The duplication I see it is in libxl_device_type.add and > libxl_device_type.list functions > for different PV devices. These functions have a lot of common code > which I've tried > to move to macros in my patches. Okay, here an example for replacement of LIBXL_DEFINE_DEVICE_LIST_FREE() void libxl_device_list_free(struct libxl_device_type *dt, void *list, int nr) { int i; for (i = 0; i < nr; i++) dt->dispose(list + i * dt->dev_elem_size); free(list); } BTW: exactly this pattern is to be found at the very end of libxl_retrieve_domain_configuration(). The others should be doable, too. Juergen > > 2017-03-23 12:21 GMT+02:00 Juergen Gross <jgross@suse.com>: >> On 23/03/17 11:10, Oleksandr Grytsov wrote: >>> From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> >>> >>> Hi all, >>> >>> We are working on series of PV drivers (display, sound, input etc.) and >>> would like to add their support to libxl and xl. These patches add PV display >>> device. PV display is based on [1] protocol. >>> >>> During implementation I see a lot of code duplication. This problem was >>> mentioned in [2]. One of the solutions was to implement common parts in IDL >>> and make them autogenerated. On my side, to minimize the copy/pasting >>> I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, >>> LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. >>> Existing PV devices implementations can be reworked to use these macros as >>> well. Any other proposals to avoid the duplications are welcome. >> >> Did you look into the device type framework I introduced with commit >> 74e857c6c7f9 and some followups? Maybe it is possible to expand this >> framework by adding more callbacks to struct libxl_device_type and >> have some common function(s) in libxl_device.c? >> >> Juergen > > > _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 12:08 ` Juergen Gross @ 2017-03-23 14:23 ` al1img . 2017-03-23 14:58 ` Juergen Gross 0 siblings, 1 reply; 11+ messages in thread From: al1img . @ 2017-03-23 14:23 UTC (permalink / raw) To: Juergen Gross; +Cc: xen-devel, Oleksandr Grytsov This example is clear. But still wrapper macro is required to make it visible for libxen client (xl): #define LIBXL_DEFINE_DEVICE_LIST_FREE(type) void libxl_device_##type##_list_free(libxl_device_##type* list, int nr) { libxl__device_list_free(libxl__##type##_devtype, list, nr); } Also where should this function (libxl__device_list_free) be located? libxl_device.c? Another case is getting this list: From one side each device should have its own implementation, from other side for PV devices there is common part like getting devId and backend domId and unique part like getting device specific parameters (uuid for vtpm). In this case I can do following: Implement void *libxl__device_list(struct libxl_device_type *dt, libxl_ctx *ctx, uint32_t domid, int *num) where I will get devId and backend domId. Then add get_params callback to libxl_device_type to get device specific parameters: void *libxl__device_pv_list(struct libxl_device_type *dt, libxl_ctx *ctx, uint32_t domid, int *num) { ... if (dt->get_patams) { dt->get_params(...); } } And vtpm get list may look like: libxl_device_vtpm *libxl_device_vtpm_list(libxl_ctx *ctx, uint32_t domid, int *num) { return libxl__device_list(&libxl__vtpm_devtype, ctx, domid, num); } DEFINE_DEVICE_TYPE_STRUCT(vtpm, .update_config = libxl_device_vtpm_update_config .get_params = libxl_device_vtpm_get_params ); Correct? 2017-03-23 14:08 GMT+02:00 Juergen Gross <jgross@suse.com>: > On 23/03/17 12:32, al1img . wrote: >> Hi Juergen, >> >> I've checked the mentioned commits. And I don't see how it can be done. >> The duplication I see it is in libxl_device_type.add and >> libxl_device_type.list functions >> for different PV devices. These functions have a lot of common code >> which I've tried >> to move to macros in my patches. > > Okay, here an example for replacement of LIBXL_DEFINE_DEVICE_LIST_FREE() > > void libxl_device_list_free(struct libxl_device_type *dt, > void *list, int nr) > { > int i; > > for (i = 0; i < nr; i++) > dt->dispose(list + i * dt->dev_elem_size); > free(list); > } > > BTW: exactly this pattern is to be found at the very end of > libxl_retrieve_domain_configuration(). > > The others should be doable, too. > > > Juergen > >> >> 2017-03-23 12:21 GMT+02:00 Juergen Gross <jgross@suse.com>: >>> On 23/03/17 11:10, Oleksandr Grytsov wrote: >>>> From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> >>>> >>>> Hi all, >>>> >>>> We are working on series of PV drivers (display, sound, input etc.) and >>>> would like to add their support to libxl and xl. These patches add PV display >>>> device. PV display is based on [1] protocol. >>>> >>>> During implementation I see a lot of code duplication. This problem was >>>> mentioned in [2]. One of the solutions was to implement common parts in IDL >>>> and make them autogenerated. On my side, to minimize the copy/pasting >>>> I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, >>>> LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. >>>> Existing PV devices implementations can be reworked to use these macros as >>>> well. Any other proposals to avoid the duplications are welcome. >>> >>> Did you look into the device type framework I introduced with commit >>> 74e857c6c7f9 and some followups? Maybe it is possible to expand this >>> framework by adding more callbacks to struct libxl_device_type and >>> have some common function(s) in libxl_device.c? >>> >>> Juergen >> >> >> > -- Best Regards, Oleksandr Grytsov. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 14:23 ` al1img . @ 2017-03-23 14:58 ` Juergen Gross 2017-03-23 15:55 ` al1img . 0 siblings, 1 reply; 11+ messages in thread From: Juergen Gross @ 2017-03-23 14:58 UTC (permalink / raw) To: al1img .; +Cc: xen-devel, Oleksandr Grytsov On 23/03/17 15:23, al1img . wrote: > This example is clear. But still wrapper macro is required to make it > visible for libxen client (xl): > > #define LIBXL_DEFINE_DEVICE_LIST_FREE(type) > void libxl_device_##type##_list_free(libxl_device_##type* list, int nr) > { > libxl__device_list_free(libxl__##type##_devtype, list, nr); > } Either this or we could switch to a more generic way avoiding the need to add multiple very similar functions to libxl: #define LIBXL_DEVTYPE_VTPM "vtpm" int libxl_device_list_free(const char *type, void *list, int nr) { int i; for (i = 0; device_type_tbl[i]; i++) { if (!strcmp(type, device_type_tbl[i]->type)) { libxl__device_list_free(device_type_tbl[i], list, nr); return 0; } } return ERROR_INVAL; } and let xl call it via libxl_device_list_free(LIBXL_DEVTYPE_VTPM, ...) This is subject to an Ack from the tools maintainers, of course. > > Also where should this function (libxl__device_list_free) be located? > libxl_device.c? I think so. > > Another case is getting this list: > > From one side each device should have its own implementation, from > other side for PV devices > there is common part like getting devId and backend domId and unique > part like getting > device specific parameters (uuid for vtpm). In this case I can do following: > > Implement void *libxl__device_list(struct libxl_device_type *dt, > libxl_ctx *ctx, uint32_t domid, int *num) > where I will get devId and backend domId. Then add get_params callback > to libxl_device_type to get device specific > parameters: > > void *libxl__device_pv_list(struct libxl_device_type *dt, libxl_ctx > *ctx, uint32_t domid, int *num) > { > ... > if (dt->get_patams) { > dt->get_params(...); > } > } > > And vtpm get list may look like: > > libxl_device_vtpm *libxl_device_vtpm_list(libxl_ctx *ctx, uint32_t > domid, int *num) > { > return libxl__device_list(&libxl__vtpm_devtype, ctx, domid, num); > } > > DEFINE_DEVICE_TYPE_STRUCT(vtpm, > .update_config = libxl_device_vtpm_update_config > .get_params = libxl_device_vtpm_get_params > ); > > Correct? Right. Possibly using the same trick as above. BTW: Please don't top-post. Juergen > > > 2017-03-23 14:08 GMT+02:00 Juergen Gross <jgross@suse.com>: >> On 23/03/17 12:32, al1img . wrote: >>> Hi Juergen, >>> >>> I've checked the mentioned commits. And I don't see how it can be done. >>> The duplication I see it is in libxl_device_type.add and >>> libxl_device_type.list functions >>> for different PV devices. These functions have a lot of common code >>> which I've tried >>> to move to macros in my patches. >> >> Okay, here an example for replacement of LIBXL_DEFINE_DEVICE_LIST_FREE() >> >> void libxl_device_list_free(struct libxl_device_type *dt, >> void *list, int nr) >> { >> int i; >> >> for (i = 0; i < nr; i++) >> dt->dispose(list + i * dt->dev_elem_size); >> free(list); >> } >> >> BTW: exactly this pattern is to be found at the very end of >> libxl_retrieve_domain_configuration(). >> >> The others should be doable, too. >> >> >> Juergen >> >>> >>> 2017-03-23 12:21 GMT+02:00 Juergen Gross <jgross@suse.com>: >>>> On 23/03/17 11:10, Oleksandr Grytsov wrote: >>>>> From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> >>>>> >>>>> Hi all, >>>>> >>>>> We are working on series of PV drivers (display, sound, input etc.) and >>>>> would like to add their support to libxl and xl. These patches add PV display >>>>> device. PV display is based on [1] protocol. >>>>> >>>>> During implementation I see a lot of code duplication. This problem was >>>>> mentioned in [2]. One of the solutions was to implement common parts in IDL >>>>> and make them autogenerated. On my side, to minimize the copy/pasting >>>>> I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, >>>>> LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. >>>>> Existing PV devices implementations can be reworked to use these macros as >>>>> well. Any other proposals to avoid the duplications are welcome. >>>> >>>> Did you look into the device type framework I introduced with commit >>>> 74e857c6c7f9 and some followups? Maybe it is possible to expand this >>>> framework by adding more callbacks to struct libxl_device_type and >>>> have some common function(s) in libxl_device.c? >>>> >>>> Juergen >>> >>> >>> >> > > > _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 14:58 ` Juergen Gross @ 2017-03-23 15:55 ` al1img . 2017-03-24 10:35 ` Oleksandr Grytsov 0 siblings, 1 reply; 11+ messages in thread From: al1img . @ 2017-03-23 15:55 UTC (permalink / raw) To: Juergen Gross; +Cc: xen-devel, Oleksandr Grytsov On Thu, Mar 23, 2017 at 4:58 PM, Juergen Gross <jgross@suse.com> wrote: > On 23/03/17 15:23, al1img . wrote: >> This example is clear. But still wrapper macro is required to make it >> visible for libxen client (xl): >> >> #define LIBXL_DEFINE_DEVICE_LIST_FREE(type) >> void libxl_device_##type##_list_free(libxl_device_##type* list, int nr) >> { >> libxl__device_list_free(libxl__##type##_devtype, list, nr); >> } > > Either this or we could switch to a more generic way avoiding the need > to add multiple very similar functions to libxl: > > #define LIBXL_DEVTYPE_VTPM "vtpm" > > int libxl_device_list_free(const char *type, void *list, int nr) > { > int i; > > for (i = 0; device_type_tbl[i]; i++) { > if (!strcmp(type, device_type_tbl[i]->type)) { > libxl__device_list_free(device_type_tbl[i], list, nr); > return 0; > } > } > return ERROR_INVAL; > } > > and let xl call it via libxl_device_list_free(LIBXL_DEVTYPE_VTPM, ...) > > This is subject to an Ack from the tools maintainers, of course. > >> >> Also where should this function (libxl__device_list_free) be located? >> libxl_device.c? > > I think so. > >> >> Another case is getting this list: >> >> From one side each device should have its own implementation, from >> other side for PV devices >> there is common part like getting devId and backend domId and unique >> part like getting >> device specific parameters (uuid for vtpm). In this case I can do following: >> >> Implement void *libxl__device_list(struct libxl_device_type *dt, >> libxl_ctx *ctx, uint32_t domid, int *num) >> where I will get devId and backend domId. Then add get_params callback >> to libxl_device_type to get device specific >> parameters: >> >> void *libxl__device_pv_list(struct libxl_device_type *dt, libxl_ctx >> *ctx, uint32_t domid, int *num) >> { >> ... >> if (dt->get_patams) { >> dt->get_params(...); >> } >> } >> >> And vtpm get list may look like: >> >> libxl_device_vtpm *libxl_device_vtpm_list(libxl_ctx *ctx, uint32_t >> domid, int *num) >> { >> return libxl__device_list(&libxl__vtpm_devtype, ctx, domid, num); >> } >> >> DEFINE_DEVICE_TYPE_STRUCT(vtpm, >> .update_config = libxl_device_vtpm_update_config >> .get_params = libxl_device_vtpm_get_params >> ); >> >> Correct? > > Right. Possibly using the same trick as above. > > BTW: Please don't top-post. > > > Juergen > >> >> >> 2017-03-23 14:08 GMT+02:00 Juergen Gross <jgross@suse.com>: >>> On 23/03/17 12:32, al1img . wrote: >>>> Hi Juergen, >>>> >>>> I've checked the mentioned commits. And I don't see how it can be done. >>>> The duplication I see it is in libxl_device_type.add and >>>> libxl_device_type.list functions >>>> for different PV devices. These functions have a lot of common code >>>> which I've tried >>>> to move to macros in my patches. >>> >>> Okay, here an example for replacement of LIBXL_DEFINE_DEVICE_LIST_FREE() >>> >>> void libxl_device_list_free(struct libxl_device_type *dt, >>> void *list, int nr) >>> { >>> int i; >>> >>> for (i = 0; i < nr; i++) >>> dt->dispose(list + i * dt->dev_elem_size); >>> free(list); >>> } >>> >>> BTW: exactly this pattern is to be found at the very end of >>> libxl_retrieve_domain_configuration(). >>> >>> The others should be doable, too. >>> >>> >>> Juergen >>> >>>> >>>> 2017-03-23 12:21 GMT+02:00 Juergen Gross <jgross@suse.com>: >>>>> On 23/03/17 11:10, Oleksandr Grytsov wrote: >>>>>> From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> >>>>>> >>>>>> Hi all, >>>>>> >>>>>> We are working on series of PV drivers (display, sound, input etc.) and >>>>>> would like to add their support to libxl and xl. These patches add PV display >>>>>> device. PV display is based on [1] protocol. >>>>>> >>>>>> During implementation I see a lot of code duplication. This problem was >>>>>> mentioned in [2]. One of the solutions was to implement common parts in IDL >>>>>> and make them autogenerated. On my side, to minimize the copy/pasting >>>>>> I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, >>>>>> LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. >>>>>> Existing PV devices implementations can be reworked to use these macros as >>>>>> well. Any other proposals to avoid the duplications are welcome. >>>>> >>>>> Did you look into the device type framework I introduced with commit >>>>> 74e857c6c7f9 and some followups? Maybe it is possible to expand this >>>>> framework by adding more callbacks to struct libxl_device_type and >>>>> have some common function(s) in libxl_device.c? >>>>> >>>>> Juergen >>>> >>>> >>>> >>> >> >> >> > For me the drawback of more generic way is to cast device_type to void* and back which may be used by client in improper way. Thanks. -- Best Regards, Oleksandr Grytsov. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-23 15:55 ` al1img . @ 2017-03-24 10:35 ` Oleksandr Grytsov 2017-03-27 15:10 ` Wei Liu 0 siblings, 1 reply; 11+ messages in thread From: Oleksandr Grytsov @ 2017-03-24 10:35 UTC (permalink / raw) To: Juergen Gross; +Cc: xen-devel, Oleksandr Grytsov, Ian Jackson, Wei Liu On 23.03.17 17:55, al1img . wrote: > On Thu, Mar 23, 2017 at 4:58 PM, Juergen Gross <jgross@suse.com> wrote: >> On 23/03/17 15:23, al1img . wrote: >>> This example is clear. But still wrapper macro is required to make it >>> visible for libxen client (xl): >>> >>> #define LIBXL_DEFINE_DEVICE_LIST_FREE(type) >>> void libxl_device_##type##_list_free(libxl_device_##type* list, int nr) >>> { >>> libxl__device_list_free(libxl__##type##_devtype, list, nr); >>> } >> >> Either this or we could switch to a more generic way avoiding the need >> to add multiple very similar functions to libxl: >> >> #define LIBXL_DEVTYPE_VTPM "vtpm" >> >> int libxl_device_list_free(const char *type, void *list, int nr) >> { >> int i; >> >> for (i = 0; device_type_tbl[i]; i++) { >> if (!strcmp(type, device_type_tbl[i]->type)) { >> libxl__device_list_free(device_type_tbl[i], list, nr); >> return 0; >> } >> } >> return ERROR_INVAL; >> } >> >> and let xl call it via libxl_device_list_free(LIBXL_DEVTYPE_VTPM, ...) >> >> This is subject to an Ack from the tools maintainers, of course. >> >>> >>> Also where should this function (libxl__device_list_free) be located? >>> libxl_device.c? >> >> I think so. >> >>> >>> Another case is getting this list: >>> >>> From one side each device should have its own implementation, from >>> other side for PV devices >>> there is common part like getting devId and backend domId and unique >>> part like getting >>> device specific parameters (uuid for vtpm). In this case I can do following: >>> >>> Implement void *libxl__device_list(struct libxl_device_type *dt, >>> libxl_ctx *ctx, uint32_t domid, int *num) >>> where I will get devId and backend domId. Then add get_params callback >>> to libxl_device_type to get device specific >>> parameters: >>> >>> void *libxl__device_pv_list(struct libxl_device_type *dt, libxl_ctx >>> *ctx, uint32_t domid, int *num) >>> { >>> ... >>> if (dt->get_patams) { >>> dt->get_params(...); >>> } >>> } >>> >>> And vtpm get list may look like: >>> >>> libxl_device_vtpm *libxl_device_vtpm_list(libxl_ctx *ctx, uint32_t >>> domid, int *num) >>> { >>> return libxl__device_list(&libxl__vtpm_devtype, ctx, domid, num); >>> } >>> >>> DEFINE_DEVICE_TYPE_STRUCT(vtpm, >>> .update_config = libxl_device_vtpm_update_config >>> .get_params = libxl_device_vtpm_get_params >>> ); >>> >>> Correct? >> >> Right. Possibly using the same trick as above. >> >> BTW: Please don't top-post. >> >> >> Juergen >> >>> >>> >>> 2017-03-23 14:08 GMT+02:00 Juergen Gross <jgross@suse.com>: >>>> On 23/03/17 12:32, al1img . wrote: >>>>> Hi Juergen, >>>>> >>>>> I've checked the mentioned commits. And I don't see how it can be done. >>>>> The duplication I see it is in libxl_device_type.add and >>>>> libxl_device_type.list functions >>>>> for different PV devices. These functions have a lot of common code >>>>> which I've tried >>>>> to move to macros in my patches. >>>> >>>> Okay, here an example for replacement of LIBXL_DEFINE_DEVICE_LIST_FREE() >>>> >>>> void libxl_device_list_free(struct libxl_device_type *dt, >>>> void *list, int nr) >>>> { >>>> int i; >>>> >>>> for (i = 0; i < nr; i++) >>>> dt->dispose(list + i * dt->dev_elem_size); >>>> free(list); >>>> } >>>> >>>> BTW: exactly this pattern is to be found at the very end of >>>> libxl_retrieve_domain_configuration(). >>>> >>>> The others should be doable, too. >>>> >>>> >>>> Juergen >>>> >>>>> >>>>> 2017-03-23 12:21 GMT+02:00 Juergen Gross <jgross@suse.com>: >>>>>> On 23/03/17 11:10, Oleksandr Grytsov wrote: >>>>>>> From: Oleksandr Grytsov <oleksandr_grytsov@epam.com> >>>>>>> >>>>>>> Hi all, >>>>>>> >>>>>>> We are working on series of PV drivers (display, sound, input etc.) and >>>>>>> would like to add their support to libxl and xl. These patches add PV display >>>>>>> device. PV display is based on [1] protocol. >>>>>>> >>>>>>> During implementation I see a lot of code duplication. This problem was >>>>>>> mentioned in [2]. One of the solutions was to implement common parts in IDL >>>>>>> and make them autogenerated. On my side, to minimize the copy/pasting >>>>>>> I've moved common parts into macro functions: LIBXL_DEFINE_DEVICE_COMMIT, >>>>>>> LIBXL_DEFINE_DEVICE_LIST_GET, LIBXL_DEFINE_DEVICE_GETINFO etc. >>>>>>> Existing PV devices implementations can be reworked to use these macros as >>>>>>> well. Any other proposals to avoid the duplications are welcome. >>>>>> >>>>>> Did you look into the device type framework I introduced with commit >>>>>> 74e857c6c7f9 and some followups? Maybe it is possible to expand this >>>>>> framework by adding more callbacks to struct libxl_device_type and >>>>>> have some common function(s) in libxl_device.c? >>>>>> >>>>>> Juergen >>>>> >>>>> >>>>> >>>> >>> >>> >>> >> > > For me the drawback of more generic way is to cast device_type to > void* and back which > may be used by client in improper way. > > Thanks. > To summarize: There are two ways to rework the patches: 1. Keep interface between xl an libxl as is and put duplicated code into libxl_device_type specific functions. 2. Change interface to call libxl_device_type specific functions directly from xl: libxl_device_vtpm *vtpms; vtpms = (libxl_device_vtpm*)libxl_device_list_get(LIBXL_DEVTYPE_VTPM, ...); ... libxl__device_list_free(LIBXL_DEVTYPE_VTPM, vtpms, nr); But I need feedback from maintainers. Adding maintainers to CC. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH 0/2] libxl: add PV display device driver interface 2017-03-24 10:35 ` Oleksandr Grytsov @ 2017-03-27 15:10 ` Wei Liu 0 siblings, 0 replies; 11+ messages in thread From: Wei Liu @ 2017-03-27 15:10 UTC (permalink / raw) To: Oleksandr Grytsov Cc: Juergen Gross, xen-devel, Oleksandr Grytsov, Ian Jackson, Wei Liu On Fri, Mar 24, 2017 at 12:35:22PM +0200, Oleksandr Grytsov wrote: > To summarize: > > There are two ways to rework the patches: > > 1. Keep interface between xl an libxl as is and put duplicated code into > libxl_device_type specific functions. > > 2. Change interface to call libxl_device_type specific functions directly > from xl: > > libxl_device_vtpm *vtpms; > > vtpms = (libxl_device_vtpm*)libxl_device_list_get(LIBXL_DEVTYPE_VTPM, ...); > > ... > > libxl__device_list_free(LIBXL_DEVTYPE_VTPM, vtpms, nr); > > But I need feedback from maintainers. > > Adding maintainers to CC. I'm leaning towards #1 because we get type-safety that way. Ian? Wei. > _______________________________________________ Xen-devel mailing list Xen-devel@lists.xen.org https://lists.xen.org/xen-devel ^ permalink raw reply [flat|nested] 11+ messages in thread
end of thread, other threads:[~2017-03-27 15:10 UTC | newest] Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2017-03-23 10:10 [PATCH 0/2] libxl: add PV display device driver interface Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 1/2] " Oleksandr Grytsov 2017-03-23 10:10 ` [PATCH 2/2] xl: add PV display device commands Oleksandr Grytsov 2017-03-23 10:21 ` [PATCH 0/2] libxl: add PV display device driver interface Juergen Gross 2017-03-23 11:32 ` al1img . 2017-03-23 12:08 ` Juergen Gross 2017-03-23 14:23 ` al1img . 2017-03-23 14:58 ` Juergen Gross 2017-03-23 15:55 ` al1img . 2017-03-24 10:35 ` Oleksandr Grytsov 2017-03-27 15:10 ` Wei Liu
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.