On Thu, Dec 05, 2024 at 03:31:05PM -0800, James Houghton wrote: > > > @@ -2062,6 +2069,20 @@ void kvm_arch_commit_memory_region(struct kvm *kvm, > > > enum kvm_mr_change change) > > > { > > > bool log_dirty_pages = new && new->flags & KVM_MEM_LOG_DIRTY_PAGES; > > > + u32 changed_flags = (new ? new->flags : 0) ^ (old ? old->flags : 0); > > > + > > > + /* > > > + * If KVM_MEM_USERFAULT changed, drop all the stage-2 mappings so that > > > + * we can (1) respect userfault-ness or (2) create block mappings. > > > + */ > > > + if ((changed_flags & KVM_MEM_USERFAULT) && change == KVM_MR_FLAGS_ONLY) > > > + kvm_arch_flush_shadow_memslot(kvm, old); > > > > I'd strongly prefer that we make (2) a userspace problem and don't > > eagerly invalidate stage-2 mappings on the USERFAULT -> !USERFAULT > > change. > > > > Having implied user-visible behaviors on ioctls is never good, and for > > systems without FEAT_S2FWB you might be better off avoiding the unmap in > > the first place. > > > > So, if userspace decides there's a benefit to invalidating the stage-2 > > MMU, it can just delete + recreate the memslot. > > Ok I think that's reasonable. So for USERFAULT -> !USERFAULT, I'll > just follow the precedent set by dirty logging. For x86 today, we > collapse the mappings, and for arm64 we do not. > > Is arm64 ever going to support collapsing back to huge mappings after > dirty logging is disabled? Patches on list is always a good place to start :) What I'd expect on FEAT_S2FWB hardware is that invalidating the whole stage-2 and faulting back in block entries would give the best experience. Only in the case of !FWB would a literal table -> block collapse be beneficial, as the MMU could potentially elide CMOs when remapping. But that assumes you're starting with a fully-mapped table and there are no holes that are "out of sync" with the guest. -- Thanks, Oliver