xref: /openbmc/qemu/hw/s390x/s390-skeys-kvm.c (revision 5227b326)
10efe406cSJason J. Herne /*
20efe406cSJason J. Herne  * s390 storage key device
30efe406cSJason J. Herne  *
40efe406cSJason J. Herne  * Copyright 2015 IBM Corp.
50efe406cSJason J. Herne  * Author(s): Jason J. Herne <jjherne@linux.vnet.ibm.com>
60efe406cSJason J. Herne  *
70efe406cSJason J. Herne  * This work is licensed under the terms of the GNU GPL, version 2 or (at
80efe406cSJason J. Herne  * your option) any later version. See the COPYING file in the top-level
90efe406cSJason J. Herne  * directory.
100efe406cSJason J. Herne  */
110efe406cSJason J. Herne 
129615495aSPeter Maydell #include "qemu/osdep.h"
130efe406cSJason J. Herne #include "hw/s390x/storage-keys.h"
140efe406cSJason J. Herne #include "sysemu/kvm.h"
150efe406cSJason J. Herne #include "qemu/error-report.h"
160b8fa32fSMarkus Armbruster #include "qemu/module.h"
170efe406cSJason J. Herne 
kvm_s390_skeys_are_enabled(S390SKeysState * ss)18*5227b326SDavid Hildenbrand static bool kvm_s390_skeys_are_enabled(S390SKeysState *ss)
190efe406cSJason J. Herne {
200efe406cSJason J. Herne     S390SKeysClass *skeyclass = S390_SKEYS_GET_CLASS(ss);
210efe406cSJason J. Herne     uint8_t single_key;
220efe406cSJason J. Herne     int r;
230efe406cSJason J. Herne 
240efe406cSJason J. Herne     r = skeyclass->get_skeys(ss, 0, 1, &single_key);
250efe406cSJason J. Herne     if (r != 0 && r != KVM_S390_GET_SKEYS_NONE) {
269af9e0feSMarkus Armbruster         error_report("S390_GET_KEYS error %d", r);
270efe406cSJason J. Herne     }
280efe406cSJason J. Herne     return (r == 0);
290efe406cSJason J. Herne }
300efe406cSJason J. Herne 
kvm_s390_skeys_get(S390SKeysState * ss,uint64_t start_gfn,uint64_t count,uint8_t * keys)310efe406cSJason J. Herne static int kvm_s390_skeys_get(S390SKeysState *ss, uint64_t start_gfn,
320efe406cSJason J. Herne                               uint64_t count, uint8_t *keys)
330efe406cSJason J. Herne {
340efe406cSJason J. Herne     struct kvm_s390_skeys args = {
350efe406cSJason J. Herne         .start_gfn = start_gfn,
360efe406cSJason J. Herne         .count = count,
370efe406cSJason J. Herne         .skeydata_addr = (__u64)keys
380efe406cSJason J. Herne     };
390efe406cSJason J. Herne 
400efe406cSJason J. Herne     return kvm_vm_ioctl(kvm_state, KVM_S390_GET_SKEYS, &args);
410efe406cSJason J. Herne }
420efe406cSJason J. Herne 
kvm_s390_skeys_set(S390SKeysState * ss,uint64_t start_gfn,uint64_t count,uint8_t * keys)430efe406cSJason J. Herne static int kvm_s390_skeys_set(S390SKeysState *ss, uint64_t start_gfn,
440efe406cSJason J. Herne                               uint64_t count, uint8_t *keys)
450efe406cSJason J. Herne {
460efe406cSJason J. Herne     struct kvm_s390_skeys args = {
470efe406cSJason J. Herne         .start_gfn = start_gfn,
480efe406cSJason J. Herne         .count = count,
490efe406cSJason J. Herne         .skeydata_addr = (__u64)keys
500efe406cSJason J. Herne     };
510efe406cSJason J. Herne 
520efe406cSJason J. Herne     return kvm_vm_ioctl(kvm_state, KVM_S390_SET_SKEYS, &args);
530efe406cSJason J. Herne }
540efe406cSJason J. Herne 
kvm_s390_skeys_class_init(ObjectClass * oc,void * data)550efe406cSJason J. Herne static void kvm_s390_skeys_class_init(ObjectClass *oc, void *data)
560efe406cSJason J. Herne {
570efe406cSJason J. Herne     S390SKeysClass *skeyclass = S390_SKEYS_CLASS(oc);
58574ee06dSThomas Huth     DeviceClass *dc = DEVICE_CLASS(oc);
590efe406cSJason J. Herne 
60*5227b326SDavid Hildenbrand     skeyclass->skeys_are_enabled = kvm_s390_skeys_are_enabled;
610efe406cSJason J. Herne     skeyclass->get_skeys = kvm_s390_skeys_get;
620efe406cSJason J. Herne     skeyclass->set_skeys = kvm_s390_skeys_set;
63574ee06dSThomas Huth 
64574ee06dSThomas Huth     /* Reason: Internal device (only one skeys device for the whole memory) */
65574ee06dSThomas Huth     dc->user_creatable = false;
660efe406cSJason J. Herne }
670efe406cSJason J. Herne 
680efe406cSJason J. Herne static const TypeInfo kvm_s390_skeys_info = {
690efe406cSJason J. Herne     .name          = TYPE_KVM_S390_SKEYS,
700efe406cSJason J. Herne     .parent        = TYPE_S390_SKEYS,
710efe406cSJason J. Herne     .instance_size = sizeof(S390SKeysState),
720efe406cSJason J. Herne     .class_init    = kvm_s390_skeys_class_init,
730efe406cSJason J. Herne     .class_size    = sizeof(S390SKeysClass),
740efe406cSJason J. Herne };
750efe406cSJason J. Herne 
kvm_s390_skeys_register_types(void)760efe406cSJason J. Herne static void kvm_s390_skeys_register_types(void)
770efe406cSJason J. Herne {
780efe406cSJason J. Herne     type_register_static(&kvm_s390_skeys_info);
790efe406cSJason J. Herne }
800efe406cSJason J. Herne 
810efe406cSJason J. Herne type_init(kvm_s390_skeys_register_types)
82