[libvirt PATCH 1/2] ch: use payload api to send kernel details

Praveen K Paladugu prapal at linux.microsoft.com
Tue Oct 10 21:42:57 UTC 2023


Starting with v28.0 cloud-hypervisor requires the use of "payload" api to pass
kernel, initramfs and cmdline options. Extend ch driver to use the new
api based on ch version.

Signed-off-by: Praveen K Paladugu <prapal at linux.microsoft.com>
---
 src/ch/ch_capabilities.c | 55 ++++++++++++++++++++++++++++++++++++++++
 src/ch/ch_capabilities.h | 34 +++++++++++++++++++++++++
 src/ch/ch_conf.h         |  6 +++++
 src/ch/ch_driver.c       |  3 +++
 src/ch/ch_monitor.c      | 48 +++++++++++++++++++++++++++++++----
 src/ch/ch_monitor.h      |  4 ++-
 src/ch/ch_process.c      |  2 +-
 src/ch/meson.build       |  2 ++
 8 files changed, 147 insertions(+), 7 deletions(-)
 create mode 100644 src/ch/ch_capabilities.c
 create mode 100644 src/ch/ch_capabilities.h

diff --git a/src/ch/ch_capabilities.c b/src/ch/ch_capabilities.c
new file mode 100644
index 0000000000..b10485820c
--- /dev/null
+++ b/src/ch/ch_capabilities.c
@@ -0,0 +1,55 @@
+/*
+ * Copyright Microsoft Corp. 2023
+ *
+ * ch_capabilities.h: CH capabilities
+ *
+ * This library 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; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ */
+
+#include <config.h>
+#include "ch_capabilities.h"
+
+static void
+virCHCapsSet(virBitmap *chCaps,
+               virCHCapsFlags flag)
+{
+    ignore_value(virBitmapSetBit(chCaps, flag));
+}
+
+/**
+ * virCHCapsInitCHVersionCaps:
+ *
+ * Set all CH capabilities based on version of CH.
+ */
+virBitmap *
+virCHCapsInitCHVersionCaps(int version)
+{
+    g_autoptr(virBitmap) chCaps = NULL;
+    chCaps = virBitmapNew(CH_CAPS_LAST);
+
+    /* Version 28 deprecated kernel API:
+     * https://github.com/cloud-hypervisor/cloud-hypervisor/releases/tag/v28.0
+     */
+    if (version >= 28000000)
+        virCHCapsSet(chCaps, CH_KERNEL_API_DEPRCATED);
+
+
+    /* Starting Version 18, serial and console can be used in parallel */
+    if (version >= 18000000)
+        virCHCapsSet(chCaps, CH_SERIAL_CONSOLE_IN_PARALLEL);
+
+    return g_steal_pointer(&chCaps);
+
+}
diff --git a/src/ch/ch_capabilities.h b/src/ch/ch_capabilities.h
new file mode 100644
index 0000000000..703a6dbfe2
--- /dev/null
+++ b/src/ch/ch_capabilities.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright Microsoft Corp. 2023
+ *
+ * ch_capabilities.h: CH capabilities
+ *
+ * This library 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; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ */
+
+#pragma once
+#include "virbitmap.h"
+
+
+typedef enum {
+    /* 0 */
+    CH_KERNEL_API_DEPRCATED, /* Use `payload` in place of `kernel` api */
+    CH_SERIAL_CONSOLE_IN_PARALLEL, /* Serial and Console ports can work in parallel */
+
+    CH_CAPS_LAST /* this must always be the last item */
+} virCHCapsFlags;
+
+virBitmap *
+virCHCapsInitCHVersionCaps(int version);
diff --git a/src/ch/ch_conf.h b/src/ch/ch_conf.h
index b927621a97..5b9b42540d 100644
--- a/src/ch/ch_conf.h
+++ b/src/ch/ch_conf.h
@@ -22,6 +22,7 @@
 
 #include "virdomainobjlist.h"
 #include "virthread.h"
+#include "ch_capabilities.h"
 
 #define CH_DRIVER_NAME "CH"
 #define CH_CMD "cloud-hypervisor"
@@ -54,6 +55,11 @@ struct _virCHDriver
      * lockless access thereafter */
     virCaps *caps;
 
+    /* Immutable pointer, Immutable object
+     * Initialized once and reused as needed
+     */
+    virBitmap *chCaps;
+
     /* Immutable pointer, Immutable object */
     virDomainXMLOption *xmlopt;
 
diff --git a/src/ch/ch_driver.c b/src/ch/ch_driver.c
index b62645a8c8..bd271fc0ee 100644
--- a/src/ch/ch_driver.c
+++ b/src/ch/ch_driver.c
@@ -20,6 +20,7 @@
 
 #include <config.h>
 
+#include "ch_capabilities.h"
 #include "ch_conf.h"
 #include "ch_domain.h"
 #include "ch_driver.h"
@@ -899,6 +900,8 @@ static int chStateInitialize(bool privileged,
         goto cleanup;
     }
 
+    ch_driver->chCaps = virCHCapsInitCHVersionCaps(ch_driver->version);
+
     ch_driver->privileged = privileged;
     ret = VIR_DRV_STATE_INIT_COMPLETE;
 
