From c3311c13adc1021e986fef12609ceb395ffc5014 Mon Sep 17 00:00:00 2001 From: Martin Schwidefsky Date: Wed, 13 Jan 2010 20:44:25 +0100 Subject: [S390] fix loading of PER control registers for utrace. If the current task enables / disables PER tracing for itself the PER control registers need to be loaded in FixPerRegisters. Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/ptrace.c | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'arch/s390') diff --git a/arch/s390/kernel/ptrace.c b/arch/s390/kernel/ptrace.c index 13815d39f7dd..7cf464234419 100644 --- a/arch/s390/kernel/ptrace.c +++ b/arch/s390/kernel/ptrace.c @@ -65,6 +65,7 @@ FixPerRegisters(struct task_struct *task) { struct pt_regs *regs; per_struct *per_info; + per_cr_words cr_words; regs = task_pt_regs(task); per_info = (per_struct *) &task->thread.per_info; @@ -98,6 +99,13 @@ FixPerRegisters(struct task_struct *task) per_info->control_regs.bits.storage_alt_space_ctl = 1; else per_info->control_regs.bits.storage_alt_space_ctl = 0; + + if (task == current) { + __ctl_store(cr_words, 9, 11); + if (memcmp(&cr_words, &per_info->control_regs.words, + sizeof(cr_words)) != 0) + __ctl_load(per_info->control_regs.words, 9, 11); + } } void user_enable_single_step(struct task_struct *task) -- cgit v1.2.2 From f8d5faf718c9ff2c04eb8484585d4963c4111cd7 Mon Sep 17 00:00:00 2001 From: Martin Schwidefsky Date: Wed, 13 Jan 2010 20:44:26 +0100 Subject: [S390] clear TIF_SINGLE_STEP for new process. Clear the TIF_SINGLE_STEP bit in copy_thread. The new process did not get a PER event of its own. It is wrong deliver a SIGTRAP that was meant for the parent process. Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/process.c | 1 + 1 file changed, 1 insertion(+) (limited to 'arch/s390') diff --git a/arch/s390/kernel/process.c b/arch/s390/kernel/process.c index 5417eb57271a..b98fe8e6e507 100644 --- a/arch/s390/kernel/process.c +++ b/arch/s390/kernel/process.c @@ -217,6 +217,7 @@ int copy_thread(unsigned long clone_flags, unsigned long new_stackp, p->thread.mm_segment = get_fs(); /* Don't copy debug registers */ memset(&p->thread.per_info, 0, sizeof(p->thread.per_info)); + clear_tsk_thread_flag(p, TIF_SINGLE_STEP); /* Initialize per thread user and system timer values */ ti = task_thread_info(p); ti->user_timer = 0; -- cgit v1.2.2 From 6f50248ef0efa7453397eb53e41e8aa5df534492 Mon Sep 17 00:00:00 2001 From: Martin Schwidefsky Date: Wed, 13 Jan 2010 20:44:27 +0100 Subject: [S390] duplicate SIGTRAP on signal delivery. The code in do_signal sets the TIF_SINGLE_STEP bit and calls tracehook_signal_handler after the signal frame has been set up. This causes two SIGTRAP signals to be delivered to the tracer. Stop setting the TIF_SINGLE_STEP bit in do_signal to get the correct number of SIGTRAPs. Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/signal.c | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/kernel/signal.c b/arch/s390/kernel/signal.c index 6b4fef877f9d..1675c48b9145 100644 --- a/arch/s390/kernel/signal.c +++ b/arch/s390/kernel/signal.c @@ -499,19 +499,11 @@ void do_signal(struct pt_regs *regs) if (test_thread_flag(TIF_RESTORE_SIGMASK)) clear_thread_flag(TIF_RESTORE_SIGMASK); - /* - * If we would have taken a single-step trap - * for a normal instruction, act like we took - * one for the handler setup. - */ - if (current->thread.per_info.single_step) - set_thread_flag(TIF_SINGLE_STEP); - /* * Let tracing know that we've done the handler setup. */ tracehook_signal_handler(signr, &info, &ka, regs, - test_thread_flag(TIF_SINGLE_STEP)); + current->thread.per_info.single_step); } return; } -- cgit v1.2.2 From bebf023d415fd8984994a596aaa83cd0a3046d0b Mon Sep 17 00:00:00 2001 From: Martin Schwidefsky Date: Wed, 13 Jan 2010 20:44:28 +0100 Subject: [S390] remove superfluous TIF_USEDFPU bit The TIF_USEDFPU bit is always 0 for s390 and it is not tested anywhere. Remove the bit. At the same time remove the calls to clear_used_math() as well. The PF_USED_MATH bit is never set for s390 either. Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/thread_info.h | 12 +++++------- arch/s390/kernel/process.c | 2 -- arch/s390/kernel/setup.c | 6 ------ 3 files changed, 5 insertions(+), 15 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/thread_info.h b/arch/s390/include/asm/thread_info.h index 07eb61b2fb3a..66069e736842 100644 --- a/arch/s390/include/asm/thread_info.h +++ b/arch/s390/include/asm/thread_info.h @@ -93,13 +93,12 @@ static inline struct thread_info *current_thread_info(void) #define TIF_SYSCALL_AUDIT 9 /* syscall auditing active */ #define TIF_SECCOMP 10 /* secure computing */ #define TIF_SYSCALL_TRACEPOINT 11 /* syscall tracepoint instrumentation */ -#define TIF_USEDFPU 16 /* FPU was used by this task this quantum (SMP) */ -#define TIF_POLLING_NRFLAG 17 /* true if poll_idle() is polling +#define TIF_POLLING_NRFLAG 16 /* true if poll_idle() is polling TIF_NEED_RESCHED */ -#define TIF_31BIT 18 /* 32bit process */ -#define TIF_MEMDIE 19 -#define TIF_RESTORE_SIGMASK 20 /* restore signal mask in do_signal() */ -#define TIF_FREEZE 21 /* thread is freezing for suspend */ +#define TIF_31BIT 17 /* 32bit process */ +#define TIF_MEMDIE 18 +#define TIF_RESTORE_SIGMASK 19 /* restore signal mask in do_signal() */ +#define TIF_FREEZE 20 /* thread is freezing for suspend */ #define _TIF_NOTIFY_RESUME (1<active_mm = &init_mm; BUG_ON(current->mm); -- cgit v1.2.2 From a58c26bba9ebe97fea99aee125728b1f3886499e Mon Sep 17 00:00:00 2001 From: Jiri Slaby Date: Wed, 13 Jan 2010 20:44:33 +0100 Subject: [S390] use helpers for rlimits Make sure compiler won't do weird things with limits. E.g. fetching them twice may return 2 different values after writable limits are implemented. I.e. either use rlimit helpers added in 3e10e716abf3c71bdb5d86b8f507f9e72236c9cd or ACCESS_ONCE if not applicable. Cc: Heiko Carstens Cc: linux390@de.ibm.com Cc: linux-s390@vger.kernel.org Signed-off-by: Jiri Slaby Signed-off-by: Martin Schwidefsky --- arch/s390/mm/mmap.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/mm/mmap.c b/arch/s390/mm/mmap.c index f4558ccf02b9..869efbaed3ea 100644 --- a/arch/s390/mm/mmap.c +++ b/arch/s390/mm/mmap.c @@ -40,7 +40,7 @@ static inline unsigned long mmap_base(void) { - unsigned long gap = current->signal->rlim[RLIMIT_STACK].rlim_cur; + unsigned long gap = rlimit(RLIMIT_STACK); if (gap < MIN_GAP) gap = MIN_GAP; @@ -61,7 +61,7 @@ static inline int mmap_is_legacy(void) #endif return sysctl_legacy_va_layout || (current->personality & ADDR_COMPAT_LAYOUT) || - current->signal->rlim[RLIMIT_STACK].rlim_cur == RLIM_INFINITY; + rlimit(RLIMIT_STACK) == RLIM_INFINITY; } #ifndef CONFIG_64BIT -- cgit v1.2.2 From 02beaccc901b7a28ac1de79f3ed122f5fda220b1 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 13 Jan 2010 20:44:34 +0100 Subject: [S390] smp: setup smp_processor_id early smp_processor_id() is supposed to work before setup_arch() gets called. Before that smp_processor_id() may return just an arbitrary value that is contained in the uninitialized boot lowcore. So provide the arch function which will override the weak function in init/main.c. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/setup.c | 1 - arch/s390/kernel/smp.c | 6 ++++++ 2 files changed, 6 insertions(+), 1 deletion(-) (limited to 'arch/s390') diff --git a/arch/s390/kernel/setup.c b/arch/s390/kernel/setup.c index 2148ad3d490d..2d6a265b0145 100644 --- a/arch/s390/kernel/setup.c +++ b/arch/s390/kernel/setup.c @@ -849,7 +849,6 @@ setup_arch(char **cmdline_p) setup_lowcore(); cpu_init(); - __cpu_logical_map[0] = stap(); s390_init_cpu_topology(); /* diff --git a/arch/s390/kernel/smp.c b/arch/s390/kernel/smp.c index 93e52039321b..eebce7fdc97c 100644 --- a/arch/s390/kernel/smp.c +++ b/arch/s390/kernel/smp.c @@ -717,6 +717,12 @@ void __init smp_cpus_done(unsigned int max_cpus) { } +void __init smp_setup_processor_id(void) +{ + S390_lowcore.cpu_nr = 0; + __cpu_logical_map[0] = stap(); +} + /* * the frequency of the profiling timer can be changed * by writing a multiplier value into /proc/profile. -- cgit v1.2.2 From c6a5f8cea2e5454fce3859ca5ed381c2535184cf Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 13 Jan 2010 20:44:35 +0100 Subject: [S390] smp: remove volatile type quilifier from __cpu_logical_map Remove pointless qualifier. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/sigp.h | 2 +- arch/s390/kernel/setup.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/sigp.h b/arch/s390/include/asm/sigp.h index ec403d4304f8..0cc620a6a2cc 100644 --- a/arch/s390/include/asm/sigp.h +++ b/arch/s390/include/asm/sigp.h @@ -19,7 +19,7 @@ #include /* get real cpu address from logical cpu number */ -extern volatile int __cpu_logical_map[]; +extern int __cpu_logical_map[]; typedef enum { diff --git a/arch/s390/kernel/setup.c b/arch/s390/kernel/setup.c index 2d6a265b0145..3fe1680c3899 100644 --- a/arch/s390/kernel/setup.c +++ b/arch/s390/kernel/setup.c @@ -87,7 +87,7 @@ unsigned long elf_hwcap = 0; char elf_platform[ELF_PLATFORM_SIZE]; struct mem_chunk __initdata memory_chunk[MEMORY_CHUNKS]; -volatile int __cpu_logical_map[NR_CPUS]; /* logical cpu to cpu address */ +int __cpu_logical_map[NR_CPUS]; /* logical cpu to cpu address */ int __initdata memory_end_set; unsigned long __initdata memory_end; -- cgit v1.2.2 From fb380aadfe34e8d3ce628cb3e386882351940874 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 13 Jan 2010 20:44:37 +0100 Subject: [S390] Move __cpu_logical_map to smp.c Finally move it to the place where it belongs to and make get rid of it for !CONFIG_SMP. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/sigp.h | 18 +++++++++++++----- arch/s390/kernel/setup.c | 1 - arch/s390/kernel/smp.c | 3 +++ arch/s390/kernel/topology.c | 2 +- arch/s390/lib/spinlock.c | 2 +- 5 files changed, 18 insertions(+), 8 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/sigp.h b/arch/s390/include/asm/sigp.h index 0cc620a6a2cc..f72d611f7e13 100644 --- a/arch/s390/include/asm/sigp.h +++ b/arch/s390/include/asm/sigp.h @@ -15,12 +15,20 @@ #ifndef __SIGP__ #define __SIGP__ -#include -#include +#include /* get real cpu address from logical cpu number */ extern int __cpu_logical_map[]; +static inline int cpu_logical_map(int cpu) +{ +#ifdef CONFIG_SMP + return __cpu_logical_map[cpu]; +#else + return stap(); +#endif +} + typedef enum { sigp_unassigned=0x0, @@ -79,7 +87,7 @@ signal_processor(__u16 cpu_addr, sigp_order_code order_code) " ipm %0\n" " srl %0,28\n" : "=d" (ccode) - : "d" (reg1), "d" (__cpu_logical_map[cpu_addr]), + : "d" (reg1), "d" (cpu_logical_map(cpu_addr)), "a" (order_code) : "cc" , "memory"); return ccode; } @@ -98,7 +106,7 @@ signal_processor_p(__u32 parameter, __u16 cpu_addr, sigp_order_code order_code) " ipm %0\n" " srl %0,28\n" : "=d" (ccode) - : "d" (reg1), "d" (__cpu_logical_map[cpu_addr]), + : "d" (reg1), "d" (cpu_logical_map(cpu_addr)), "a" (order_code) : "cc" , "memory"); return ccode; } @@ -118,7 +126,7 @@ signal_processor_ps(__u32 *statusptr, __u32 parameter, __u16 cpu_addr, " ipm %0\n" " srl %0,28\n" : "=d" (ccode), "+d" (reg1) - : "d" (__cpu_logical_map[cpu_addr]), "a" (order_code) + : "d" (cpu_logical_map(cpu_addr)), "a" (order_code) : "cc" , "memory"); *statusptr = reg1; return ccode; diff --git a/arch/s390/kernel/setup.c b/arch/s390/kernel/setup.c index 3fe1680c3899..8d8957b38ab3 100644 --- a/arch/s390/kernel/setup.c +++ b/arch/s390/kernel/setup.c @@ -87,7 +87,6 @@ unsigned long elf_hwcap = 0; char elf_platform[ELF_PLATFORM_SIZE]; struct mem_chunk __initdata memory_chunk[MEMORY_CHUNKS]; -int __cpu_logical_map[NR_CPUS]; /* logical cpu to cpu address */ int __initdata memory_end_set; unsigned long __initdata memory_end; diff --git a/arch/s390/kernel/smp.c b/arch/s390/kernel/smp.c index eebce7fdc97c..76a6fdd46c45 100644 --- a/arch/s390/kernel/smp.c +++ b/arch/s390/kernel/smp.c @@ -52,6 +52,9 @@ #include #include "entry.h" +/* logical cpu to cpu address */ +int __cpu_logical_map[NR_CPUS]; + static struct task_struct *current_set[NR_CPUS]; static u8 smp_cpu_type; diff --git a/arch/s390/kernel/topology.c b/arch/s390/kernel/topology.c index 3c72c9cf22b6..14ef6f05e432 100644 --- a/arch/s390/kernel/topology.c +++ b/arch/s390/kernel/topology.c @@ -114,7 +114,7 @@ static void add_cpus_to_core(struct tl_cpu *tl_cpu, struct core_info *core) rcpu = CPU_BITS - 1 - cpu + tl_cpu->origin; for_each_present_cpu(lcpu) { - if (__cpu_logical_map[lcpu] == rcpu) { + if (cpu_logical_map(lcpu) == rcpu) { cpu_set(lcpu, core->mask); smp_cpu_polarization[lcpu] = tl_cpu->pp; } diff --git a/arch/s390/lib/spinlock.c b/arch/s390/lib/spinlock.c index 10754a375668..cff327f109a8 100644 --- a/arch/s390/lib/spinlock.c +++ b/arch/s390/lib/spinlock.c @@ -34,7 +34,7 @@ static inline void _raw_yield_cpu(int cpu) { if (MACHINE_HAS_DIAG9C) asm volatile("diag %0,0,0x9c" - : : "d" (__cpu_logical_map[cpu])); + : : "d" (cpu_logical_map(cpu))); else _raw_yield(); } -- cgit v1.2.2 From a9df8e325d0de527c2e97297704ebbec48c01cbf Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 13 Jan 2010 20:44:38 +0100 Subject: [S390] bug: implement arch specific __WARN macro This one will trap, generates shorter code and emits better debug data than the generic version. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/bug.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/bug.h b/arch/s390/include/asm/bug.h index efb74fd5156e..b1066b9fb5f8 100644 --- a/arch/s390/include/asm/bug.h +++ b/arch/s390/include/asm/bug.h @@ -52,6 +52,10 @@ unreachable(); \ } while (0) +#define __WARN() do { \ + __EMIT_BUG(BUGFLAG_WARNING); \ +} while (0) + #define WARN_ON(x) ({ \ int __ret_warn_on = !!(x); \ if (__builtin_constant_p(__ret_warn_on)) { \ -- cgit v1.2.2 From d381589834aa69f51f95b1e364fe79688692aab4 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 13 Jan 2010 20:44:39 +0100 Subject: [S390] mmap: add missing compat_ptr conversion to both mmap compat syscalls Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/compat_linux.c | 41 ++++++++++++++++------------------------- 1 file changed, 16 insertions(+), 25 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/kernel/compat_linux.c b/arch/s390/kernel/compat_linux.c index 22c9e557bb22..11c3aba664ea 100644 --- a/arch/s390/kernel/compat_linux.c +++ b/arch/s390/kernel/compat_linux.c @@ -616,44 +616,35 @@ asmlinkage long sys32_fstatat64(unsigned int dfd, char __user *filename, */ struct mmap_arg_struct_emu31 { - u32 addr; - u32 len; - u32 prot; - u32 flags; - u32 fd; - u32 offset; + compat_ulong_t addr; + compat_ulong_t len; + compat_ulong_t prot; + compat_ulong_t flags; + compat_ulong_t fd; + compat_ulong_t offset; }; -asmlinkage unsigned long -old32_mmap(struct mmap_arg_struct_emu31 __user *arg) +asmlinkage unsigned long old32_mmap(struct mmap_arg_struct_emu31 __user *arg) { struct mmap_arg_struct_emu31 a; - int error = -EFAULT; if (copy_from_user(&a, arg, sizeof(a))) - goto out; - - error = -EINVAL; + return -EFAULT; if (a.offset & ~PAGE_MASK) - goto out; - - error = sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, - a.offset >> PAGE_SHIFT); -out: - return error; + return -EINVAL; + a.addr = (unsigned long) compat_ptr(a.addr); + return sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, + a.offset >> PAGE_SHIFT); } -asmlinkage long -sys32_mmap2(struct mmap_arg_struct_emu31 __user *arg) +asmlinkage long sys32_mmap2(struct mmap_arg_struct_emu31 __user *arg) { struct mmap_arg_struct_emu31 a; - int error = -EFAULT; if (copy_from_user(&a, arg, sizeof(a))) - goto out; - error = sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, a.offset); -out: - return error; + return -EFAULT; + a.addr = (unsigned long) compat_ptr(a.addr); + return sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, a.offset); } asmlinkage long sys32_read(unsigned int fd, char __user * buf, size_t count) -- cgit v1.2.2 From 94e587f61ef5da3b4da40289cdb7e9a62d455313 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 13 Jan 2010 20:44:42 +0100 Subject: [S390] unwire sys_recvmmsg again sys_recvmmsg is reachable via sys_socketcall. So unwire it again since there is no point in having two entry points for it. Also put it to the ignore list so we don't get reminded anymore in order to wire it up. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/unistd.h | 6 ++++-- arch/s390/kernel/compat_wrapper.S | 9 --------- arch/s390/kernel/syscalls.S | 1 - 3 files changed, 4 insertions(+), 12 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/unistd.h b/arch/s390/include/asm/unistd.h index 192a7203a14f..6e9f049fa823 100644 --- a/arch/s390/include/asm/unistd.h +++ b/arch/s390/include/asm/unistd.h @@ -269,8 +269,7 @@ #define __NR_pwritev 329 #define __NR_rt_tgsigqueueinfo 330 #define __NR_perf_event_open 331 -#define __NR_recvmmsg 332 -#define NR_syscalls 333 +#define NR_syscalls 332 /* * There are some system calls that are not present on 64 bit, some @@ -377,6 +376,9 @@ #define __IGNORE_migrate_pages #define __IGNORE_move_pages +/* Ignore system calls that are also reachable via sys_socket */ +#define __IGNORE_recvmmsg + #define __ARCH_WANT_IPC_PARSE_VERSION #define __ARCH_WANT_OLD_READDIR #define __ARCH_WANT_SYS_ALARM diff --git a/arch/s390/kernel/compat_wrapper.S b/arch/s390/kernel/compat_wrapper.S index faeaccc7d7d9..30de2d0e52bb 100644 --- a/arch/s390/kernel/compat_wrapper.S +++ b/arch/s390/kernel/compat_wrapper.S @@ -1853,12 +1853,3 @@ sys32_execve_wrapper: llgtr %r3,%r3 # compat_uptr_t * llgtr %r4,%r4 # compat_uptr_t * jg sys32_execve # branch to system call - - .globl compat_sys_recvmmsg_wrapper -compat_sys_recvmmsg_wrapper: - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct compat_mmsghdr * - llgfr %r4,%r4 # unsigned int - llgfr %r5,%r5 # unsigned int - llgtr %r6,%r6 # struct compat_timespec * - jg compat_sys_recvmmsg diff --git a/arch/s390/kernel/syscalls.S b/arch/s390/kernel/syscalls.S index 4f292c936872..30eca070d426 100644 --- a/arch/s390/kernel/syscalls.S +++ b/arch/s390/kernel/syscalls.S @@ -340,4 +340,3 @@ SYSCALL(sys_preadv,sys_preadv,compat_sys_preadv_wrapper) SYSCALL(sys_pwritev,sys_pwritev,compat_sys_pwritev_wrapper) SYSCALL(sys_rt_tgsigqueueinfo,sys_rt_tgsigqueueinfo,compat_sys_rt_tgsigqueueinfo_wrapper) /* 330 */ SYSCALL(sys_perf_event_open,sys_perf_event_open,sys_perf_event_open_wrapper) -SYSCALL(sys_recvmmsg,sys_recvmmsg,compat_sys_recvmmsg_wrapper) -- cgit v1.2.2 From 062d5e9b0d714f449b261bb522eadaaf6f00f438 Mon Sep 17 00:00:00 2001 From: Christian Borntraeger Date: Thu, 21 Jan 2010 12:19:07 +0100 Subject: KVM: S390: fix potential array overrun in intercept handling kvm_handle_sie_intercept uses a jump table to get the intercept handler for a SIE intercept. Static code analysis revealed a potential problem: the intercept_funcs jump table was defined to contain (0x48 >> 2) entries, but we only checked for code > 0x48 which would cause an off-by-one array overflow if code == 0x48. Use the compiler and ARRAY_SIZE to automatically set the limits. Cc: stable@kernel.org Signed-off-by: Christian Borntraeger Signed-off-by: Marcelo Tosatti --- arch/s390/kvm/intercept.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/kvm/intercept.c b/arch/s390/kvm/intercept.c index ba9d8a7bc1ac..b40096494e46 100644 --- a/arch/s390/kvm/intercept.c +++ b/arch/s390/kvm/intercept.c @@ -213,7 +213,7 @@ static int handle_instruction_and_prog(struct kvm_vcpu *vcpu) return rc2; } -static const intercept_handler_t intercept_funcs[0x48 >> 2] = { +static const intercept_handler_t intercept_funcs[] = { [0x00 >> 2] = handle_noop, [0x04 >> 2] = handle_instruction, [0x08 >> 2] = handle_prog, @@ -230,7 +230,7 @@ int kvm_handle_sie_intercept(struct kvm_vcpu *vcpu) intercept_handler_t func; u8 code = vcpu->arch.sie_block->icptcode; - if (code & 3 || code > 0x48) + if (code & 3 || (code >> 2) >= ARRAY_SIZE(intercept_funcs)) return -ENOTSUPP; func = intercept_funcs[code >> 2]; if (func) -- cgit v1.2.2 From 428aecf67cf673d546627b2813bd4acabd20e3a9 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Wed, 27 Jan 2010 10:12:36 +0100 Subject: [S390] irqflags: add missing types.h include Add missing types.h include. Otherwise would cause build breakages on hw breakpoint support, because of undefined BITS_PER_LONG. Also fix up the copyright line and remove the superfluous __KERNEL__ ifdef. Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/irqflags.h | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/irqflags.h b/arch/s390/include/asm/irqflags.h index 3f26131120b7..c2fb432f576a 100644 --- a/arch/s390/include/asm/irqflags.h +++ b/arch/s390/include/asm/irqflags.h @@ -1,14 +1,12 @@ /* - * include/asm-s390/irqflags.h - * - * Copyright (C) IBM Corp. 2006 - * Author(s): Heiko Carstens + * Copyright IBM Corp. 2006,2010 + * Author(s): Martin Schwidefsky */ #ifndef __ASM_IRQFLAGS_H #define __ASM_IRQFLAGS_H -#ifdef __KERNEL__ +#include #if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2) @@ -102,5 +100,4 @@ static inline int raw_irqs_disabled_flags(unsigned long flags) /* For spinlocks etc */ #define raw_local_irq_save(x) ((x) = raw_local_irq_disable()) -#endif /* __KERNEL__ */ #endif /* __ASM_IRQFLAGS_H */ -- cgit v1.2.2 From 0b4d78903bf48fe6b125c4c9f0755437a4f21d47 Mon Sep 17 00:00:00 2001 From: Martin Schwidefsky Date: Wed, 27 Jan 2010 10:12:37 +0100 Subject: [S390] use set_current_state in sigsuspend Use set_current_state instead of a direct assignment to set the task state of the current process. Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/signal.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'arch/s390') diff --git a/arch/s390/kernel/signal.c b/arch/s390/kernel/signal.c index 1675c48b9145..6289945562b0 100644 --- a/arch/s390/kernel/signal.c +++ b/arch/s390/kernel/signal.c @@ -64,7 +64,7 @@ SYSCALL_DEFINE3(sigsuspend, int, history0, int, history1, old_sigset_t, mask) recalc_sigpending(); spin_unlock_irq(¤t->sighand->siglock); - current->state = TASK_INTERRUPTIBLE; + set_current_state(TASK_INTERRUPTIBLE); schedule(); set_thread_flag(TIF_RESTORE_SIGMASK); -- cgit v1.2.2 From 21ec7f6dbf10492ce9a21718040677d3e68bd57d Mon Sep 17 00:00:00 2001 From: Martin Schwidefsky Date: Wed, 27 Jan 2010 10:12:40 +0100 Subject: [S390] fix single stepped svcs with TRACE_IRQFLAGS=y If irq flags tracing is enabled the TRACE_IRQS_ON macros expands to a function call which clobbers registers %r0-%r5. The macro is used in the code path for single stepped system calls. The argument registers %r2-%r6 need to be restored from the stack before the system call function is called. Cc: stable@kernel.org Signed-off-by: Martin Schwidefsky --- arch/s390/kernel/entry.S | 1 + arch/s390/kernel/entry64.S | 1 + 2 files changed, 2 insertions(+) (limited to 'arch/s390') diff --git a/arch/s390/kernel/entry.S b/arch/s390/kernel/entry.S index 48215d15762b..e8ef21c51bbe 100644 --- a/arch/s390/kernel/entry.S +++ b/arch/s390/kernel/entry.S @@ -571,6 +571,7 @@ pgm_svcper: mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID oi __TI_flags+3(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP TRACE_IRQS_ON + lm %r2,%r6,SP_R2(%r15) # load svc arguments stosm __SF_EMPTY(%r15),0x03 # reenable interrupts b BASED(sysc_do_svc) diff --git a/arch/s390/kernel/entry64.S b/arch/s390/kernel/entry64.S index 9aff1d449b6e..f33658f09dd7 100644 --- a/arch/s390/kernel/entry64.S +++ b/arch/s390/kernel/entry64.S @@ -549,6 +549,7 @@ pgm_svcper: mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID oi __TI_flags+7(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP TRACE_IRQS_ON + lmg %r2,%r6,SP_R2(%r15) # load svc arguments stosm __SF_EMPTY(%r15),0x03 # reenable interrupts j sysc_do_svc -- cgit v1.2.2 From 7717aefff3290c61e5f9e6aa39e9e1dc63cd4e81 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Tue, 9 Feb 2010 09:46:09 +0100 Subject: [S390] Fix struct _lowcore layout. Offsets and sizes are wrong for 32 bit. Got broken with 866ba284 "[S390] cleanup lowcore.h". Reported-by: Mahesh Salgaonkar Signed-off-by: Heiko Carstens Signed-off-by: Martin Schwidefsky --- arch/s390/include/asm/lowcore.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'arch/s390') diff --git a/arch/s390/include/asm/lowcore.h b/arch/s390/include/asm/lowcore.h index f2ef4b619ce1..c25dfac7dd76 100644 --- a/arch/s390/include/asm/lowcore.h +++ b/arch/s390/include/asm/lowcore.h @@ -293,12 +293,12 @@ struct _lowcore __u64 clock_comparator; /* 0x02d0 */ __u32 machine_flags; /* 0x02d8 */ __u32 ftrace_func; /* 0x02dc */ - __u8 pad_0x02f0[0x0300-0x02f0]; /* 0x02f0 */ + __u8 pad_0x02e0[0x0300-0x02e0]; /* 0x02e0 */ /* Interrupt response block */ __u8 irb[64]; /* 0x0300 */ - __u8 pad_0x0400[0x0e00-0x0400]; /* 0x0400 */ + __u8 pad_0x0340[0x0e00-0x0340]; /* 0x0340 */ /* * 0xe00 contains the address of the IPL Parameter Information -- cgit v1.2.2