Hi, I'd like to kindly ping this patch. It has been a few weeks since submission and I haven't received any feedback yet. I'm working on getting familiar with the contribution flux. Any review, even brief comments on the approach would be very helpful! Thanks in advance, Razvan
În dum., 1 feb. 2026 la 03:08, Razvan Ghiorghe <[email protected]> a scris: > When old_size is zero and old_address refers to a shareable mapping, > mremap() should create a new mapping of the same pages according to the > mremap(2) man page. The MREMAP_MAYMOVE flag must be specified in this case. > Previously, QEMU's target_mremap() rejected this valid case with EFAULT > during > the initial validation, before checking for the special old_size == 0 > behaviour. > > This patch adds proper handling for old_size == 0: > - Validates that MREMAP_MAYMOVE flag is set (required by man spec) > - Passes the call through to the host mremap() > - Creates a new mapping without invalidating the original, with both > beeing valid and sharing the same physical memory frames. > > Tested with the reproducer from the issue on qemu-riscv64. > Resolves: https://gitlab.com/qemu-project/qemu/-/issues/3105 > Signed-off-by: Razvan Ghiorghe <[email protected]> > --- > linux-user/mmap.c | 32 ++++++++++++++++++++++++++++++++ > 1 file changed, 32 insertions(+) > > diff --git a/linux-user/mmap.c b/linux-user/mmap.c > index 4bcfaf7894..b1a84eb60a 100644 > --- a/linux-user/mmap.c > +++ b/linux-user/mmap.c > @@ -1117,6 +1117,38 @@ abi_long target_mremap(abi_ulong old_addr, > abi_ulong old_size, > errno = EINVAL; > return -1; > } > + > + if (!old_size) { > + if (!(flags & MREMAP_MAYMOVE)) { > + errno = EINVAL; > + return -1; > + } > + mmap_lock(); > + if (flags & MREMAP_FIXED) { > + host_addr = mremap(g2h_untagged(old_addr), old_size, new_size, > + flags, g2h_untagged(new_addr)); > + } else { > + host_addr = mremap(g2h_untagged(old_addr), old_size, new_size, > + flags); > + } > + > + if (host_addr == MAP_FAILED) { > + mmap_unlock(); > + return -1; > + } > + new_addr = h2g(host_addr); > + prot = page_get_flags(old_addr); > + /* > + * For old_size zero, there is nothing to clear at old_addr. > + * Only set the flags for the new mapping. They both are valid. > + */ > + page_set_flags(new_addr, new_addr + new_size - 1, > + prot | PAGE_VALID, PAGE_VALID); > + shm_region_rm_complete(new_addr, new_addr + new_size - 1); > + mmap_unlock(); > + return new_addr; > + } > + > if (!guest_range_valid_untagged(old_addr, old_size)) { > errno = EFAULT; > return -1; > -- > 2.43.0 > >
