All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH for-8.1 v8 00/17] linux-user: brk fixes
@ 2023-08-04  1:45 Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 01/17] linux-user: Unset MAP_FIXED_NOREPLACE for host Richard Henderson
                   ` (16 more replies)
  0 siblings, 17 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Changes for v8:
  * Remove adjustments to the image mapping for host page size.
    Instead, rely on target_mmap to do its job in that respect.
    This was the root cause of the 64k host page size issues.

Please review.


r~


Akihiko Odaki (6):
  linux-user: Unset MAP_FIXED_NOREPLACE for host
  linux-user: Fix MAP_FIXED_NOREPLACE on old kernels
  linux-user: Do not call get_errno() in do_brk()
  linux-user: Use MAP_FIXED_NOREPLACE for do_brk()
  linux-user: Do nothing if too small brk is specified
  linux-user: Do not align brk with host page size

Helge Deller (1):
  linux-user: Adjust initial brk when interpreter is close to executable

Richard Henderson (10):
  linux-user: Remove last_brk
  linux-user: Adjust task_unmapped_base for reserved_va
  linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h
  linux-user: Define ELF_ET_DYN_BASE in $guest/target_mman.h
  linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap
  linux-user: Use elf_et_dyn_base for ET_DYN with interpreter
  linux-user: Properly set image_info.brk in flatload
  linux-user: Do not adjust image mapping for host page size
  linux-user: Do not adjust zero_bss for host page size
  linux-user: Use zero_bss for PT_LOAD with no file contents too

 linux-user/aarch64/target_mman.h     |  13 ++
 linux-user/alpha/target_mman.h       |  11 ++
 linux-user/arm/target_mman.h         |  11 ++
 linux-user/cris/target_mman.h        |  12 ++
 linux-user/hexagon/target_mman.h     |  13 ++
 linux-user/hppa/target_mman.h        |   6 +
 linux-user/i386/target_mman.h        |  16 +++
 linux-user/loongarch64/target_mman.h |  11 ++
 linux-user/m68k/target_mman.h        |   5 +
 linux-user/microblaze/target_mman.h  |  11 ++
 linux-user/mips/target_mman.h        |  10 ++
 linux-user/nios2/target_mman.h       |  10 ++
 linux-user/openrisc/target_mman.h    |  10 ++
 linux-user/ppc/target_mman.h         |  20 +++
 linux-user/qemu.h                    |   2 -
 linux-user/riscv/target_mman.h       |  10 ++
 linux-user/s390x/target_mman.h       |  20 +++
 linux-user/sh4/target_mman.h         |   7 ++
 linux-user/sparc/target_mman.h       |  25 ++++
 linux-user/user-mmap.h               |   6 +-
 linux-user/x86_64/target_mman.h      |  15 +++
 linux-user/xtensa/target_mman.h      |  10 ++
 linux-user/elfload.c                 | 181 ++++++++++++---------------
 linux-user/flatload.c                |   2 +-
 linux-user/main.c                    |  35 +++++-
 linux-user/mmap.c                    |  68 ++++++----
 linux-user/syscall.c                 |  69 +++-------
 27 files changed, 417 insertions(+), 192 deletions(-)

-- 
2.34.1



^ permalink raw reply	[flat|nested] 40+ messages in thread

* [PATCH v8 01/17] linux-user: Unset MAP_FIXED_NOREPLACE for host
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 02/17] linux-user: Fix MAP_FIXED_NOREPLACE on old kernels Richard Henderson
                   ` (15 subsequent siblings)
  16 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Akihiko Odaki <akihiko.odaki@daynix.com>

Passing MAP_FIXED_NOREPLACE to host will fail for reserved_va because
the address space is reserved with mmap.  Replace it with MAP_FIXED
in that case.

Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com>
Message-Id: <20230802071754.14876-2-akihiko.odaki@daynix.com>
[rth: Expand inline commentary.]
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/mmap.c | 25 ++++++++++++++++++++-----
 1 file changed, 20 insertions(+), 5 deletions(-)

diff --git a/linux-user/mmap.c b/linux-user/mmap.c
index a5dfb56545..a11c630a7b 100644
--- a/linux-user/mmap.c
+++ b/linux-user/mmap.c
@@ -603,11 +603,26 @@ abi_long target_mmap(abi_ulong start, abi_ulong len, int target_prot,
             goto fail;
         }
 
-        /* Validate that the chosen range is empty. */
-        if ((flags & MAP_FIXED_NOREPLACE)
-            && !page_check_range_empty(start, last)) {
-            errno = EEXIST;
-            goto fail;
+        if (flags & MAP_FIXED_NOREPLACE) {
+            /* Validate that the chosen range is empty. */
+            if (!page_check_range_empty(start, last)) {
+                errno = EEXIST;
+                goto fail;
+            }
+
+            /*
+             * With reserved_va, the entire address space is mmaped in the
+             * host to ensure it isn't accidentally used for something else.
+             * We have just checked that the guest address is not mapped
+             * within the guest, but need to replace the host reservation.
+             *
+             * Without reserved_va, despite the guest address check above,
+             * keep MAP_FIXED_NOREPLACE so that the guest does not overwrite
+             * any host address mappings.
+             */
+            if (reserved_va) {
+                flags = (flags & ~MAP_FIXED_NOREPLACE) | MAP_FIXED;
+            }
         }
 
         /*
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 02/17] linux-user: Fix MAP_FIXED_NOREPLACE on old kernels
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 01/17] linux-user: Unset MAP_FIXED_NOREPLACE for host Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 03/17] linux-user: Do not call get_errno() in do_brk() Richard Henderson
                   ` (14 subsequent siblings)
  16 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Akihiko Odaki <akihiko.odaki@daynix.com>

The man page states:
> Note that older kernels which do not recognize the MAP_FIXED_NOREPLACE
> flag will typically (upon detecting a collision with a preexisting
> mapping) fall back to a “non-MAP_FIXED” type of behavior: they will
> return an address that is different from the requested address.
> Therefore, backward-compatible software should check the returned
> address against the requested address.
https://man7.org/linux/man-pages/man2/mmap.2.html

Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com>
Message-Id: <20230802071754.14876-3-akihiko.odaki@daynix.com>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/mmap.c | 22 +++++++++++++++++-----
 1 file changed, 17 insertions(+), 5 deletions(-)

diff --git a/linux-user/mmap.c b/linux-user/mmap.c
index a11c630a7b..90b3ef2140 100644
--- a/linux-user/mmap.c
+++ b/linux-user/mmap.c
@@ -263,7 +263,11 @@ static bool mmap_frag(abi_ulong real_start, abi_ulong start, abi_ulong last,
         void *p = mmap(host_start, qemu_host_page_size,
                        target_to_host_prot(prot),
                        flags | MAP_ANONYMOUS, -1, 0);
-        if (p == MAP_FAILED) {
+        if (p != host_start) {
+            if (p != MAP_FAILED) {
+                munmap(p, qemu_host_page_size);
+                errno = EEXIST;
+            }
             return false;
         }
         prot_old = prot;
@@ -687,17 +691,25 @@ abi_long target_mmap(abi_ulong start, abi_ulong len, int target_prot,
 
         /* map the middle (easier) */
         if (real_start < real_last) {
-            void *p;
+            void *p, *want_p;
             off_t offset1;
+            size_t len1;
 
             if (flags & MAP_ANONYMOUS) {
                 offset1 = 0;
             } else {
                 offset1 = offset + real_start - start;
             }
-            p = mmap(g2h_untagged(real_start), real_last - real_start + 1,
-                     target_to_host_prot(target_prot), flags, fd, offset1);
-            if (p == MAP_FAILED) {
+            len1 = real_last - real_start + 1;
+            want_p = g2h_untagged(real_start);
+
+            p = mmap(want_p, len1, target_to_host_prot(target_prot),
+                     flags, fd, offset1);
+            if (p != want_p) {
+                if (p != MAP_FAILED) {
+                    munmap(p, len1);
+                    errno = EEXIST;
+                }
                 goto fail;
             }
             passthrough_start = real_start;
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 03/17] linux-user: Do not call get_errno() in do_brk()
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 01/17] linux-user: Unset MAP_FIXED_NOREPLACE for host Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 02/17] linux-user: Fix MAP_FIXED_NOREPLACE on old kernels Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 04/17] linux-user: Use MAP_FIXED_NOREPLACE for do_brk() Richard Henderson
                   ` (13 subsequent siblings)
  16 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Akihiko Odaki <akihiko.odaki@daynix.com>

Later the returned value is compared with -1, and negated errno is not
expected.

Fixes: 00faf08c95 ("linux-user: Don't use MAP_FIXED in do_brk()")
Reviewed-by: Helge Deller <deller@gmx.de>
Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com>
Message-Id: <20230802071754.14876-4-akihiko.odaki@daynix.com>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/syscall.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 95727a816a..b9d2ec02f9 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -862,9 +862,9 @@ abi_long do_brk(abi_ulong brk_val)
      */
     if (new_host_brk_page > brk_page) {
         new_alloc_size = new_host_brk_page - brk_page;
-        mapped_addr = get_errno(target_mmap(brk_page, new_alloc_size,
-                                        PROT_READ|PROT_WRITE,
-                                        MAP_ANON|MAP_PRIVATE, 0, 0));
+        mapped_addr = target_mmap(brk_page, new_alloc_size,
+                                  PROT_READ|PROT_WRITE,
+                                  MAP_ANON|MAP_PRIVATE, 0, 0);
     } else {
         new_alloc_size = 0;
         mapped_addr = brk_page;
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 04/17] linux-user: Use MAP_FIXED_NOREPLACE for do_brk()
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (2 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 03/17] linux-user: Do not call get_errno() in do_brk() Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 05/17] linux-user: Do nothing if too small brk is specified Richard Henderson
                   ` (12 subsequent siblings)
  16 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Akihiko Odaki <akihiko.odaki@daynix.com>

MAP_FIXED_NOREPLACE can ensure the mapped address is fixed without
concerning that the new mapping overwrites something else.

Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com>
Message-Id: <20230802071754.14876-5-akihiko.odaki@daynix.com>
[rth: Pass -1 as fd for MAP_ANON]
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/syscall.c | 17 +++--------------
 1 file changed, 3 insertions(+), 14 deletions(-)

diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index b9d2ec02f9..f64024273f 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -854,17 +854,12 @@ abi_long do_brk(abi_ulong brk_val)
         return target_brk;
     }
 
-    /* We need to allocate more memory after the brk... Note that
-     * we don't use MAP_FIXED because that will map over the top of
-     * any existing mapping (like the one with the host libc or qemu
-     * itself); instead we treat "mapped but at wrong address" as
-     * a failure and unmap again.
-     */
     if (new_host_brk_page > brk_page) {
         new_alloc_size = new_host_brk_page - brk_page;
         mapped_addr = target_mmap(brk_page, new_alloc_size,
-                                  PROT_READ|PROT_WRITE,
-                                  MAP_ANON|MAP_PRIVATE, 0, 0);
+                                  PROT_READ | PROT_WRITE,
+                                  MAP_FIXED_NOREPLACE | MAP_ANON | MAP_PRIVATE,
+                                  -1, 0);
     } else {
         new_alloc_size = 0;
         mapped_addr = brk_page;
@@ -883,12 +878,6 @@ abi_long do_brk(abi_ulong brk_val)
         target_brk = brk_val;
         brk_page = new_host_brk_page;
         return target_brk;
-    } else if (mapped_addr != -1) {
-        /* Mapped but at wrong address, meaning there wasn't actually
-         * enough space for this brk.
-         */
-        target_munmap(mapped_addr, new_alloc_size);
-        mapped_addr = -1;
     }
 
 #if defined(TARGET_ALPHA)
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 05/17] linux-user: Do nothing if too small brk is specified
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (3 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 04/17] linux-user: Use MAP_FIXED_NOREPLACE for do_brk() Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 06/17] linux-user: Do not align brk with host page size Richard Henderson
                   ` (11 subsequent siblings)
  16 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Akihiko Odaki <akihiko.odaki@daynix.com>

Linux 6.4.7 does nothing when a value smaller than the initial brk is
specified.

Fixes: 86f04735ac ("linux-user: Fix brk() to release pages")
Reviewed-by: Helge Deller <deller@gmx.de>
Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com>
Message-Id: <20230802071754.14876-6-akihiko.odaki@daynix.com>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/syscall.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index f64024273f..e1436a3962 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -820,14 +820,14 @@ abi_long do_brk(abi_ulong brk_val)
 
     /* brk pointers are always untagged */
 
-    /* return old brk value if brk_val unchanged or zero */
-    if (!brk_val || brk_val == target_brk) {
+    /* return old brk value if brk_val unchanged */
+    if (brk_val == target_brk) {
         return target_brk;
     }
 
     /* do not allow to shrink below initial brk value */
     if (brk_val < initial_target_brk) {
-        brk_val = initial_target_brk;
+        return target_brk;
     }
 
     new_brk = TARGET_PAGE_ALIGN(brk_val);
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 06/17] linux-user: Do not align brk with host page size
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (4 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 05/17] linux-user: Do nothing if too small brk is specified Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 07/17] linux-user: Remove last_brk Richard Henderson
                   ` (10 subsequent siblings)
  16 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Akihiko Odaki <akihiko.odaki@daynix.com>

do_brk() minimizes calls into target_mmap() by aligning the address
with host page size, which is potentially larger than the target page
size. However, the current implementation of this optimization has two
bugs:

- The start of brk is rounded up with the host page size while brk
  advertises an address aligned with the target page size as the
  beginning of brk. This makes the beginning of brk unmapped.
- Content clearing after mapping is flawed. The size to clear is
  specified as HOST_PAGE_ALIGN(brk_page) - brk_page, but brk_page is
  aligned with the host page size so it is always zero.

