summaryrefslogtreecommitdiffstats
path: root/linux-user/syscall.c
diff options
context:
space:
mode:
authorStefan Hajnoczi2022-10-25 17:36:41 +0200
committerStefan Hajnoczi2022-10-25 17:36:41 +0200
commitd3553079286c9b0add5bcf953c4ea4a3df40b748 (patch)
tree13393a2687701ab002d83684aebe61f9c7a84487 /linux-user/syscall.c
parentMerge tag 'pull-9p-20221024' of https://github.com/cschoenebeck/qemu into sta... (diff)
parentlinux-user: Add guest memory layout to exception dump (diff)
downloadqemu-d3553079286c9b0add5bcf953c4ea4a3df40b748.tar.gz
qemu-d3553079286c9b0add5bcf953c4ea4a3df40b748.tar.xz
qemu-d3553079286c9b0add5bcf953c4ea4a3df40b748.zip
Merge tag 'linux-user-for-7.2-pull-request' of https://gitlab.com/laurent_vivier/qemu into staging
linux-user pull request 20221025 Add faccess2() Fix ioclt(), execve(), pidfd_send_signal() and MIPS n32 syscall ABI Improve EXCP_DUMP() # -----BEGIN PGP SIGNATURE----- # # iQJGBAABCAAwFiEEzS913cjjpNwuT1Fz8ww4vT8vvjwFAmNXkawSHGxhdXJlbnRA # dml2aWVyLmV1AAoJEPMMOL0/L748uvUQAJ3Br5Yh+0uuT0524DvVHjvE/bYys43A # JRilXtYsTrmGhatiF5vaaOmhRbsQ8Ljq8l/R4D7b7cLmRUJ7Q0pbZM5k3PRAEYOa # rMdTY8aSNhlKPvioOhLE5Ha4eua17YGQfP1LJW4jvEGqrhNV2qhUPPFbN3WlZKyt # 6T4N8y3FWWVD3C/qGpmHic3xK9CZW5hUIT3rL2BLxNx23rjCVViFhU4uFz7/43d1 # Rf3pKLWbNOsUB4P0g56otlviPrNRwGoKEr2MGAGr2pz6ZHvSPUCD0PnJvOZ/0iHa # jpswpStPYYpmEXHOjwTT6ua1Roe0EaNJfcI5FoUDBYjCMyoyQ+4XoPfMvm/SqPKr # TbK/cEBEUUej7anUX6faNaofh3mDz5BMF+/r7scCqHKem2+/ZnoBFdx8f/meKwYB # Te29eC8/y4eFGlI6RsE7dcvwH+wz/z0aVCdX4luxzX0pjWp7ZhIs9ljLjEbdelUO # D6+nWACUF1HnTLIGSGWY4oihF4ST/NaZ0u+NLHqE5WoS3vq4xgas9agqkr6f5HnM # 1hdjcDFOJs6Xjac+IM6bi3MX0vAeGrBWK1YA/3vQRaF91uOfwBRhNjHSXwI+dWwM # LL6pLjiDIIrEXY3QbO/TZFfFKRhooDVSOopiRvPkZVHeugbsYdKVwZ8geTyvGlmn # vsxDnihSUWot # =o10I # -----END PGP SIGNATURE----- # gpg: Signature made Tue 25 Oct 2022 03:35:08 EDT # gpg: using RSA key CD2F75DDC8E3A4DC2E4F5173F30C38BD3F2FBE3C # gpg: issuer "laurent@vivier.eu" # gpg: Good signature from "Laurent Vivier <lvivier@redhat.com>" [full] # gpg: aka "Laurent Vivier <laurent@vivier.eu>" [full] # gpg: aka "Laurent Vivier (Red Hat) <lvivier@redhat.com>" [full] # Primary key fingerprint: CD2F 75DD C8E3 A4DC 2E4F 5173 F30C 38BD 3F2F BE3C * tag 'linux-user-for-7.2-pull-request' of https://gitlab.com/laurent_vivier/qemu: linux-user: Add guest memory layout to exception dump linux-user: Implement faccessat2 linux-user: remove conditionals for many fs.h ioctls linux-user: add more compat ioctl definitions linux-user: don't use AT_EXECFD in do_openat() linux-user: handle /proc/self/exe with execve() syscall linux-user: fix pidfd_send_signal() linux-user: Fix more MIPS n32 syscall ABI issues Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
Diffstat (limited to 'linux-user/syscall.c')
-rw-r--r--linux-user/syscall.c100
1 files changed, 85 insertions, 15 deletions
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 2e954d8dbd..8402c1399d 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -111,6 +111,31 @@
#define FS_IOC32_SETFLAGS _IOW('f', 2, int)
#define FS_IOC32_GETVERSION _IOR('v', 1, int)
#define FS_IOC32_SETVERSION _IOW('v', 2, int)
+
+#define BLKGETSIZE64 _IOR(0x12,114,size_t)
+#define BLKDISCARD _IO(0x12,119)
+#define BLKIOMIN _IO(0x12,120)
+#define BLKIOOPT _IO(0x12,121)
+#define BLKALIGNOFF _IO(0x12,122)
+#define BLKPBSZGET _IO(0x12,123)
+#define BLKDISCARDZEROES _IO(0x12,124)
+#define BLKSECDISCARD _IO(0x12,125)
+#define BLKROTATIONAL _IO(0x12,126)
+#define BLKZEROOUT _IO(0x12,127)
+
+#define FIBMAP _IO(0x00,1)
+#define FIGETBSZ _IO(0x00,2)
+
+struct file_clone_range {
+ __s64 src_fd;
+ __u64 src_offset;
+ __u64 src_length;
+ __u64 dest_offset;
+};
+
+#define FICLONE _IOW(0x94, 9, int)
+#define FICLONERANGE _IOW(0x94, 13, struct file_clone_range)
+
#else
#include <linux/fs.h>
#endif
@@ -158,6 +183,7 @@
#include "qapi/error.h"
#include "fd-trans.h"
#include "tcg/tcg.h"
+#include "cpu_loop-common.h"
#ifndef CLONE_IO
#define CLONE_IO 0x80000000 /* Clone io context */
@@ -8144,6 +8170,33 @@ static int is_proc_myself(const char *filename, const char *entry)
return 0;
}
+static void excp_dump_file(FILE *logfile, CPUArchState *env,
+ const char *fmt, int code)
+{
+ if (logfile) {
+ CPUState *cs = env_cpu(env);
+
+ fprintf(logfile, fmt, code);
+ fprintf(logfile, "Failing executable: %s\n", exec_path);
+ cpu_dump_state(cs, logfile, 0);
+ open_self_maps(env, fileno(logfile));
+ }
+}
+
+void target_exception_dump(CPUArchState *env, const char *fmt, int code)
+{
+ /* dump to console */
+ excp_dump_file(stderr, env, fmt, code);
+
+ /* dump to log file */
+ if (qemu_log_separate()) {
+ FILE *logfile = qemu_log_trylock();
+
+ excp_dump_file(logfile, env, fmt, code);
+ qemu_log_unlock(logfile);
+ }
+}
+
#if HOST_BIG_ENDIAN != TARGET_BIG_ENDIAN || \
defined(TARGET_SPARC) || defined(TARGET_M68K) || defined(TARGET_HPPA)
static int is_proc(const char *filename, const char *entry)
@@ -8251,8 +8304,7 @@ static int do_openat(CPUArchState *cpu_env, int dirfd, const char *pathname, int
};
if (is_proc_myself(pathname, "exe")) {
- int execfd = qemu_getauxval(AT_EXECFD);
- return execfd ? execfd : safe_openat(dirfd, exec_path, flags, mode);
+ return safe_openat(dirfd, exec_path, flags, mode);
}
for (fake_open = fakes; fake_open->filename; fake_open++) {
@@ -8679,16 +8731,21 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
#if defined(__NR_pidfd_send_signal) && defined(TARGET_NR_pidfd_send_signal)
case TARGET_NR_pidfd_send_signal:
{
- siginfo_t uinfo;
+ siginfo_t uinfo, *puinfo;
- p = lock_user(VERIFY_READ, arg3, sizeof(target_siginfo_t), 1);
- if (!p) {
- return -TARGET_EFAULT;
+ if (arg3) {
+ p = lock_user(VERIFY_READ, arg3, sizeof(target_siginfo_t), 1);
+ if (!p) {
+ return -TARGET_EFAULT;
+ }
+ target_to_host_siginfo(&uinfo, p);
+ unlock_user(p, arg3, 0);
+ puinfo = &uinfo;
+ } else {
+ puinfo = NULL;
}
- target_to_host_siginfo(&uinfo, p);
- unlock_user(p, arg3, 0);
ret = get_errno(pidfd_send_signal(arg1, target_to_host_signal(arg2),
- &uinfo, arg4));
+ puinfo, arg4));
}
return ret;
#endif
@@ -8855,7 +8912,11 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
* before the execve completes and makes it the other
* program's problem.
*/
- ret = get_errno(safe_execve(p, argp, envp));
+ if (is_proc_myself(p, "exe")) {
+ ret = get_errno(safe_execve(exec_path, argp, envp));
+ } else {
+ ret = get_errno(safe_execve(p, argp, envp));
+ }
unlock_user(p, arg1, 0);
goto execve_end;
@@ -9110,6 +9171,15 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
unlock_user(p, arg2, 0);
return ret;
#endif
+#if defined(TARGET_NR_faccessat2)
+ case TARGET_NR_faccessat2:
+ if (!(p = lock_user_string(arg2))) {
+ return -TARGET_EFAULT;
+ }
+ ret = get_errno(faccessat(arg1, p, arg3, arg4));
+ unlock_user(p, arg2, 0);
+ return ret;
+#endif
#ifdef TARGET_NR_nice /* not on alpha */
case TARGET_NR_nice:
return get_errno(nice(arg1));
@@ -11793,7 +11863,7 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
return -host_to_target_errno(ret);
#endif
-#if TARGET_ABI_BITS == 32
+#if TARGET_ABI_BITS == 32 && !defined(TARGET_ABI_MIPSN32)
#ifdef TARGET_NR_fadvise64_64
case TARGET_NR_fadvise64_64:
@@ -11920,7 +11990,7 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
return get_errno(sys_gettid());
#ifdef TARGET_NR_readahead
case TARGET_NR_readahead:
-#if TARGET_ABI_BITS == 32
+#if TARGET_ABI_BITS == 32 && !defined(TARGET_ABI_MIPSN32)
if (regpairs_aligned(cpu_env, num)) {
arg2 = arg3;
arg3 = arg4;
@@ -12612,7 +12682,7 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
#endif /* CONFIG_EVENTFD */
#if defined(CONFIG_FALLOCATE) && defined(TARGET_NR_fallocate)
case TARGET_NR_fallocate:
-#if TARGET_ABI_BITS == 32
+#if TARGET_ABI_BITS == 32 && !defined(TARGET_ABI_MIPSN32)
ret = get_errno(fallocate(arg1, arg2, target_offset64(arg3, arg4),
target_offset64(arg5, arg6)));
#else
@@ -12623,7 +12693,7 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
#if defined(CONFIG_SYNC_FILE_RANGE)
#if defined(TARGET_NR_sync_file_range)
case TARGET_NR_sync_file_range:
-#if TARGET_ABI_BITS == 32
+#if TARGET_ABI_BITS == 32 && !defined(TARGET_ABI_MIPSN32)
#if defined(TARGET_MIPS)
ret = get_errno(sync_file_range(arg1, target_offset64(arg3, arg4),
target_offset64(arg5, arg6), arg7));
@@ -12645,7 +12715,7 @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
case TARGET_NR_arm_sync_file_range:
#endif
/* This is like sync_file_range but the arguments are reordered */
-#if TARGET_ABI_BITS == 32
+#if TARGET_ABI_BITS == 32 && !defined(TARGET_ABI_MIPSN32)
ret = get_errno(sync_file_range(arg1, target_offset64(arg3, arg4),
target_offset64(arg5, arg6), arg2));
#else