diff --git a/linux-user/mmap.c b/linux-user/mmap.c
index 4e7a6be6ee..fbb50e3e98 100644
--- a/linux-user/mmap.c
+++ b/linux-user/mmap.c
@@ -899,3 +899,23 @@ abi_long target_madvise(abi_ulong start, abi_ulong len_in, int advice)
 
     return ret;
 }
+
+abi_long old_mmap_get_args(abi_long *arg1, abi_long *arg2, abi_long *arg3,
+                           abi_long *arg4, abi_long *arg5, abi_long *arg6)
+{
+    abi_long orig_arg1 = *arg1, *v;
+
+    v = lock_user(VERIFY_READ, orig_arg1, 6 * sizeof(abi_ulong), 1);
+    if (!v) {
+        return -TARGET_EFAULT;
+    }
+    *arg1 = tswapal(v[0]);
+    *arg2 = tswapal(v[1]);
+    *arg3 = tswapal(v[2]);
+    *arg4 = tswapal(v[3]);
+    *arg5 = tswapal(v[4]);
+    *arg6 = tswapal(v[5]);
+    unlock_user(v, orig_arg1, 0);
+
+    return 0;
+}
diff --git a/linux-user/strace.c b/linux-user/strace.c
index 7d882526da..f25195ae85 100644
--- a/linux-user/strace.c
+++ b/linux-user/strace.c
@@ -16,6 +16,7 @@
 #include <sched.h>
 #include "qemu.h"
 #include "user-internals.h"
+#include "user-mmap.h"
 #include "strace.h"
 
 struct syscallname {
@@ -3532,9 +3533,9 @@ print_utimensat(CPUArchState *cpu_env, const struct syscallname *name,
 
 #if defined(TARGET_NR_mmap) || defined(TARGET_NR_mmap2)
 static void
-print_mmap(CPUArchState *cpu_env, const struct syscallname *name,
-           abi_long arg0, abi_long arg1, abi_long arg2,
-           abi_long arg3, abi_long arg4, abi_long arg5)
+print_mmap2(CPUArchState *cpu_env, const struct syscallname *name,
+            abi_long arg0, abi_long arg1, abi_long arg2,
+            abi_long arg3, abi_long arg4, abi_long arg5)
 {
     print_syscall_prologue(name);
     print_pointer(arg0, 0);
@@ -3545,7 +3546,22 @@ print_mmap(CPUArchState *cpu_env, const struct syscallname *name,
     print_raw_param("%#x", arg5, 1);
     print_syscall_epilogue(name);
 }
-#define print_mmap2     print_mmap
+#endif
+
+#if defined(TARGET_NR_mmap)
+static void
+print_mmap(CPUArchState *cpu_env, const struct syscallname *name,
+           abi_long arg0, abi_long arg1, abi_long arg2,
+           abi_long arg3, abi_long arg4, abi_long arg5)
+{
+    if (mmap_get_args(&arg0, &arg1, &arg2, &arg3, &arg4, &arg5)) {
+        print_syscall_prologue(name);
+        print_pointer(arg0, 0);
+        print_syscall_epilogue(name);
+        return;
+    }
+    print_mmap2(cpu_env, name, arg0, arg1, arg2, arg3, arg4, arg5);
+}
 #endif
 
 #ifdef TARGET_NR_mprotect
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 669add74c1..00d4be9094 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -9917,33 +9917,14 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
         return ret;
 #ifdef TARGET_NR_mmap
     case TARGET_NR_mmap:
-#if (defined(TARGET_I386) && defined(TARGET_ABI32)) || \
-    (defined(TARGET_ARM) && defined(TARGET_ABI32)) || \
-    defined(TARGET_M68K) || defined(TARGET_CRIS) || defined(TARGET_MICROBLAZE) \
-    || defined(TARGET_S390X)
-        {
-            abi_ulong *v;
-            abi_ulong v1, v2, v3, v4, v5, v6;
-            if (!(v = lock_user(VERIFY_READ, arg1, 6 * sizeof(abi_ulong), 1)))
-                return -TARGET_EFAULT;
-            v1 = tswapal(v[0]);
-            v2 = tswapal(v[1]);
-            v3 = tswapal(v[2]);
-            v4 = tswapal(v[3]);
-            v5 = tswapal(v[4]);
-            v6 = tswapal(v[5]);
-            unlock_user(v, arg1, 0);
-            ret = get_errno(target_mmap(v1, v2, v3,
-                                        target_to_host_bitmask(v4, mmap_flags_tbl),
-                                        v5, v6));
+        ret = mmap_get_args(&arg1, &arg2, &arg3, &arg4, &arg5, &arg6);
+        if (ret) {
+            return ret;
         }
-#else
-        /* mmap pointers are always untagged */
         ret = get_errno(target_mmap(arg1, arg2, arg3,
                                     target_to_host_bitmask(arg4, mmap_flags_tbl),
                                     arg5,
                                     arg6));
-#endif
         return ret;
 #endif
 #ifdef TARGET_NR_mmap2
diff --git a/linux-user/user-mmap.h b/linux-user/user-mmap.h
index 480ce1c114..f48474bd1d 100644
--- a/linux-user/user-mmap.h
+++ b/linux-user/user-mmap.h
@@ -31,5 +31,17 @@ 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);
+abi_long old_mmap_get_args(abi_long *arg1, abi_long *arg2, abi_long *arg3,
+                           abi_long *arg4, abi_long *arg5, abi_long *arg6);
+
+#if (defined(TARGET_I386) && defined(TARGET_ABI32)) || \
+    (defined(TARGET_ARM) && defined(TARGET_ABI32)) || \
+    defined(TARGET_M68K) || defined(TARGET_CRIS) || \
+    defined(TARGET_MICROBLAZE) || defined(TARGET_S390X)
+/* __ARCH_WANT_SYS_OLD_MMAP */
+#define mmap_get_args old_mmap_get_args
+#else
+#define mmap_get_args(arg1, arg2, arg3, arg4, arg5, arg6) 0
+#endif
 
 #endif /* LINUX_USER_USER_MMAP_H */
