Package: guix-patches;
Reported by: Maxim Cournoyer <maxim.cournoyer <at> gmail.com>
Date: Wed, 19 Mar 2025 07:17:02 UTC
Severity: normal
Tags: patch
Done: Maxim Cournoyer <maxim.cournoyer <at> gmail.com>
Bug is archived. No further changes may be made.
View this message in rfc822 format
From: Maxim Cournoyer <maxim.cournoyer <at> gmail.com> To: 77110 <at> debbugs.gnu.org Cc: Maxim Cournoyer <maxim.cournoyer <at> gmail.com>, Ludovic Courtès <ludo <at> gnu.org>, Maxim Cournoyer <maxim.cournoyer <at> gmail.com> Subject: [bug#77110] [PATCH 2/2] services: libvirt: Add UEFI firmware support. Date: Wed, 19 Mar 2025 21:45:13 +0900
This makes libvirt able to boot images that require a UEFI bootloader, with the available firmwares exposed to libvirt made configurable via a new configuration field. For more background on the problem this fixes, see the same issue that was reported in NixOS (see: https://github.com/NixOS/nixpkgs/issues/115996). * gnu/services/virtualization.scm: (list-of-file-likes?): New predicate. (libvirt-configuration): [firmwares]: New field. (/etc/qemu/firmware): New procedure. (libvirt-service-type): Extend the etc-service-type with it. (generate-libvirt-documentation): Delete obsolete procedure. * doc/guix.texi: Re-generate doc. * gnu/tests/virtualization.scm (run-libvirt-test): Augment memory from 256 to 512 MiB. Test it. Change-Id: I40694964405f13681520bf1e28b7365b0200d8f7 --- doc/guix.texi | 506 ++++++++------------------------ gnu/services/virtualization.scm | 76 +++-- gnu/tests/virtualization.scm | 33 ++- 3 files changed, 211 insertions(+), 404 deletions(-) diff --git a/doc/guix.texi b/doc/guix.texi index 0488559332..e36fbad19f 100644 --- a/doc/guix.texi +++ b/doc/guix.texi @@ -37895,406 +37895,220 @@ Virtualization Services @end lisp @end defvar -@c Auto-generated with (generate-libvirt-documentation) +@c Auto-generated with (configuration->documentation 'libvirt-configuration) +@c %start of fragment +@deftp {Data Type} libvirt-configuration Available @code{libvirt-configuration} fields are: -@deftypevr {@code{libvirt-configuration} parameter} package libvirt +@table @asis +@item @code{libvirt} (default: @code{libvirt}) (type: file-like) Libvirt package. -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} boolean listen-tls? -Flag listening for secure TLS connections on the public TCP/IP port. -You must set @code{listen} for this to have any effect. - -It is necessary to setup a CA and issue server certificates before using -this capability. - -Defaults to @samp{#t}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} boolean listen-tcp? -Listen for unencrypted TCP connections on the public TCP/IP port. You must -set @code{listen} for this to have any effect. - -Using the TCP socket requires SASL authentication by default. Only SASL -mechanisms which support data encryption are allowed. This is -DIGEST_MD5 and GSSAPI (Kerberos5). - -Defaults to @samp{#f}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string tls-port -Port for accepting secure TLS connections. This can be a port number, -or service name. +@item @code{qemu} (default: @code{qemu}) (type: file-like) +Qemu package. -Defaults to @samp{"16514"}. +@item @code{firmwares} (default: @code{(ovmf-x86-64)}) (type: list-of-file-likes) +List of UEFI/BIOS firmware packages to make available. Each firmware +package should contain a @file{share/qemu/firmware/@var{NAME}.json} QEMU +firmware metadata file. -@end deftypevr +@item @code{listen-tls?} (default: @code{#t}) (type: boolean) +Flag listening for secure TLS connections on the public TCP/IP port. +must set @code{listen} for this to have any effect. It is necessary to +setup a CA and issue server certificates before using this capability. -@deftypevr {@code{libvirt-configuration} parameter} string tcp-port -Port for accepting insecure TCP connections. This can be a port number, -or service name. +@item @code{listen-tcp?} (default: @code{#f}) (type: boolean) +Listen for unencrypted TCP connections on the public TCP/IP port. must +set @code{listen} for this to have any effect. Using the TCP socket +requires SASL authentication by default. Only SASL mechanisms which +support data encryption are allowed. This is DIGEST_MD5 and GSSAPI +(Kerberos5) -Defaults to @samp{"16509"}. +@item @code{tls-port} (default: @code{"16514"}) (type: string) +Port for accepting secure TLS connections This can be a port number, or +service name -@end deftypevr +@item @code{tcp-port} (default: @code{"16509"}) (type: string) +Port for accepting insecure TCP connections This can be a port number, +or service name -@deftypevr {@code{libvirt-configuration} parameter} string listen-addr +@item @code{listen-addr} (default: @code{"0.0.0.0"}) (type: string) IP address or hostname used for client connections. -Defaults to @samp{"0.0.0.0"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} boolean mdns-adv? -Flag toggling mDNS advertisement of the libvirt service. - -Alternatively can disable for all services on a host by stopping the -Avahi daemon. +@item @code{mdns-adv?} (default: @code{#f}) (type: boolean) +Flag toggling mDNS advertisement of the libvirt service. Alternatively +can disable for all services on a host by stopping the Avahi daemon. -Defaults to @samp{#f}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string mdns-name +@item @code{mdns-name} (default: @code{"Virtualization Host terra"}) (type: string) Default mDNS advertisement name. This must be unique on the immediate broadcast network. -Defaults to @samp{"Virtualization Host <hostname>"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string unix-sock-group +@item @code{unix-sock-group} (default: @code{"libvirt"}) (type: string) UNIX domain socket group ownership. This can be used to allow a 'trusted' set of users access to management capabilities without becoming root. -Defaults to @samp{"libvirt"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string unix-sock-ro-perms +@item @code{unix-sock-ro-perms} (default: @code{"0777"}) (type: string) UNIX socket permissions for the R/O socket. This is used for monitoring VM status only. -Defaults to @samp{"0777"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string unix-sock-rw-perms +@item @code{unix-sock-rw-perms} (default: @code{"0770"}) (type: string) UNIX socket permissions for the R/W socket. Default allows only root. If PolicyKit is enabled on the socket, the default will change to allow everyone (eg, 0777) -Defaults to @samp{"0770"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string unix-sock-admin-perms +@item @code{unix-sock-admin-perms} (default: @code{"0777"}) (type: string) UNIX socket permissions for the admin socket. Default allows only owner (root), do not change it unless you are sure to whom you are exposing the access to. -Defaults to @samp{"0777"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string unix-sock-dir +@item @code{unix-sock-dir} (default: @code{"/var/run/libvirt"}) (type: string) The directory in which sockets will be found/created. -Defaults to @samp{"/var/run/libvirt"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string auth-unix-ro +@item @code{auth-unix-ro} (default: @code{"polkit"}) (type: string) Authentication scheme for UNIX read-only sockets. By default socket permissions allow anyone to connect -Defaults to @samp{"polkit"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string auth-unix-rw +@item @code{auth-unix-rw} (default: @code{"polkit"}) (type: string) Authentication scheme for UNIX read-write sockets. By default socket permissions only allow root. If PolicyKit support was compiled into libvirt, the default will be to use 'polkit' auth. -Defaults to @samp{"polkit"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string auth-tcp +@item @code{auth-tcp} (default: @code{"sasl"}) (type: string) Authentication scheme for TCP sockets. If you don't enable SASL, then all TCP traffic is cleartext. Don't do this outside of a dev/test scenario. -Defaults to @samp{"sasl"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string auth-tls +@item @code{auth-tls} (default: @code{"none"}) (type: string) Authentication scheme for TLS sockets. TLS sockets already have encryption provided by the TLS layer, and limited authentication is done -by certificates. - -It is possible to make use of any SASL authentication mechanism as well, -by using 'sasl' for this option +by certificates. It is possible to make use of any SASL authentication +mechanism as well, by using 'sasl' for this option -Defaults to @samp{"none"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} optional-list access-drivers -API access control scheme. - -By default an authenticated user is allowed access to all APIs. Access -drivers can place restrictions on this. - -Defaults to @samp{'()}. - -@end deftypevr +@item @code{access-drivers} (default: @code{()}) (type: optional-list) +API access control scheme. By default an authenticated user is allowed +access to all APIs. Access drivers can place restrictions on this. -@deftypevr {@code{libvirt-configuration} parameter} string key-file +@item @code{key-file} (default: @code{""}) (type: string) Server key file path. If set to an empty string, then no private key is loaded. -Defaults to @samp{""}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string cert-file +@item @code{cert-file} (default: @code{""}) (type: string) Server key file path. If set to an empty string, then no certificate is loaded. -Defaults to @samp{""}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string ca-file +@item @code{ca-file} (default: @code{""}) (type: string) Server key file path. If set to an empty string, then no CA certificate is loaded. -Defaults to @samp{""}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string crl-file +@item @code{crl-file} (default: @code{""}) (type: string) Certificate revocation list path. If set to an empty string, then no CRL is loaded. -Defaults to @samp{""}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} boolean tls-no-sanity-cert -Disable verification of our own server certificates. +@item @code{tls-no-sanity-cert} (default: @code{#f}) (type: boolean) +Disable verification of our own server certificates. When libvirtd +starts it performs some sanity checks against its own certificates. -When libvirtd starts it performs some sanity checks against its own -certificates. +@item @code{tls-no-verify-cert} (default: @code{#f}) (type: boolean) +Disable verification of client certificates. Client certificate +verification is the primary authentication mechanism. Any client which +does not present a certificate signed by the CA will be rejected. -Defaults to @samp{#f}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} boolean tls-no-verify-cert -Disable verification of client certificates. - -Client certificate verification is the primary authentication mechanism. -Any client which does not present a certificate signed by the CA will be -rejected. - -Defaults to @samp{#f}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} optional-list tls-allowed-dn-list +@item @code{tls-allowed-dn-list} (default: @code{()}) (type: optional-list) Whitelist of allowed x509 Distinguished Name. -Defaults to @samp{'()}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} optional-list sasl-allowed-usernames +@item @code{sasl-allowed-usernames} (default: @code{()}) (type: optional-list) Whitelist of allowed SASL usernames. The format for username depends on the SASL authentication mechanism. -Defaults to @samp{'()}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string tls-priority +@item @code{tls-priority} (default: @code{"NORMAL"}) (type: string) Override the compile time default TLS priority string. The default is -usually @samp{"NORMAL"} unless overridden at build time. Only set this is it +usually "NORMAL" unless overridden at build time. Only set this is it is desired for libvirt to deviate from the global default settings. -Defaults to @samp{"NORMAL"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer max-clients +@item @code{max-clients} (default: @code{5000}) (type: integer) Maximum number of concurrent client connections to allow over all sockets combined. -Defaults to @samp{5000}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer max-queued-clients +@item @code{max-queued-clients} (default: @code{1000}) (type: integer) Maximum length of queue of connections waiting to be accepted by the daemon. Note, that some protocols supporting retransmission may obey this so that a later reattempt at connection succeeds. -Defaults to @samp{1000}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer max-anonymous-clients +@item @code{max-anonymous-clients} (default: @code{20}) (type: integer) Maximum length of queue of accepted but not yet authenticated clients. Set this to zero to turn this feature off -Defaults to @samp{20}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer min-workers +@item @code{min-workers} (default: @code{5}) (type: integer) Number of workers to start up initially. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer max-workers -Maximum number of worker threads. - -If the number of active clients exceeds @code{min-workers}, then more -threads are spawned, up to max_workers limit. Typically you'd want -max_workers to equal maximum number of clients allowed. - -Defaults to @samp{20}. - -@end deftypevr +@item @code{max-workers} (default: @code{20}) (type: integer) +Maximum number of worker threads. If the number of active clients +exceeds @code{min-workers}, then more threads are spawned, up to +max_workers limit. Typically you'd want max_workers to equal maximum +number of clients allowed. -@deftypevr {@code{libvirt-configuration} parameter} integer prio-workers +@item @code{prio-workers} (default: @code{5}) (type: integer) Number of priority workers. If all workers from above pool are stuck, some calls marked as high priority (notably domainDestroy) can be executed in this pool. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer max-requests +@item @code{max-requests} (default: @code{20}) (type: integer) Total global limit on concurrent RPC calls. -Defaults to @samp{20}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer max-client-requests +@item @code{max-client-requests} (default: @code{5}) (type: integer) Limit on concurrent requests from a single client connection. To avoid one client monopolizing the server this should be a small fraction of the global max_requests and max_workers parameter. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-min-workers +@item @code{admin-min-workers} (default: @code{1}) (type: integer) Same as @code{min-workers} but for the admin interface. -Defaults to @samp{1}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-max-workers +@item @code{admin-max-workers} (default: @code{5}) (type: integer) Same as @code{max-workers} but for the admin interface. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-max-clients +@item @code{admin-max-clients} (default: @code{5}) (type: integer) Same as @code{max-clients} but for the admin interface. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-max-queued-clients +@item @code{admin-max-queued-clients} (default: @code{5}) (type: integer) Same as @code{max-queued-clients} but for the admin interface. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-max-client-requests +@item @code{admin-max-client-requests} (default: @code{5}) (type: integer) Same as @code{max-client-requests} but for the admin interface. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer log-level +@item @code{log-level} (default: @code{3}) (type: integer) Logging level. 4 errors, 3 warnings, 2 information, 1 debug. -Defaults to @samp{3}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string log-filters -Logging filters. - -A filter allows to select a different logging level for a given category -of logs. The format for a filter is one of: +@item @code{log-filters} (default: @code{"3:remote 4:event"}) (type: string) +Logging filters. A filter allows selecting a different logging level +for a given category of logs The format for a filter is one of: @itemize @bullet -@item -x:name - -@item -x:+name - +@item x:name +@item x:+name @end itemize where @code{name} is a string which is matched against the category given in the @code{VIR_LOG_INIT()} at the top of each libvirt source -file, e.g., @samp{"remote"}, @samp{"qemu"}, or @samp{"util.json"} (the -name in the filter can be a substring of the full category name, in -order to match multiple similar categories), the optional @samp{"+"} -prefix tells libvirt to log stack trace for each message matching name, -and @code{x} is the minimal level where matching messages should be -logged: +file, e.g., "remote", "qemu", or "util.json" (the name in the filter can +be a substring of the full category name, in order to match multiple +similar categories), the optional "+" prefix tells libvirt to log stack +trace for each message matching name, and @code{x} is the minimal level +where matching messages should be logged: @itemize @bullet -@item -1: DEBUG - -@item -2: INFO - -@item -3: WARNING - -@item -4: ERROR - +@item 1: DEBUG +@item 2: INFO +@item 3: WARNING +@item 4: ERROR @end itemize Multiple filters can be defined in a single filters statement, they just need to be separated by spaces. -Defaults to @samp{"3:remote 4:event"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} string log-outputs -Logging outputs. - -An output is one of the places to save logging information. The format -for an output can be: +@item @code{log-outputs} (default: @code{"3:syslog:libvirtd"}) (type: string) +Logging outputs. An output is one of the places to save logging +information The format for an output can be: @table @code @item x:stderr @@ -38308,137 +38122,77 @@ Virtualization Services @item x:journald output to journald logging system - @end table -In all case the x prefix is the minimal level, acting as a filter +In all case the x prefix is the minimal level, acting as a +filter @itemize @bullet -@item -1: DEBUG - -@item -2: INFO - -@item -3: WARNING - -@item -4: ERROR - +@item 1: DEBUG +@item 2: INFO +@item 3: WARNING +@item 4: ERROR @end itemize Multiple outputs can be defined, they just need to be separated by spaces. -Defaults to @samp{"3:stderr"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer audit-level +@item @code{audit-level} (default: @code{1}) (type: integer) Allows usage of the auditing subsystem to be altered @itemize @bullet -@item -0: disable all auditing - -@item -1: enable auditing, only if enabled on host - -@item -2: enable auditing, and exit if disabled on host. - +@item 0: disable all auditing +@item 1: enable auditing, only if enabled on host +@item 2: enable auditing, and exit if disabled on host. @end itemize -Defaults to @samp{1}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} boolean audit-logging +@item @code{audit-logging} (default: @code{#f}) (type: boolean) Send audit messages via libvirt logging infrastructure. -Defaults to @samp{#f}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} optional-string host-uuid -Host UUID@. UUID must not have all digits be the same. - -Defaults to @samp{""}. - -@end deftypevr +@item @code{host-uuid} (default: @code{""}) (type: optional-string) +Host UUID. UUID must not have all digits be the same. -@deftypevr {@code{libvirt-configuration} parameter} string host-uuid-source +@item @code{host-uuid-source} (default: @code{"smbios"}) (type: string) Source to read host UUID. @itemize @bullet -@item -@code{smbios}: fetch the UUID from @code{dmidecode -s system-uuid} - -@item -@code{machine-id}: fetch the UUID from @code{/etc/machine-id} - +@item @code{smbios}: fetch the UUID from @code{dmidecode -s system-uuid} +@item @code{machine-id}: fetch the UUID from @code{/etc/machine-id} @end itemize If @code{dmidecode} does not provide a valid UUID a temporary UUID will be generated. -Defaults to @samp{"smbios"}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer keepalive-interval +@item @code{keepalive-interval} (default: @code{5}) (type: integer) A keepalive message is sent to a client after @code{keepalive_interval} seconds of inactivity to check if the client is still responding. If set to -1, libvirtd will never send keepalive requests; however clients can still send them and the daemon will send responses. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer keepalive-count +@item @code{keepalive-count} (default: @code{5}) (type: integer) Maximum number of keepalive messages that are allowed to be sent to the client without getting any response before the connection is considered -broken. - -In other words, the connection is automatically closed approximately -after @code{keepalive_interval * (keepalive_count + 1)} seconds since -the last message received from the client. When @code{keepalive-count} -is set to 0, connections will be automatically closed after -@code{keepalive-interval} seconds of inactivity without sending any -keepalive messages. - -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-keepalive-interval +broken. In other words, the connection is automatically closed +approximately after @code{keepalive_interval * (keepalive_count + 1)} +seconds since the last message received from the client. When +@code{keepalive-count} is set to 0, connections will be automatically +closed after @code{keepalive-interval} seconds of inactivity without +sending any keepalive messages. + +@item @code{admin-keepalive-interval} (default: @code{5}) (type: integer) Same as above but for admin interface. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer admin-keepalive-count +@item @code{admin-keepalive-count} (default: @code{5}) (type: integer) Same as above but for admin interface. -Defaults to @samp{5}. - -@end deftypevr - -@deftypevr {@code{libvirt-configuration} parameter} integer ovs-timeout -Timeout for Open vSwitch calls. +@item @code{ovs-timeout} (default: @code{5}) (type: integer) +Timeout for Open vSwitch calls. The @code{ovs-vsctl} utility is used +for the configuration and its timeout option is set by default to 5 +seconds to avoid potential infinite waits blocking libvirt. -The @code{ovs-vsctl} utility is used for the configuration and its -timeout option is set by default to 5 seconds to avoid potential -infinite waits blocking libvirt. - -Defaults to @samp{5}. - -@end deftypevr - -@c %end of autogenerated docs +@end table +@end deftp +@c %end of fragment @subsubheading Virtlog daemon The virtlogd service is a server side daemon component of libvirt that is diff --git a/gnu/services/virtualization.scm b/gnu/services/virtualization.scm index 555c0be55e..40dad7dc1e 100644 --- a/gnu/services/virtualization.scm +++ b/gnu/services/virtualization.scm @@ -7,6 +7,7 @@ ;;; Copyright © 2022 Leo Nikkilä <hello <at> lnikki.la> ;;; Copyright © 2023 Efraim Flashner <efraim <at> flashner.co.il> ;;; Copyright © 2024 Raven Hallsby <karl <at> hallsby.com> +;;; Copyright © 2025 Maxim Cournoyer <maxim.cournoyer <at> gmail.com> ;;; ;;; This file is part of GNU Guix. ;;; @@ -29,6 +30,7 @@ (define-module (gnu services virtualization) #:use-module (gnu image) #:use-module (gnu packages admin) #:use-module (gnu packages bash) + #:use-module (gnu packages firmware) #:use-module (gnu packages gdb) #:autoload (gnu packages gnupg) (guile-gcrypt) #:use-module (gnu packages package-management) @@ -107,6 +109,7 @@ (define-module (gnu services virtualization) libvirt-configuration-ca-file libvirt-configuration-cert-file libvirt-configuration-crl-file + libvirt-configuration-firmwares libvirt-configuration-host-uuid libvirt-configuration-host-uuid-source libvirt-configuration-keepalive-count @@ -205,6 +208,9 @@ (define (serialize-optional-string field-name val) (format #t "# ~a = \"\"\n" (uglify-field-name field-name)) (serialize-string field-name val))) +(define list-of-file-likes? + (list-of file-like?)) + (define-configuration libvirt-configuration (libvirt (file-like libvirt) @@ -212,7 +218,12 @@ (define-configuration libvirt-configuration (qemu (file-like qemu) "Qemu package.") - + (firmwares + (list-of-file-likes (list ovmf-x86-64)) + "List of UEFI/BIOS firmware packages to make available. Each firmware +package should contain a @file{share/qemu/firmware/@var{NAME}.json} QEMU +firmware metadata file." + (serializer empty-serializer)) (listen-tls? (boolean #t) "Flag listening for secure TLS connections on the public TCP/IP port. @@ -540,7 +551,6 @@ (define (%libvirt-activation config) (use-modules (guix build utils)) (mkdir-p #$sock-dir)))) - (define (libvirt-shepherd-service config) (let* ((config-file (libvirt-conf-file config)) (libvirt (libvirt-configuration-libvirt config)) @@ -553,7 +563,8 @@ (define (libvirt-shepherd-service config) (list (string-append #$libvirt "/sbin/libvirtd") "-f" #$config-file #$@(if listen-tcp? '("--listen") '())) - ;; For finding qemu, ip binaries and kernel modules. + ;; For finding qemu, firmwares, the 'ip' command and + ;; kernel modules. #:environment-variables (list (string-append @@ -564,29 +575,45 @@ (define (libvirt-shepherd-service config) "/run/booted-system/kernel/lib/modules")))) (stop #~(make-kill-destructor)))))) +(define (/etc/qemu/firmware config) + (let ((firmwares (libvirt-configuration-firmwares config))) + `(("qemu" + ,(computed-file + "etc-qemu-firmware" + (with-imported-modules '((guix build union)) + #~(begin + (use-modules (guix build union) (srfi srfi-26)) + (mkdir #$output) + (union-build (string-append #$output "/firmware") + (map (cut string-append <> "/share/qemu/firmware") + (list #$@firmwares)))))))))) + (define libvirt-service-type - (service-type (name 'libvirt) - (extensions - (list - (service-extension polkit-service-type - (compose list libvirt-configuration-libvirt)) - (service-extension profile-service-type - (lambda (config) - (list - (libvirt-configuration-libvirt config) - (libvirt-configuration-qemu config)))) - (service-extension activation-service-type - %libvirt-activation) - (service-extension shepherd-root-service-type - libvirt-shepherd-service) - (service-extension account-service-type - (const %libvirt-accounts)))) - (default-value (libvirt-configuration)) - (description "Run @command{libvirtd}, a daemon of the libvirt + (service-type + (name 'libvirt) + (extensions + (list + (service-extension polkit-service-type + (compose list libvirt-configuration-libvirt)) + (service-extension profile-service-type + (lambda (config) + (list (libvirt-configuration-libvirt config) + (libvirt-configuration-qemu config)))) + ;; Libvirt only considers the $libvirt/share/qemu/firmware and + ;; /etc/qemu/firmware directories to locate the QEMU firmware metadata + ;; specifications. + (service-extension etc-service-type /etc/qemu/firmware) + (service-extension activation-service-type + %libvirt-activation) + (service-extension shepherd-root-service-type + libvirt-shepherd-service) + (service-extension account-service-type + (const %libvirt-accounts)))) + (default-value (libvirt-configuration)) + (description "Run @command{libvirtd}, a daemon of the libvirt virtualization management system. This daemon runs on host servers and performs required management tasks for virtualized guests."))) - (define-record-type* <virtlog-configuration> virtlog-configuration make-virtlog-configuration virtlog-configuration? @@ -638,11 +665,6 @@ (define virtlog-service-type (description "Run @command{virtlogd}, a daemon libvirt that is used to manage logs from @acronym{VM, virtual machine} consoles."))) -(define (generate-libvirt-documentation) - (generate-documentation - `((libvirt-configuration ,libvirt-configuration-fields)) - 'libvirt-configuration)) - ;;; ;;; Transparent QEMU emulation via binfmt_misc. diff --git a/gnu/tests/virtualization.scm b/gnu/tests/virtualization.scm index a3c9c4014b..e08f66eb28 100644 --- a/gnu/tests/virtualization.scm +++ b/gnu/tests/virtualization.scm @@ -4,6 +4,7 @@ ;;; Copyright © 2020 Jan (janneke) Nieuwenhuizen <janneke <at> gnu.org> ;;; Copyright © 2021 Pierre Langlois <pierre.langlois <at> gmx.com> ;;; Copyright © 2022 Marius Bakke <marius <at> gnu.org> +;;; Copyright © 2025 Maxim Cournoyer <maxim.cournoyer <at> gmail.com> ;;; ;;; This file is part of GNU Guix. ;;; @@ -69,7 +70,8 @@ (define (run-libvirt-test) (define vm (virtual-machine (operating-system os) - (port-forwardings '()))) + (port-forwardings '()) + (memory-size 512))) (define test (with-imported-modules '((gnu build marionette)) @@ -135,6 +137,35 @@ (define (run-libvirt-test) "-c" "qemu:///system" "net-start" "default")) marionette)) + (test-assert "configured firmwares are available to libvirt" + (marionette-eval + '(begin + (use-modules (ice-9 popen) + (ice-9 textual-ports) + (srfi srfi-1) + (srfi srfi-26)) + (let* ((conf-firmwares (list #$@(libvirt-configuration-firmwares + (libvirt-configuration)))) + (virsh #$(file-append libvirt "/bin/virsh")) + (input-pipe (open-pipe* + OPEN_READ + virsh "-c" "qemu:///system" + "domcapabilities" "--xpath" + "/domainCapabilities/os/loader/value/text()")) + (output (get-string-all input-pipe)) + (found-firmwares (string-split (string-trim-both output) + #\newline))) + (close-pipe input-pipe) + ;; Check that every configured firmware package is covered + ;; by at least by one firmware file available to libvirt. + (every (lambda (conf-firmware) + ;; The firmwares listed by virsh contains their + ;; full file names, not just their package output. + (any (cut string-prefix? conf-firmware <>) + found-firmwares)) + conf-firmwares))) + marionette)) + (test-end)))) (gexp->derivation "libvirt-test" test)) -- 2.48.1
GNU bug tracking system
Copyright (C) 1999 Darren O. Benham,
1997,2003 nCipher Corporation Ltd,
1994-97 Ian Jackson.