Re: [Part2 PATCH v7 35/38] KVM: SVM: Pin guest memory when SEV is active

From: Borislav Petkov
Date: Mon Nov 06 2017 - 09:43:54 EST


On Wed, Nov 01, 2017 at 04:17:20PM -0500, Brijesh Singh wrote:
> The SEV memory encryption engine uses a tweak such that two identical
> plaintext pages at different location will have different ciphertext.
> So swapping or moving ciphertext of two pages will not result in
> plaintext being swapped. Relocating (or migrating) physical backing
> pages for a SEV guest will require some additional steps. The current SEV
> key management spec does not provide commands to swap or migrate (move)
> ciphertext pages. For now, we pin the guest memory registered through
> KVM_MEMORY_ENCRYPT_REGISTER_REGION ioctl.

...

> +static int svm_register_enc_region(struct kvm *kvm,
> + struct kvm_enc_region *range)
> +{
> + struct kvm_sev_info *sev = &kvm->arch.sev_info;
> + struct enc_region *region;
> + int ret = 0;
> +
> + if (!sev_guest(kvm))
> + return -ENOTTY;
> +
> + region = kzalloc(sizeof(*region), GFP_KERNEL);
> + if (!region)
> + return -ENOMEM;
> +
> + region->pages = sev_pin_memory(kvm, range->addr, range->size, &region->npages, 1);
> + if (!region->pages) {
> + ret = -ENOMEM;
> + goto e_free;
> + }
> +
> + /*
> + * The guest may change the memory encryption attribute from C=0 -> C=1
> + * or vice versa for this memory range. Lets make sure caches are
> + * flushed to ensure that guest data gets written into memory with
> + * correct C-bit.
> + */
> + sev_clflush_pages(region->pages, region->npages);
> +
> + region->uaddr = range->addr;
> + region->size = range->size;
> + list_add_tail(&region->list, &sev->regions_list);
> + return ret;

Nothing's protecting that list from concurrent modifications of adding
and removal of regions.

--
Regards/Gruss,
Boris.

Good mailing practices for 400: avoid top-posting and trim the reply.