Re: [libvirt PATCH 4/9] Jailhouse driver: Implementation of DomainCreate* callbacks
On Thu, Sep 17, 2020 at 04:23:54PM +0100, Daniel P. Berrangé wrote: > From: Prakhar Bansal > > Implemented Jailhouse hypervisor APIs for cell > load/start/shutdown/destroy. > --- > src/jailhouse/jailhouse_api.c| 100 -- > src/jailhouse/jailhouse_api.h| 29 + > src/jailhouse/jailhouse_driver.c | 217 +-- > src/jailhouse/jailhouse_driver.h | 8 ++ > 4 files changed, 335 insertions(+), 19 deletions(-) > > diff --git a/src/jailhouse/jailhouse_api.c b/src/jailhouse/jailhouse_api.c > index cda00b50e7..783903e939 100644 > --- a/src/jailhouse/jailhouse_api.c > +++ b/src/jailhouse/jailhouse_api.c > @@ -43,11 +43,14 @@ > #define JAILHOUSE_CELLS > "/sys/devices/jailhouse/cells" > #define MAX_JAILHOUSE_SYS_CONFIG_FILE_SIZE 1024*1024 > #define MAX_JAILHOUSE_CELL_CONFIG_FILE_SIZE 1024 > +#define MAX_JAILHOUSE_CELL_IMAGE_FILE_SIZE 64*1024*1024 > > > #define JAILHOUSE_ENABLE _IOW(0, 0, void *) > #define JAILHOUSE_DISABLE _IO(0, 1) > #define JAILHOUSE_CELL_CREATE _IOW(0, 2, virJailhouseCellCreate) > +#define JAILHOUSE_CELL_LOAD_IOW(0, 3, virJailhouseCellLoad) > +#define JAILHOUSE_CELL_START _IOW(0, 4, virJailhouseCellId) > #define JAILHOUSE_CELL_DESTROY _IOW(0, 5, virJailhouseCellId) > > #define VIR_FROM_THIS VIR_FROM_JAILHOUSE > @@ -68,8 +71,6 @@ int cell_match(const struct dirent *dirent); > > int createCell(const char *conf_file); > > -int destroyCell(virJailhouseCellId cell_id); > - > int getCellInfo(const unsigned int id, > virJailhouseCellInfoPtr * cell_info); > > @@ -254,7 +255,7 @@ readSysfsCellString(const unsigned int id, const char > *entry) > } > > int > -getCellInfo(const unsigned int id, virJailhouseCellInfoPtr * cell_info_ptr) > +getCellInfo(const unsigned int id, virJailhouseCellInfoPtr *cell_info_ptr) > { > char *tmp; > > @@ -345,28 +346,105 @@ getJailhouseCellsInfo(void) > } > > int > -destroyCell(virJailhouseCellId cell_id) > +loadImagesInCell(virJailhouseCellId cell_id, char **images, int num_images) > +{ > + virJailhousePreloadImagePtr image; > + virJailhouseCellLoadPtr cell_load; > + g_autofree char *buffer = NULL; > + unsigned int n; > + int len = -1, err = -1; > + VIR_AUTOCLOSE fd = -1; > + > + > + if (VIR_ALLOC(cell_load) < 0) { > +virReportError(VIR_ERR_INTERNAL_ERROR, > + "%s", > + _("Insufficient memory for cell load")); > +return -1; > + } > + > + > + if (VIR_ALLOC_N(cell_load->image, num_images) < 0) { > +virReportError(VIR_ERR_INTERNAL_ERROR, > + "%s", > + _("Insufficient memory for cell load images")); > +return -1; > + } No need to check failure - these abort on OOM. > + > + cell_load->id = cell_id; > + cell_load->num_preload_images = num_images; > + > + for (n = 0, image = cell_load->image; n < num_images; n++, image++) { > +len = virFileReadAll(images[n], MAX_JAILHOUSE_CELL_IMAGE_FILE_SIZE, > &buffer); > +if (len < 0 || !buffer) { > + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, > +_("Failed to read the image file %s"), > +images[n]); > + return -1; > +} > + > +image->source_address = (unsigned long)buffer; > +image->size = len; > + > +// TODO(Prakhar): Add support for target address. > +image->target_address = 0; > + } > + > + fd = openDev(); Check error here. > + > + err = ioctl(fd, JAILHOUSE_CELL_LOAD, cell_load); > + if (err) { > + virReportSystemError(errno, > +_("Loading cell images for %d failed"), > +cell_id.id); > + return -1; > + } > + > + return 0; > +} > -destroyJailhouseCells(virJailhouseCellInfoPtr *cell_info_list G_GNUC_UNUSED) > +destroyCell(virJailhouseCellId cell_id) > { > +int err = -1; > +VIR_AUTOCLOSE fd = -1; > + > +fd = openDev(); Check error > > -/* Iterate over all cells in cell_info_list and destroy each cell */ > -// TODO: Not implemented yet. > +err = ioctl(fd, JAILHOUSE_CELL_DESTROY, &cell_id); > +if (err) { > +virReportSystemError(errno, > + _("Destroying cell %d failed"), > + cell_id.id); > + > +return -1; > +} > +typedef struct _virJailhousePreloadImage virJailhousePreloadImage; > +typedef virJailhousePreloadImage *virJailhousePreloadImagePtr; > + > +struct _virJailhousePreloadImage { > +__u64 source_address; uint64_t, etc > +__u64 size; > +__u64 target_address; > +__u64 padding; > +}; > + > +typedef struct _virJailhouseCellLoad virJailhouseCellLoad; > +typedef virJailhouseCellLoad *virJailhouseCellLoadPtr; > + > +struct _virJailhouseCellLoad { > +str
[libvirt PATCH 4/9] Jailhouse driver: Implementation of DomainCreate* callbacks
From: Prakhar Bansal Implemented Jailhouse hypervisor APIs for cell load/start/shutdown/destroy. --- src/jailhouse/jailhouse_api.c| 100 -- src/jailhouse/jailhouse_api.h| 29 + src/jailhouse/jailhouse_driver.c | 217 +-- src/jailhouse/jailhouse_driver.h | 8 ++ 4 files changed, 335 insertions(+), 19 deletions(-) diff --git a/src/jailhouse/jailhouse_api.c b/src/jailhouse/jailhouse_api.c index cda00b50e7..783903e939 100644 --- a/src/jailhouse/jailhouse_api.c +++ b/src/jailhouse/jailhouse_api.c @@ -43,11 +43,14 @@ #define JAILHOUSE_CELLS "/sys/devices/jailhouse/cells" #define MAX_JAILHOUSE_SYS_CONFIG_FILE_SIZE 1024*1024 #define MAX_JAILHOUSE_CELL_CONFIG_FILE_SIZE 1024 +#define MAX_JAILHOUSE_CELL_IMAGE_FILE_SIZE 64*1024*1024 #define JAILHOUSE_ENABLE _IOW(0, 0, void *) #define JAILHOUSE_DISABLE _IO(0, 1) #define JAILHOUSE_CELL_CREATE _IOW(0, 2, virJailhouseCellCreate) +#define JAILHOUSE_CELL_LOAD_IOW(0, 3, virJailhouseCellLoad) +#define JAILHOUSE_CELL_START _IOW(0, 4, virJailhouseCellId) #define JAILHOUSE_CELL_DESTROY _IOW(0, 5, virJailhouseCellId) #define VIR_FROM_THIS VIR_FROM_JAILHOUSE @@ -68,8 +71,6 @@ int cell_match(const struct dirent *dirent); int createCell(const char *conf_file); -int destroyCell(virJailhouseCellId cell_id); - int getCellInfo(const unsigned int id, virJailhouseCellInfoPtr * cell_info); @@ -254,7 +255,7 @@ readSysfsCellString(const unsigned int id, const char *entry) } int -getCellInfo(const unsigned int id, virJailhouseCellInfoPtr * cell_info_ptr) +getCellInfo(const unsigned int id, virJailhouseCellInfoPtr *cell_info_ptr) { char *tmp; @@ -345,28 +346,105 @@ getJailhouseCellsInfo(void) } int -destroyCell(virJailhouseCellId cell_id) +loadImagesInCell(virJailhouseCellId cell_id, char **images, int num_images) +{ + virJailhousePreloadImagePtr image; + virJailhouseCellLoadPtr cell_load; + g_autofree char *buffer = NULL; + unsigned int n; + int len = -1, err = -1; + VIR_AUTOCLOSE fd = -1; + + + if (VIR_ALLOC(cell_load) < 0) { +virReportError(VIR_ERR_INTERNAL_ERROR, + "%s", + _("Insufficient memory for cell load")); +return -1; + } + + + if (VIR_ALLOC_N(cell_load->image, num_images) < 0) { +virReportError(VIR_ERR_INTERNAL_ERROR, + "%s", + _("Insufficient memory for cell load images")); +return -1; + } + + cell_load->id = cell_id; + cell_load->num_preload_images = num_images; + + for (n = 0, image = cell_load->image; n < num_images; n++, image++) { +len = virFileReadAll(images[n], MAX_JAILHOUSE_CELL_IMAGE_FILE_SIZE, &buffer); +if (len < 0 || !buffer) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, +_("Failed to read the image file %s"), +images[n]); + return -1; +} + +image->source_address = (unsigned long)buffer; +image->size = len; + +// TODO(Prakhar): Add support for target address. +image->target_address = 0; + } + + fd = openDev(); + + err = ioctl(fd, JAILHOUSE_CELL_LOAD, cell_load); + if (err) { + virReportSystemError(errno, +_("Loading cell images for %d failed"), +cell_id.id); + return -1; + } + + return 0; +} + +int +shutdownCell(virJailhouseCellId cell_id) +{ +// Loading 0 images in the cell causes cell to shutdown. +return loadImagesInCell(cell_id, NULL, 0); +} + +int +startCell(virJailhouseCellId cell_id) { int err = -1; VIR_AUTOCLOSE fd = -1; fd = openDev(); -err = ioctl(fd, JAILHOUSE_CELL_DESTROY, &cell_id); -if (err) +err = ioctl(fd, JAILHOUSE_CELL_START, &cell_id); +if (err) { virReportSystemError(errno, - _("Destroying cell %d failed"), + _("Start cell %d failed"), cell_id.id); +return -1; +} -return err; +return 0; } int -destroyJailhouseCells(virJailhouseCellInfoPtr *cell_info_list G_GNUC_UNUSED) +destroyCell(virJailhouseCellId cell_id) { +int err = -1; +VIR_AUTOCLOSE fd = -1; + +fd = openDev(); -/* Iterate over all cells in cell_info_list and destroy each cell */ -// TODO: Not implemented yet. +err = ioctl(fd, JAILHOUSE_CELL_DESTROY, &cell_id); +if (err) { +virReportSystemError(errno, + _("Destroying cell %d failed"), + cell_id.id); + +return -1; +} return 0; } diff --git a/src/jailhouse/jailhouse_api.h b/src/jailhouse/jailhouse_api.h index 8362cb3d0f..ba39a4c8b7 100644 --- a/src/jailhouse/jailhouse_api.h +++ b/src/jailhouse/jail