aboutsummaryrefslogtreecommitdiffstats
path: root/arch/s390/kernel/ptrace.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/s390/kernel/ptrace.c')
-rw-r--r--arch/s390/kernel/ptrace.c46
1 files changed, 5 insertions, 41 deletions
diff --git a/arch/s390/kernel/ptrace.c b/arch/s390/kernel/ptrace.c
index eabfb4594517..d363c9c322a1 100644
--- a/arch/s390/kernel/ptrace.c
+++ b/arch/s390/kernel/ptrace.c
@@ -44,7 +44,6 @@ void update_cr_regs(struct task_struct *task)
44 struct thread_struct *thread = &task->thread; 44 struct thread_struct *thread = &task->thread;
45 struct per_regs old, new; 45 struct per_regs old, new;
46 46
47#ifdef CONFIG_64BIT
48 /* Take care of the enable/disable of transactional execution. */ 47 /* Take care of the enable/disable of transactional execution. */
49 if (MACHINE_HAS_TE || MACHINE_HAS_VX) { 48 if (MACHINE_HAS_TE || MACHINE_HAS_VX) {
50 unsigned long cr, cr_new; 49 unsigned long cr, cr_new;
@@ -80,7 +79,6 @@ void update_cr_regs(struct task_struct *task)
80 __ctl_load(cr_new, 2, 2); 79 __ctl_load(cr_new, 2, 2);
81 } 80 }
82 } 81 }
83#endif
84 /* Copy user specified PER registers */ 82 /* Copy user specified PER registers */
85 new.control = thread->per_user.control; 83 new.control = thread->per_user.control;
86 new.start = thread->per_user.start; 84 new.start = thread->per_user.start;
@@ -93,10 +91,8 @@ void update_cr_regs(struct task_struct *task)
93 new.control |= PER_EVENT_BRANCH; 91 new.control |= PER_EVENT_BRANCH;
94 else 92 else
95 new.control |= PER_EVENT_IFETCH; 93 new.control |= PER_EVENT_IFETCH;
96#ifdef CONFIG_64BIT
97 new.control |= PER_CONTROL_SUSPENSION; 94 new.control |= PER_CONTROL_SUSPENSION;
98 new.control |= PER_EVENT_TRANSACTION_END; 95 new.control |= PER_EVENT_TRANSACTION_END;
99#endif
100 if (test_tsk_thread_flag(task, TIF_UPROBE_SINGLESTEP)) 96 if (test_tsk_thread_flag(task, TIF_UPROBE_SINGLESTEP))
101 new.control |= PER_EVENT_IFETCH; 97 new.control |= PER_EVENT_IFETCH;
102 new.start = 0; 98 new.start = 0;
@@ -146,11 +142,7 @@ void ptrace_disable(struct task_struct *task)
146 task->thread.per_flags = 0; 142 task->thread.per_flags = 0;
147} 143}
148 144
149#ifndef CONFIG_64BIT 145#define __ADDR_MASK 7
150# define __ADDR_MASK 3
151#else
152# define __ADDR_MASK 7
153#endif
154 146
155static inline unsigned long __peek_user_per(struct task_struct *child, 147static inline unsigned long __peek_user_per(struct task_struct *child,
156 addr_t addr) 148 addr_t addr)
@@ -223,7 +215,6 @@ static unsigned long __peek_user(struct task_struct *child, addr_t addr)
223 * access registers are stored in the thread structure 215 * access registers are stored in the thread structure
224 */ 216 */
225 offset = addr - (addr_t) &dummy->regs.acrs; 217 offset = addr - (addr_t) &dummy->regs.acrs;
226#ifdef CONFIG_64BIT
227 /* 218 /*
228 * Very special case: old & broken 64 bit gdb reading 219 * Very special case: old & broken 64 bit gdb reading
229 * from acrs[15]. Result is a 64 bit value. Read the 220 * from acrs[15]. Result is a 64 bit value. Read the
@@ -232,8 +223,7 @@ static unsigned long __peek_user(struct task_struct *child, addr_t addr)
232 if (addr == (addr_t) &dummy->regs.acrs[15]) 223 if (addr == (addr_t) &dummy->regs.acrs[15])
233 tmp = ((unsigned long) child->thread.acrs[15]) << 32; 224 tmp = ((unsigned long) child->thread.acrs[15]) << 32;
234 else 225 else
235#endif 226 tmp = *(addr_t *)((addr_t) &child->thread.acrs + offset);
236 tmp = *(addr_t *)((addr_t) &child->thread.acrs + offset);
237 227
238 } else if (addr == (addr_t) &dummy->regs.orig_gpr2) { 228 } else if (addr == (addr_t) &dummy->regs.orig_gpr2) {
239 /* 229 /*
@@ -261,12 +251,10 @@ static unsigned long __peek_user(struct task_struct *child, addr_t addr)
261 * or the child->thread.vxrs array 251 * or the child->thread.vxrs array
262 */ 252 */
263 offset = addr - (addr_t) &dummy->regs.fp_regs.fprs; 253 offset = addr - (addr_t) &dummy->regs.fp_regs.fprs;
264#ifdef CONFIG_64BIT
265 if (child->thread.vxrs) 254 if (child->thread.vxrs)
266 tmp = *(addr_t *) 255 tmp = *(addr_t *)
267 ((addr_t) child->thread.vxrs + 2*offset); 256 ((addr_t) child->thread.vxrs + 2*offset);
268 else 257 else
269#endif
270 tmp = *(addr_t *) 258 tmp = *(addr_t *)
271 ((addr_t) &child->thread.fp_regs.fprs + offset); 259 ((addr_t) &child->thread.fp_regs.fprs + offset);
272 260
@@ -293,11 +281,9 @@ peek_user(struct task_struct *child, addr_t addr, addr_t data)
293 * an alignment of 4. Programmers from hell... 281 * an alignment of 4. Programmers from hell...
294 */ 282 */
295 mask = __ADDR_MASK; 283 mask = __ADDR_MASK;
296#ifdef CONFIG_64BIT
297 if (addr >= (addr_t) &((struct user *) NULL)->regs.acrs && 284 if (addr >= (addr_t) &((struct user *) NULL)->regs.acrs &&
298 addr < (addr_t) &((struct user *) NULL)->regs.orig_gpr2) 285 addr < (addr_t) &((struct user *) NULL)->regs.orig_gpr2)
299 mask = 3; 286 mask = 3;
300#endif
301 if ((addr & mask) || addr > sizeof(struct user) - __ADDR_MASK) 287 if ((addr & mask) || addr > sizeof(struct user) - __ADDR_MASK)
302 return -EIO; 288 return -EIO;
303 289
@@ -370,7 +356,6 @@ static int __poke_user(struct task_struct *child, addr_t addr, addr_t data)
370 * access registers are stored in the thread structure 356 * access registers are stored in the thread structure
371 */ 357 */
372 offset = addr - (addr_t) &dummy->regs.acrs; 358 offset = addr - (addr_t) &dummy->regs.acrs;
373#ifdef CONFIG_64BIT
374 /* 359 /*
375 * Very special case: old & broken 64 bit gdb writing 360 * Very special case: old & broken 64 bit gdb writing
376 * to acrs[15] with a 64 bit value. Ignore the lower 361 * to acrs[15] with a 64 bit value. Ignore the lower
@@ -380,8 +365,7 @@ static int __poke_user(struct task_struct *child, addr_t addr, addr_t data)
380 if (addr == (addr_t) &dummy->regs.acrs[15]) 365 if (addr == (addr_t) &dummy->regs.acrs[15])
381 child->thread.acrs[15] = (unsigned int) (data >> 32); 366 child->thread.acrs[15] = (unsigned int) (data >> 32);
382 else 367 else
383#endif 368 *(addr_t *)((addr_t) &child->thread.acrs + offset) = data;
384 *(addr_t *)((addr_t) &child->thread.acrs + offset) = data;
385 369
386 } else if (addr == (addr_t) &dummy->regs.orig_gpr2) { 370 } else if (addr == (addr_t) &dummy->regs.orig_gpr2) {
387 /* 371 /*
@@ -411,12 +395,10 @@ static int __poke_user(struct task_struct *child, addr_t addr, addr_t data)
411 * or the child->thread.vxrs array 395 * or the child->thread.vxrs array
412 */ 396 */
413 offset = addr - (addr_t) &dummy->regs.fp_regs.fprs; 397 offset = addr - (addr_t) &dummy->regs.fp_regs.fprs;
414#ifdef CONFIG_64BIT
415 if (child->thread.vxrs) 398 if (child->thread.vxrs)
416 *(addr_t *)((addr_t) 399 *(addr_t *)((addr_t)
417 child->thread.vxrs + 2*offset) = data; 400 child->thread.vxrs + 2*offset) = data;
418 else 401 else
419#endif
420 *(addr_t *)((addr_t) 402 *(addr_t *)((addr_t)
421 &child->thread.fp_regs.fprs + offset) = data; 403 &child->thread.fp_regs.fprs + offset) = data;
422 404
@@ -441,11 +423,9 @@ static int poke_user(struct task_struct *child, addr_t addr, addr_t data)
441 * an alignment of 4. Programmers from hell indeed... 423 * an alignment of 4. Programmers from hell indeed...
442 */ 424 */
443 mask = __ADDR_MASK; 425 mask = __ADDR_MASK;
444#ifdef CONFIG_64BIT
445 if (addr >= (addr_t) &((struct user *) NULL)->regs.acrs && 426 if (addr >= (addr_t) &((struct user *) NULL)->regs.acrs &&
446 addr < (addr_t) &((struct user *) NULL)->regs.orig_gpr2) 427 addr < (addr_t) &((struct user *) NULL)->regs.orig_gpr2)
447 mask = 3; 428 mask = 3;
448#endif
449 if ((addr & mask) || addr > sizeof(struct user) - __ADDR_MASK) 429 if ((addr & mask) || addr > sizeof(struct user) - __ADDR_MASK)
450 return -EIO; 430 return -EIO;
451 431
@@ -649,12 +629,10 @@ static u32 __peek_user_compat(struct task_struct *child, addr_t addr)
649 * or the child->thread.vxrs array 629 * or the child->thread.vxrs array
650 */ 630 */
651 offset = addr - (addr_t) &dummy32->regs.fp_regs.fprs; 631 offset = addr - (addr_t) &dummy32->regs.fp_regs.fprs;
652#ifdef CONFIG_64BIT
653 if (child->thread.vxrs) 632 if (child->thread.vxrs)
654 tmp = *(__u32 *) 633 tmp = *(__u32 *)
655 ((addr_t) child->thread.vxrs + 2*offset); 634 ((addr_t) child->thread.vxrs + 2*offset);
656 else 635 else
657#endif
658 tmp = *(__u32 *) 636 tmp = *(__u32 *)
659 ((addr_t) &child->thread.fp_regs.fprs + offset); 637 ((addr_t) &child->thread.fp_regs.fprs + offset);
660 638
@@ -776,12 +754,10 @@ static int __poke_user_compat(struct task_struct *child,
776 * or the child->thread.vxrs array 754 * or the child->thread.vxrs array
777 */ 755 */
778 offset = addr - (addr_t) &dummy32->regs.fp_regs.fprs; 756 offset = addr - (addr_t) &dummy32->regs.fp_regs.fprs;
779#ifdef CONFIG_64BIT
780 if (child->thread.vxrs) 757 if (child->thread.vxrs)
781 *(__u32 *)((addr_t) 758 *(__u32 *)((addr_t)
782 child->thread.vxrs + 2*offset) = tmp; 759 child->thread.vxrs + 2*offset) = tmp;
783 else 760 else
784#endif
785 *(__u32 *)((addr_t) 761 *(__u32 *)((addr_t)
786 &child->thread.fp_regs.fprs + offset) = tmp; 762 &child->thread.fp_regs.fprs + offset) = tmp;
787 763
@@ -979,16 +955,13 @@ static int s390_fpregs_get(struct task_struct *target,
979 if (target == current) { 955 if (target == current) {
980 save_fp_ctl(&target->thread.fp_regs.fpc); 956 save_fp_ctl(&target->thread.fp_regs.fpc);
981 save_fp_regs(target->thread.fp_regs.fprs); 957 save_fp_regs(target->thread.fp_regs.fprs);
982 } 958 } else if (target->thread.vxrs) {
983#ifdef CONFIG_64BIT
984 else if (target->thread.vxrs) {
985 int i; 959 int i;
986 960
987 for (i = 0; i < __NUM_VXRS_LOW; i++) 961 for (i = 0; i < __NUM_VXRS_LOW; i++)
988 target->thread.fp_regs.fprs[i] = 962 target->thread.fp_regs.fprs[i] =
989 *(freg_t *)(target->thread.vxrs + i); 963 *(freg_t *)(target->thread.vxrs + i);
990 } 964 }
991#endif
992 return user_regset_copyout(&pos, &count, &kbuf, &ubuf, 965 return user_regset_copyout(&pos, &count, &kbuf, &ubuf,
993 &target->thread.fp_regs, 0, -1); 966 &target->thread.fp_regs, 0, -1);
994} 967}
@@ -1026,23 +999,18 @@ static int s390_fpregs_set(struct task_struct *target,
1026 if (target == current) { 999 if (target == current) {
1027 restore_fp_ctl(&target->thread.fp_regs.fpc); 1000 restore_fp_ctl(&target->thread.fp_regs.fpc);
1028 restore_fp_regs(target->thread.fp_regs.fprs); 1001 restore_fp_regs(target->thread.fp_regs.fprs);
1029 } 1002 } else if (target->thread.vxrs) {
1030#ifdef CONFIG_64BIT
1031 else if (target->thread.vxrs) {
1032 int i; 1003 int i;
1033 1004
1034 for (i = 0; i < __NUM_VXRS_LOW; i++) 1005 for (i = 0; i < __NUM_VXRS_LOW; i++)
1035 *(freg_t *)(target->thread.vxrs + i) = 1006 *(freg_t *)(target->thread.vxrs + i) =
1036 target->thread.fp_regs.fprs[i]; 1007 target->thread.fp_regs.fprs[i];
1037 } 1008 }
1038#endif
1039 } 1009 }
1040 1010
1041 return rc; 1011 return rc;
1042} 1012}
1043 1013
1044#ifdef CONFIG_64BIT
1045
1046static int s390_last_break_get(struct task_struct *target, 1014static int s390_last_break_get(struct task_struct *target,
1047 const struct user_regset *regset, 1015 const struct user_regset *regset,
1048 unsigned int pos, unsigned int count, 1016 unsigned int pos, unsigned int count,
@@ -1182,8 +1150,6 @@ static int s390_vxrs_high_set(struct task_struct *target,
1182 return rc; 1150 return rc;
1183} 1151}
1184 1152
1185#endif
1186
1187static int s390_system_call_get(struct task_struct *target, 1153static int s390_system_call_get(struct task_struct *target,
1188 const struct user_regset *regset, 1154 const struct user_regset *regset,
1189 unsigned int pos, unsigned int count, 1155 unsigned int pos, unsigned int count,
@@ -1229,7 +1195,6 @@ static const struct user_regset s390_regsets[] = {
1229 .get = s390_system_call_get, 1195 .get = s390_system_call_get,
1230 .set = s390_system_call_set, 1196 .set = s390_system_call_set,
1231 }, 1197 },
1232#ifdef CONFIG_64BIT
1233 { 1198 {
1234 .core_note_type = NT_S390_LAST_BREAK, 1199 .core_note_type = NT_S390_LAST_BREAK,
1235 .n = 1, 1200 .n = 1,
@@ -1262,7 +1227,6 @@ static const struct user_regset s390_regsets[] = {
1262 .get = s390_vxrs_high_get, 1227 .get = s390_vxrs_high_get,
1263 .set = s390_vxrs_high_set, 1228 .set = s390_vxrs_high_set,
1264 }, 1229 },
1265#endif
1266}; 1230};
1267 1231
1268static const struct user_regset_view user_s390_view = { 1232static const struct user_regset_view user_s390_view = {