Commit Graph

12229 Commits

Author SHA1 Message Date
Richard W.M. Jones
cfbdf9bcc7 lib/qemu.c: Remove guestfs_int_qemu_supports_device
Previously we ran 'qemu -device ?' to list devices, using the output
to test if qemu supported particular devices.  This was extensively
used in the past, but after recent commits there are no further users
of this code, so we can remove it all completely.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
4872c0cf09 lib/launch-direct.c: Assume virtio-rng
It's always a good idea to provide proper entropy to the libguestfs
appliance (eg. for any cryptographic operations).  We already assume
virtio, so we can assume virtio-rng is present.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
d8b08eac38 lib/launch-libvirt.c: Don't store libvirt_version in handle
We no longer use the libvirt version anywhere, except when reporting
the version.  Remove this from the handle.

Simplify the remaining code.  In particular:

* don't bother parsing the libvirt version, just print what
  virGetVersion gives us

* guestfs_int_version_from_libvirt is dead code, so it can be removed
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
48bad58024 lib/launch-libvirt.c: Assume libvirt >= 9.0.0 and passt support
Libvirt 9.0.0 was released in January 2023, and it seems safe to
assume that if you're enabling the non-default backend, you can at
least use a new version of libvirt.

If you're using new libvirt, might as well also assume passt is
available.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
d730fc8b7c lib/launch-libvirt.c: Remove a workaround for libvirt < 3.8.0
This version of libvirt was released in 2017.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
a68f3eee15 lib/launch-libvirt.c: Add virtio-rng unconditionally
This tested for an ancient version of libvirt, but we can assume we
are always using something more recent.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
1a45db7465 lib/qemu.c: Remove qemu -help invocation
Previously we parsed qemu -help output to get the version of qemu and
to test for other features.  After prior commits, this is no longer
done, so we can remove the qemu -help invocation and associated code
completely.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
593a382840 lib: Remove guestfs_int_qemu_version
This function is now only used in one place, to print the version of
qemu in direct mode, when debugging is enabled.

Remove this function and replace with a direct command invocation
('qemu --version').  We only need to run this command when debugging
is enabled, and we copy all of the output to the debug channel.

I have made the assumption here that qemu -version does not try to
create a display device.  (The previous invocation of qemu -help
actually ran 'qemu -display none -help' indicating that this was not
always the case.)

This is actually an improvement on before, since now we get to see the
full output of 'qemu --version'.  The new output looks like:

  libguestfs: begin testing qemu features
  libguestfs: command: run: /usr/bin/qemu-kvm
  libguestfs: command: run: \ -version
  libguestfs: qemu: QEMU emulator version 10.1.0 (qemu-10.1.0-8.fc44)
  libguestfs: qemu: Copyright (c) 2003-2025 Fabrice Bellard and the QEMU Project developers
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
788a1e4993 lib/launch-direct.c: Don't store qemu_version in handle
As we no longer use this field, no longer store it in the handle
struct.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
99921de6e0 lib/launch-direct.c: Move baseline to qemu 7.2.0 and assume passt support
We already effectively assume that qemu is much newer than the 1.3.0
baseline previously documented.  As one example, commit 47857751a7
("lib: direct: Remove test for qemu mandatory locking") assumes that
qemu >= 2.10.  Because passt support is desirable in general, let's
assume that qemu is at least version 7.2.0, and document it.

qemu 7.2.0 was released in December 2022, nearly 3 years ago, and RHEL
9 is currently on qemu 9.1.0.