This optimization actually has no practical benefit. It makes difference
when brk() is called multiple times with values in a range of the host
page size. However, sophisticated memory allocators try to avoid to
make such frequent brk() calls. For example, glibc 2.37 calls brk() to
shrink the heap only when there is a room more than 128 KiB. It is
rare to have a page size larger than 128 KiB if it happens.

Let's remove the optimization to fix the bugs and make the code simpler.

Fixes: 86f04735ac ("linux-user: Fix brk() to release pages")
Resolves: https://gitlab.com/qemu-project/qemu/-/issues/1616
Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com>
Message-Id: <20230802071754.14876-7-akihiko.odaki@daynix.com>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/elfload.c |  4 ++--
 linux-user/syscall.c | 54 ++++++++++----------------------------------
 2 files changed, 14 insertions(+), 44 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index 861ec07abc..2aee2298ec 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -3678,8 +3678,8 @@ int load_elf_binary(struct linux_binprm *bprm, struct image_info *info)
      * to mmap pages in this space.
      */
     if (info->reserve_brk) {
-        abi_ulong start_brk = HOST_PAGE_ALIGN(info->brk);
-        abi_ulong end_brk = HOST_PAGE_ALIGN(info->brk + info->reserve_brk);
+        abi_ulong start_brk = TARGET_PAGE_ALIGN(info->brk);
+        abi_ulong end_brk = TARGET_PAGE_ALIGN(info->brk + info->reserve_brk);
         target_munmap(start_brk, end_brk - start_brk);
     }
 
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index e1436a3962..7c2c2f6e2f 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -802,81 +802,51 @@ static inline int host_to_target_sock_type(int host_type)
 }
 
 static abi_ulong target_brk, initial_target_brk;
