summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Ellerman <mpe@ellerman.id.au>2015-07-23 20:21:05 +1000
committerMichael Ellerman <mpe@ellerman.id.au>2015-07-29 11:56:12 +1000
commita7657844296e796bf33922192743ddeacbcd4d7a (patch)
tree2847a8ab0e9176691ce07ca6b8ded749ed550bf8
parent1b1a3702a65c1a6511e4c95ecb3770dfdf235bcf (diff)
powerpc: Rework syscall_get_arguments() so there is only one loop
Currently syscall_get_arguments() has two loops, one for compat and one for regular tasks. In prepartion for the next patch, which changes which registers we use, switch it to only have one loop, so we only have one place to update. Signed-off-by: Michael Ellerman <mpe@ellerman.id.au> Reviewed-by: Kees Cook <keescook@chromium.org>
-rw-r--r--arch/powerpc/include/asm/syscall.h19
1 files changed, 8 insertions, 11 deletions
diff --git a/arch/powerpc/include/asm/syscall.h b/arch/powerpc/include/asm/syscall.h
index cabe90133e69..403e2303fe18 100644
--- a/arch/powerpc/include/asm/syscall.h
+++ b/arch/powerpc/include/asm/syscall.h
@@ -64,19 +64,16 @@ static inline void syscall_get_arguments(struct task_struct *task,
unsigned int i, unsigned int n,
unsigned long *args)
{
+ unsigned long mask = -1UL;
+
BUG_ON(i + n > 6);
-#ifdef CONFIG_PPC64
- if (test_tsk_thread_flag(task, TIF_32BIT)) {
- /*
- * Zero-extend 32-bit argument values. The high bits are
- * garbage ignored by the actual syscall dispatch.
- */
- while (n-- > 0)
- args[n] = (u32) regs->gpr[3 + i + n];
- return;
- }
+
+#ifdef CONFIG_COMPAT
+ if (test_tsk_thread_flag(task, TIF_32BIT))
+ mask = 0xffffffff;
#endif
- memcpy(args, &regs->gpr[3 + i], n * sizeof(args[0]));
+ while (n--)
+ args[n] = regs->gpr[3 + i + n] & mask;
}
static inline void syscall_set_arguments(struct task_struct *task,