diff --git a/src/ch/ch_monitor.c b/src/ch/ch_monitor.c
index 1691a4efb6..6f960c3a51 100644
--- a/src/ch/ch_monitor.c
+++ b/src/ch/ch_monitor.c
@@ -106,6 +106,37 @@ virCHMonitorBuildPTYJson(virJSONValue *content, virDomainDef *vmdef)
     return 0;
 }
 
+static int
+virCHMonitorBuildPayloadJson(virJSONValue *content, virDomainDef *vmdef)
+{
+    g_autoptr(virJSONValue) payload = virJSONValueNewObject();
+
+
+    if (vmdef->os.kernel == NULL) {
+        virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+                       _("Kernel image path in this domain is not defined"));
+        return -1;
+    } else {
+        if (virJSONValueObjectAppendString(payload, "kernel", vmdef->os.kernel) < 0)
+            return -1;
+    }
+
+    if (vmdef->os.cmdline) {
+        if (virJSONValueObjectAppendString(payload, "cmdline", vmdef->os.cmdline) < 0)
+            return -1;
+    }
+
+    if (vmdef->os.initrd != NULL) {
+        if (virJSONValueObjectAppendString(payload, "initramfs", vmdef->os.initrd) < 0)
+            return -1;
+    }
+
+    if (virJSONValueObjectAppend(content, "payload", &payload) < 0)
+    return -1;
+
+    return 0;
+}
+
 static int
 virCHMonitorBuildKernelRelatedJson(virJSONValue *content, virDomainDef *vmdef)
 {
@@ -425,7 +456,8 @@ virCHMonitorBuildDevicesJson(virJSONValue *content,
 }
 
 static int
-virCHMonitorBuildVMJson(virDomainDef *vmdef,
+virCHMonitorBuildVMJson(virCHDriver *driver,
+                        virDomainDef *vmdef,
                         char **jsonstr,
                         size_t *nnicindexes,
                         int **nicindexes)
@@ -447,8 +479,13 @@ virCHMonitorBuildVMJson(virDomainDef *vmdef,
     if (virCHMonitorBuildMemoryJson(content, vmdef) < 0)
         return -1;
 
-    if (virCHMonitorBuildKernelRelatedJson(content, vmdef) < 0)
-        return -1;
+    if (virBitmapIsBitSet(driver->chCaps, CH_KERNEL_API_DEPRCATED)) {
+        if (virCHMonitorBuildPayloadJson(content, vmdef) < 0)
+            return -1;
+    } else if (virCHMonitorBuildKernelRelatedJson(content, vmdef) < 0) {
+            return -1;
+    }
+
 
     if (virCHMonitorBuildDisksJson(content, vmdef) < 0)
         return -1;
@@ -840,7 +877,8 @@ virCHMonitorShutdownVMM(virCHMonitor *mon)
 }
 
 int
-virCHMonitorCreateVM(virCHMonitor *mon,
+virCHMonitorCreateVM(virCHDriver *driver,
+                     virCHMonitor *mon,
                      size_t *nnicindexes,
                      int **nicindexes)
 {
@@ -854,7 +892,7 @@ virCHMonitorCreateVM(virCHMonitor *mon,
     headers = curl_slist_append(headers, "Accept: application/json");
     headers = curl_slist_append(headers, "Content-Type: application/json");
 
-    if (virCHMonitorBuildVMJson(mon->vm->def, &payload,
+    if (virCHMonitorBuildVMJson(driver, mon->vm->def, &payload,
                                 nnicindexes, nicindexes) != 0)
         return -1;
 
diff --git a/src/ch/ch_monitor.h b/src/ch/ch_monitor.h
index ffc80e8910..bbfa77cdff 100644
--- a/src/ch/ch_monitor.h
+++ b/src/ch/ch_monitor.h
@@ -25,6 +25,7 @@
 #include "virobject.h"
 #include "virjson.h"
 #include "domain_conf.h"
+#include "ch_conf.h"
 
 #define URL_ROOT "http://localhost/api/v1"
 #define URL_VMM_SHUTDOWN "vmm.shutdown"
@@ -103,7 +104,8 @@ void virCHMonitorClose(virCHMonitor *mon);
 G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCHMonitor, virCHMonitorClose);
 
 
-int virCHMonitorCreateVM(virCHMonitor *mon,
+int virCHMonitorCreateVM(virCHDriver *driver,
+                         virCHMonitor *mon,
                          size_t *nnicindexes,
                          int **nicindexes);
 int virCHMonitorBootVM(virCHMonitor *mon);
diff --git a/src/ch/ch_process.c b/src/ch/ch_process.c
index 6d3a9612bd..f3bb4a7280 100644
--- a/src/ch/ch_process.c
+++ b/src/ch/ch_process.c
@@ -483,7 +483,7 @@ virCHProcessStart(virCHDriver *driver,
             goto cleanup;
         }
 
-        if (virCHMonitorCreateVM(priv->monitor,
+        if (virCHMonitorCreateVM(driver, priv->monitor,
                                  &nnicindexes, &nicindexes) < 0) {
             virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
                            _("failed to create guest VM"));
diff --git a/src/ch/meson.build b/src/ch/meson.build
index df246ef9b0..6311b84f3e 100644
--- a/src/ch/meson.build
+++ b/src/ch/meson.build
@@ -1,4 +1,6 @@
 ch_driver_sources = [
+  'ch_capabilities.h',
+  'ch_capabilities.c',
   'ch_conf.c',
   'ch_conf.h',
   'ch_domain.c',
-- 
2.41.0



More information about the libvir-list mailing list