-static abi_ulong brk_page;
 
 void target_set_brk(abi_ulong new_brk)
 {
     target_brk = TARGET_PAGE_ALIGN(new_brk);
     initial_target_brk = target_brk;
-    brk_page = HOST_PAGE_ALIGN(target_brk);
 }
 
 /* do_brk() must return target values and target errnos. */
 abi_long do_brk(abi_ulong brk_val)
 {
     abi_long mapped_addr;
-    abi_ulong new_alloc_size;
-    abi_ulong new_brk, new_host_brk_page;
+    abi_ulong new_brk;
+    abi_ulong old_brk;
 
     /* brk pointers are always untagged */
 
-    /* return old brk value if brk_val unchanged */
-    if (brk_val == target_brk) {
-        return target_brk;
-    }
-
     /* do not allow to shrink below initial brk value */
     if (brk_val < initial_target_brk) {
         return target_brk;
     }
 
     new_brk = TARGET_PAGE_ALIGN(brk_val);
-    new_host_brk_page = HOST_PAGE_ALIGN(brk_val);
+    old_brk = TARGET_PAGE_ALIGN(target_brk);
 
-    /* brk_val and old target_brk might be on the same page */
-    if (new_brk == TARGET_PAGE_ALIGN(target_brk)) {
-        /* empty remaining bytes in (possibly larger) host page */
-        memset(g2h_untagged(new_brk), 0, new_host_brk_page - new_brk);
+    /* new and old target_brk might be on the same page */
+    if (new_brk == old_brk) {
         target_brk = brk_val;
         return target_brk;
     }
 
     /* Release heap if necesary */
-    if (new_brk < target_brk) {
-        /* empty remaining bytes in (possibly larger) host page */
-        memset(g2h_untagged(new_brk), 0, new_host_brk_page - new_brk);
-
-        /* free unused host pages and set new brk_page */
-        target_munmap(new_host_brk_page, brk_page - new_host_brk_page);
-        brk_page = new_host_brk_page;
+    if (new_brk < old_brk) {
+        target_munmap(new_brk, old_brk - new_brk);
 
         target_brk = brk_val;
         return target_brk;
     }
 
-    if (new_host_brk_page > brk_page) {
-        new_alloc_size = new_host_brk_page - brk_page;
-        mapped_addr = target_mmap(brk_page, new_alloc_size,
-                                  PROT_READ | PROT_WRITE,
-                                  MAP_FIXED_NOREPLACE | MAP_ANON | MAP_PRIVATE,
-                                  -1, 0);
-    } else {
-        new_alloc_size = 0;
-        mapped_addr = brk_page;
-    }
-
-    if (mapped_addr == brk_page) {
-        /* Heap contents are initialized to zero, as for anonymous
-         * mapped pages.  Technically the new pages are already
-         * initialized to zero since they *are* anonymous mapped
-         * pages, however we have to take care with the contents that
-         * come from the remaining part of the previous page: it may
-         * contains garbage data due to a previous heap usage (grown
-         * then shrunken).  */
-        memset(g2h_untagged(brk_page), 0, HOST_PAGE_ALIGN(brk_page) - brk_page);
+    mapped_addr = target_mmap(old_brk, new_brk - old_brk,
+                              PROT_READ | PROT_WRITE,
+                              MAP_FIXED_NOREPLACE | MAP_ANON | MAP_PRIVATE,
+                              -1, 0);
 
+    if (mapped_addr == old_brk) {
         target_brk = brk_val;
-        brk_page = new_host_brk_page;
         return target_brk;
     }
 
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 07/17] linux-user: Remove last_brk
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (5 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 06/17] linux-user: Do not align brk with host page size Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:09   ` Akihiko Odaki
  2023-08-04  8:51   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 08/17] linux-user: Adjust task_unmapped_base for reserved_va Richard Henderson
                   ` (9 subsequent siblings)
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

This variable is unused.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/user-mmap.h | 1 -
 linux-user/mmap.c      | 2 --
 2 files changed, 3 deletions(-)

diff --git a/linux-user/user-mmap.h b/linux-user/user-mmap.h
index 3fc986f92f..7265c2c116 100644
--- a/linux-user/user-mmap.h
+++ b/linux-user/user-mmap.h
@@ -26,7 +26,6 @@ abi_long target_mremap(abi_ulong old_addr, abi_ulong old_size,
                        abi_ulong new_size, unsigned long flags,
                        abi_ulong new_addr);
 abi_long target_madvise(abi_ulong start, abi_ulong len_in, int advice);
-extern unsigned long last_brk;
 extern abi_ulong mmap_next_start;
 abi_ulong mmap_find_vma(abi_ulong, abi_ulong, abi_ulong);
 void mmap_fork_start(void);
diff --git a/linux-user/mmap.c b/linux-user/mmap.c
index 90b3ef2140..eb04fab8ab 100644
--- a/linux-user/mmap.c
+++ b/linux-user/mmap.c
@@ -314,8 +314,6 @@ static bool mmap_frag(abi_ulong real_start, abi_ulong start, abi_ulong last,
 #endif
 abi_ulong mmap_next_start = TASK_UNMAPPED_BASE;
 
-unsigned long last_brk;
-
 /*
  * Subroutine of mmap_find_vma, used when we have pre-allocated
  * a chunk of guest address space.
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 08/17] linux-user: Adjust task_unmapped_base for reserved_va
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (6 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 07/17] linux-user: Remove last_brk Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:14   ` Akihiko Odaki
  2023-08-04  1:45 ` [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h Richard Henderson
                   ` (8 subsequent siblings)
  16 siblings, 1 reply; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Ensure that the chosen values for mmap_next_start and
task_unmapped_base are within the guest address space.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/user-mmap.h | 18 +++++++++++++++++-
 linux-user/main.c      | 18 ++++++++++++++++++
 linux-user/mmap.c      | 18 +++---------------
 3 files changed, 38 insertions(+), 16 deletions(-)

diff --git a/linux-user/user-mmap.h b/linux-user/user-mmap.h
index 7265c2c116..fd456e024e 100644
--- a/linux-user/user-mmap.h
+++ b/linux-user/user-mmap.h
@@ -18,6 +18,23 @@
 #ifndef LINUX_USER_USER_MMAP_H
 #define LINUX_USER_USER_MMAP_H
 
+#if HOST_LONG_BITS == 64 && TARGET_ABI_BITS == 64
+#ifdef TARGET_AARCH64
+# define TASK_UNMAPPED_BASE  0x5500000000
+#else
+# define TASK_UNMAPPED_BASE  (1ul << 38)
+#endif
+#else
+#ifdef TARGET_HPPA
+# define TASK_UNMAPPED_BASE  0xfa000000
+#else
+# define TASK_UNMAPPED_BASE  0x40000000
+#endif
+#endif
+
+extern abi_ulong task_unmapped_base;
+extern abi_ulong mmap_next_start;
+
 int target_mprotect(abi_ulong start, abi_ulong len, int prot);
 abi_long target_mmap(abi_ulong start, abi_ulong len, int prot,
                      int flags, int fd, off_t offset);
@@ -26,7 +43,6 @@ abi_long target_mremap(abi_ulong old_addr, abi_ulong old_size,
                        abi_ulong new_size, unsigned long flags,
                        abi_ulong new_addr);
 abi_long target_madvise(abi_ulong start, abi_ulong len_in, int advice);
-extern abi_ulong mmap_next_start;
 abi_ulong mmap_find_vma(abi_ulong, abi_ulong, abi_ulong);
 void mmap_fork_start(void);
 void mmap_fork_end(int child);
diff --git a/linux-user/main.c b/linux-user/main.c
index dba67ffa36..52809c260a 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -821,6 +821,24 @@ int main(int argc, char **argv, char **envp)
         reserved_va = max_reserved_va;
     }
 
+    /*
+     * Select an initial value for task_unmapped_base that is in range.
+     */
+    if (reserved_va) {
+        if (TASK_UNMAPPED_BASE < reserved_va) {
+            task_unmapped_base = TASK_UNMAPPED_BASE;
+        } else {
+            /* The most common default formula is TASK_SIZE / 3. */
+            task_unmapped_base = TARGET_PAGE_ALIGN(reserved_va / 3);
+        }
+    } else if (TASK_UNMAPPED_BASE < UINTPTR_MAX) {
+        task_unmapped_base = TASK_UNMAPPED_BASE;
+    } else {
+        /* 32-bit host: pick something medium size. */
+        task_unmapped_base = 0x10000000;
+    }
+    mmap_next_start = task_unmapped_base;
+
     {
         Error *err = NULL;
         if (seed_optarg != NULL) {
diff --git a/linux-user/mmap.c b/linux-user/mmap.c
index eb04fab8ab..84436d45c8 100644
--- a/linux-user/mmap.c
+++ b/linux-user/mmap.c
@@ -299,20 +299,8 @@ static bool mmap_frag(abi_ulong real_start, abi_ulong start, abi_ulong last,
     return true;
 }
 
-#if HOST_LONG_BITS == 64 && TARGET_ABI_BITS == 64
-#ifdef TARGET_AARCH64
-# define TASK_UNMAPPED_BASE  0x5500000000
-#else
-# define TASK_UNMAPPED_BASE  (1ul << 38)
-#endif
-#else
-#ifdef TARGET_HPPA
-# define TASK_UNMAPPED_BASE  0xfa000000
-#else
-# define TASK_UNMAPPED_BASE  0x40000000
-#endif
-#endif
-abi_ulong mmap_next_start = TASK_UNMAPPED_BASE;
+abi_ulong task_unmapped_base;
+abi_ulong mmap_next_start;
 
 /*
  * Subroutine of mmap_find_vma, used when we have pre-allocated
@@ -391,7 +379,7 @@ abi_ulong mmap_find_vma(abi_ulong start, abi_ulong size, abi_ulong align)
 
             if ((addr & (align - 1)) == 0) {
                 /* Success.  */
-                if (start == mmap_next_start && addr >= TASK_UNMAPPED_BASE) {
+                if (start == mmap_next_start && addr >= task_unmapped_base) {
                     mmap_next_start = addr + size;
                 }
                 return addr;
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (7 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 08/17] linux-user: Adjust task_unmapped_base for reserved_va Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:17   ` Akihiko Odaki
  2023-08-04 10:17   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE " Richard Henderson
                   ` (7 subsequent siblings)
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Provide default values that are as close as possible to the
values used by the guest's kernel.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/aarch64/target_mman.h     | 10 ++++++++++
 linux-user/alpha/target_mman.h       |  8 ++++++++
 linux-user/arm/target_mman.h         |  8 ++++++++
 linux-user/cris/target_mman.h        |  9 +++++++++
 linux-user/hexagon/target_mman.h     | 10 ++++++++++
 linux-user/hppa/target_mman.h        |  3 +++
 linux-user/i386/target_mman.h        | 13 +++++++++++++
 linux-user/loongarch64/target_mman.h |  8 ++++++++
 linux-user/m68k/target_mman.h        |  3 +++
 linux-user/microblaze/target_mman.h  |  8 ++++++++
 linux-user/mips/target_mman.h        |  7 +++++++
 linux-user/nios2/target_mman.h       |  7 +++++++
 linux-user/openrisc/target_mman.h    |  7 +++++++
 linux-user/ppc/target_mman.h         | 13 +++++++++++++
 linux-user/riscv/target_mman.h       |  7 +++++++
 linux-user/s390x/target_mman.h       | 10 ++++++++++
 linux-user/sh4/target_mman.h         |  4 ++++
 linux-user/sparc/target_mman.h       | 14 ++++++++++++++
 linux-user/user-mmap.h               | 14 --------------
 linux-user/x86_64/target_mman.h      | 12 ++++++++++++
 linux-user/xtensa/target_mman.h      |  6 ++++++
 21 files changed, 167 insertions(+), 14 deletions(-)

diff --git a/linux-user/aarch64/target_mman.h b/linux-user/aarch64/target_mman.h
index f721295fe1..4d3eecfb26 100644
--- a/linux-user/aarch64/target_mman.h
+++ b/linux-user/aarch64/target_mman.h
@@ -4,6 +4,16 @@
 #define TARGET_PROT_BTI         0x10
 #define TARGET_PROT_MTE         0x20
 
+/*
+ * arch/arm64/include/asm/processor.h:
+ *
+ * TASK_UNMAPPED_BASE     DEFAULT_MAP_WINDOW / 4
+ * DEFAULT_MAP_WINDOW     DEFAULT_MAP_WINDOW_64
+ * DEFAULT_MAP_WINDOW_64  UL(1) << VA_BITS_MIN
+ * VA_BITS_MIN            48 (unless explicitly configured smaller)
+ */
+#define TASK_UNMAPPED_BASE      (1ull << (48 - 2))
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/alpha/target_mman.h b/linux-user/alpha/target_mman.h
index 6bb03e7336..c90b493711 100644
--- a/linux-user/alpha/target_mman.h
+++ b/linux-user/alpha/target_mman.h
@@ -20,6 +20,14 @@
 #define TARGET_MS_SYNC 2
 #define TARGET_MS_INVALIDATE 4
 
+/*
+ * arch/alpha/include/asm/processor.h:
+ *
+ * TASK_UNMAPPED_BASE           TASK_SIZE / 2
+ * TASK_SIZE                    0x40000000000UL
+ */
+#define TASK_UNMAPPED_BASE      0x20000000000ull
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/arm/target_mman.h b/linux-user/arm/target_mman.h
index e7ba6070fe..76275b2c7e 100644
--- a/linux-user/arm/target_mman.h
+++ b/linux-user/arm/target_mman.h
@@ -1 +1,9 @@
+/*
+ * arch/arm/include/asm/memory.h
+ * TASK_UNMAPPED_BASE        ALIGN(TASK_SIZE / 3, SZ_16M)
+ * TASK_SIZE                 CONFIG_PAGE_OFFSET
+ * CONFIG_PAGE_OFFSET        0xC0000000 (default in Kconfig)
+ */
+#define TASK_UNMAPPED_BASE   0x40000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/cris/target_mman.h b/linux-user/cris/target_mman.h
index e7ba6070fe..9df7b1eda5 100644
--- a/linux-user/cris/target_mman.h
+++ b/linux-user/cris/target_mman.h
@@ -1 +1,10 @@
+/*
+ * arch/cris/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE      (PAGE_ALIGN(TASK_SIZE / 3))
+ *
+ * arch/cris/include/arch-v32/arch/processor.h
+ * TASK_SIZE               0xb0000000
+ */
+#define TASK_UNMAPPED_BASE TARGET_PAGE_ALIGN(0xb0000000 / 3)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/hexagon/target_mman.h b/linux-user/hexagon/target_mman.h
index e7ba6070fe..c5ae336e07 100644
--- a/linux-user/hexagon/target_mman.h
+++ b/linux-user/hexagon/target_mman.h
@@ -1 +1,11 @@
+/*
+ * arch/hexgon/include/asm/processor.h
+ * TASK_UNMAPPED_BASE        PAGE_ALIGN(TASK_SIZE / 3)
+ *
+ * arch/hexagon/include/asm/mem-layout.h
+ * TASK_SIZE                 PAGE_OFFSET
+ * PAGE_OFFSET               0xc0000000
+ */
+#define TASK_UNMAPPED_BASE   0x40000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/hppa/target_mman.h b/linux-user/hppa/target_mman.h
index 97f87d042a..6459e7dbdd 100644
--- a/linux-user/hppa/target_mman.h
+++ b/linux-user/hppa/target_mman.h
@@ -24,6 +24,9 @@
 #define TARGET_MS_ASYNC 2
 #define TARGET_MS_INVALIDATE 4
 
+/* arch/parisc/include/asm/processor.h: DEFAULT_MAP_BASE32 */
+#define TASK_UNMAPPED_BASE      0x40000000
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/i386/target_mman.h b/linux-user/i386/target_mman.h
index e7ba6070fe..cc3382007f 100644
--- a/linux-user/i386/target_mman.h
+++ b/linux-user/i386/target_mman.h
@@ -1 +1,14 @@
+/*
+ * arch/x86/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE         __TASK_UNMAPPED_BASE(TASK_SIZE_LOW)
+ * __TASK_UNMAPPED_BASE(S)    PAGE_ALIGN(S / 3)
+ *
+ * arch/x86/include/asm/page_32_types.h:
+ * TASK_SIZE_LOW              TASK_SIZE
+ * TASK_SIZE                  __PAGE_OFFSET
+ * __PAGE_OFFSET              CONFIG_PAGE_OFFSET
+ * CONFIG_PAGE_OFFSET         0xc0000000 (default in Kconfig)
+ */
+#define TASK_UNMAPPED_BASE    0x40000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/loongarch64/target_mman.h b/linux-user/loongarch64/target_mman.h
index e7ba6070fe..d70e44d44c 100644
--- a/linux-user/loongarch64/target_mman.h
+++ b/linux-user/loongarch64/target_mman.h
@@ -1 +1,9 @@
+/*
+ * arch/loongarch/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE         PAGE_ALIGN(TASK_SIZE / 3)
+ * TASK_SIZE64                0x1UL << (... ? VA_BITS : ...)
+ */
+#define TASK_UNMAPPED_BASE \
+    TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/m68k/target_mman.h b/linux-user/m68k/target_mman.h
index e7ba6070fe..d3eceb663b 100644
--- a/linux-user/m68k/target_mman.h
+++ b/linux-user/m68k/target_mman.h
@@ -1 +1,4 @@
+/* arch/m68k/include/asm/processor.h */
+#define TASK_UNMAPPED_BASE      0xC0000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/microblaze/target_mman.h b/linux-user/microblaze/target_mman.h
index e7ba6070fe..ffee869db4 100644
--- a/linux-user/microblaze/target_mman.h
+++ b/linux-user/microblaze/target_mman.h
@@ -1 +1,9 @@
+/*
+ * arch/microblaze/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE           (TASK_SIZE / 8 * 3)
+ * TASK_SIZE                    CONFIG_KERNEL_START
+ * CONFIG_KERNEL_START          0xc0000000 (default in Kconfig)
+ */
+#define TASK_UNMAPPED_BASE      0x48000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/mips/target_mman.h b/linux-user/mips/target_mman.h
index e97694aa4e..fe1eec2d0b 100644
--- a/linux-user/mips/target_mman.h
+++ b/linux-user/mips/target_mman.h
@@ -14,6 +14,13 @@
 #define TARGET_MAP_STACK                0x40000
 #define TARGET_MAP_HUGETLB              0x80000
 
+/*
+ * arch/mips/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE         PAGE_ALIGN(TASK_SIZE / 3)
+ */
+#define TASK_UNMAPPED_BASE \
+    TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/nios2/target_mman.h b/linux-user/nios2/target_mman.h
index e7ba6070fe..ce18f4f871 100644
--- a/linux-user/nios2/target_mman.h
+++ b/linux-user/nios2/target_mman.h
@@ -1 +1,8 @@
+/*
+ * arch/nios2/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE         PAGE_ALIGN(TASK_SIZE / 3)
+ * TASK_SIZE                  0x7FFF0000UL
+ */
+#define TASK_UNMAPPED_BASE    TARGET_PAGE_ALIGN(0x7FFF0000 / 3)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/openrisc/target_mman.h b/linux-user/openrisc/target_mman.h
index e7ba6070fe..f1aaad809d 100644
--- a/linux-user/openrisc/target_mman.h
+++ b/linux-user/openrisc/target_mman.h
@@ -1 +1,8 @@
+/*
+ * arch/openrisc/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE      (TASK_SIZE / 8 * 3)
+ * TASK_SIZE               (0x80000000UL)
+ */
+#define TASK_UNMAPPED_BASE      0x30000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/ppc/target_mman.h b/linux-user/ppc/target_mman.h
index 67cc218f2e..04f99c6077 100644
--- a/linux-user/ppc/target_mman.h
+++ b/linux-user/ppc/target_mman.h
@@ -4,6 +4,19 @@
 #define TARGET_MAP_NORESERVE            0x40
 #define TARGET_MAP_LOCKED               0x80
 
+/*
+ * arch/powerpc/include/asm/task_size_64.h
+ * TASK_UNMAPPED_BASE_USER32    (PAGE_ALIGN(TASK_SIZE_USER32 / 4))
+ * TASK_UNMAPPED_BASE_USER64    (PAGE_ALIGN(DEFAULT_MAP_WINDOW_USER64 / 4))
+ * TASK_SIZE_USER32             (0x0000000100000000UL - (1 * PAGE_SIZE))
+ * DEFAULT_MAP_WINDOW_USER64    TASK_SIZE_64TB (with 4k pages)
+ */
+#ifdef TARGET_PPC64
+#define TASK_UNMAPPED_BASE      0x0000100000000000ull
+#else
+#define TASK_UNMAPPED_BASE      0x40000000
+#endif
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/riscv/target_mman.h b/linux-user/riscv/target_mman.h
index e7ba6070fe..0f06dadbd4 100644
--- a/linux-user/riscv/target_mman.h
+++ b/linux-user/riscv/target_mman.h
@@ -1 +1,8 @@
+/*
+ * arch/loongarch/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE         PAGE_ALIGN(TASK_SIZE / 3)
+ */
+#define TASK_UNMAPPED_BASE \
+    TARGET_PAGE_ALIGN((1ull << (TARGET_VIRT_ADDR_SPACE_BITS - 1)) / 3)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/s390x/target_mman.h b/linux-user/s390x/target_mman.h
index e7ba6070fe..40d149b329 100644
--- a/linux-user/s390x/target_mman.h
+++ b/linux-user/s390x/target_mman.h
@@ -1 +1,11 @@
+/*
+ * arch/s390/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE           (... : (_REGION2_SIZE >> 1))
+ *
+ * arch/s390/include/asm/pgtable.h:
+ * _REGION2_SIZE                (1UL << _REGION2_SHIFT)
+ * _REGION2_SHIFT               42
+ */
+#define TASK_UNMAPPED_BASE      (1ull << 41)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/sh4/target_mman.h b/linux-user/sh4/target_mman.h
index e7ba6070fe..bbbc223398 100644
--- a/linux-user/sh4/target_mman.h
+++ b/linux-user/sh4/target_mman.h
@@ -1 +1,5 @@
+/* arch/sh/include/asm/processor_32.h */
+#define TASK_UNMAPPED_BASE \
+    TARGET_PAGE_ALIGN((1u << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/sparc/target_mman.h b/linux-user/sparc/target_mman.h
index 9bad99c852..692ebf9dd7 100644
--- a/linux-user/sparc/target_mman.h
+++ b/linux-user/sparc/target_mman.h
@@ -5,6 +5,20 @@
 #define TARGET_MAP_LOCKED              0x100
 #define TARGET_MAP_GROWSDOWN           0x0200
 
+/*
+ * arch/sparc/include/asm/page_64.h:
+ * TASK_UNMAPPED_BASE      (test_thread_flag(TIF_32BIT) ? \
+ *                          _AC(0x0000000070000000,UL) : \
+ *                          VA_EXCLUDE_END)
+ * But VA_EXCLUDE_END is > 0xffff800000000000UL which doesn't work
+ * in userland emulation.
+ */
+#ifdef TARGET_ABI32
+#define TASK_UNMAPPED_BASE      0x70000000
+#else
+#define TASK_UNMAPPED_BASE      (1ull << (TARGET_VIRT_ADDR_SPACE_BITS - 2))
+#endif
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/user-mmap.h b/linux-user/user-mmap.h
index fd456e024e..bae49059e0 100644
--- a/linux-user/user-mmap.h
+++ b/linux-user/user-mmap.h
@@ -18,20 +18,6 @@
 #ifndef LINUX_USER_USER_MMAP_H
 #define LINUX_USER_USER_MMAP_H
 
-#if HOST_LONG_BITS == 64 && TARGET_ABI_BITS == 64
-#ifdef TARGET_AARCH64
-# define TASK_UNMAPPED_BASE  0x5500000000
-#else
-# define TASK_UNMAPPED_BASE  (1ul << 38)
-#endif
-#else
-#ifdef TARGET_HPPA
-# define TASK_UNMAPPED_BASE  0xfa000000
-#else
-# define TASK_UNMAPPED_BASE  0x40000000
-#endif
-#endif
-
 extern abi_ulong task_unmapped_base;
 extern abi_ulong mmap_next_start;
 
diff --git a/linux-user/x86_64/target_mman.h b/linux-user/x86_64/target_mman.h
index e7ba6070fe..f9ff652b37 100644
--- a/linux-user/x86_64/target_mman.h
+++ b/linux-user/x86_64/target_mman.h
@@ -1 +1,13 @@
+/*
+ * arch/x86/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE         __TASK_UNMAPPED_BASE(TASK_SIZE_LOW)
+ * __TASK_UNMAPPED_BASE(S)    PAGE_ALIGN(S / 3)
+ *
+ * arch/x86/include/asm/page_64_types.h:
+ * TASK_SIZE_LOW              DEFAULT_MAP_WINDOW
+ * DEFAULT_MAP_WINDOW         ((1UL << 47) - PAGE_SIZE)
+ */
+#define TASK_UNMAPPED_BASE \
+    TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/xtensa/target_mman.h b/linux-user/xtensa/target_mman.h
index 3933771b5b..c4f671adb7 100644
--- a/linux-user/xtensa/target_mman.h
+++ b/linux-user/xtensa/target_mman.h
@@ -14,6 +14,12 @@
 #define TARGET_MAP_STACK                0x40000
 #define TARGET_MAP_HUGETLB              0x80000
 
+/*
+ * arch/xtensa/include/asm/processor.h:
+ * TASK_UNMAPPED_BASE           (TASK_SIZE / 2)
+ */
+#define TASK_UNMAPPED_BASE      (1u << (TARGET_VIRT_ADDR_SPACE_BITS - 1))
+
 #include "../generic/target_mman.h"
 
 #endif
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE in $guest/target_mman.h
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (8 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:20   ` Akihiko Odaki
  2023-08-04  9:50   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap Richard Henderson
                   ` (6 subsequent siblings)
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Copy each guest kernel's default value, then bound it
against reserved_va or the host address space.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/aarch64/target_mman.h     |  3 +++
 linux-user/alpha/target_mman.h       |  3 +++
 linux-user/arm/target_mman.h         |  3 +++
 linux-user/cris/target_mman.h        |  3 +++
 linux-user/hexagon/target_mman.h     |  3 +++
 linux-user/hppa/target_mman.h        |  3 +++
 linux-user/i386/target_mman.h        |  3 +++
 linux-user/loongarch64/target_mman.h |  3 +++
 linux-user/m68k/target_mman.h        |  2 ++
 linux-user/microblaze/target_mman.h  |  3 +++
 linux-user/mips/target_mman.h        |  3 +++
 linux-user/nios2/target_mman.h       |  3 +++
 linux-user/openrisc/target_mman.h    |  3 +++
 linux-user/ppc/target_mman.h         |  7 +++++++
 linux-user/riscv/target_mman.h       |  3 +++
 linux-user/s390x/target_mman.h       | 10 ++++++++++
 linux-user/sh4/target_mman.h         |  3 +++
 linux-user/sparc/target_mman.h       | 11 +++++++++++
 linux-user/user-mmap.h               |  1 +
 linux-user/x86_64/target_mman.h      |  3 +++
 linux-user/xtensa/target_mman.h      |  4 ++++
 linux-user/main.c                    | 15 +++++++++++++++
 linux-user/mmap.c                    |  1 +
 23 files changed, 96 insertions(+)

diff --git a/linux-user/aarch64/target_mman.h b/linux-user/aarch64/target_mman.h
index 4d3eecfb26..69ec5d5739 100644
--- a/linux-user/aarch64/target_mman.h
+++ b/linux-user/aarch64/target_mman.h
@@ -14,6 +14,9 @@
  */
 #define TASK_UNMAPPED_BASE      (1ull << (48 - 2))
 
+/* arch/arm64/include/asm/elf.h */
+#define ELF_ET_DYN_BASE         TARGET_PAGE_ALIGN((1ull << 48) / 3 * 2)
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/alpha/target_mman.h b/linux-user/alpha/target_mman.h
index c90b493711..8edfe2b88c 100644
--- a/linux-user/alpha/target_mman.h
+++ b/linux-user/alpha/target_mman.h
@@ -28,6 +28,9 @@
  */
 #define TASK_UNMAPPED_BASE      0x20000000000ull
 
+/* arch/alpha/include/asm/elf.h */
+#define ELF_ET_DYN_BASE         (TASK_UNMAPPED_BASE + 0x1000000)
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/arm/target_mman.h b/linux-user/arm/target_mman.h
index 76275b2c7e..51005da869 100644
--- a/linux-user/arm/target_mman.h
+++ b/linux-user/arm/target_mman.h
@@ -6,4 +6,7 @@
  */
 #define TASK_UNMAPPED_BASE   0x40000000
 
+/* arch/arm/include/asm/elf.h */
+#define ELF_ET_DYN_BASE      0x00400000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/cris/target_mman.h b/linux-user/cris/target_mman.h
index 9df7b1eda5..9ace8ac292 100644
--- a/linux-user/cris/target_mman.h
+++ b/linux-user/cris/target_mman.h
@@ -7,4 +7,7 @@
  */
 #define TASK_UNMAPPED_BASE TARGET_PAGE_ALIGN(0xb0000000 / 3)
 
+/* arch/cris/include/uapi/asm/elf.h */
+#define ELF_ET_DYN_BASE    (TASK_UNMAPPED_BASE * 2)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/hexagon/target_mman.h b/linux-user/hexagon/target_mman.h
index c5ae336e07..e6b5e2ca36 100644
--- a/linux-user/hexagon/target_mman.h
+++ b/linux-user/hexagon/target_mman.h
@@ -8,4 +8,7 @@
  */
 #define TASK_UNMAPPED_BASE   0x40000000
 
+/* arch/hexagon/include/asm/elf.h */
+#define ELF_ET_DYN_BASE      0x08000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/hppa/target_mman.h b/linux-user/hppa/target_mman.h
index 6459e7dbdd..ccda46e842 100644
--- a/linux-user/hppa/target_mman.h
+++ b/linux-user/hppa/target_mman.h
@@ -27,6 +27,9 @@
 /* arch/parisc/include/asm/processor.h: DEFAULT_MAP_BASE32 */
 #define TASK_UNMAPPED_BASE      0x40000000
 
+/* arch/parisc/include/asm/elf.h */
+#define ELF_ET_DYN_BASE         (TASK_UNMAPPED_BASE + 0x01000000)
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/i386/target_mman.h b/linux-user/i386/target_mman.h
index cc3382007f..e3b8e1eaa6 100644
--- a/linux-user/i386/target_mman.h
+++ b/linux-user/i386/target_mman.h
@@ -11,4 +11,7 @@
  */
 #define TASK_UNMAPPED_BASE    0x40000000
 
+/* arch/x86/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       0x00400000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/loongarch64/target_mman.h b/linux-user/loongarch64/target_mman.h
index d70e44d44c..8c2a3d5596 100644
--- a/linux-user/loongarch64/target_mman.h
+++ b/linux-user/loongarch64/target_mman.h
@@ -6,4 +6,7 @@
 #define TASK_UNMAPPED_BASE \
     TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
 
+/* arch/loongarch/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/m68k/target_mman.h b/linux-user/m68k/target_mman.h
index d3eceb663b..20cfe750c5 100644
--- a/linux-user/m68k/target_mman.h
+++ b/linux-user/m68k/target_mman.h
@@ -1,4 +1,6 @@
 /* arch/m68k/include/asm/processor.h */
 #define TASK_UNMAPPED_BASE      0xC0000000
+/* arch/m68k/include/asm/elf.h */
+#define ELF_ET_DYN_BASE         0xD0000000
 
 #include "../generic/target_mman.h"
diff --git a/linux-user/microblaze/target_mman.h b/linux-user/microblaze/target_mman.h
index ffee869db4..6b3dd54f89 100644
--- a/linux-user/microblaze/target_mman.h
+++ b/linux-user/microblaze/target_mman.h
@@ -6,4 +6,7 @@
  */
 #define TASK_UNMAPPED_BASE      0x48000000
 
+/* arch/microblaze/include/uapi/asm/elf.h */
+#define ELF_ET_DYN_BASE         0x08000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/mips/target_mman.h b/linux-user/mips/target_mman.h
index fe1eec2d0b..b84fe1e8a8 100644
--- a/linux-user/mips/target_mman.h
+++ b/linux-user/mips/target_mman.h
@@ -21,6 +21,9 @@
 #define TASK_UNMAPPED_BASE \
     TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
 
+/* arch/mips/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/nios2/target_mman.h b/linux-user/nios2/target_mman.h
index ce18f4f871..ab16ad4f03 100644
--- a/linux-user/nios2/target_mman.h
+++ b/linux-user/nios2/target_mman.h
@@ -5,4 +5,7 @@
  */
 #define TASK_UNMAPPED_BASE    TARGET_PAGE_ALIGN(0x7FFF0000 / 3)
 
+/* arch/nios2/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       0xD0000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/openrisc/target_mman.h b/linux-user/openrisc/target_mman.h
index f1aaad809d..243c1d5f26 100644
--- a/linux-user/openrisc/target_mman.h
+++ b/linux-user/openrisc/target_mman.h
@@ -5,4 +5,7 @@
  */
 #define TASK_UNMAPPED_BASE      0x30000000
 
+/* arch/openrisc/include/asm/elf.h */
+#define ELF_ET_DYN_BASE         0x08000000
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/ppc/target_mman.h b/linux-user/ppc/target_mman.h
index 04f99c6077..646d1ccae7 100644
--- a/linux-user/ppc/target_mman.h
+++ b/linux-user/ppc/target_mman.h
@@ -17,6 +17,13 @@
 #define TASK_UNMAPPED_BASE      0x40000000
 #endif
 
+/* arch/powerpc/include/asm/elf.h */
+#ifdef TARGET_PPC64
+#define ELF_ET_DYN_BASE         0x100000000ull
+#else
+#define ELF_ET_DYN_BASE         0x000400000
+#endif
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/riscv/target_mman.h b/linux-user/riscv/target_mman.h
index 0f06dadbd4..3049bcc67d 100644
--- a/linux-user/riscv/target_mman.h
+++ b/linux-user/riscv/target_mman.h
@@ -5,4 +5,7 @@
 #define TASK_UNMAPPED_BASE \
     TARGET_PAGE_ALIGN((1ull << (TARGET_VIRT_ADDR_SPACE_BITS - 1)) / 3)
 
+/* arch/riscv/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/s390x/target_mman.h b/linux-user/s390x/target_mman.h
index 40d149b329..c82435e381 100644
--- a/linux-user/s390x/target_mman.h
+++ b/linux-user/s390x/target_mman.h
@@ -8,4 +8,14 @@
  */
 #define TASK_UNMAPPED_BASE      (1ull << 41)
 
+/*
+ * arch/s390/include/asm/elf.h:
+ * ELF_ET_DYN_BASE              (STACK_TOP / 3 * 2) & ~((1UL << 32) - 1)
+ *
+ * arch/s390/include/asm/processor.h:
+ * STACK_TOP                    VDSO_LIMIT - VDSO_SIZE - PAGE_SIZE
+ * VDSO_LIMIT                   _REGION2_SIZE
+ */
+#define ELF_ET_DYN_BASE         (((1ull << 42) / 3 * 2) & ~0xffffffffull)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/sh4/target_mman.h b/linux-user/sh4/target_mman.h
index bbbc223398..dd9016081e 100644
--- a/linux-user/sh4/target_mman.h
+++ b/linux-user/sh4/target_mman.h
@@ -2,4 +2,7 @@
 #define TASK_UNMAPPED_BASE \
     TARGET_PAGE_ALIGN((1u << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
 
+/* arch/sh/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/sparc/target_mman.h b/linux-user/sparc/target_mman.h
index 692ebf9dd7..696ca73fe4 100644
--- a/linux-user/sparc/target_mman.h
+++ b/linux-user/sparc/target_mman.h
@@ -19,6 +19,17 @@
 #define TASK_UNMAPPED_BASE      (1ull << (TARGET_VIRT_ADDR_SPACE_BITS - 2))
 #endif
 
+/*
+ * arch/sparc/include/asm/elf_64.h
+ * Except that COMPAT_ELF_ET_DYN_BASE exactly matches TASK_UNMAPPED_BASE,
+ * so move it up a bit.
+ */
+#ifdef TARGET_ABI32
+#define ELF_ET_DYN_BASE         0x78000000
+#else
+#define ELF_ET_DYN_BASE         0x0000010000000000ull
+#endif
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/user-mmap.h b/linux-user/user-mmap.h
index bae49059e0..5dd48a458d 100644
--- a/linux-user/user-mmap.h
+++ b/linux-user/user-mmap.h
@@ -20,6 +20,7 @@
 
 extern abi_ulong task_unmapped_base;
 extern abi_ulong mmap_next_start;
+extern abi_ulong elf_et_dyn_base;
 
 int target_mprotect(abi_ulong start, abi_ulong len, int prot);
 abi_long target_mmap(abi_ulong start, abi_ulong len, int prot,
diff --git a/linux-user/x86_64/target_mman.h b/linux-user/x86_64/target_mman.h
index f9ff652b37..48fbf20b42 100644
--- a/linux-user/x86_64/target_mman.h
+++ b/linux-user/x86_64/target_mman.h
@@ -10,4 +10,7 @@
 #define TASK_UNMAPPED_BASE \
     TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
 
+/* arch/x86/include/asm/elf.h */
+#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
+
 #include "../generic/target_mman.h"
diff --git a/linux-user/xtensa/target_mman.h b/linux-user/xtensa/target_mman.h
index c4f671adb7..8fa6337a97 100644
--- a/linux-user/xtensa/target_mman.h
+++ b/linux-user/xtensa/target_mman.h
@@ -20,6 +20,10 @@
  */
 #define TASK_UNMAPPED_BASE      (1u << (TARGET_VIRT_ADDR_SPACE_BITS - 1))
 
+/* arch/xtensa/include/asm/elf.h */
+#define ELF_ET_DYN_BASE \
+    TARGET_PAGE_ALIGN((1u << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
+
 #include "../generic/target_mman.h"
 
 #endif
diff --git a/linux-user/main.c b/linux-user/main.c
index 52809c260a..e089123cfa 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -839,6 +839,21 @@ int main(int argc, char **argv, char **envp)
     }
     mmap_next_start = task_unmapped_base;
 
+    /* Similarly for elf_et_dyn_base. */
+    if (reserved_va) {
+        if (ELF_ET_DYN_BASE < reserved_va) {
+            elf_et_dyn_base = ELF_ET_DYN_BASE;
+        } else {
+            /* The most common default formula is TASK_SIZE / 3 * 2. */
+            task_unmapped_base = TARGET_PAGE_ALIGN(reserved_va / 3) * 2;
+        }
+    } else if (ELF_ET_DYN_BASE < UINTPTR_MAX) {
+        elf_et_dyn_base = ELF_ET_DYN_BASE;
+    } else {
+        /* 32-bit host: pick something medium size. */
+        task_unmapped_base = 0x18000000;
+    }
+
     {
         Error *err = NULL;
         if (seed_optarg != NULL) {
diff --git a/linux-user/mmap.c b/linux-user/mmap.c
index 84436d45c8..949c4090f3 100644
--- a/linux-user/mmap.c
+++ b/linux-user/mmap.c
@@ -301,6 +301,7 @@ static bool mmap_frag(abi_ulong real_start, abi_ulong start, abi_ulong last,
 
 abi_ulong task_unmapped_base;
 abi_ulong mmap_next_start;
+abi_ulong elf_et_dyn_base;
 
 /*
  * Subroutine of mmap_find_vma, used when we have pre-allocated
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (9 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE " Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:22   ` Akihiko Odaki
  2023-08-04 10:18   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter Richard Henderson
                   ` (5 subsequent siblings)
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Use this as extra protection for the guest mapping over
any qemu host mappings.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/elfload.c | 9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index 2aee2298ec..0c64aad8a5 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -3146,8 +3146,11 @@ static void load_elf_image(const char *image_name, int image_fd,
     /*
      * Reserve address space for all of this.
      *
-     * In the case of ET_EXEC, we supply MAP_FIXED so that we get
-     * exactly the address range that is required.
+     * In the case of ET_EXEC, we supply MAP_FIXED_NOREPLACE so that we get
+     * exactly the address range that is required.  Without reserved_va,
+     * the guest address space is not isolated.  We have attempted to avoid
+     * conflict with the host program itself via probe_guest_base, but using
+     * MAP_FIXED_NOREPLACE instead of MAP_FIXED provides an extra check.
      *
      * Otherwise this is ET_DYN, and we are searching for a location
      * that can hold the memory space required.  If the image is
@@ -3159,7 +3162,7 @@ static void load_elf_image(const char *image_name, int image_fd,
      */
     load_addr = target_mmap(loaddr, (size_t)hiaddr - loaddr + 1, PROT_NONE,
                             MAP_PRIVATE | MAP_ANON | MAP_NORESERVE |
-                            (ehdr->e_type == ET_EXEC ? MAP_FIXED : 0),
+                            (ehdr->e_type == ET_EXEC ? MAP_FIXED_NOREPLACE : 0),
                             -1, 0);
     if (load_addr == -1) {
         goto exit_mmap;
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (10 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:24   ` Akihiko Odaki
  2023-08-04 10:20   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 13/17] linux-user: Adjust initial brk when interpreter is close to executable Richard Henderson
                   ` (4 subsequent siblings)
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Follow the lead of the linux kernel in fs/binfmt_elf.c,
in which an ET_DYN executable which uses an interpreter
(usually a PIE executable) is loaded away from where the
interpreter itself will be loaded.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/elfload.c | 27 +++++++++++++++++++++++++--
 1 file changed, 25 insertions(+), 2 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index 0c64aad8a5..a3aa08a13e 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -3106,6 +3106,8 @@ static void load_elf_image(const char *image_name, int image_fd,
         }
     }
 
+    load_addr = loaddr;
+
     if (pinterp_name != NULL) {
         /*
          * This is the main executable.
@@ -3135,11 +3137,32 @@ static void load_elf_image(const char *image_name, int image_fd,
              */
             probe_guest_base(image_name, loaddr, hiaddr);
         } else {
+            abi_ulong align;
+
             /*
              * The binary is dynamic, but we still need to
              * select guest_base.  In this case we pass a size.
              */
             probe_guest_base(image_name, 0, hiaddr - loaddr);
+
+            /*
+             * Avoid collision with the loader by providing a different
+             * default load address.
+             */
+            load_addr += elf_et_dyn_base;
+
+            /*
+             * TODO: Better support for mmap alignment is desirable.
+             * Since we do not have complete control over the guest
+             * address space, we prefer the kernel to choose some address
+             * rather than force the use of LOAD_ADDR via MAP_FIXED.
+             * But without MAP_FIXED we cannot guarantee alignment,
+             * only suggest it.
+             */
+            align = pow2ceil(info->alignment);
+            if (align) {
+                load_addr &= -align;
+            }
         }
     }
 
@@ -3154,13 +3177,13 @@ static void load_elf_image(const char *image_name, int image_fd,
      *
      * Otherwise this is ET_DYN, and we are searching for a location
      * that can hold the memory space required.  If the image is
-     * pre-linked, LOADDR will be non-zero, and the kernel should
+     * pre-linked, LOAD_ADDR will be non-zero, and the kernel should
      * honor that address if it happens to be free.
      *
      * In both cases, we will overwrite pages in this range with mappings
      * from the executable.
      */
-    load_addr = target_mmap(loaddr, (size_t)hiaddr - loaddr + 1, PROT_NONE,
+    load_addr = target_mmap(load_addr, (size_t)hiaddr - loaddr + 1, PROT_NONE,
                             MAP_PRIVATE | MAP_ANON | MAP_NORESERVE |
                             (ehdr->e_type == ET_EXEC ? MAP_FIXED_NOREPLACE : 0),
                             -1, 0);
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 13/17] linux-user: Adjust initial brk when interpreter is close to executable
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (11 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:26   ` Akihiko Odaki
  2023-08-04  1:45 ` [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload Richard Henderson
                   ` (3 subsequent siblings)
  16 siblings, 1 reply; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

From: Helge Deller <deller@gmx.de>

While we attempt to load a ET_DYN executable far away from
TASK_UNMAPPED_BASE, we are not completely in control of the
address space layout.  If the interpreter lands close to
the executable, leaving insufficient heap space, move brk.

Signed-off-by: Helge Deller <deller@gmx.de>
[rth: Re-order after ELF_ET_DYN_BASE patch so that we do not
 "temporarily break" tsan, and also to minimize the changes required.
 Remove image_info.reserve_brk as unused.]
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/qemu.h    |  1 -
 linux-user/elfload.c | 51 +++++++++++++-------------------------------
 2 files changed, 15 insertions(+), 37 deletions(-)

diff --git a/linux-user/qemu.h b/linux-user/qemu.h
index 802794db63..4b0c9da0dc 100644
--- a/linux-user/qemu.h
+++ b/linux-user/qemu.h
@@ -31,7 +31,6 @@ struct image_info {
         abi_ulong       end_data;
         abi_ulong       start_brk;
         abi_ulong       brk;
-        abi_ulong       reserve_brk;
         abi_ulong       start_mmap;
         abi_ulong       start_stack;
         abi_ulong       stack_limit;
diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index a3aa08a13e..fa0c9ace8e 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -3109,27 +3109,6 @@ static void load_elf_image(const char *image_name, int image_fd,
     load_addr = loaddr;
 
     if (pinterp_name != NULL) {
-        /*
-         * This is the main executable.
-         *
-         * Reserve extra space for brk.
-         * We hold on to this space while placing the interpreter
-         * and the stack, lest they be placed immediately after
-         * the data segment and block allocation from the brk.
-         *
-         * 16MB is chosen as "large enough" without being so large as
-         * to allow the result to not fit with a 32-bit guest on a
-         * 32-bit host. However some 64 bit guests (e.g. s390x)
-         * attempt to place their heap further ahead and currently
-         * nothing stops them smashing into QEMUs address space.
-         */
-#if TARGET_LONG_BITS == 64
-        info->reserve_brk = 32 * MiB;
-#else
-        info->reserve_brk = 16 * MiB;
-#endif
-        hiaddr += info->reserve_brk;
-
         if (ehdr->e_type == ET_EXEC) {
             /*
              * Make sure that the low address does not conflict with
@@ -3220,7 +3199,8 @@ static void load_elf_image(const char *image_name, int image_fd,
     info->end_code = 0;
     info->start_data = -1;
     info->end_data = 0;
-    info->brk = 0;
+    /* Usual start for brk is after all sections of the main executable. */
+    info->brk = TARGET_PAGE_ALIGN(hiaddr);
     info->elf_flags = ehdr->e_flags;
 
     prot_exec = PROT_EXEC;
@@ -3314,9 +3294,6 @@ static void load_elf_image(const char *image_name, int image_fd,
                     info->end_data = vaddr_ef;
                 }
             }
-            if (vaddr_em > info->brk) {
-                info->brk = vaddr_em;
-            }
 #ifdef TARGET_MIPS
         } else if (eppnt->p_type == PT_MIPS_ABIFLAGS) {
             Mips_elf_abiflags_v0 abiflags;
@@ -3645,6 +3622,19 @@ int load_elf_binary(struct linux_binprm *bprm, struct image_info *info)
     if (elf_interpreter) {
         load_elf_interp(elf_interpreter, &interp_info, bprm->buf);
 
+        /*
+         * While unusual because of ELF_ET_DYN_BASE, if we are unlucky
+         * with the mappings the interpreter can be loaded above but
+         * near the main executable, which can leave very little room
+         * for the heap.
+         * If the current brk has less than 16MB, use the end of the
+         * interpreter.
+         */
+        if (interp_info.brk > info->brk &&
+            interp_info.load_bias - info->brk < 16 * MiB)  {
+            info->brk = interp_info.brk;
+        }
+
         /* If the program interpreter is one of these two, then assume
            an iBCS2 image.  Otherwise assume a native linux image.  */
 
@@ -3698,17 +3688,6 @@ int load_elf_binary(struct linux_binprm *bprm, struct image_info *info)
     bprm->core_dump = &elf_core_dump;
 #endif
 
-    /*
-     * If we reserved extra space for brk, release it now.
-     * The implementation of do_brk in syscalls.c expects to be able
-     * to mmap pages in this space.
-     */
-    if (info->reserve_brk) {
-        abi_ulong start_brk = TARGET_PAGE_ALIGN(info->brk);
-        abi_ulong end_brk = TARGET_PAGE_ALIGN(info->brk + info->reserve_brk);
-        target_munmap(start_brk, end_brk - start_brk);
-    }
-
     return 0;
 }
 
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (12 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 13/17] linux-user: Adjust initial brk when interpreter is close to executable Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:27   ` Akihiko Odaki
  2023-08-04 10:22   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size Richard Henderson
                   ` (2 subsequent siblings)
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

The heap starts at "brk" not "start_brk".  With this fixed,
image_info.start_brk is unused and may be removed.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/qemu.h     | 1 -
 linux-user/flatload.c | 2 +-
 linux-user/main.c     | 2 --
 3 files changed, 1 insertion(+), 4 deletions(-)

diff --git a/linux-user/qemu.h b/linux-user/qemu.h
index 4b0c9da0dc..4f8b55e2fb 100644
--- a/linux-user/qemu.h
+++ b/linux-user/qemu.h
@@ -29,7 +29,6 @@ struct image_info {
         abi_ulong       end_code;
         abi_ulong       start_data;
         abi_ulong       end_data;
-        abi_ulong       start_brk;
         abi_ulong       brk;
         abi_ulong       start_mmap;
         abi_ulong       start_stack;
diff --git a/linux-user/flatload.c b/linux-user/flatload.c
index 5efec2630e..8f5e9f489b 100644
--- a/linux-user/flatload.c
+++ b/linux-user/flatload.c
@@ -811,7 +811,7 @@ int load_flt_binary(struct linux_binprm *bprm, struct image_info *info)
     info->end_code = libinfo[0].start_code + libinfo[0].text_len;
     info->start_data = libinfo[0].start_data;
     info->end_data = libinfo[0].end_data;
-    info->start_brk = libinfo[0].start_brk;
+    info->brk = libinfo[0].start_brk;
     info->start_stack = sp;
     info->stack_limit = libinfo[0].start_brk;
     info->entry = start_addr;
diff --git a/linux-user/main.c b/linux-user/main.c
index e089123cfa..51ee8649e2 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -953,8 +953,6 @@ int main(int argc, char **argv, char **envp)
             fprintf(f, "page layout changed following binary load\n");
             page_dump(f);
 
-            fprintf(f, "start_brk   0x" TARGET_ABI_FMT_lx "\n",
-                    info->start_brk);
             fprintf(f, "end_code    0x" TARGET_ABI_FMT_lx "\n",
                     info->end_code);
             fprintf(f, "start_code  0x" TARGET_ABI_FMT_lx "\n",
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (13 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:28   ` Akihiko Odaki
  2023-08-04 10:23   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 16/17] linux-user: Do not adjust zero_bss " Richard Henderson
  2023-08-04  1:45 ` [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too Richard Henderson
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Remove TARGET_ELF_EXEC_PAGESIZE, and 3 other TARGET_ELF_PAGE* macros
based off of that.  Rely on target_mmap to handle guest vs host page
size mismatch.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/elfload.c | 17 ++++-------------
 1 file changed, 4 insertions(+), 13 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index fa0c9ace8e..e853a4ab33 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -1959,15 +1959,6 @@ struct exec
 #define ZMAGIC 0413
 #define QMAGIC 0314
 
-/* Necessary parameters */
-#define TARGET_ELF_EXEC_PAGESIZE \
-        (((eppnt->p_align & ~qemu_host_page_mask) != 0) ? \
-         TARGET_PAGE_SIZE : MAX(qemu_host_page_size, TARGET_PAGE_SIZE))
-#define TARGET_ELF_PAGELENGTH(_v) ROUND_UP((_v), TARGET_ELF_EXEC_PAGESIZE)
-#define TARGET_ELF_PAGESTART(_v) ((_v) & \
-                                 ~(abi_ulong)(TARGET_ELF_EXEC_PAGESIZE-1))
-#define TARGET_ELF_PAGEOFFSET(_v) ((_v) & (TARGET_ELF_EXEC_PAGESIZE-1))
-
 #define DLINFO_ITEMS 16
 
 static inline void memcpy_fromfs(void * to, const void * from, unsigned long n)
@@ -3240,8 +3231,8 @@ static void load_elf_image(const char *image_name, int image_fd,
             }
 
             vaddr = load_bias + eppnt->p_vaddr;
-            vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr);
-            vaddr_ps = TARGET_ELF_PAGESTART(vaddr);
+            vaddr_po = vaddr & ~TARGET_PAGE_MASK;
+            vaddr_ps = vaddr & TARGET_PAGE_MASK;
 
             vaddr_ef = vaddr + eppnt->p_filesz;
             vaddr_em = vaddr + eppnt->p_memsz;
@@ -3251,7 +3242,7 @@ static void load_elf_image(const char *image_name, int image_fd,
              * but no backing file segment.
              */
             if (eppnt->p_filesz != 0) {
-                vaddr_len = TARGET_ELF_PAGELENGTH(eppnt->p_filesz + vaddr_po);
+                vaddr_len = eppnt->p_filesz + vaddr_po;
                 error = target_mmap(vaddr_ps, vaddr_len, elf_prot,
                                     MAP_PRIVATE | MAP_FIXED,
                                     image_fd, eppnt->p_offset - vaddr_po);
@@ -3267,7 +3258,7 @@ static void load_elf_image(const char *image_name, int image_fd,
                     zero_bss(vaddr_ef, vaddr_em, elf_prot);
                 }
             } else if (eppnt->p_memsz != 0) {
-                vaddr_len = TARGET_ELF_PAGELENGTH(eppnt->p_memsz + vaddr_po);
+                vaddr_len = eppnt->p_memsz + vaddr_po;
                 error = target_mmap(vaddr_ps, vaddr_len, elf_prot,
                                     MAP_PRIVATE | MAP_FIXED | MAP_ANONYMOUS,
                                     -1, 0);
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 16/17] linux-user: Do not adjust zero_bss for host page size
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (14 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  5:56   ` Akihiko Odaki
  2023-08-04 10:24   ` Helge Deller
  2023-08-04  1:45 ` [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too Richard Henderson
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

Rely on target_mmap to handle guest vs host page size mismatch.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/elfload.c | 54 +++++++++++++++++++-------------------------
 1 file changed, 23 insertions(+), 31 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index e853a4ab33..66ab617bd1 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -2212,44 +2212,36 @@ static abi_ulong setup_arg_pages(struct linux_binprm *bprm,
 
 /* Map and zero the bss.  We need to explicitly zero any fractional pages
    after the data section (i.e. bss).  */
-static void zero_bss(abi_ulong elf_bss, abi_ulong last_bss, int prot)
+static void zero_bss(abi_ulong start_bss, abi_ulong end_bss, int prot)
 {
-    uintptr_t host_start, host_map_start, host_end;
+    abi_ulong align_bss;
 
-    last_bss = TARGET_PAGE_ALIGN(last_bss);
+    align_bss = TARGET_PAGE_ALIGN(start_bss);
+    end_bss = TARGET_PAGE_ALIGN(end_bss);
 
-    /* ??? There is confusion between qemu_real_host_page_size and
-       qemu_host_page_size here and elsewhere in target_mmap, which
-       may lead to the end of the data section mapping from the file
-       not being mapped.  At least there was an explicit test and
-       comment for that here, suggesting that "the file size must
-       be known".  The comment probably pre-dates the introduction
-       of the fstat system call in target_mmap which does in fact
-       find out the size.  What isn't clear is if the workaround
-       here is still actually needed.  For now, continue with it,
-       but merge it with the "normal" mmap that would allocate the bss.  */
+    if (start_bss < align_bss) {
+        int flags = page_get_flags(start_bss);
 
-    host_start = (uintptr_t) g2h_untagged(elf_bss);
-    host_end = (uintptr_t) g2h_untagged(last_bss);
-    host_map_start = REAL_HOST_PAGE_ALIGN(host_start);
-
-    if (host_map_start < host_end) {
-        void *p = mmap((void *)host_map_start, host_end - host_map_start,
-                       prot, MAP_FIXED | MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
-        if (p == MAP_FAILED) {
-            perror("cannot mmap brk");
-            exit(-1);
+        if (!(flags & PAGE_VALID)) {
+            /* Map the start of the bss. */
+            align_bss -= TARGET_PAGE_SIZE;
+        } else if (flags & PAGE_WRITE) {
+            /* The page is already mapped writable. */
+            memset(g2h_untagged(start_bss), 0, align_bss - start_bss);
+        } else {
+            /* Read-only zeros? */
+            g_assert_not_reached();
         }
     }
 
-    /* Ensure that the bss page(s) are valid */
-    if ((page_get_flags(last_bss-1) & prot) != prot) {
-        page_set_flags(elf_bss & TARGET_PAGE_MASK, last_bss - 1,
-                       prot | PAGE_VALID);
-    }
-
-    if (host_start < host_map_start) {
-        memset((void *)host_start, 0, host_map_start - host_start);
+    if (align_bss < end_bss) {
+        abi_long err = target_mmap(align_bss, end_bss - align_bss, prot,
+                                   MAP_FIXED | MAP_PRIVATE | MAP_ANONYMOUS,
+                                   -1, 0);
+        if (err == -1) {
+            perror("cannot mmap brk");
+            exit(-1);
+        }
     }
 }
 
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too
  2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
                   ` (15 preceding siblings ...)
  2023-08-04  1:45 ` [PATCH v8 16/17] linux-user: Do not adjust zero_bss " Richard Henderson
@ 2023-08-04  1:45 ` Richard Henderson
  2023-08-04  6:02   ` Akihiko Odaki
  2023-08-04 10:25   ` Helge Deller
  16 siblings, 2 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04  1:45 UTC (permalink / raw)
  To: qemu-devel; +Cc: joel, akihiko.odaki, laurent, deller

If p_filesz == 0, then vaddr_ef == vaddr.  We can reuse the
code in zero_bss rather than incompletely duplicating it in
load_elf_image.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 linux-user/elfload.c | 27 +++++++--------------------
 1 file changed, 7 insertions(+), 20 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index 66ab617bd1..51591a1d94 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -3209,7 +3209,7 @@ static void load_elf_image(const char *image_name, int image_fd,
     for (i = 0; i < ehdr->e_phnum; i++) {
         struct elf_phdr *eppnt = phdr + i;
         if (eppnt->p_type == PT_LOAD) {
-            abi_ulong vaddr, vaddr_po, vaddr_ps, vaddr_ef, vaddr_em, vaddr_len;
+            abi_ulong vaddr, vaddr_po, vaddr_ps, vaddr_ef, vaddr_em;
             int elf_prot = 0;
 
             if (eppnt->p_flags & PF_R) {
@@ -3234,30 +3234,17 @@ static void load_elf_image(const char *image_name, int image_fd,
              * but no backing file segment.
              */
             if (eppnt->p_filesz != 0) {
-                vaddr_len = eppnt->p_filesz + vaddr_po;
-                error = target_mmap(vaddr_ps, vaddr_len, elf_prot,
-                                    MAP_PRIVATE | MAP_FIXED,
+                error = target_mmap(vaddr_ps, eppnt->p_filesz + vaddr_po,
+                                    elf_prot, MAP_PRIVATE | MAP_FIXED,
                                     image_fd, eppnt->p_offset - vaddr_po);
-
                 if (error == -1) {
                     goto exit_mmap;
                 }
+            }
 
-                /*
-                 * If the load segment requests extra zeros (e.g. bss), map it.
-                 */
-                if (eppnt->p_filesz < eppnt->p_memsz) {
-                    zero_bss(vaddr_ef, vaddr_em, elf_prot);
-                }
-            } else if (eppnt->p_memsz != 0) {
-                vaddr_len = eppnt->p_memsz + vaddr_po;
-                error = target_mmap(vaddr_ps, vaddr_len, elf_prot,
-                                    MAP_PRIVATE | MAP_FIXED | MAP_ANONYMOUS,
-                                    -1, 0);
-
-                if (error == -1) {
-                    goto exit_mmap;
-                }
+            /* If the load segment requests extra zeros (e.g. bss), map it. */
+            if (vaddr_ef < vaddr_em) {
+                zero_bss(vaddr_ef, vaddr_em, elf_prot);
             }
 
             /* Find the full program boundaries.  */
-- 
2.34.1



^ permalink raw reply related	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 07/17] linux-user: Remove last_brk
  2023-08-04  1:45 ` [PATCH v8 07/17] linux-user: Remove last_brk Richard Henderson
@ 2023-08-04  5:09   ` Akihiko Odaki
  2023-08-04  8:51   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:09 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> This variable is unused.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 08/17] linux-user: Adjust task_unmapped_base for reserved_va
  2023-08-04  1:45 ` [PATCH v8 08/17] linux-user: Adjust task_unmapped_base for reserved_va Richard Henderson
@ 2023-08-04  5:14   ` Akihiko Odaki
  0 siblings, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:14 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Ensure that the chosen values for mmap_next_start and
> task_unmapped_base are within the guest address space.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h
  2023-08-04  1:45 ` [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h Richard Henderson
@ 2023-08-04  5:17   ` Akihiko Odaki
  2023-08-04 10:17   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:17 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Provide default values that are as close as possible to the
> values used by the guest's kernel.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE in $guest/target_mman.h
  2023-08-04  1:45 ` [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE " Richard Henderson
@ 2023-08-04  5:20   ` Akihiko Odaki
  2023-08-04 14:09     ` Richard Henderson
  2023-08-04  9:50   ` Helge Deller
  1 sibling, 1 reply; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:20 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Copy each guest kernel's default value, then bound it
> against reserved_va or the host address space.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>   linux-user/aarch64/target_mman.h     |  3 +++
>   linux-user/alpha/target_mman.h       |  3 +++
>   linux-user/arm/target_mman.h         |  3 +++
>   linux-user/cris/target_mman.h        |  3 +++
>   linux-user/hexagon/target_mman.h     |  3 +++
>   linux-user/hppa/target_mman.h        |  3 +++
>   linux-user/i386/target_mman.h        |  3 +++
>   linux-user/loongarch64/target_mman.h |  3 +++
>   linux-user/m68k/target_mman.h        |  2 ++
>   linux-user/microblaze/target_mman.h  |  3 +++
>   linux-user/mips/target_mman.h        |  3 +++
>   linux-user/nios2/target_mman.h       |  3 +++
>   linux-user/openrisc/target_mman.h    |  3 +++
>   linux-user/ppc/target_mman.h         |  7 +++++++
>   linux-user/riscv/target_mman.h       |  3 +++
>   linux-user/s390x/target_mman.h       | 10 ++++++++++
>   linux-user/sh4/target_mman.h         |  3 +++
>   linux-user/sparc/target_mman.h       | 11 +++++++++++
>   linux-user/user-mmap.h               |  1 +
>   linux-user/x86_64/target_mman.h      |  3 +++
>   linux-user/xtensa/target_mman.h      |  4 ++++
>   linux-user/main.c                    | 15 +++++++++++++++
>   linux-user/mmap.c                    |  1 +
>   23 files changed, 96 insertions(+)
> 
> diff --git a/linux-user/aarch64/target_mman.h b/linux-user/aarch64/target_mman.h
> index 4d3eecfb26..69ec5d5739 100644
> --- a/linux-user/aarch64/target_mman.h
> +++ b/linux-user/aarch64/target_mman.h
> @@ -14,6 +14,9 @@
>    */
>   #define TASK_UNMAPPED_BASE      (1ull << (48 - 2))
>   
> +/* arch/arm64/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE         TARGET_PAGE_ALIGN((1ull << 48) / 3 * 2)
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/alpha/target_mman.h b/linux-user/alpha/target_mman.h
> index c90b493711..8edfe2b88c 100644
> --- a/linux-user/alpha/target_mman.h
> +++ b/linux-user/alpha/target_mman.h
> @@ -28,6 +28,9 @@
>    */
>   #define TASK_UNMAPPED_BASE      0x20000000000ull
>   
> +/* arch/alpha/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE         (TASK_UNMAPPED_BASE + 0x1000000)
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/arm/target_mman.h b/linux-user/arm/target_mman.h
> index 76275b2c7e..51005da869 100644
> --- a/linux-user/arm/target_mman.h
> +++ b/linux-user/arm/target_mman.h
> @@ -6,4 +6,7 @@
>    */
>   #define TASK_UNMAPPED_BASE   0x40000000
>   
> +/* arch/arm/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE      0x00400000
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/cris/target_mman.h b/linux-user/cris/target_mman.h
> index 9df7b1eda5..9ace8ac292 100644
> --- a/linux-user/cris/target_mman.h
> +++ b/linux-user/cris/target_mman.h
> @@ -7,4 +7,7 @@
>    */
>   #define TASK_UNMAPPED_BASE TARGET_PAGE_ALIGN(0xb0000000 / 3)
>   
> +/* arch/cris/include/uapi/asm/elf.h */
> +#define ELF_ET_DYN_BASE    (TASK_UNMAPPED_BASE * 2)
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/hexagon/target_mman.h b/linux-user/hexagon/target_mman.h
> index c5ae336e07..e6b5e2ca36 100644
> --- a/linux-user/hexagon/target_mman.h
> +++ b/linux-user/hexagon/target_mman.h
> @@ -8,4 +8,7 @@
>    */
>   #define TASK_UNMAPPED_BASE   0x40000000
>   
> +/* arch/hexagon/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE      0x08000000
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/hppa/target_mman.h b/linux-user/hppa/target_mman.h
> index 6459e7dbdd..ccda46e842 100644
> --- a/linux-user/hppa/target_mman.h
> +++ b/linux-user/hppa/target_mman.h
> @@ -27,6 +27,9 @@
>   /* arch/parisc/include/asm/processor.h: DEFAULT_MAP_BASE32 */
>   #define TASK_UNMAPPED_BASE      0x40000000
>   
> +/* arch/parisc/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE         (TASK_UNMAPPED_BASE + 0x01000000)
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/i386/target_mman.h b/linux-user/i386/target_mman.h
> index cc3382007f..e3b8e1eaa6 100644
> --- a/linux-user/i386/target_mman.h
> +++ b/linux-user/i386/target_mman.h
> @@ -11,4 +11,7 @@
>    */
>   #define TASK_UNMAPPED_BASE    0x40000000
>   
> +/* arch/x86/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       0x00400000
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/loongarch64/target_mman.h b/linux-user/loongarch64/target_mman.h
> index d70e44d44c..8c2a3d5596 100644
> --- a/linux-user/loongarch64/target_mman.h
> +++ b/linux-user/loongarch64/target_mman.h
> @@ -6,4 +6,7 @@
>   #define TASK_UNMAPPED_BASE \
>       TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
>   
> +/* arch/loongarch/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/m68k/target_mman.h b/linux-user/m68k/target_mman.h
> index d3eceb663b..20cfe750c5 100644
> --- a/linux-user/m68k/target_mman.h
> +++ b/linux-user/m68k/target_mman.h
> @@ -1,4 +1,6 @@
>   /* arch/m68k/include/asm/processor.h */
>   #define TASK_UNMAPPED_BASE      0xC0000000
> +/* arch/m68k/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE         0xD0000000
>   
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/microblaze/target_mman.h b/linux-user/microblaze/target_mman.h
> index ffee869db4..6b3dd54f89 100644
> --- a/linux-user/microblaze/target_mman.h
> +++ b/linux-user/microblaze/target_mman.h
> @@ -6,4 +6,7 @@
>    */
>   #define TASK_UNMAPPED_BASE      0x48000000
>   
> +/* arch/microblaze/include/uapi/asm/elf.h */
> +#define ELF_ET_DYN_BASE         0x08000000
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/mips/target_mman.h b/linux-user/mips/target_mman.h
> index fe1eec2d0b..b84fe1e8a8 100644
> --- a/linux-user/mips/target_mman.h
> +++ b/linux-user/mips/target_mman.h
> @@ -21,6 +21,9 @@
>   #define TASK_UNMAPPED_BASE \
>       TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
>   
> +/* arch/mips/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/nios2/target_mman.h b/linux-user/nios2/target_mman.h
> index ce18f4f871..ab16ad4f03 100644
> --- a/linux-user/nios2/target_mman.h
> +++ b/linux-user/nios2/target_mman.h
> @@ -5,4 +5,7 @@
>    */
>   #define TASK_UNMAPPED_BASE    TARGET_PAGE_ALIGN(0x7FFF0000 / 3)
>   
> +/* arch/nios2/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       0xD0000000
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/openrisc/target_mman.h b/linux-user/openrisc/target_mman.h
> index f1aaad809d..243c1d5f26 100644
> --- a/linux-user/openrisc/target_mman.h
> +++ b/linux-user/openrisc/target_mman.h
> @@ -5,4 +5,7 @@
>    */
>   #define TASK_UNMAPPED_BASE      0x30000000
>   
> +/* arch/openrisc/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE         0x08000000
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/ppc/target_mman.h b/linux-user/ppc/target_mman.h
> index 04f99c6077..646d1ccae7 100644
> --- a/linux-user/ppc/target_mman.h
> +++ b/linux-user/ppc/target_mman.h
> @@ -17,6 +17,13 @@
>   #define TASK_UNMAPPED_BASE      0x40000000
>   #endif
>   
> +/* arch/powerpc/include/asm/elf.h */
> +#ifdef TARGET_PPC64
> +#define ELF_ET_DYN_BASE         0x100000000ull
> +#else
> +#define ELF_ET_DYN_BASE         0x000400000
> +#endif
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/riscv/target_mman.h b/linux-user/riscv/target_mman.h
> index 0f06dadbd4..3049bcc67d 100644
> --- a/linux-user/riscv/target_mman.h
> +++ b/linux-user/riscv/target_mman.h
> @@ -5,4 +5,7 @@
>   #define TASK_UNMAPPED_BASE \
>       TARGET_PAGE_ALIGN((1ull << (TARGET_VIRT_ADDR_SPACE_BITS - 1)) / 3)
>   
> +/* arch/riscv/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/s390x/target_mman.h b/linux-user/s390x/target_mman.h
> index 40d149b329..c82435e381 100644
> --- a/linux-user/s390x/target_mman.h
> +++ b/linux-user/s390x/target_mman.h
> @@ -8,4 +8,14 @@
>    */
>   #define TASK_UNMAPPED_BASE      (1ull << 41)
>   
> +/*
> + * arch/s390/include/asm/elf.h:
> + * ELF_ET_DYN_BASE              (STACK_TOP / 3 * 2) & ~((1UL << 32) - 1)
> + *
> + * arch/s390/include/asm/processor.h:
> + * STACK_TOP                    VDSO_LIMIT - VDSO_SIZE - PAGE_SIZE
> + * VDSO_LIMIT                   _REGION2_SIZE
> + */
> +#define ELF_ET_DYN_BASE         (((1ull << 42) / 3 * 2) & ~0xffffffffull)
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/sh4/target_mman.h b/linux-user/sh4/target_mman.h
> index bbbc223398..dd9016081e 100644
> --- a/linux-user/sh4/target_mman.h
> +++ b/linux-user/sh4/target_mman.h
> @@ -2,4 +2,7 @@
>   #define TASK_UNMAPPED_BASE \
>       TARGET_PAGE_ALIGN((1u << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
>   
> +/* arch/sh/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/sparc/target_mman.h b/linux-user/sparc/target_mman.h
> index 692ebf9dd7..696ca73fe4 100644
> --- a/linux-user/sparc/target_mman.h
> +++ b/linux-user/sparc/target_mman.h
> @@ -19,6 +19,17 @@
>   #define TASK_UNMAPPED_BASE      (1ull << (TARGET_VIRT_ADDR_SPACE_BITS - 2))
>   #endif
>   
> +/*
> + * arch/sparc/include/asm/elf_64.h
> + * Except that COMPAT_ELF_ET_DYN_BASE exactly matches TASK_UNMAPPED_BASE,
> + * so move it up a bit.
> + */
> +#ifdef TARGET_ABI32
> +#define ELF_ET_DYN_BASE         0x78000000
> +#else
> +#define ELF_ET_DYN_BASE         0x0000010000000000ull
> +#endif
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/user-mmap.h b/linux-user/user-mmap.h
> index bae49059e0..5dd48a458d 100644
> --- a/linux-user/user-mmap.h
> +++ b/linux-user/user-mmap.h
> @@ -20,6 +20,7 @@
>   
>   extern abi_ulong task_unmapped_base;
>   extern abi_ulong mmap_next_start;
> +extern abi_ulong elf_et_dyn_base;
>   
>   int target_mprotect(abi_ulong start, abi_ulong len, int prot);
>   abi_long target_mmap(abi_ulong start, abi_ulong len, int prot,
> diff --git a/linux-user/x86_64/target_mman.h b/linux-user/x86_64/target_mman.h
> index f9ff652b37..48fbf20b42 100644
> --- a/linux-user/x86_64/target_mman.h
> +++ b/linux-user/x86_64/target_mman.h
> @@ -10,4 +10,7 @@
>   #define TASK_UNMAPPED_BASE \
>       TARGET_PAGE_ALIGN((1ull << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
>   
> +/* arch/x86/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE       (TASK_UNMAPPED_BASE * 2)
> +
>   #include "../generic/target_mman.h"
> diff --git a/linux-user/xtensa/target_mman.h b/linux-user/xtensa/target_mman.h
> index c4f671adb7..8fa6337a97 100644
> --- a/linux-user/xtensa/target_mman.h
> +++ b/linux-user/xtensa/target_mman.h
> @@ -20,6 +20,10 @@
>    */
>   #define TASK_UNMAPPED_BASE      (1u << (TARGET_VIRT_ADDR_SPACE_BITS - 1))
>   
> +/* arch/xtensa/include/asm/elf.h */
> +#define ELF_ET_DYN_BASE \
> +    TARGET_PAGE_ALIGN((1u << TARGET_VIRT_ADDR_SPACE_BITS) / 3)
> +
>   #include "../generic/target_mman.h"
>   
>   #endif
> diff --git a/linux-user/main.c b/linux-user/main.c
> index 52809c260a..e089123cfa 100644
> --- a/linux-user/main.c
> +++ b/linux-user/main.c
> @@ -839,6 +839,21 @@ int main(int argc, char **argv, char **envp)
>       }
>       mmap_next_start = task_unmapped_base;
>   
> +    /* Similarly for elf_et_dyn_base. */
> +    if (reserved_va) {
> +        if (ELF_ET_DYN_BASE < reserved_va) {
> +            elf_et_dyn_base = ELF_ET_DYN_BASE;
> +        } else {
> +            /* The most common default formula is TASK_SIZE / 3 * 2. */
> +            task_unmapped_base = TARGET_PAGE_ALIGN(reserved_va / 3) * 2;

This assigns a value to task_unmapped_base and that does not seem correct.

> +        }
> +    } else if (ELF_ET_DYN_BASE < UINTPTR_MAX) {
> +        elf_et_dyn_base = ELF_ET_DYN_BASE;
> +    } else {
> +        /* 32-bit host: pick something medium size. */
> +        task_unmapped_base = 0x18000000;
> +    }
> +
>       {
>           Error *err = NULL;
>           if (seed_optarg != NULL) {
> diff --git a/linux-user/mmap.c b/linux-user/mmap.c
> index 84436d45c8..949c4090f3 100644
> --- a/linux-user/mmap.c
> +++ b/linux-user/mmap.c
> @@ -301,6 +301,7 @@ static bool mmap_frag(abi_ulong real_start, abi_ulong start, abi_ulong last,
>   
>   abi_ulong task_unmapped_base;
>   abi_ulong mmap_next_start;
> +abi_ulong elf_et_dyn_base;
>   
>   /*
>    * Subroutine of mmap_find_vma, used when we have pre-allocated


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap
  2023-08-04  1:45 ` [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap Richard Henderson
@ 2023-08-04  5:22   ` Akihiko Odaki
  2023-08-04 10:18   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:22 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Use this as extra protection for the guest mapping over
> any qemu host mappings.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter
  2023-08-04  1:45 ` [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter Richard Henderson
@ 2023-08-04  5:24   ` Akihiko Odaki
  2023-08-04 10:20   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:24 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Follow the lead of the linux kernel in fs/binfmt_elf.c,
> in which an ET_DYN executable which uses an interpreter
> (usually a PIE executable) is loaded away from where the
> interpreter itself will be loaded.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 13/17] linux-user: Adjust initial brk when interpreter is close to executable
  2023-08-04  1:45 ` [PATCH v8 13/17] linux-user: Adjust initial brk when interpreter is close to executable Richard Henderson
@ 2023-08-04  5:26   ` Akihiko Odaki
  0 siblings, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:26 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> From: Helge Deller <deller@gmx.de>
> 
> While we attempt to load a ET_DYN executable far away from
> TASK_UNMAPPED_BASE, we are not completely in control of the
> address space layout.  If the interpreter lands close to
> the executable, leaving insufficient heap space, move brk.
> 
> Signed-off-by: Helge Deller <deller@gmx.de>
> [rth: Re-order after ELF_ET_DYN_BASE patch so that we do not
>   "temporarily break" tsan, and also to minimize the changes required.
>   Remove image_info.reserve_brk as unused.]
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload
  2023-08-04  1:45 ` [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload Richard Henderson
@ 2023-08-04  5:27   ` Akihiko Odaki
  2023-08-04 10:22   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:27 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> The heap starts at "brk" not "start_brk".  With this fixed,
> image_info.start_brk is unused and may be removed.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size
  2023-08-04  1:45 ` [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size Richard Henderson
@ 2023-08-04  5:28   ` Akihiko Odaki
  2023-08-04 10:23   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:28 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Remove TARGET_ELF_EXEC_PAGESIZE, and 3 other TARGET_ELF_PAGE* macros
> based off of that.  Rely on target_mmap to handle guest vs host page
> size mismatch.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 16/17] linux-user: Do not adjust zero_bss for host page size
  2023-08-04  1:45 ` [PATCH v8 16/17] linux-user: Do not adjust zero_bss " Richard Henderson
@ 2023-08-04  5:56   ` Akihiko Odaki
  2023-08-04 10:24   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  5:56 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> Rely on target_mmap to handle guest vs host page size mismatch.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too
  2023-08-04  1:45 ` [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too Richard Henderson
@ 2023-08-04  6:02   ` Akihiko Odaki
  2023-08-04 10:25   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Akihiko Odaki @ 2023-08-04  6:02 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, laurent, deller

On 2023/08/04 10:45, Richard Henderson wrote:
> If p_filesz == 0, then vaddr_ef == vaddr.  We can reuse the
> code in zero_bss rather than incompletely duplicating it in
> load_elf_image.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Akihiko Odaki <akihiko.odaki@daynix.com>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 07/17] linux-user: Remove last_brk
  2023-08-04  1:45 ` [PATCH v8 07/17] linux-user: Remove last_brk Richard Henderson
  2023-08-04  5:09   ` Akihiko Odaki
@ 2023-08-04  8:51   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04  8:51 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, akihiko.odaki, laurent

On 8/4/23 03:45, Richard Henderson wrote:
> This variable is unused.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>



^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE in $guest/target_mman.h
  2023-08-04  1:45 ` [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE " Richard Henderson
  2023-08-04  5:20   ` Akihiko Odaki
@ 2023-08-04  9:50   ` Helge Deller
  2023-08-04 14:09     ` Richard Henderson
  1 sibling, 1 reply; 40+ messages in thread
From: Helge Deller @ 2023-08-04  9:50 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: joel, akihiko.odaki, laurent

On 8/4/23 03:45, Richard Henderson wrote:
> Copy each guest kernel's default value, then bound it
> against reserved_va or the host address space.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>   linux-user/aarch64/target_mman.h     |  3 +++
>   linux-user/alpha/target_mman.h       |  3 +++
> ...

I've successfully tested the whole series on the following
chroots (on x86 host):
alpha, arm64, armhf, hppa, m68k, mips64el, mipsel
powerpc, ppc64, ppc64el, s390x, sh4, sparc64.
Both static and dynamically linked programs work as expected.

It's a big step forward compared to qemu v8.0, so feel free
to add to the whole series:
Tested-by: Helge Deller <deller@gmx.de>

For this patch:
Reviewed-by: Helge Deller <deller@gmx.de>

One thing to mention here is, that those values (ELF_ET_DYN_BASE)
reflects the legacy (standard) memory layout of the kernel only.
The process personality defines which layout should be used,
ADDR_COMPAT_LAYOUT means to use the legacy (standard) memory layout.

The Linux kernel on 390, parisc, sparc and x86 doesn't use by
default the legacy memory model, but instead allocates new mappings
from top downwards. This leaves much more space for heap.
Search for mmap_is_legacy() in the kernel sources.

That said, we should implement the top-downwards allocation
after qemu 8.1.
In this regard, could you please include my latest patch titled:

    linux-user: Show heap address in /proc/pid/maps

in your patch series? I sent an updated version today to the mailing
list, which applies to your series. .

If applied, the "[heap]" entry is visible in /proc/cpuinfo output, and
it's much easier to see potential future memory isses, e.g.

armhf-chroot:
-> heap is limited in region 21000 to 00400000.
-> 00421000 to 40000000 would give much more space for heap.
-> arm32 doesn't seem to support non-legacy memory model yet...
Linux p100 6.4.6-200.fc38.x86_64 #1 SMP PREEMPT_DYNAMIC Mon Jul 24 20:51:12 UTC 2023 armv7l GNU/Linux
00021000-00042000 rw-p 00000000 00:00 0                                  [heap]
00400000-00406000 r-xp 00000000 fd:00 675877                             /usr/bin/cat
00406000-0041f000 ---p 00000000 00:00 0
0041f000-00420000 r--p 0000f000 fd:00 675877                             /usr/bin/cat
00420000-00421000 rw-p 00010000 fd:00 675877                             /usr/bin/cat
40000000-40001000 ---p 00000000 00:00 0
40001000-40801000 rw-p 00000000 00:00 0                                  [stack]
40801000-4081d000 r-xp 00000000 fd:00 682674                             /usr/lib/arm-linux-gnueabihf/ld-linux-armhf.so.3
4081d000-4081e000 r--p 0001c000 fd:00 682674                             /usr/lib/arm-linux-gnueabihf/ld-linux-armhf.so.3
4081e000-4081f000 rw-p 0001d000 fd:00 682674                             /usr/lib/arm-linux-gnueabihf/ld-linux-armhf.so.3
4081f000-40820000 r-xp 00000000 00:00 0
40820000-40822000 rw-p 00000000 00:00 0
40822000-4092b000 r-xp 00000000 fd:00 682677                             /usr/lib/arm-linux-gnueabihf/libc.so.6
4092b000-4092d000 r--p 00108000 fd:00 682677                             /usr/lib/arm-linux-gnueabihf/libc.so.6
4092d000-4092e000 rw-p 0010a000 fd:00 682677                             /usr/lib/arm-linux-gnueabihf/libc.so.6
4092e000-40938000 rw-p 00000000 00:00 0
ffff0000-ffff1000 r-xp 00000000 00:00 0

mipsel-chroot
-> heap is locked in from 00021000 to 2aaab000
Linux p100 6.4.6-200.fc38.x86_64 #1 SMP PREEMPT_DYNAMIC Mon Jul 24 20:51:12 UTC 2023 mips GNU/Linux
00021000-00042000 rw-p 00000000 00:00 0                                  [heap]
2aaab000-2aaac000 ---p 00000000 00:00 0
2aaac000-2b2ac000 rwxp 00000000 00:00 0                                  [stack]
2b2ac000-2b2d8000 r-xp 00000000 fd:00 816208                             /usr/lib/mipsel-linux-gnu/ld.so.1
2b2d8000-2b2eb000 ---p 00000000 00:00 0
2b2eb000-2b2ec000 r--p 0002f000 fd:00 816208                             /usr/lib/mipsel-linux-gnu/ld.so.1
2b2ec000-2b2ed000 rw-p 00030000 fd:00 816208                             /usr/lib/mipsel-linux-gnu/ld.so.1
2b2ed000-2b2ee000 r-xp 00000000 00:00 0
2b2ee000-2b2f0000 rw-p 00000000 00:00 0
2b2f0000-2b4ae000 r-xp 00000000 fd:00 816216                             /usr/lib/mipsel-linux-gnu/libc.so.6
2b4ae000-2b4bd000 ---p 001be000 fd:00 816216                             /usr/lib/mipsel-linux-gnu/libc.so.6
2b4bd000-2b4c0000 r--p 001bd000 fd:00 816216                             /usr/lib/mipsel-linux-gnu/libc.so.6
2b4c0000-2b4c3000 rw-p 001c0000 fd:00 816216                             /usr/lib/mipsel-linux-gnu/libc.so.6
2b4c3000-2b4cd000 rw-p 00000000 00:00 0
55550000-55559000 r-xp 00000000 fd:00 818831                             /usr/bin/cat
55559000-5556f000 ---p 00000000 00:00 0
5556f000-55570000 r--p 0000f000 fd:00 818831                             /usr/bin/cat
55570000-55571000 rw-p 00010000 fd:00 818831                             /usr/bin/cat


hppa-chroot
-> heap & stack is ok.
-> heap could greatly benefit if qemu later supports top-down mmap allocation,
    because then the shared libs will be mapped >fa000000 and heap&stack can grow
    from 0001a000 up to fa000000.
Linux p100 6.4.6-200.fc38.x86_64 #1 SMP PREEMPT_DYNAMIC Mon Jul 24 20:51:12 UTC 2023 parisc GNU/Linux
00000000-00001000 --xp 00000000 00:00 0
00010000-00019000 r-xp 00000000 fd:00 1061893                            /usr/bin/cat
00019000-0001a000 rwxp 00009000 fd:00 1061893                            /usr/bin/cat
0001a000-0003b000 rw-p 00000000 00:00 0                                  [heap]
40000000-45000000 rwxp 00000000 00:00 0                                  [stack]
45000000-4502f000 r-xp 00000000 fd:00 1069300                            /usr/lib/hppa-linux-gnu/ld.so.1
4502f000-45030000 r--p 0002f000 fd:00 1069300                            /usr/lib/hppa-linux-gnu/ld.so.1
45030000-45034000 rwxp 00030000 fd:00 1069300                            /usr/lib/hppa-linux-gnu/ld.so.1
45034000-45035000 r-xp 00000000 00:00 0
45037000-45039000 rw-p 00000000 00:00 0
45039000-451f5000 r-xp 00000000 fd:00 1069303                            /usr/lib/hppa-linux-gnu/libc.so.6
451f5000-451f7000 r--p 001bc000 fd:00 1069303                            /usr/lib/hppa-linux-gnu/libc.so.6
451f7000-451fc000 rwxp 001be000 fd:00 1069303                            /usr/lib/hppa-linux-gnu/libc.so.6

Thanks!
Helge


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h
  2023-08-04  1:45 ` [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h Richard Henderson
  2023-08-04  5:17   ` Akihiko Odaki
@ 2023-08-04 10:17   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:17 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> Provide default values that are as close as possible to the
> values used by the guest's kernel.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap
  2023-08-04  1:45 ` [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap Richard Henderson
  2023-08-04  5:22   ` Akihiko Odaki
@ 2023-08-04 10:18   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:18 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> Use this as extra protection for the guest mapping over
> any qemu host mappings.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter
  2023-08-04  1:45 ` [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter Richard Henderson
  2023-08-04  5:24   ` Akihiko Odaki
@ 2023-08-04 10:20   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:20 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> Follow the lead of the linux kernel in fs/binfmt_elf.c,
> in which an ET_DYN executable which uses an interpreter
> (usually a PIE executable) is loaded away from where the
> interpreter itself will be loaded.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload
  2023-08-04  1:45 ` [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload Richard Henderson
  2023-08-04  5:27   ` Akihiko Odaki
@ 2023-08-04 10:22   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:22 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> The heap starts at "brk" not "start_brk".  With this fixed,
> image_info.start_brk is unused and may be removed.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size
  2023-08-04  1:45 ` [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size Richard Henderson
  2023-08-04  5:28   ` Akihiko Odaki
@ 2023-08-04 10:23   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:23 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> Remove TARGET_ELF_EXEC_PAGESIZE, and 3 other TARGET_ELF_PAGE* macros
> based off of that.  Rely on target_mmap to handle guest vs host page
> size mismatch.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 16/17] linux-user: Do not adjust zero_bss for host page size
  2023-08-04  1:45 ` [PATCH v8 16/17] linux-user: Do not adjust zero_bss " Richard Henderson
  2023-08-04  5:56   ` Akihiko Odaki
@ 2023-08-04 10:24   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:24 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> Rely on target_mmap to handle guest vs host page size mismatch.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too
  2023-08-04  1:45 ` [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too Richard Henderson
  2023-08-04  6:02   ` Akihiko Odaki
@ 2023-08-04 10:25   ` Helge Deller
  1 sibling, 0 replies; 40+ messages in thread
From: Helge Deller @ 2023-08-04 10:25 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel, joel, akihiko.odaki, laurent, deller

* Richard Henderson <richard.henderson@linaro.org>:
> If p_filesz == 0, then vaddr_ef == vaddr.  We can reuse the
> code in zero_bss rather than incompletely duplicating it in
> load_elf_image.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

Reviewed-by: Helge Deller <deller@gmx.de>


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE in $guest/target_mman.h
  2023-08-04  9:50   ` Helge Deller
@ 2023-08-04 14:09     ` Richard Henderson
  0 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04 14:09 UTC (permalink / raw)
  To: Helge Deller, qemu-devel; +Cc: joel, akihiko.odaki, laurent

On 8/4/23 02:50, Helge Deller wrote:
> In this regard, could you please include my latest patch titled:
> 
>     linux-user: Show heap address in /proc/pid/maps
> 
> in your patch series?

No, as it's not a bug fix.  It can wait for 8.2.


> If applied, the "[heap]" entry is visible in /proc/cpuinfo output, and
> it's much easier to see potential future memory isses, e.g.

Anyway, changing the guest /proc/cpuinfo output seems much less useful than improving -d 
page (which misses out on logging lots of the PAGE_* bits).


r~


^ permalink raw reply	[flat|nested] 40+ messages in thread

* Re: [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE in $guest/target_mman.h
  2023-08-04  5:20   ` Akihiko Odaki
@ 2023-08-04 14:09     ` Richard Henderson
  0 siblings, 0 replies; 40+ messages in thread
From: Richard Henderson @ 2023-08-04 14:09 UTC (permalink / raw)
  To: Akihiko Odaki, qemu-devel; +Cc: joel, laurent, deller

On 8/3/23 22:20, Akihiko Odaki wrote:
>> +    if (reserved_va) {
>> +        if (ELF_ET_DYN_BASE < reserved_va) {
>> +            elf_et_dyn_base = ELF_ET_DYN_BASE;
>> +        } else {
>> +            /* The most common default formula is TASK_SIZE / 3 * 2. */
>> +            task_unmapped_base = TARGET_PAGE_ALIGN(reserved_va / 3) * 2;
> 
> This assigns a value to task_unmapped_base and that does not seem correct.
> 

Gah, I fixed this on a different copy of my branch, then lost it.


r~


^ permalink raw reply	[flat|nested] 40+ messages in thread

end of thread, other threads:[~2023-08-04 14:10 UTC | newest]

Thread overview: 40+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-08-04  1:45 [PATCH for-8.1 v8 00/17] linux-user: brk fixes Richard Henderson
2023-08-04  1:45 ` [PATCH v8 01/17] linux-user: Unset MAP_FIXED_NOREPLACE for host Richard Henderson
2023-08-04  1:45 ` [PATCH v8 02/17] linux-user: Fix MAP_FIXED_NOREPLACE on old kernels Richard Henderson
2023-08-04  1:45 ` [PATCH v8 03/17] linux-user: Do not call get_errno() in do_brk() Richard Henderson
2023-08-04  1:45 ` [PATCH v8 04/17] linux-user: Use MAP_FIXED_NOREPLACE for do_brk() Richard Henderson
2023-08-04  1:45 ` [PATCH v8 05/17] linux-user: Do nothing if too small brk is specified Richard Henderson
2023-08-04  1:45 ` [PATCH v8 06/17] linux-user: Do not align brk with host page size Richard Henderson
2023-08-04  1:45 ` [PATCH v8 07/17] linux-user: Remove last_brk Richard Henderson
2023-08-04  5:09   ` Akihiko Odaki
2023-08-04  8:51   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 08/17] linux-user: Adjust task_unmapped_base for reserved_va Richard Henderson
2023-08-04  5:14   ` Akihiko Odaki
2023-08-04  1:45 ` [PATCH v8 09/17] linux-user: Define TASK_UNMAPPED_BASE in $guest/target_mman.h Richard Henderson
2023-08-04  5:17   ` Akihiko Odaki
2023-08-04 10:17   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 10/17] linux-user: Define ELF_ET_DYN_BASE " Richard Henderson
2023-08-04  5:20   ` Akihiko Odaki
2023-08-04 14:09     ` Richard Henderson
2023-08-04  9:50   ` Helge Deller
2023-08-04 14:09     ` Richard Henderson
2023-08-04  1:45 ` [PATCH v8 11/17] linux-user: Use MAP_FIXED_NOREPLACE for initial image mmap Richard Henderson
2023-08-04  5:22   ` Akihiko Odaki
2023-08-04 10:18   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 12/17] linux-user: Use elf_et_dyn_base for ET_DYN with interpreter Richard Henderson
2023-08-04  5:24   ` Akihiko Odaki
2023-08-04 10:20   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 13/17] linux-user: Adjust initial brk when interpreter is close to executable Richard Henderson
2023-08-04  5:26   ` Akihiko Odaki
2023-08-04  1:45 ` [PATCH v8 14/17] linux-user: Properly set image_info.brk in flatload Richard Henderson
2023-08-04  5:27   ` Akihiko Odaki
2023-08-04 10:22   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 15/17] linux-user: Do not adjust image mapping for host page size Richard Henderson
2023-08-04  5:28   ` Akihiko Odaki
2023-08-04 10:23   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 16/17] linux-user: Do not adjust zero_bss " Richard Henderson
2023-08-04  5:56   ` Akihiko Odaki
2023-08-04 10:24   ` Helge Deller
2023-08-04  1:45 ` [PATCH v8 17/17] linux-user: Use zero_bss for PT_LOAD with no file contents too Richard Henderson
2023-08-04  6:02   ` Akihiko Odaki
2023-08-04 10:25   ` Helge Deller

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.