Hello,
This mail is a Request for Comment.
On recent Intel CPUs, some of the CPU features (mostly vmx-* subfeatures) are listed and controlled
via the MSRs (Model Specific Registers) instead of the traditional CPUID instruction method.
Right now, libvirt reads the MSR's values via /dev/cpu/*/cpu populated by the msr kernel module.
src/cpu/cpu_x86.c:
...
/* This is best effort since there might be no way to read the MSR
* when we are not running as root. */
for (i = 0; i < nmsrs; i++) {
if (virHostCPUGetMSR(msrs[i], &msr) == 0) {
virCPUx86DataItem item = {
.type = VIR_CPU_X86_DATA_MSR,
.data.msr = {
...
There are 2 potential issues:
1) As stated in the source code comment above, MSR values read might fail when libvirt is not run as root.
2) MSR values read might fail if the MSR kernel module is not loaded, this is still the case in some of the Linux distros.
but the feedback was to try to fix the issue in the libvirt source code itself. Indeed, libvirt already loads some kernel modules it depends on.
For example the NBD kernel module in src/util/virtfile.c
...
static bool
virFileNBDLoadDriver(void)
{
if (virKModIsProhibited(NBD_DRIVER)) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
_("Failed to load nbd module: administratively prohibited"));
return false;
} else {
g_autofree char *errbuf = NULL;
if ((errbuf = virKModLoad(NBD_DRIVER))) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
_("Failed to load nbd module"));
...
Andrea Bolognani's proposal of an approach that could work:
- try using the unprivileged KVM API is available (or maybe the necessary information is exposed via QMP too?) like how QEMU does;
- if that fails, try using the privileged
/dev
API; - if that fails too, load the
msr
module and try again;
I would like to have some feedback from the libvirt community about if that is worth tackling these issues and the right way to do that.
If we can end up with an agreement in this mail thread, I can work on the solution implementation and send it in a separate submission.
Best regards,
Hector