This keeps the SLIRP fallback path in case passt isn't installed, but
we should remove that fallback in future too.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
dce5ce605d lib/launch-direct.c: Set lost_tick_policy=discard unconditionally
We already assume qemu version is must greater than 1.3.0 so we do not
need this qemu version test.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
ec47331b12 lib/launch-libvirt.c: Don't store qemu_version in handle
After previous commits, we no longer use the qemu version elsewhere
(after simply reporting it).  Remove all the code for storing the qemu
version.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
02d82a3c3a lib: Remove qemu version when testing for discard feature
We can assume much more recent qemu, so we don't need to have special
cases for qemu 1.5/1.6.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
5df7da7e81 lib/qemu.c: Remove int_qemu_supports function
This function, which grepped the qemu -help output to see if a command
line option was supported, is no longer used and can be removed.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
fc243a36bd lib/launch-direct.c: Remove unnecessary tests for ancient qemu features
We can safely assume that qemu supports -nodefaults and
-no-user-config, since these have been supported since forever.

-no-hpet was deprecated in qemu 8.0 and the option removed in early
2024, replaced with -machine hpet=off.  HPET defaults to 'on' in
upstream qemu, and to 'off' in downstream RHEL rebuilds.

Since (for libguestfs) we can assume an up to date Linux kernel is
running inside the guest, and that the kernel will do the right thing
with regards to timers, we don't need to mess with qemu defaults.  In
practice, Linux chooses kvm-clock.

