2 * PEF (Protected Execution Facility) for POWER support
6 * This work is licensed under the terms of the GNU GPL, version 2 or later.
7 * See the COPYING file in the top-level directory.
11 #include "qemu/osdep.h"
13 #include "qapi/error.h"
14 #include "qom/object_interfaces.h"
15 #include "sysemu/kvm.h"
16 #include "migration/blocker.h"
17 #include "exec/confidential-guest-support.h"
19 #define TYPE_PEF_GUEST "pef-guest"
20 OBJECT_DECLARE_SIMPLE_TYPE(PefGuest
, PEF_GUEST
)
22 typedef struct PefGuest PefGuest
;
23 typedef struct PefGuestClass PefGuestClass
;
25 struct PefGuestClass
{
26 ConfidentialGuestSupportClass parent_class
;
32 * The PefGuest object is used for creating and managing a PEF
36 * -object pef-guest,id=pef0 \
37 * -machine ...,confidential-guest-support=pef0
40 ConfidentialGuestSupport parent_obj
;
43 static int kvmppc_svm_init(ConfidentialGuestSupport
*cgs
, Error
**errp
)
46 static Error
*pef_mig_blocker
;
48 if (!kvm_check_extension(kvm_state
, KVM_CAP_PPC_SECURE_GUEST
)) {
50 "KVM implementation does not support Secure VMs (is an ultravisor running?)");
53 int ret
= kvm_vm_enable_cap(kvm_state
, KVM_CAP_PPC_SECURE_GUEST
, 0, 1);
57 "Error enabling PEF with KVM");
62 /* add migration blocker */
63 error_setg(&pef_mig_blocker
, "PEF: Migration is not implemented");
64 /* NB: This can fail if --only-migratable is used */
65 migrate_add_blocker(&pef_mig_blocker
, &error_fatal
);
71 g_assert_not_reached();
76 * Don't set error if KVM_PPC_SVM_OFF ioctl is invoked on kernels
77 * that don't support this ioctl.
79 static int kvmppc_svm_off(Error
**errp
)
84 rc
= kvm_vm_ioctl(KVM_STATE(current_accel()), KVM_PPC_SVM_OFF
);
85 if (rc
&& rc
!= -ENOTTY
) {
86 error_setg_errno(errp
, -rc
, "KVM_PPC_SVM_OFF ioctl failed");
91 g_assert_not_reached();
95 static int pef_kvm_init(ConfidentialGuestSupport
*cgs
, Error
**errp
)
97 if (!object_dynamic_cast(OBJECT(cgs
), TYPE_PEF_GUEST
)) {
101 if (!kvm_enabled()) {
102 error_setg(errp
, "PEF requires KVM");
106 return kvmppc_svm_init(cgs
, errp
);
109 static int pef_kvm_reset(ConfidentialGuestSupport
*cgs
, Error
**errp
)
111 if (!object_dynamic_cast(OBJECT(cgs
), TYPE_PEF_GUEST
)) {
116 * If we don't have KVM we should never have been able to
117 * initialize PEF, so we should never get this far
119 assert(kvm_enabled());
121 return kvmppc_svm_off(errp
);
124 OBJECT_DEFINE_TYPE_WITH_INTERFACES(PefGuest
,
127 CONFIDENTIAL_GUEST_SUPPORT
,
128 { TYPE_USER_CREATABLE
},
131 static void pef_guest_class_init(ObjectClass
*oc
, void *data
)
133 ConfidentialGuestSupportClass
*klass
= CONFIDENTIAL_GUEST_SUPPORT_CLASS(oc
);
135 klass
->kvm_init
= pef_kvm_init
;
136 klass
->kvm_reset
= pef_kvm_reset
;
139 static void pef_guest_init(Object
*obj
)
143 static void pef_guest_finalize(Object
*obj
)