* [Qemu-devel] [PATCH 0/3] linux-user: three minor fixes
@ 2016-06-20 14:50 Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls Peter Maydell
` (2 more replies)
0 siblings, 3 replies; 8+ messages in thread
From: Peter Maydell @ 2016-06-20 14:50 UTC (permalink / raw)
To: qemu-devel; +Cc: patches, Riku Voipio, Laurent Vivier
This patchset fixes a couple of minor bugs in linux-user which
were manifesting as LTP test failures:
* syscalls which take a sigsetsize argument should check it
matches the target's sigset_t size, or fail EINVAL
* a typo meant we weren't locking enough data for the argument
to rt_sigqueuinfo
* we didn't implement the F_GETPIPE_SZ and F_SETPIPE_SZ fnctl ops
thanks
-- PMM
Peter Maydell (3):
linux-user: Check sigsetsize argument to syscalls
linux-user: Fix wrong type used for argument to rt_sigqueueinfo
linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls
linux-user/strace.c | 7 ++++++
linux-user/syscall.c | 57 +++++++++++++++++++++++++++++++++++++++++++++--
linux-user/syscall_defs.h | 2 ++
3 files changed, 64 insertions(+), 2 deletions(-)
--
1.9.1
^ permalink raw reply [flat|nested] 8+ messages in thread
* [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls
2016-06-20 14:50 [Qemu-devel] [PATCH 0/3] linux-user: three minor fixes Peter Maydell
@ 2016-06-20 14:50 ` Peter Maydell
2016-06-21 19:09 ` Laurent Vivier
2016-06-20 14:50 ` [Qemu-devel] [PATCH 2/3] linux-user: Fix wrong type used for argument to rt_sigqueueinfo Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 3/3] linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls Peter Maydell
2 siblings, 1 reply; 8+ messages in thread
From: Peter Maydell @ 2016-06-20 14:50 UTC (permalink / raw)
To: qemu-devel; +Cc: patches, Riku Voipio, Laurent Vivier
Many syscalls which take a sigset_t argument also take an argument
giving the size of the sigset_t. The kernel insists that this
matches its idea of the type size and fails EINVAL if it is not.
Implement this logic in QEMU. (This mostly just means some LTP test
cases which check error cases now pass.)
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
linux-user/syscall.c | 46 +++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 45 insertions(+), 1 deletion(-)
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 95eafeb..7b3d129 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -7592,7 +7592,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
#if defined(TARGET_ALPHA)
struct target_sigaction act, oact, *pact = 0;
struct target_rt_sigaction *rt_act;
- /* ??? arg4 == sizeof(sigset_t). */
+
+ if (arg4 != sizeof(target_sigset_t)) {
+ ret = -TARGET_EINVAL;
+ break;
+ }
if (arg2) {
if (!lock_user_struct(VERIFY_READ, rt_act, arg2, 1))
goto efault;
@@ -7616,6 +7620,10 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
struct target_sigaction *act;
struct target_sigaction *oact;
+ if (arg4 != sizeof(target_sigset_t)) {
+ ret = -TARGET_EINVAL;
+ break;
+ }
if (arg2) {
if (!lock_user_struct(VERIFY_READ, act, arg2, 1))
goto efault;
@@ -7747,6 +7755,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
int how = arg1;
sigset_t set, oldset, *set_ptr;
+ if (arg4 != sizeof(target_sigset_t)) {
+ ret = -TARGET_EINVAL;
+ goto fail;
+ }
+
if (arg2) {
switch(how) {
case TARGET_SIG_BLOCK:
@@ -7797,6 +7810,16 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
case TARGET_NR_rt_sigpending:
{
sigset_t set;
+
+ /* Yes, this check is >, not != like most. We follow the kernel's
+ * logic and it does it like this because it implements
+ * NR_sigpending through the same code path, and in that case
+ * the old_sigset_t is smaller in size.
+ */
+ if (arg2 > sizeof(target_sigset_t)) {
+ return -TARGET_EINVAL;
+ }
+
ret = get_errno(sigpending(&set));
if (!is_error(ret)) {
if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
@@ -7830,6 +7853,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
case TARGET_NR_rt_sigsuspend:
{
TaskState *ts = cpu->opaque;
+
+ if (arg2 != sizeof(target_sigset_t)) {
+ ret = -TARGET_EINVAL;
+ break;
+ }
if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
goto efault;
target_to_host_sigset(&ts->sigsuspend_mask, p);
@@ -7847,6 +7875,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
struct timespec uts, *puts;
siginfo_t uinfo;
+ if (arg4 != sizeof(target_sigset_t)) {
+ ret = -TARGET_EINVAL;
+ break;
+ }
+
if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
goto efault;
target_to_host_sigset(&set, p);
@@ -9095,6 +9128,12 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
}
if (arg4) {
+ if (arg5 != sizeof(target_sigset_t)) {
+ unlock_user(target_pfd, arg1, 0);
+ ret = -TARGET_EINVAL;
+ break;
+ }
+
target_set = lock_user(VERIFY_READ, arg4, sizeof(target_sigset_t), 1);
if (!target_set) {
unlock_user(target_pfd, arg1, 0);
@@ -10914,6 +10953,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
sigset_t _set, *set = &_set;
if (arg5) {
+ if (arg6 != sizeof(target_sigset_t)) {
+ ret = -TARGET_EINVAL;
+ break;
+ }
+
target_set = lock_user(VERIFY_READ, arg5,
sizeof(target_sigset_t), 1);
if (!target_set) {
--
1.9.1
^ permalink raw reply related [flat|nested] 8+ messages in thread
* [Qemu-devel] [PATCH 2/3] linux-user: Fix wrong type used for argument to rt_sigqueueinfo
2016-06-20 14:50 [Qemu-devel] [PATCH 0/3] linux-user: three minor fixes Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls Peter Maydell
@ 2016-06-20 14:50 ` Peter Maydell
2016-06-21 19:10 ` Laurent Vivier
2016-06-20 14:50 ` [Qemu-devel] [PATCH 3/3] linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls Peter Maydell
2 siblings, 1 reply; 8+ messages in thread
From: Peter Maydell @ 2016-06-20 14:50 UTC (permalink / raw)
To: qemu-devel; +Cc: patches, Riku Voipio, Laurent Vivier
The third argument to the rt_sigqueueinfo syscall is a pointer to
a siginfo_t, not a pointer to a sigset_t. Fix the error in the
arguments to lock_user(), which meant that we would not have
detected some faults that we should.
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
linux-user/syscall.c | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 7b3d129..8065284 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -7909,8 +7909,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
case TARGET_NR_rt_sigqueueinfo:
{
siginfo_t uinfo;
- if (!(p = lock_user(VERIFY_READ, arg3, sizeof(target_sigset_t), 1)))
+
+ p = lock_user(VERIFY_READ, arg3, sizeof(target_siginfo_t), 1);
+ if (!p) {
goto efault;
+ }
target_to_host_siginfo(&uinfo, p);
unlock_user(p, arg1, 0);
ret = get_errno(sys_rt_sigqueueinfo(arg1, arg2, &uinfo));
--
1.9.1
^ permalink raw reply related [flat|nested] 8+ messages in thread
* [Qemu-devel] [PATCH 3/3] linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls
2016-06-20 14:50 [Qemu-devel] [PATCH 0/3] linux-user: three minor fixes Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 2/3] linux-user: Fix wrong type used for argument to rt_sigqueueinfo Peter Maydell
@ 2016-06-20 14:50 ` Peter Maydell
2016-06-21 19:13 ` Laurent Vivier
2 siblings, 1 reply; 8+ messages in thread
From: Peter Maydell @ 2016-06-20 14:50 UTC (permalink / raw)
To: qemu-devel; +Cc: patches, Riku Voipio, Laurent Vivier
Support the F_GETPIPE_SZ and F_SETPIPE_SZ fcntl operations.
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
linux-user/strace.c | 7 +++++++
linux-user/syscall.c | 6 ++++++
linux-user/syscall_defs.h | 2 ++
3 files changed, 15 insertions(+)
diff --git a/linux-user/strace.c b/linux-user/strace.c
index 4046b81..6ef5d38 100644
--- a/linux-user/strace.c
+++ b/linux-user/strace.c
@@ -918,6 +918,13 @@ print_fcntl(const struct syscallname *name,
case TARGET_F_GETLEASE:
gemu_log("F_GETLEASE");
break;
+ case TARGET_F_SETPIPE_SZ:
+ gemu_log("F_SETPIPE_SZ,");
+ print_raw_param(TARGET_ABI_FMT_ld, arg2, 1);
+ break;
+ case TARGET_F_GETPIPE_SZ:
+ gemu_log("F_GETPIPE_SZ");
+ break;
case TARGET_F_DUPFD_CLOEXEC:
gemu_log("F_DUPFD_CLOEXEC,");
print_raw_param(TARGET_ABI_FMT_ld, arg2, 1);
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 8065284..719ca20 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -5585,6 +5585,10 @@ static int target_to_host_fcntl_cmd(int cmd)
case TARGET_F_SETOWN_EX:
return F_SETOWN_EX;
#endif
+ case TARGET_F_SETPIPE_SZ:
+ return F_SETPIPE_SZ;
+ case TARGET_F_GETPIPE_SZ:
+ return F_GETPIPE_SZ;
default:
return -TARGET_EINVAL;
}
@@ -5822,6 +5826,8 @@ static abi_long do_fcntl(int fd, int cmd, abi_ulong arg)
case TARGET_F_GETSIG:
case TARGET_F_SETLEASE:
case TARGET_F_GETLEASE:
+ case TARGET_F_SETPIPE_SZ:
+ case TARGET_F_GETPIPE_SZ:
ret = get_errno(safe_fcntl(fd, host_cmd, arg));
break;
diff --git a/linux-user/syscall_defs.h b/linux-user/syscall_defs.h
index 6ee9251..420463b 100644
--- a/linux-user/syscall_defs.h
+++ b/linux-user/syscall_defs.h
@@ -2166,6 +2166,8 @@ struct target_statfs64 {
#define TARGET_F_SETLEASE (TARGET_F_LINUX_SPECIFIC_BASE + 0)
#define TARGET_F_GETLEASE (TARGET_F_LINUX_SPECIFIC_BASE + 1)
#define TARGET_F_DUPFD_CLOEXEC (TARGET_F_LINUX_SPECIFIC_BASE + 6)
+#define TARGET_F_SETPIPE_SZ (TARGET_F_LINUX_SPECIFIC_BASE + 7)
+#define TARGET_F_GETPIPE_SZ (TARGET_F_LINUX_SPECIFIC_BASE + 8)
#define TARGET_F_NOTIFY (TARGET_F_LINUX_SPECIFIC_BASE+2)
#if defined(TARGET_ALPHA)
--
1.9.1
^ permalink raw reply related [flat|nested] 8+ messages in thread
* Re: [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls
2016-06-20 14:50 ` [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls Peter Maydell
@ 2016-06-21 19:09 ` Laurent Vivier
2016-06-21 19:50 ` Peter Maydell
0 siblings, 1 reply; 8+ messages in thread
From: Laurent Vivier @ 2016-06-21 19:09 UTC (permalink / raw)
To: Peter Maydell, qemu-devel; +Cc: patches, Riku Voipio
Le 20/06/2016 à 16:50, Peter Maydell a écrit :
> Many syscalls which take a sigset_t argument also take an argument
> giving the size of the sigset_t. The kernel insists that this
> matches its idea of the type size and fails EINVAL if it is not.
> Implement this logic in QEMU. (This mostly just means some LTP test
> cases which check error cases now pass.)
>
> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
> ---
> linux-user/syscall.c | 46 +++++++++++++++++++++++++++++++++++++++++++++-
> 1 file changed, 45 insertions(+), 1 deletion(-)
>
> diff --git a/linux-user/syscall.c b/linux-user/syscall.c
> index 95eafeb..7b3d129 100644
> --- a/linux-user/syscall.c
> +++ b/linux-user/syscall.c
> @@ -7592,7 +7592,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> #if defined(TARGET_ALPHA)
> struct target_sigaction act, oact, *pact = 0;
> struct target_rt_sigaction *rt_act;
> - /* ??? arg4 == sizeof(sigset_t). */
> +
> + if (arg4 != sizeof(target_sigset_t)) {
> + ret = -TARGET_EINVAL;
> + break;
> + }
> if (arg2) {
> if (!lock_user_struct(VERIFY_READ, rt_act, arg2, 1))
> goto efault;
> @@ -7616,6 +7620,10 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> struct target_sigaction *act;
> struct target_sigaction *oact;
>
> + if (arg4 != sizeof(target_sigset_t)) {
> + ret = -TARGET_EINVAL;
> + break;
> + }
> if (arg2) {
> if (!lock_user_struct(VERIFY_READ, act, arg2, 1))
> goto efault;
> @@ -7747,6 +7755,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> int how = arg1;
> sigset_t set, oldset, *set_ptr;
>
> + if (arg4 != sizeof(target_sigset_t)) {
> + ret = -TARGET_EINVAL;
> + goto fail;
> + }
why "goto fail" instead of "break"?
[you're not in a switch()]
> +
> if (arg2) {
> switch(how) {
> case TARGET_SIG_BLOCK:
> @@ -7797,6 +7810,16 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> case TARGET_NR_rt_sigpending:
> {
> sigset_t set;
> +
> + /* Yes, this check is >, not != like most. We follow the kernel's
> + * logic and it does it like this because it implements
> + * NR_sigpending through the same code path, and in that case
> + * the old_sigset_t is smaller in size.
> + */
> + if (arg2 > sizeof(target_sigset_t)) {
> + return -TARGET_EINVAL;
> + }
why "return" instead of "break"?
> +
> ret = get_errno(sigpending(&set));
> if (!is_error(ret)) {
> if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
> @@ -7830,6 +7853,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> case TARGET_NR_rt_sigsuspend:
> {
> TaskState *ts = cpu->opaque;
> +
> + if (arg2 != sizeof(target_sigset_t)) {
> + ret = -TARGET_EINVAL;
> + break;
> + }
> if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
> goto efault;
> target_to_host_sigset(&ts->sigsuspend_mask, p);
> @@ -7847,6 +7875,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> struct timespec uts, *puts;
> siginfo_t uinfo;
>
> + if (arg4 != sizeof(target_sigset_t)) {
> + ret = -TARGET_EINVAL;
> + break;
> + }
> +
> if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
> goto efault;
> target_to_host_sigset(&set, p);
> @@ -9095,6 +9128,12 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> }
>
> if (arg4) {
> + if (arg5 != sizeof(target_sigset_t)) {
> + unlock_user(target_pfd, arg1, 0);
> + ret = -TARGET_EINVAL;
> + break;
> + }
> +
> target_set = lock_user(VERIFY_READ, arg4, sizeof(target_sigset_t), 1);
> if (!target_set) {
> unlock_user(target_pfd, arg1, 0);
> @@ -10914,6 +10953,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> sigset_t _set, *set = &_set;
>
> if (arg5) {
> + if (arg6 != sizeof(target_sigset_t)) {
> + ret = -TARGET_EINVAL;
> + break;
> + }
> +
> target_set = lock_user(VERIFY_READ, arg5,
> sizeof(target_sigset_t), 1);
> if (!target_set) {
>
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Qemu-devel] [PATCH 2/3] linux-user: Fix wrong type used for argument to rt_sigqueueinfo
2016-06-20 14:50 ` [Qemu-devel] [PATCH 2/3] linux-user: Fix wrong type used for argument to rt_sigqueueinfo Peter Maydell
@ 2016-06-21 19:10 ` Laurent Vivier
0 siblings, 0 replies; 8+ messages in thread
From: Laurent Vivier @ 2016-06-21 19:10 UTC (permalink / raw)
To: Peter Maydell, qemu-devel; +Cc: patches, Riku Voipio
Le 20/06/2016 à 16:50, Peter Maydell a écrit :
> The third argument to the rt_sigqueueinfo syscall is a pointer to
> a siginfo_t, not a pointer to a sigset_t. Fix the error in the
> arguments to lock_user(), which meant that we would not have
> detected some faults that we should.
>
> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Laurent Vivier <laurent@vivier.eu>
> ---
> linux-user/syscall.c | 5 ++++-
> 1 file changed, 4 insertions(+), 1 deletion(-)
>
> diff --git a/linux-user/syscall.c b/linux-user/syscall.c
> index 7b3d129..8065284 100644
> --- a/linux-user/syscall.c
> +++ b/linux-user/syscall.c
> @@ -7909,8 +7909,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
> case TARGET_NR_rt_sigqueueinfo:
> {
> siginfo_t uinfo;
> - if (!(p = lock_user(VERIFY_READ, arg3, sizeof(target_sigset_t), 1)))
> +
> + p = lock_user(VERIFY_READ, arg3, sizeof(target_siginfo_t), 1);
> + if (!p) {
> goto efault;
> + }
> target_to_host_siginfo(&uinfo, p);
> unlock_user(p, arg1, 0);
> ret = get_errno(sys_rt_sigqueueinfo(arg1, arg2, &uinfo));
>
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Qemu-devel] [PATCH 3/3] linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls
2016-06-20 14:50 ` [Qemu-devel] [PATCH 3/3] linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls Peter Maydell
@ 2016-06-21 19:13 ` Laurent Vivier
0 siblings, 0 replies; 8+ messages in thread
From: Laurent Vivier @ 2016-06-21 19:13 UTC (permalink / raw)
To: Peter Maydell, qemu-devel; +Cc: patches, Riku Voipio
Le 20/06/2016 à 16:50, Peter Maydell a écrit :
> Support the F_GETPIPE_SZ and F_SETPIPE_SZ fcntl operations.
>
> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Laurent Vivier <laurent@vivier.eu>
> ---
> linux-user/strace.c | 7 +++++++
> linux-user/syscall.c | 6 ++++++
> linux-user/syscall_defs.h | 2 ++
> 3 files changed, 15 insertions(+)
>
> diff --git a/linux-user/strace.c b/linux-user/strace.c
> index 4046b81..6ef5d38 100644
> --- a/linux-user/strace.c
> +++ b/linux-user/strace.c
> @@ -918,6 +918,13 @@ print_fcntl(const struct syscallname *name,
> case TARGET_F_GETLEASE:
> gemu_log("F_GETLEASE");
> break;
> + case TARGET_F_SETPIPE_SZ:
> + gemu_log("F_SETPIPE_SZ,");
> + print_raw_param(TARGET_ABI_FMT_ld, arg2, 1);
> + break;
> + case TARGET_F_GETPIPE_SZ:
> + gemu_log("F_GETPIPE_SZ");
> + break;
> case TARGET_F_DUPFD_CLOEXEC:
> gemu_log("F_DUPFD_CLOEXEC,");
> print_raw_param(TARGET_ABI_FMT_ld, arg2, 1);
> diff --git a/linux-user/syscall.c b/linux-user/syscall.c
> index 8065284..719ca20 100644
> --- a/linux-user/syscall.c
> +++ b/linux-user/syscall.c
> @@ -5585,6 +5585,10 @@ static int target_to_host_fcntl_cmd(int cmd)
> case TARGET_F_SETOWN_EX:
> return F_SETOWN_EX;
> #endif
> + case TARGET_F_SETPIPE_SZ:
> + return F_SETPIPE_SZ;
> + case TARGET_F_GETPIPE_SZ:
> + return F_GETPIPE_SZ;
> default:
> return -TARGET_EINVAL;
> }
> @@ -5822,6 +5826,8 @@ static abi_long do_fcntl(int fd, int cmd, abi_ulong arg)
> case TARGET_F_GETSIG:
> case TARGET_F_SETLEASE:
> case TARGET_F_GETLEASE:
> + case TARGET_F_SETPIPE_SZ:
> + case TARGET_F_GETPIPE_SZ:
> ret = get_errno(safe_fcntl(fd, host_cmd, arg));
> break;
>
> diff --git a/linux-user/syscall_defs.h b/linux-user/syscall_defs.h
> index 6ee9251..420463b 100644
> --- a/linux-user/syscall_defs.h
> +++ b/linux-user/syscall_defs.h
> @@ -2166,6 +2166,8 @@ struct target_statfs64 {
> #define TARGET_F_SETLEASE (TARGET_F_LINUX_SPECIFIC_BASE + 0)
> #define TARGET_F_GETLEASE (TARGET_F_LINUX_SPECIFIC_BASE + 1)
> #define TARGET_F_DUPFD_CLOEXEC (TARGET_F_LINUX_SPECIFIC_BASE + 6)
> +#define TARGET_F_SETPIPE_SZ (TARGET_F_LINUX_SPECIFIC_BASE + 7)
> +#define TARGET_F_GETPIPE_SZ (TARGET_F_LINUX_SPECIFIC_BASE + 8)
> #define TARGET_F_NOTIFY (TARGET_F_LINUX_SPECIFIC_BASE+2)
>
> #if defined(TARGET_ALPHA)
>
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls
2016-06-21 19:09 ` Laurent Vivier
@ 2016-06-21 19:50 ` Peter Maydell
0 siblings, 0 replies; 8+ messages in thread
From: Peter Maydell @ 2016-06-21 19:50 UTC (permalink / raw)
To: Laurent Vivier; +Cc: QEMU Developers, Patch Tracking, Riku Voipio
On 21 June 2016 at 20:09, Laurent Vivier <laurent@vivier.eu> wrote:
>
>
> Le 20/06/2016 à 16:50, Peter Maydell a écrit :
>> Many syscalls which take a sigset_t argument also take an argument
>> giving the size of the sigset_t. The kernel insists that this
>> matches its idea of the type size and fails EINVAL if it is not.
>> Implement this logic in QEMU. (This mostly just means some LTP test
>> cases which check error cases now pass.)
>>
>> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
>> ---
>> linux-user/syscall.c | 46 +++++++++++++++++++++++++++++++++++++++++++++-
>> 1 file changed, 45 insertions(+), 1 deletion(-)
>>
>> diff --git a/linux-user/syscall.c b/linux-user/syscall.c
>> index 95eafeb..7b3d129 100644
>> --- a/linux-user/syscall.c
>> +++ b/linux-user/syscall.c
>> @@ -7592,7 +7592,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
>> #if defined(TARGET_ALPHA)
>> struct target_sigaction act, oact, *pact = 0;
>> struct target_rt_sigaction *rt_act;
>> - /* ??? arg4 == sizeof(sigset_t). */
>> +
>> + if (arg4 != sizeof(target_sigset_t)) {
>> + ret = -TARGET_EINVAL;
>> + break;
>> + }
>> if (arg2) {
>> if (!lock_user_struct(VERIFY_READ, rt_act, arg2, 1))
>> goto efault;
>> @@ -7616,6 +7620,10 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
>> struct target_sigaction *act;
>> struct target_sigaction *oact;
>>
>> + if (arg4 != sizeof(target_sigset_t)) {
>> + ret = -TARGET_EINVAL;
>> + break;
>> + }
>> if (arg2) {
>> if (!lock_user_struct(VERIFY_READ, act, arg2, 1))
>> goto efault;
>> @@ -7747,6 +7755,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
>> int how = arg1;
>> sigset_t set, oldset, *set_ptr;
>>
>> + if (arg4 != sizeof(target_sigset_t)) {
>> + ret = -TARGET_EINVAL;
>> + goto fail;
>> + }
>
> why "goto fail" instead of "break"?
> [you're not in a switch()]
>
>> +
>> if (arg2) {
>> switch(how) {
>> case TARGET_SIG_BLOCK:
>> @@ -7797,6 +7810,16 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
>> case TARGET_NR_rt_sigpending:
>> {
>> sigset_t set;
>> +
>> + /* Yes, this check is >, not != like most. We follow the kernel's
>> + * logic and it does it like this because it implements
>> + * NR_sigpending through the same code path, and in that case
>> + * the old_sigset_t is smaller in size.
>> + */
>> + if (arg2 > sizeof(target_sigset_t)) {
>> + return -TARGET_EINVAL;
>> + }
>
> why "return" instead of "break"?
Yeah, there's no particular reason for these inconsistencies,
so I guess we should just use 'break' everywhere.
thanks
-- PMM
^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2016-06-21 19:51 UTC | newest]
Thread overview: 8+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2016-06-20 14:50 [Qemu-devel] [PATCH 0/3] linux-user: three minor fixes Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 1/3] linux-user: Check sigsetsize argument to syscalls Peter Maydell
2016-06-21 19:09 ` Laurent Vivier
2016-06-21 19:50 ` Peter Maydell
2016-06-20 14:50 ` [Qemu-devel] [PATCH 2/3] linux-user: Fix wrong type used for argument to rt_sigqueueinfo Peter Maydell
2016-06-21 19:10 ` Laurent Vivier
2016-06-20 14:50 ` [Qemu-devel] [PATCH 3/3] linux-user: Support F_GETPIPE_SZ and F_SETPIPE_SZ fcntls Peter Maydell
2016-06-21 19:13 ` Laurent Vivier
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).