Re: [PATCH v11 15/46] KVM: guest_memfd: Call arch make_shared callback for to-shared conversion

From: Ackerley Tng

Date: Fri Aug 28 2026 - 00:20:47 EST


Sean Christopherson <seanjc@xxxxxxxxxx> writes:

> On Wed, Aug 26, 2026, Ackerley Tng wrote:
>> Omit support for calling the arch hook to make private, since SNP, the only
>> implementer of the arch make-private hook today, would actually prefer
>> making private only just before faulting memory into the NPTs.
>>
>> Calling the make-private arch hook would require iterating both bindings
>> and the filemap to find the intersection of bindings and allocated
>> folios.
>
> Why would KVM need to iterate over the bindings? Only the RMP needs to be updated,
> whether or not the RMP is currently reachable is irrelevant, no?
>
> Subsequent calls to kvm_arch_gmem_make_private() from kvm_gmem_get_pfn() would be
> superfluous, but that's already possible, e.g. if an NPT mappings is removed for
> whatever reason.
>

make_private takes a gfn and pfn, so __kvm_gmem_set_attributes() would
need to iterate bindings to get gfns and filemap to find folios to get
pfns.

>> On top of that, SNP would need to figure out whether to actually
>> make private based on whether the memory is about to be faulted, or
>> whether it is a conversion.
>
> This is a non-issue, no? As above, sev_gmem_make_private() already bails early
> if the page is already assigned in the RMP.
>

I'll remove this, you're right.

> I don't care terribly about how SNP handles this, but I do want accurate reasoning
> and justification so that if/when we revisit any of this in the future, we can make
> informed decisions. Because unless I'm missing something, this is an optimization
> choice (eager vs. lazy to-private conversions), not a complexity tradeoff, and it's
> not clear to me how we decided the lazy approach would provide better performance.
>

How's this, to replace the entire commit message? I hope it captures
points from this discussion:

When memory in guest_memfd is converted from private to shared, the
platform-specific state associated with the guest-private pages must
be invalidated or cleaned up.

Iterate over the folios in the affected range and call the
kvm_arch_gmem_make_shared() hook for each PFN range. This allows
architectures to update hardware metadata or encryption states to
transition pages to the shared state, instead of leaving hardware
state as private while guest_memfd tracks it as shared. Transitioning
hardware state ensures that guest_memfd upholds the guarantee that
userspace only maps shared memory.

Invoke this helper after indicating to KVM's mmu code that an
invalidation is in progress to stop in-flight page faults from
succeeding. Calling the invalidation helper also calls the arch
invalidate hook. For SNP, this kicks any vCPU with a registered VMSA
within the range being converted out of the guest. This ensures that
make_shared never fails due to the VMSA page being in-use and is
important because if make_shared fails, the RMP table would track the
page as private while guest_memfd is unaware and tracks the page as
shared.

Omit support for calling the arch hook to make private during
to-private conversions. Making private lazily at fault time aligns
with how it works on other platforms like TDX.

Furthermore, making pages shared only requires PFNs, which are
obtained by iterating folios in the filemap. In contrast, making pages
private in the RMP also requires the GFN, which would require
iterating bindings to get GFNs and the filemap to get PFNs from
allocated folios. Deferring the transition to fault time avoids this
additional complexity.

>> Calling the make-shared arch hook and not the make-private arch hook does
>> leak SNP-specific details into guest_memfd (as in, why only make-shared
>> during conversions but not make-private?), but the additional complexity is
>> not worth taking on until guest_memfd has a user actually requiring an arch
>> make-private call.
>
> [...snip...]
>