Thanks: Thomas Huth, Daniel Berrange
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
1f1ac69b11 lib/qemu.c: Remove qmp_schema
We used to read the QMP schema so we could see if the binary supported
qemu mandatory locking.  However after commit 47857751a7 ("lib:
direct: Remove test for qemu mandatory locking") this is dead code, so
remove it.

Updates: commit 47857751a7
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
bc431d9b64 tests/regressions/rhbz790721.c: Remove this test
This was a test for a 13 year old problem to do with problems
launching libguestfs appliances in parallel.  That problem does not
affect current code.

Testing build/launch of libguestfs appliances is a valuable thing to
test.  However we start libguestfs in parallel in both the current
test suite and in higher level tools, and this test was dubious (and
breaks with recent changes).  Therefore remove the test.
2025-09-29 16:49:03 +01:00
Richard W.M. Jones
495f71affc daemon, generator: Use power of 2 for initial size of Hashtbl.create
Before 2011 it was recommended to use a prime number for the initial
size.  In 2011 the OCaml hash table was reimplemented using a hash
function based on Murmur 3.  Hashtbl.create now adjusts the initial
size to the next power of 2 (minimum 16).  So replace obsolete
'Hashtbl.create 13' with 'Hashtbl.create 16'.
2025-09-12 08:37:58 +01:00
Richard W.M. Jones
30ccb9a3e6 daemon/selinux.ml: Use setfiles -A option to reduce memory usage
In filesystems that have many millions of files, the default behaviour
of setfiles is to build a huge hash table containing every filename.
This uses up lots of memory which prevents relabelling from happening
in the reduced memory environment of the libguestfs appliance.

I added the setfiles -A option to change this default behaviour.  If
setfiles has the option then use it.

Fixes: https://issues.redhat.com/browse/RHEL-114292
Related: https://issues.redhat.com/browse/RHEL-111165
Related: https://issues.redhat.com/browse/RHEL-111505
2025-09-11 21:03:37 +01:00
Richard W.M. Jones
5f47af7f3e Version 1.57.3. v1.57.3 2025-09-09 19:18:04 +01:00
Richard W.M. Jones
a5b7de4a71 github: Add workflows file to EXTRA_DIST
Fixes: commit e218dd73cc
2025-09-09 19:11:31 +01:00
Richard W.M. Jones
365e7d79f7 github: Don't test on Ubuntu 24.04 twice
It turns out that ubuntu-latest is the same as 24.04, so we're just
testing on the same version twice.  Remove the duplication.

Thanks: Stephen Gallagher
Fixes: commit e218dd73cc
2025-09-09 17:34:15 +01:00
Cole Robinson
a2e7dfc73b New API: ntfs_chmod
Add an API to do the equivalent of `chmod [-r] MODE PATH` for
NTFS filesystems.

Files created on a linux ntfs-3g mount can not change permissions
directly. New files and directories are created with rough windows
equivalent of `chmod 777`. These wide open permissions can generate
security warnings on windows after virt-v2v installs bits into
`Program Files\Guestfs`.

Behind the scenes we use `ntfssecaudit(8)` from `ntfsprogs`
which is already part of the appliance. We only expose the chmod-style
feature; the rest of `ntfssecaudit` is concerned reporting and
managing fine grained windows security info which is way more than
we need.

Also note, `ntfssecaudit` needs to run on an unmounted partition
so using this is more complicated than a traditional `chmod` call.

Related: https://issues.redhat.com/browse/RHEL-104352

Signed-off-by: Cole Robinson <crobinso@redhat.com>
2025-09-09 16:29:13 +01:00
Richard W.M. Jones
e218dd73cc github: Add basic github CI tests
This builds libguestfs and runs the in-tree tests, ie. the basic
'./configure && make && make check'.

We're using the "free for public repositories" plan.  We run the tests
directly on an Ubuntu VM, versions 24.04 & latest.  Also on Fedora 42,
43 in a container (running on the Ubuntu VM).

The tests are run on pushes to the master branch, and on pull
requests to the master branch.

GObject is not built, since the tests fail and anyway there are some
deep problems with the GObject bindings and they probably will be
removed.

Thanks: Stephen Gallagher, Cole Robinson
2025-09-09 13:40:49 +01:00
Richard W.M. Jones
e7b36e0eba generator: Use quoted string literals for regexps
The output of the generator is identical after this change.
2025-09-02 09:11:38 +01:00
Richard W.M. Jones
02b64d5cec generator: Use quoted string literals in many places
This change was done almost entirely automatically using the script
below.  This uses the OCaml lexer to read the source files and extract
the strings and locations.  Strings which are "candidates" (in this
case, longer than 3 lines) are replaced in the output with quoted
string literals.

Since the OCaml lexer is used, it already substitutes all escape
sequences correctly.  I diffed the output of the generator and it is
identical after this change, except for UUIDs, which change because of
how Utils.stable_uuid is implemented.

Thanks: Nicolas Ojeda Bar

$ ocamlfind opt -package unix,compiler-libs.common find_strings.ml \
                -o find_strings.opt -linkpkg
$ for f in $( git ls-files -- \*.ml ) ; do ./find_strings.opt $f ; done

open Printf

let read_whole_file path =
  let buf = Buffer.create 16384 in
  let chan = open_in path in
  let maxlen = 16384 in
  let b = Bytes.create maxlen in
  let rec loop () =
    let r = input chan b 0 maxlen in
    if r > 0 then (
      Buffer.add_substring buf (Bytes.to_string b) 0 r;
      loop ()
    )
  in
  loop ();
  close_in chan;
  Buffer.contents buf

let count_chars c str =
  let count = ref 0 in
  for i = 0 to String.length str - 1 do
    if c = String.unsafe_get str i then incr count
  done;
  !count

let subs = ref []

let consider_string str loc =
  let nr_lines = count_chars '\n' str in
  if nr_lines > 3 then
    subs := (str, loc) :: !subs

let () =
  Lexer.init ();
  let filename = Sys.argv.(1) in
  let content = read_whole_file filename in
  let lexbuf = Lexing.from_string content in
  let rec loop () =
    let token = Lexer.token lexbuf in
    (match token with
     | Parser.EOF -> ();
     | STRING (s, loc, sopt) ->
        consider_string s loc; (* sopt? *)
        loop ();
     | token ->
        loop ();
    )
  in
  loop ();

  (* The list of subs is already reversed, which is convenient
   * because we must the file substitutions in reverse order.
   *)
  let subs = !subs in
  let new_content = ref content in
  List.iter (
    fun (str, loc) ->
      let { Location.loc_start = { pos_cnum = p1 };
            loc_end = { pos_cnum = p2 } } = loc in
      let len = String.length !new_content in
      let before = String.sub !new_content 0 (p1-1) in
      let after = String.sub !new_content (p2+1) (len - p2 - 1) in
      new_content := before ^ "{|" ^ str ^ "|}" ^ after
  ) subs;

  let new_content = !new_content in

  if content <> new_content then (
    (* Update the file in place. *)
    let new_filename = filename ^ ".new"
    and backup_filename = filename ^ ".bak" in
    let chan = open_out new_filename in
    fprintf chan "%s" new_content;
    close_out chan;
    Unix.rename filename backup_filename;
    Unix.rename new_filename filename
  )
2025-09-01 17:08:52 +01:00
Richard W.M. Jones
b4a98fe13a generator/actions_core.ml: Fix typo in description of read_file 2025-09-01 16:54:43 +01:00
Richard W.M. Jones
32b911a061 daemon/inspect_fs_windows.ml: Use {|..|} string literal 2025-09-01 13:59:56 +01:00
Richard W.M. Jones
f857f39a2d daemon/selinux.ml: Simplify setfiles option testing
Updates: commit 1c0b56158a
2025-08-30 14:05:34 +01:00
Richard W.M. Jones
91ee98523e daemon/selinux.ml: Fix typo in comment
Fixes: commit d0d8e67384
2025-08-27 10:43:00 +01:00
Richard W.M. Jones
e6f93dfb9f Update common submodule
Pulls in the commits listed below.  This has no effect as all changes
are confined to the common/mlcustomize subdirectory which we do not
use or ship.

  Richard W.M. Jones (4):
      mlcustomize/SELinux_relabel.ml: Add comment
      mlcustomize/SELinux_relabel.ml: Use new guestfs_setfiles API
      mlcustomize/SELinux_relabel.ml: Relabel every mountpoint
      mlcustomize/firstboot.ml: Use quoted string literals for firstboot

  Vadim Rozenfeld (1):
      Modify the firstboot script to check the scripts execution return status
2025-08-20 10:36:48 +01:00
Richard W.M. Jones
6b19b97aa6 website: Remove very old stable branches from the index page
There's no point linking to anything other than the current stable
branch.
2025-08-15 21:37:30 +01:00
Richard W.M. Jones
82764f1b3a Version 1.57.2. v1.57.2 2025-08-15 10:56:08 +01:00
Richard W.M. Jones
1c00248ac1 daemon/inspect_fs_windows.ml: Ignore blank disks in drive mapping
If HKLM\System\MountedDevices references a blank disk, then when we
try to search for the actual backing device we will get an error from
parted:

  parted: /dev/sdb: parted exited with status 1: Error: /dev/sdb: unrecognised disk label: Invalid argument

Just ignore these errors instead of failing inspection.

Fixes: https://issues.redhat.com/browse/RHEL-108803
Reported-by: Ameen Barakat
Thanks: Ming Xie
2025-08-14 15:45:59 +01:00
Richard W.M. Jones
5c7e15cfae daemon/inspect_fs_windows.ml: Add debugging when we start registry analysis
Add some debugging when we begin the process of analyzing the Windows
registry of a guest.
2025-08-14 15:45:59 +01:00
Richard W.M. Jones
e18bd72c8e daemon/inspect_fs_windows.ml: Add debugging for MBR drive mappings
The function 'map_registry_disk_blob_gpt' immediately below this one
has a debugging statement.  Add the equivalent to the function
'map_registry_disk_blob_mbr'.

The output looks like:

  map_registry_disk_blob_mbr: searching for MBR disk ID 31 32 33 34
  map_registry_disk_blob_mbr: searching for MBR partition offset 00 00 00 10 00 00 00 00
2025-08-14 15:45:59 +01:00
Richard W.M. Jones
f6267d5f71 Version 1.57.1. v1.57.1 2025-08-13 17:06:15 +01:00
Richard W.M. Jones
1c0b56158a daemon: Deprecate guestfs_selinux_relabel, replace with guestfs_setfiles
The guestfs_selinux_relabel function was very hard to use.  In
particular it didn't just do an SELinux relabel as you might expect.
Instead you have to write a whole bunch of code around it (example[1])
to make it useful.

Another problem is that it doesn't let you pass multiple paths to the
setfiles command, but the command itself does permit that (and, as it
turns out, will require it).  There is no backwards compatible way to
extend the existing definition to allow a list parameter without
breaking API.

So deprecate guestfs_selinux_relabel.  Reimplement it as
guestfs_setfiles.  The new function is basically the same as the old
one, but allows you to pass a list of paths.  The old function calls
the new function with a single path parameter.

[1] https://github.com/libguestfs/libguestfs-common/blob/master/mlcustomize/SELinux_relabel.ml
2025-08-13 16:08:28 +01:00
Richard W.M. Jones
e4d9ee3fbc generator: Allow StringList(Pathname) parameters
This was previously not implemented.  It just requires us to call
ABS_PATH on each parameter.  ABS_PATH checks the parameter is an
absolute path.
2025-08-13 16:08:28 +01:00
Richard W.M. Jones
fd4db60cff generator: Implement StringList for OCaml functions
No existing OCaml functions have a StringList parameter, but we would
like to add one.

The original plan seems to have been to map these to 'string array'
types, but 'string list' is more natural, albeit marginally less
efficient.  The implementation here just has to convert the 'char **'
into the OCaml linked list of values.
2025-08-13 16:08:28 +01:00
Richard W.M. Jones
ed40333a23 daemon: Reimplement guestfs_selinux_relabel in OCaml
No change, just reimplement the existing C implementation in OCaml.
2025-08-13 16:08:28 +01:00
Richard W.M. Jones
c931ab3bc8 daemon: sysroot: Avoid copying the path every time we call sysroot ()
This path never changes once the daemon has started up, so we don't
need to call into C code and copy the string every time.
2025-08-13 16:08:28 +01:00
Richard W.M. Jones
1e0099671a daemon: sysroot: Avoid double-/ when creating sysroot paths in OCaml
Previously calling 'sysroot_path "/dev"' for example would return the
string "/sysroot//dev".  While this is not wrong, it confuses some
external programs (hello, setfiles), and it's not very "clean".  Be a
bit more careful to avoid doubling the '/' character in the common case.
2025-08-13 16:08:28 +01:00
Cole Robinson
06db19c56c daemon: inspect: check /etc/crypttab for /dev/mapper/*
Encrypted root fs on SUSE distros will present itself like so:

```
/dev/mapper/cr_root                         /                   btrfs   defaults                0 0
UUID=588905f9-bfa4-47b5-9fe8-893cb8ad4a0b   /var                btrfs   subvol=/@/var           0 0
... more subvols here ...
UUID=8a278363-3042-4dea-a878-592f5e1b7381   swap                btrfs   defaults                0 0
/dev/mapper/cr_root                         /.snapshots         btrfs   subvol=/@/.snapshots    0 0

cr_root  UUID=5289379a-a707-41b5-994c-c383f7ed54cc  none  x-initrd.attach
```

This breaks `-i` inspection, since libguestfs doesn't know what
/dev/mapper/cr_root is supposed to be, and nothing in the appliance
will autopopulate that path. This isn't a problem on Fedora, where
it uses UUID= instead of a /dev/mapper path.

Currently when we see /dev/mapper as a mount prefix, we only attempt
to do some LVM name mapping. This extends libguestfs to check
/etc/crypttab first. If we find an entry for the mapper path, and it
points to the encrypted luks UUID, we use that UUID to build the
associated /dev/disk/by-id/dm-uuid-CRYPT-* path, which is a symlink
to the unencrypted /dev/dm-X path

Resolves: https://issues.redhat.com/browse/RHEL-93584

Signed-off-by: Cole Robinson <crobinso@redhat.com>
2025-08-12 17:55:06 +01:00
Cole Robinson
701667b6f5 docs: Fix dead ntfs-3g doc links 2025-08-04 15:49:50 +01:00
Richard W.M. Jones
217823da95 appliance/init: Add lsblk and blkid output to verbose log
This is useful for debugging.  The output looks like:

  + lsblk
  NAME        MAJ:MIN RM  SIZE RO TYPE MOUNTPOINTS
  sda           8:0    0    1G  0 disk
  |-sda1        8:1    0  512M  0 part
  `-sda2        8:2    0  512M  0 part
    |-VG-Root 252:0    0   32M  0 lvm
    |-VG-LV1  252:1    0   32M  0 lvm
    |-VG-LV2  252:2    0   32M  0 lvm
    `-VG-LV3  252:3    0   64M  0 lvm
  sdb           8:16   0    4G  0 disk /
  + blkid
  /dev/mapper/VG-LV1: UUID="cc8a3437-4169-4b1c-b432-ee8adc563f6d" BLOCK_SIZE="4096" TYPE="ext2"
  /dev/sdb: UUID="30c70ddc-d00b-4620-a408-025890e59aa6" BLOCK_SIZE="4096" TYPE="ext2"
  /dev/mapper/VG-LV2: UUID="747009aa-e183-46ba-a034-0c437b15cebc" BLOCK_SIZE="1024" TYPE="ext2"
  /dev/mapper/VG-Root: LABEL="ROOT" UUID="01234567-0123-0123-0123-012345678902" BLOCK_SIZE="4096" TYPE="ext2"
  /dev/sda2: UUID="DfEjc1-wRU6-vh8U-we7U-ivEl-FRwo-rG0ZuL" TYPE="LVM2_member" PARTUUID="184cbb43-02"
  /dev/sda1: LABEL="BOOT" UUID="01234567-0123-0123-0123-012345678901" BLOCK_SIZE="4096" TYPE="ext2" PARTUUID="184cbb43-01"
  /dev/mapper/VG-LV3: UUID="f9e5dc21-9a2a-45a0-85b0-e2889607139a" BLOCK_SIZE="2048" TYPE="ext2"

Fixes: https://issues.redhat.com/browse/RHEL-106490
2025-07-30 11:06:37 +01:00
Richard W.M. Jones
f4f84a8824 daemon: Add contents of /etc/fstab to verbose log
Also some mdadm configuration files.  This is useful for debugging.

The output looks like this:

  info: /etc/fstab in /dev/VG/Root
  LABEL=BOOT /boot ext2 default 0 0$
  LABEL=ROOT / ext2 default 0 0$

Fixes: https://issues.redhat.com/browse/RHEL-106490
2025-07-30 11:01:03 +01:00
Richard W.M. Jones
c7aaa89fba lib: libvirt: Sleep before retrying virDomainDestroyFlags
This saves us going into a loop if virDomainDestroyFlags keeps
returning -EBUSY quickly, which apparenrly can happen in containers.

The equivalent 'direct' backend code sleeps for 2 seconds in this case.
2025-07-25 09:42:39 +01:00
Richard W.M. Jones
0a91731356 lib: libvirt: Debug error from virDomainDestroyFlags
It's useful to see the error returned from virDomainDestroyFlags, so
make sure this gets written to debug output.
2025-07-25 09:41:27 +01:00
Richard W.M. Jones
dc218b25f0 appliance: Ignore sit0 network device in the guest
Reported-by: Srikanth Aithal <sraithal@amd.com>
Fixed-by: Stefano Brivio <sbrivio@redhat.com>
Tested-by: Srikanth Aithal <sraithal@amd.com>
See-also: https://lists.libguestfs.org/archives/list/guestfs@lists.libguestfs.org/thread/566LAY7RNM7T7EMQQQYIQA2VK5TXETK5/
2025-06-25 11:15:31 +01:00