1/* 2 * This file is subject to the terms and conditions of the GNU General Public 3 * License. See the file "COPYING" in the main directory of this archive 4 * for more details. 5 * 6 * Copyright (C) 1992 Ross Biro 7 * Copyright (C) Linus Torvalds 8 * Copyright (C) 1994, 95, 96, 97, 98, 2000 Ralf Baechle 9 * Copyright (C) 1996 David S. Miller 10 * Kevin D. Kissell, kevink@mips.com and Carsten Langgaard, carstenl@mips.com 11 * Copyright (C) 1999 MIPS Technologies, Inc. 12 * Copyright (C) 2000 Ulf Carlsson 13 * 14 * At this time Linux/MIPS64 only supports syscall tracing, even for 32-bit 15 * binaries. 16 */ 17#include <linux/compiler.h> 18#include <linux/context_tracking.h> 19#include <linux/elf.h> 20#include <linux/kernel.h> 21#include <linux/sched.h> 22#include <linux/mm.h> 23#include <linux/errno.h> 24#include <linux/ptrace.h> 25#include <linux/regset.h> 26#include <linux/smp.h> 27#include <linux/security.h> 28#include <linux/tracehook.h> 29#include <linux/audit.h> 30#include <linux/seccomp.h> 31#include <linux/ftrace.h> 32 33#include <asm/byteorder.h> 34#include <asm/cpu.h> 35#include <asm/cpu-info.h> 36#include <asm/dsp.h> 37#include <asm/fpu.h> 38#include <asm/mipsregs.h> 39#include <asm/mipsmtregs.h> 40#include <asm/pgtable.h> 41#include <asm/page.h> 42#include <asm/syscall.h> 43#include <asm/uaccess.h> 44#include <asm/bootinfo.h> 45#include <asm/reg.h> 46 47#define CREATE_TRACE_POINTS 48#include <trace/events/syscalls.h> 49 50static void init_fp_ctx(struct task_struct *target) 51{ 52 /* If FP has been used then the target already has context */ 53 if (tsk_used_math(target)) 54 return; 55 56 /* Begin with data registers set to all 1s... */ 57 memset(&target->thread.fpu.fpr, ~0, sizeof(target->thread.fpu.fpr)); 58 59 /* FCSR has been preset by `mips_set_personality_nan'. */ 60 61 /* 62 * Record that the target has "used" math, such that the context 63 * just initialised, and any modifications made by the caller, 64 * aren't discarded. 65 */ 66 set_stopped_child_used_math(target); 67} 68 69/* 70 * Called by kernel/ptrace.c when detaching.. 71 * 72 * Make sure single step bits etc are not set. 73 */ 74void ptrace_disable(struct task_struct *child) 75{ 76 /* Don't load the watchpoint registers for the ex-child. */ 77 clear_tsk_thread_flag(child, TIF_LOAD_WATCH); 78} 79 80/* 81 * Poke at FCSR according to its mask. Don't set the cause bits as 82 * this is currently not handled correctly in FP context restoration 83 * and will cause an oops if a corresponding enable bit is set. 84 */ 85static void ptrace_setfcr31(struct task_struct *child, u32 value) 86{ 87 u32 fcr31; 88 u32 mask; 89 90 value &= ~FPU_CSR_ALL_X; 91 fcr31 = child->thread.fpu.fcr31; 92 mask = boot_cpu_data.fpu_msk31; 93 child->thread.fpu.fcr31 = (value & ~mask) | (fcr31 & mask); 94} 95 96/* 97 * Read a general register set. We always use the 64-bit format, even 98 * for 32-bit kernels and for 32-bit processes on a 64-bit kernel. 99 * Registers are sign extended to fill the available space. 100 */ 101int ptrace_getregs(struct task_struct *child, struct user_pt_regs __user *data) 102{ 103 struct pt_regs *regs; 104 int i; 105 106 if (!access_ok(VERIFY_WRITE, data, 38 * 8)) 107 return -EIO; 108 109 regs = task_pt_regs(child); 110 111 for (i = 0; i < 32; i++) 112 __put_user((long)regs->regs[i], (__s64 __user *)&data->regs[i]); 113 __put_user((long)regs->lo, (__s64 __user *)&data->lo); 114 __put_user((long)regs->hi, (__s64 __user *)&data->hi); 115 __put_user((long)regs->cp0_epc, (__s64 __user *)&data->cp0_epc); 116 __put_user((long)regs->cp0_badvaddr, (__s64 __user *)&data->cp0_badvaddr); 117 __put_user((long)regs->cp0_status, (__s64 __user *)&data->cp0_status); 118 __put_user((long)regs->cp0_cause, (__s64 __user *)&data->cp0_cause); 119 120 return 0; 121} 122 123/* 124 * Write a general register set. As for PTRACE_GETREGS, we always use 125 * the 64-bit format. On a 32-bit kernel only the lower order half 126 * (according to endianness) will be used. 127 */ 128int ptrace_setregs(struct task_struct *child, struct user_pt_regs __user *data) 129{ 130 struct pt_regs *regs; 131 int i; 132 133 if (!access_ok(VERIFY_READ, data, 38 * 8)) 134 return -EIO; 135 136 regs = task_pt_regs(child); 137 138 for (i = 0; i < 32; i++) 139 __get_user(regs->regs[i], (__s64 __user *)&data->regs[i]); 140 __get_user(regs->lo, (__s64 __user *)&data->lo); 141 __get_user(regs->hi, (__s64 __user *)&data->hi); 142 __get_user(regs->cp0_epc, (__s64 __user *)&data->cp0_epc); 143 144 /* badvaddr, status, and cause may not be written. */ 145 146 return 0; 147} 148 149int ptrace_getfpregs(struct task_struct *child, __u32 __user *data) 150{ 151 int i; 152 153 if (!access_ok(VERIFY_WRITE, data, 33 * 8)) 154 return -EIO; 155 156 if (tsk_used_math(child)) { 157 union fpureg *fregs = get_fpu_regs(child); 158 for (i = 0; i < 32; i++) 159 __put_user(get_fpr64(&fregs[i], 0), 160 i + (__u64 __user *)data); 161 } else { 162 for (i = 0; i < 32; i++) 163 __put_user((__u64) -1, i + (__u64 __user *) data); 164 } 165 166 __put_user(child->thread.fpu.fcr31, data + 64); 167 __put_user(boot_cpu_data.fpu_id, data + 65); 168 169 return 0; 170} 171 172int ptrace_setfpregs(struct task_struct *child, __u32 __user *data) 173{ 174 union fpureg *fregs; 175 u64 fpr_val; 176 u32 value; 177 int i; 178 179 if (!access_ok(VERIFY_READ, data, 33 * 8)) 180 return -EIO; 181 182 init_fp_ctx(child); 183 fregs = get_fpu_regs(child); 184 185 for (i = 0; i < 32; i++) { 186 __get_user(fpr_val, i + (__u64 __user *)data); 187 set_fpr64(&fregs[i], 0, fpr_val); 188 } 189 190 __get_user(value, data + 64); 191 ptrace_setfcr31(child, value); 192 193 /* FIR may not be written. */ 194 195 return 0; 196} 197 198int ptrace_get_watch_regs(struct task_struct *child, 199 struct pt_watch_regs __user *addr) 200{ 201 enum pt_watch_style style; 202 int i; 203 204 if (!cpu_has_watch || boot_cpu_data.watch_reg_use_cnt == 0) 205 return -EIO; 206 if (!access_ok(VERIFY_WRITE, addr, sizeof(struct pt_watch_regs))) 207 return -EIO; 208 209#ifdef CONFIG_32BIT 210 style = pt_watch_style_mips32; 211#define WATCH_STYLE mips32 212#else 213 style = pt_watch_style_mips64; 214#define WATCH_STYLE mips64 215#endif 216 217 __put_user(style, &addr->style); 218 __put_user(boot_cpu_data.watch_reg_use_cnt, 219 &addr->WATCH_STYLE.num_valid); 220 for (i = 0; i < boot_cpu_data.watch_reg_use_cnt; i++) { 221 __put_user(child->thread.watch.mips3264.watchlo[i], 222 &addr->WATCH_STYLE.watchlo[i]); 223 __put_user(child->thread.watch.mips3264.watchhi[i] & 0xfff, 224 &addr->WATCH_STYLE.watchhi[i]); 225 __put_user(boot_cpu_data.watch_reg_masks[i], 226 &addr->WATCH_STYLE.watch_masks[i]); 227 } 228 for (; i < 8; i++) { 229 __put_user(0, &addr->WATCH_STYLE.watchlo[i]); 230 __put_user(0, &addr->WATCH_STYLE.watchhi[i]); 231 __put_user(0, &addr->WATCH_STYLE.watch_masks[i]); 232 } 233 234 return 0; 235} 236 237int ptrace_set_watch_regs(struct task_struct *child, 238 struct pt_watch_regs __user *addr) 239{ 240 int i; 241 int watch_active = 0; 242 unsigned long lt[NUM_WATCH_REGS]; 243 u16 ht[NUM_WATCH_REGS]; 244 245 if (!cpu_has_watch || boot_cpu_data.watch_reg_use_cnt == 0) 246 return -EIO; 247 if (!access_ok(VERIFY_READ, addr, sizeof(struct pt_watch_regs))) 248 return -EIO; 249 /* Check the values. */ 250 for (i = 0; i < boot_cpu_data.watch_reg_use_cnt; i++) { 251 __get_user(lt[i], &addr->WATCH_STYLE.watchlo[i]); 252#ifdef CONFIG_32BIT 253 if (lt[i] & __UA_LIMIT) 254 return -EINVAL; 255#else 256 if (test_tsk_thread_flag(child, TIF_32BIT_ADDR)) { 257 if (lt[i] & 0xffffffff80000000UL) 258 return -EINVAL; 259 } else { 260 if (lt[i] & __UA_LIMIT) 261 return -EINVAL; 262 } 263#endif 264 __get_user(ht[i], &addr->WATCH_STYLE.watchhi[i]); 265 if (ht[i] & ~0xff8) 266 return -EINVAL; 267 } 268 /* Install them. */ 269 for (i = 0; i < boot_cpu_data.watch_reg_use_cnt; i++) { 270 if (lt[i] & 7) 271 watch_active = 1; 272 child->thread.watch.mips3264.watchlo[i] = lt[i]; 273 /* Set the G bit. */ 274 child->thread.watch.mips3264.watchhi[i] = ht[i]; 275 } 276 277 if (watch_active) 278 set_tsk_thread_flag(child, TIF_LOAD_WATCH); 279 else 280 clear_tsk_thread_flag(child, TIF_LOAD_WATCH); 281 282 return 0; 283} 284 285/* regset get/set implementations */ 286 287#if defined(CONFIG_32BIT) || defined(CONFIG_MIPS32_O32) 288 289static int gpr32_get(struct task_struct *target, 290 const struct user_regset *regset, 291 unsigned int pos, unsigned int count, 292 void *kbuf, void __user *ubuf) 293{ 294 struct pt_regs *regs = task_pt_regs(target); 295 u32 uregs[ELF_NGREG] = {}; 296 unsigned i; 297 298 for (i = MIPS32_EF_R1; i <= MIPS32_EF_R31; i++) { 299 /* k0/k1 are copied as zero. */ 300 if (i == MIPS32_EF_R26 || i == MIPS32_EF_R27) 301 continue; 302 303 uregs[i] = regs->regs[i - MIPS32_EF_R0]; 304 } 305 306 uregs[MIPS32_EF_LO] = regs->lo; 307 uregs[MIPS32_EF_HI] = regs->hi; 308 uregs[MIPS32_EF_CP0_EPC] = regs->cp0_epc; 309 uregs[MIPS32_EF_CP0_BADVADDR] = regs->cp0_badvaddr; 310 uregs[MIPS32_EF_CP0_STATUS] = regs->cp0_status; 311 uregs[MIPS32_EF_CP0_CAUSE] = regs->cp0_cause; 312 313 return user_regset_copyout(&pos, &count, &kbuf, &ubuf, uregs, 0, 314 sizeof(uregs)); 315} 316 317static int gpr32_set(struct task_struct *target, 318 const struct user_regset *regset, 319 unsigned int pos, unsigned int count, 320 const void *kbuf, const void __user *ubuf) 321{ 322 struct pt_regs *regs = task_pt_regs(target); 323 u32 uregs[ELF_NGREG]; 324 unsigned start, num_regs, i; 325 int err; 326 327 start = pos / sizeof(u32); 328 num_regs = count / sizeof(u32); 329 330 if (start + num_regs > ELF_NGREG) 331 return -EIO; 332 333 err = user_regset_copyin(&pos, &count, &kbuf, &ubuf, uregs, 0, 334 sizeof(uregs)); 335 if (err) 336 return err; 337 338 for (i = start; i < num_regs; i++) { 339 /* 340 * Cast all values to signed here so that if this is a 64-bit 341 * kernel, the supplied 32-bit values will be sign extended. 342 */ 343 switch (i) { 344 case MIPS32_EF_R1 ... MIPS32_EF_R25: 345 /* k0/k1 are ignored. */ 346 case MIPS32_EF_R28 ... MIPS32_EF_R31: 347 regs->regs[i - MIPS32_EF_R0] = (s32)uregs[i]; 348 break; 349 case MIPS32_EF_LO: 350 regs->lo = (s32)uregs[i]; 351 break; 352 case MIPS32_EF_HI: 353 regs->hi = (s32)uregs[i]; 354 break; 355 case MIPS32_EF_CP0_EPC: 356 regs->cp0_epc = (s32)uregs[i]; 357 break; 358 } 359 } 360 361 return 0; 362} 363 364#endif /* CONFIG_32BIT || CONFIG_MIPS32_O32 */ 365 366#ifdef CONFIG_64BIT 367 368static int gpr64_get(struct task_struct *target, 369 const struct user_regset *regset, 370 unsigned int pos, unsigned int count, 371 void *kbuf, void __user *ubuf) 372{ 373 struct pt_regs *regs = task_pt_regs(target); 374 u64 uregs[ELF_NGREG] = {}; 375 unsigned i; 376 377 for (i = MIPS64_EF_R1; i <= MIPS64_EF_R31; i++) { 378 /* k0/k1 are copied as zero. */ 379 if (i == MIPS64_EF_R26 || i == MIPS64_EF_R27) 380 continue; 381 382 uregs[i] = regs->regs[i - MIPS64_EF_R0]; 383 } 384 385 uregs[MIPS64_EF_LO] = regs->lo; 386 uregs[MIPS64_EF_HI] = regs->hi; 387 uregs[MIPS64_EF_CP0_EPC] = regs->cp0_epc; 388 uregs[MIPS64_EF_CP0_BADVADDR] = regs->cp0_badvaddr; 389 uregs[MIPS64_EF_CP0_STATUS] = regs->cp0_status; 390 uregs[MIPS64_EF_CP0_CAUSE] = regs->cp0_cause; 391 392 return user_regset_copyout(&pos, &count, &kbuf, &ubuf, uregs, 0, 393 sizeof(uregs)); 394} 395 396static int gpr64_set(struct task_struct *target, 397 const struct user_regset *regset, 398 unsigned int pos, unsigned int count, 399 const void *kbuf, const void __user *ubuf) 400{ 401 struct pt_regs *regs = task_pt_regs(target); 402 u64 uregs[ELF_NGREG]; 403 unsigned start, num_regs, i; 404 int err; 405 406 start = pos / sizeof(u64); 407 num_regs = count / sizeof(u64); 408 409 if (start + num_regs > ELF_NGREG) 410 return -EIO; 411 412 err = user_regset_copyin(&pos, &count, &kbuf, &ubuf, uregs, 0, 413 sizeof(uregs)); 414 if (err) 415 return err; 416 417 for (i = start; i < num_regs; i++) { 418 switch (i) { 419 case MIPS64_EF_R1 ... MIPS64_EF_R25: 420 /* k0/k1 are ignored. */ 421 case MIPS64_EF_R28 ... MIPS64_EF_R31: 422 regs->regs[i - MIPS64_EF_R0] = uregs[i]; 423 break; 424 case MIPS64_EF_LO: 425 regs->lo = uregs[i]; 426 break; 427 case MIPS64_EF_HI: 428 regs->hi = uregs[i]; 429 break; 430 case MIPS64_EF_CP0_EPC: 431 regs->cp0_epc = uregs[i]; 432 break; 433 } 434 } 435 436 return 0; 437} 438 439#endif /* CONFIG_64BIT */ 440 441static int fpr_get(struct task_struct *target, 442 const struct user_regset *regset, 443 unsigned int pos, unsigned int count, 444 void *kbuf, void __user *ubuf) 445{ 446 unsigned i; 447 int err; 448 u64 fpr_val; 449 450 /* XXX fcr31 */ 451 452 if (sizeof(target->thread.fpu.fpr[i]) == sizeof(elf_fpreg_t)) 453 return user_regset_copyout(&pos, &count, &kbuf, &ubuf, 454 &target->thread.fpu, 455 0, sizeof(elf_fpregset_t)); 456 457 for (i = 0; i < NUM_FPU_REGS; i++) { 458 fpr_val = get_fpr64(&target->thread.fpu.fpr[i], 0); 459 err = user_regset_copyout(&pos, &count, &kbuf, &ubuf, 460 &fpr_val, i * sizeof(elf_fpreg_t), 461 (i + 1) * sizeof(elf_fpreg_t)); 462 if (err) 463 return err; 464 } 465 466 return 0; 467} 468 469static int fpr_set(struct task_struct *target, 470 const struct user_regset *regset, 471 unsigned int pos, unsigned int count, 472 const void *kbuf, const void __user *ubuf) 473{ 474 unsigned i; 475 int err; 476 u64 fpr_val; 477 478 /* XXX fcr31 */ 479 480 init_fp_ctx(target); 481 482 if (sizeof(target->thread.fpu.fpr[i]) == sizeof(elf_fpreg_t)) 483 return user_regset_copyin(&pos, &count, &kbuf, &ubuf, 484 &target->thread.fpu, 485 0, sizeof(elf_fpregset_t)); 486 487 for (i = 0; i < NUM_FPU_REGS; i++) { 488 err = user_regset_copyin(&pos, &count, &kbuf, &ubuf, 489 &fpr_val, i * sizeof(elf_fpreg_t), 490 (i + 1) * sizeof(elf_fpreg_t)); 491 if (err) 492 return err; 493 set_fpr64(&target->thread.fpu.fpr[i], 0, fpr_val); 494 } 495 496 return 0; 497} 498 499enum mips_regset { 500 REGSET_GPR, 501 REGSET_FPR, 502}; 503 504#if defined(CONFIG_32BIT) || defined(CONFIG_MIPS32_O32) 505 506static const struct user_regset mips_regsets[] = { 507 [REGSET_GPR] = { 508 .core_note_type = NT_PRSTATUS, 509 .n = ELF_NGREG, 510 .size = sizeof(unsigned int), 511 .align = sizeof(unsigned int), 512 .get = gpr32_get, 513 .set = gpr32_set, 514 }, 515 [REGSET_FPR] = { 516 .core_note_type = NT_PRFPREG, 517 .n = ELF_NFPREG, 518 .size = sizeof(elf_fpreg_t), 519 .align = sizeof(elf_fpreg_t), 520 .get = fpr_get, 521 .set = fpr_set, 522 }, 523}; 524 525static const struct user_regset_view user_mips_view = { 526 .name = "mips", 527 .e_machine = ELF_ARCH, 528 .ei_osabi = ELF_OSABI, 529 .regsets = mips_regsets, 530 .n = ARRAY_SIZE(mips_regsets), 531}; 532 533#endif /* CONFIG_32BIT || CONFIG_MIPS32_O32 */ 534 535#ifdef CONFIG_64BIT 536 537static const struct user_regset mips64_regsets[] = { 538 [REGSET_GPR] = { 539 .core_note_type = NT_PRSTATUS, 540 .n = ELF_NGREG, 541 .size = sizeof(unsigned long), 542 .align = sizeof(unsigned long), 543 .get = gpr64_get, 544 .set = gpr64_set, 545 }, 546 [REGSET_FPR] = { 547 .core_note_type = NT_PRFPREG, 548 .n = ELF_NFPREG, 549 .size = sizeof(elf_fpreg_t), 550 .align = sizeof(elf_fpreg_t), 551 .get = fpr_get, 552 .set = fpr_set, 553 }, 554}; 555 556static const struct user_regset_view user_mips64_view = { 557 .name = "mips64", 558 .e_machine = ELF_ARCH, 559 .ei_osabi = ELF_OSABI, 560 .regsets = mips64_regsets, 561 .n = ARRAY_SIZE(mips64_regsets), 562}; 563 564#endif /* CONFIG_64BIT */ 565 566const struct user_regset_view *task_user_regset_view(struct task_struct *task) 567{ 568#ifdef CONFIG_32BIT 569 return &user_mips_view; 570#else 571#ifdef CONFIG_MIPS32_O32 572 if (test_tsk_thread_flag(task, TIF_32BIT_REGS)) 573 return &user_mips_view; 574#endif 575 return &user_mips64_view; 576#endif 577} 578 579long arch_ptrace(struct task_struct *child, long request, 580 unsigned long addr, unsigned long data) 581{ 582 int ret; 583 void __user *addrp = (void __user *) addr; 584 void __user *datavp = (void __user *) data; 585 unsigned long __user *datalp = (void __user *) data; 586 587 switch (request) { 588 /* when I and D space are separate, these will need to be fixed. */ 589 case PTRACE_PEEKTEXT: /* read word at location addr. */ 590 case PTRACE_PEEKDATA: 591 ret = generic_ptrace_peekdata(child, addr, data); 592 break; 593 594 /* Read the word at location addr in the USER area. */ 595 case PTRACE_PEEKUSR: { 596 struct pt_regs *regs; 597 union fpureg *fregs; 598 unsigned long tmp = 0; 599 600 regs = task_pt_regs(child); 601 ret = 0; /* Default return value. */ 602 603 switch (addr) { 604 case 0 ... 31: 605 tmp = regs->regs[addr]; 606 break; 607 case FPR_BASE ... FPR_BASE + 31: 608 if (!tsk_used_math(child)) { 609 /* FP not yet used */ 610 tmp = -1; 611 break; 612 } 613 fregs = get_fpu_regs(child); 614 615#ifdef CONFIG_32BIT 616 if (test_thread_flag(TIF_32BIT_FPREGS)) { 617 /* 618 * The odd registers are actually the high 619 * order bits of the values stored in the even 620 * registers - unless we're using r2k_switch.S. 621 */ 622 tmp = get_fpr32(&fregs[(addr & ~1) - FPR_BASE], 623 addr & 1); 624 break; 625 } 626#endif 627 tmp = get_fpr32(&fregs[addr - FPR_BASE], 0); 628 break; 629 case PC: 630 tmp = regs->cp0_epc; 631 break; 632 case CAUSE: 633 tmp = regs->cp0_cause; 634 break; 635 case BADVADDR: 636 tmp = regs->cp0_badvaddr; 637 break; 638 case MMHI: 639 tmp = regs->hi; 640 break; 641 case MMLO: 642 tmp = regs->lo; 643 break; 644#ifdef CONFIG_CPU_HAS_SMARTMIPS 645 case ACX: 646 tmp = regs->acx; 647 break; 648#endif 649 case FPC_CSR: 650 tmp = child->thread.fpu.fcr31; 651 break; 652 case FPC_EIR: 653 /* implementation / version register */ 654 tmp = boot_cpu_data.fpu_id; 655 break; 656 case DSP_BASE ... DSP_BASE + 5: { 657 dspreg_t *dregs; 658 659 if (!cpu_has_dsp) { 660 tmp = 0; 661 ret = -EIO; 662 goto out; 663 } 664 dregs = __get_dsp_regs(child); 665 tmp = (unsigned long) (dregs[addr - DSP_BASE]); 666 break; 667 } 668 case DSP_CONTROL: 669 if (!cpu_has_dsp) { 670 tmp = 0; 671 ret = -EIO; 672 goto out; 673 } 674 tmp = child->thread.dsp.dspcontrol; 675 break; 676 default: 677 tmp = 0; 678 ret = -EIO; 679 goto out; 680 } 681 ret = put_user(tmp, datalp); 682 break; 683 } 684 685 /* when I and D space are separate, this will have to be fixed. */ 686 case PTRACE_POKETEXT: /* write the word at location addr. */ 687 case PTRACE_POKEDATA: 688 ret = generic_ptrace_pokedata(child, addr, data); 689 break; 690 691 case PTRACE_POKEUSR: { 692 struct pt_regs *regs; 693 ret = 0; 694 regs = task_pt_regs(child); 695 696 switch (addr) { 697 case 0 ... 31: 698 regs->regs[addr] = data; 699 break; 700 case FPR_BASE ... FPR_BASE + 31: { 701 union fpureg *fregs = get_fpu_regs(child); 702 703 init_fp_ctx(child); 704#ifdef CONFIG_32BIT 705 if (test_thread_flag(TIF_32BIT_FPREGS)) { 706 /* 707 * The odd registers are actually the high 708 * order bits of the values stored in the even 709 * registers - unless we're using r2k_switch.S. 710 */ 711 set_fpr32(&fregs[(addr & ~1) - FPR_BASE], 712 addr & 1, data); 713 break; 714 } 715#endif 716 set_fpr64(&fregs[addr - FPR_BASE], 0, data); 717 break; 718 } 719 case PC: 720 regs->cp0_epc = data; 721 break; 722 case MMHI: 723 regs->hi = data; 724 break; 725 case MMLO: 726 regs->lo = data; 727 break; 728#ifdef CONFIG_CPU_HAS_SMARTMIPS 729 case ACX: 730 regs->acx = data; 731 break; 732#endif 733 case FPC_CSR: 734 ptrace_setfcr31(child, data); 735 break; 736 case DSP_BASE ... DSP_BASE + 5: { 737 dspreg_t *dregs; 738 739 if (!cpu_has_dsp) { 740 ret = -EIO; 741 break; 742 } 743 744 dregs = __get_dsp_regs(child); 745 dregs[addr - DSP_BASE] = data; 746 break; 747 } 748 case DSP_CONTROL: 749 if (!cpu_has_dsp) { 750 ret = -EIO; 751 break; 752 } 753 child->thread.dsp.dspcontrol = data; 754 break; 755 default: 756 /* The rest are not allowed. */ 757 ret = -EIO; 758 break; 759 } 760 break; 761 } 762 763 case PTRACE_GETREGS: 764 ret = ptrace_getregs(child, datavp); 765 break; 766 767 case PTRACE_SETREGS: 768 ret = ptrace_setregs(child, datavp); 769 break; 770 771 case PTRACE_GETFPREGS: 772 ret = ptrace_getfpregs(child, datavp); 773 break; 774 775 case PTRACE_SETFPREGS: 776 ret = ptrace_setfpregs(child, datavp); 777 break; 778 779 case PTRACE_GET_THREAD_AREA: 780 ret = put_user(task_thread_info(child)->tp_value, datalp); 781 break; 782 783 case PTRACE_GET_WATCH_REGS: 784 ret = ptrace_get_watch_regs(child, addrp); 785 break; 786 787 case PTRACE_SET_WATCH_REGS: 788 ret = ptrace_set_watch_regs(child, addrp); 789 break; 790 791 default: 792 ret = ptrace_request(child, request, addr, data); 793 break; 794 } 795 out: 796 return ret; 797} 798 799/* 800 * Notification of system call entry/exit 801 * - triggered by current->work.syscall_trace 802 */ 803asmlinkage long syscall_trace_enter(struct pt_regs *regs, long syscall) 804{ 805 long ret = 0; 806 user_exit(); 807 808 current_thread_info()->syscall = syscall; 809 810 if (secure_computing() == -1) 811 return -1; 812 813 if (test_thread_flag(TIF_SYSCALL_TRACE) && 814 tracehook_report_syscall_entry(regs)) 815 ret = -1; 816 817 if (unlikely(test_thread_flag(TIF_SYSCALL_TRACEPOINT))) 818 trace_sys_enter(regs, regs->regs[2]); 819 820 audit_syscall_entry(syscall, regs->regs[4], regs->regs[5], 821 regs->regs[6], regs->regs[7]); 822 return syscall; 823} 824 825/* 826 * Notification of system call entry/exit 827 * - triggered by current->work.syscall_trace 828 */ 829asmlinkage void syscall_trace_leave(struct pt_regs *regs) 830{ 831 /* 832 * We may come here right after calling schedule_user() 833 * or do_notify_resume(), in which case we can be in RCU 834 * user mode. 835 */ 836 user_exit(); 837 838 audit_syscall_exit(regs); 839 840 if (unlikely(test_thread_flag(TIF_SYSCALL_TRACEPOINT))) 841 trace_sys_exit(regs, regs->regs[2]); 842 843 if (test_thread_flag(TIF_SYSCALL_TRACE)) 844 tracehook_report_syscall_exit(regs, 0); 845 846 user_enter(); 847} 848