ptrace.c 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587
  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) 2001 - 2007 Tensilica Inc.
  7. *
  8. * Joe Taylor <joe@tensilica.com, joetylr@yahoo.com>
  9. * Chris Zankel <chris@zankel.net>
  10. * Scott Foehner<sfoehner@yahoo.com>,
  11. * Kevin Chea
  12. * Marc Gauthier<marc@tensilica.com> <marc@alumni.uwaterloo.ca>
  13. */
  14. #include <linux/audit.h>
  15. #include <linux/errno.h>
  16. #include <linux/hw_breakpoint.h>
  17. #include <linux/kernel.h>
  18. #include <linux/mm.h>
  19. #include <linux/perf_event.h>
  20. #include <linux/ptrace.h>
  21. #include <linux/regset.h>
  22. #include <linux/sched.h>
  23. #include <linux/sched/task_stack.h>
  24. #include <linux/seccomp.h>
  25. #include <linux/security.h>
  26. #include <linux/signal.h>
  27. #include <linux/smp.h>
  28. #include <linux/tracehook.h>
  29. #include <linux/uaccess.h>
  30. #define CREATE_TRACE_POINTS
  31. #include <trace/events/syscalls.h>
  32. #include <asm/coprocessor.h>
  33. #include <asm/elf.h>
  34. #include <asm/page.h>
  35. #include <asm/ptrace.h>
  36. static int gpr_get(struct task_struct *target,
  37. const struct user_regset *regset,
  38. struct membuf to)
  39. {
  40. struct pt_regs *regs = task_pt_regs(target);
  41. struct user_pt_regs newregs = {
  42. .pc = regs->pc,
  43. .ps = regs->ps & ~(1 << PS_EXCM_BIT),
  44. .lbeg = regs->lbeg,
  45. .lend = regs->lend,
  46. .lcount = regs->lcount,
  47. .sar = regs->sar,
  48. .threadptr = regs->threadptr,
  49. .windowbase = regs->windowbase,
  50. .windowstart = regs->windowstart,
  51. .syscall = regs->syscall,
  52. };
  53. memcpy(newregs.a,
  54. regs->areg + XCHAL_NUM_AREGS - regs->windowbase * 4,
  55. regs->windowbase * 16);
  56. memcpy(newregs.a + regs->windowbase * 4,
  57. regs->areg,
  58. (WSBITS - regs->windowbase) * 16);
  59. return membuf_write(&to, &newregs, sizeof(newregs));
  60. }
  61. static int gpr_set(struct task_struct *target,
  62. const struct user_regset *regset,
  63. unsigned int pos, unsigned int count,
  64. const void *kbuf, const void __user *ubuf)
  65. {
  66. int ret;
  67. struct user_pt_regs newregs = {0};
  68. struct pt_regs *regs;
  69. const u32 ps_mask = PS_CALLINC_MASK | PS_OWB_MASK;
  70. ret = user_regset_copyin(&pos, &count, &kbuf, &ubuf, &newregs, 0, -1);
  71. if (ret)
  72. return ret;
  73. if (newregs.windowbase >= XCHAL_NUM_AREGS / 4)
  74. return -EINVAL;
  75. regs = task_pt_regs(target);
  76. regs->pc = newregs.pc;
  77. regs->ps = (regs->ps & ~ps_mask) | (newregs.ps & ps_mask);
  78. regs->lbeg = newregs.lbeg;
  79. regs->lend = newregs.lend;
  80. regs->lcount = newregs.lcount;
  81. regs->sar = newregs.sar;
  82. regs->threadptr = newregs.threadptr;
  83. if (newregs.syscall)
  84. regs->syscall = newregs.syscall;
  85. if (newregs.windowbase != regs->windowbase ||
  86. newregs.windowstart != regs->windowstart) {
  87. u32 rotws, wmask;
  88. rotws = (((newregs.windowstart |
  89. (newregs.windowstart << WSBITS)) >>
  90. newregs.windowbase) &
  91. ((1 << WSBITS) - 1)) & ~1;
  92. wmask = ((rotws ? WSBITS + 1 - ffs(rotws) : 0) << 4) |
  93. (rotws & 0xF) | 1;
  94. regs->windowbase = newregs.windowbase;
  95. regs->windowstart = newregs.windowstart;
  96. regs->wmask = wmask;
  97. }
  98. memcpy(regs->areg + XCHAL_NUM_AREGS - newregs.windowbase * 4,
  99. newregs.a, newregs.windowbase * 16);
  100. memcpy(regs->areg, newregs.a + newregs.windowbase * 4,
  101. (WSBITS - newregs.windowbase) * 16);
  102. return 0;
  103. }
  104. static int tie_get(struct task_struct *target,
  105. const struct user_regset *regset,
  106. struct membuf to)
  107. {
  108. int ret;
  109. struct pt_regs *regs = task_pt_regs(target);
  110. struct thread_info *ti = task_thread_info(target);
  111. elf_xtregs_t *newregs = kzalloc(sizeof(elf_xtregs_t), GFP_KERNEL);
  112. if (!newregs)
  113. return -ENOMEM;
  114. newregs->opt = regs->xtregs_opt;
  115. newregs->user = ti->xtregs_user;
  116. #if XTENSA_HAVE_COPROCESSORS
  117. /* Flush all coprocessor registers to memory. */
  118. coprocessor_flush_all(ti);
  119. newregs->cp0 = ti->xtregs_cp.cp0;
  120. newregs->cp1 = ti->xtregs_cp.cp1;
  121. newregs->cp2 = ti->xtregs_cp.cp2;
  122. newregs->cp3 = ti->xtregs_cp.cp3;
  123. newregs->cp4 = ti->xtregs_cp.cp4;
  124. newregs->cp5 = ti->xtregs_cp.cp5;
  125. newregs->cp6 = ti->xtregs_cp.cp6;
  126. newregs->cp7 = ti->xtregs_cp.cp7;
  127. #endif
  128. ret = membuf_write(&to, newregs, sizeof(*newregs));
  129. kfree(newregs);
  130. return ret;
  131. }
  132. static int tie_set(struct task_struct *target,
  133. const struct user_regset *regset,
  134. unsigned int pos, unsigned int count,
  135. const void *kbuf, const void __user *ubuf)
  136. {
  137. int ret;
  138. struct pt_regs *regs = task_pt_regs(target);
  139. struct thread_info *ti = task_thread_info(target);
  140. elf_xtregs_t *newregs = kzalloc(sizeof(elf_xtregs_t), GFP_KERNEL);
  141. if (!newregs)
  142. return -ENOMEM;
  143. ret = user_regset_copyin(&pos, &count, &kbuf, &ubuf,
  144. newregs, 0, -1);
  145. if (ret)
  146. goto exit;
  147. regs->xtregs_opt = newregs->opt;
  148. ti->xtregs_user = newregs->user;
  149. #if XTENSA_HAVE_COPROCESSORS
  150. /* Flush all coprocessors before we overwrite them. */
  151. coprocessor_flush_all(ti);
  152. coprocessor_release_all(ti);
  153. ti->xtregs_cp.cp0 = newregs->cp0;
  154. ti->xtregs_cp.cp1 = newregs->cp1;
  155. ti->xtregs_cp.cp2 = newregs->cp2;
  156. ti->xtregs_cp.cp3 = newregs->cp3;
  157. ti->xtregs_cp.cp4 = newregs->cp4;
  158. ti->xtregs_cp.cp5 = newregs->cp5;
  159. ti->xtregs_cp.cp6 = newregs->cp6;
  160. ti->xtregs_cp.cp7 = newregs->cp7;
  161. #endif
  162. exit:
  163. kfree(newregs);
  164. return ret;
  165. }
  166. enum xtensa_regset {
  167. REGSET_GPR,
  168. REGSET_TIE,
  169. };
  170. static const struct user_regset xtensa_regsets[] = {
  171. [REGSET_GPR] = {
  172. .core_note_type = NT_PRSTATUS,
  173. .n = sizeof(struct user_pt_regs) / sizeof(u32),
  174. .size = sizeof(u32),
  175. .align = sizeof(u32),
  176. .regset_get = gpr_get,
  177. .set = gpr_set,
  178. },
  179. [REGSET_TIE] = {
  180. .core_note_type = NT_PRFPREG,
  181. .n = sizeof(elf_xtregs_t) / sizeof(u32),
  182. .size = sizeof(u32),
  183. .align = sizeof(u32),
  184. .regset_get = tie_get,
  185. .set = tie_set,
  186. },
  187. };
  188. static const struct user_regset_view user_xtensa_view = {
  189. .name = "xtensa",
  190. .e_machine = EM_XTENSA,
  191. .regsets = xtensa_regsets,
  192. .n = ARRAY_SIZE(xtensa_regsets)
  193. };
  194. const struct user_regset_view *task_user_regset_view(struct task_struct *task)
  195. {
  196. return &user_xtensa_view;
  197. }
  198. void user_enable_single_step(struct task_struct *child)
  199. {
  200. child->ptrace |= PT_SINGLESTEP;
  201. }
  202. void user_disable_single_step(struct task_struct *child)
  203. {
  204. child->ptrace &= ~PT_SINGLESTEP;
  205. }
  206. /*
  207. * Called by kernel/ptrace.c when detaching to disable single stepping.
  208. */
  209. void ptrace_disable(struct task_struct *child)
  210. {
  211. /* Nothing to do.. */
  212. }
  213. static int ptrace_getregs(struct task_struct *child, void __user *uregs)
  214. {
  215. return copy_regset_to_user(child, &user_xtensa_view, REGSET_GPR,
  216. 0, sizeof(xtensa_gregset_t), uregs);
  217. }
  218. static int ptrace_setregs(struct task_struct *child, void __user *uregs)
  219. {
  220. return copy_regset_from_user(child, &user_xtensa_view, REGSET_GPR,
  221. 0, sizeof(xtensa_gregset_t), uregs);
  222. }
  223. static int ptrace_getxregs(struct task_struct *child, void __user *uregs)
  224. {
  225. return copy_regset_to_user(child, &user_xtensa_view, REGSET_TIE,
  226. 0, sizeof(elf_xtregs_t), uregs);
  227. }
  228. static int ptrace_setxregs(struct task_struct *child, void __user *uregs)
  229. {
  230. return copy_regset_from_user(child, &user_xtensa_view, REGSET_TIE,
  231. 0, sizeof(elf_xtregs_t), uregs);
  232. }
  233. static int ptrace_peekusr(struct task_struct *child, long regno,
  234. long __user *ret)
  235. {
  236. struct pt_regs *regs;
  237. unsigned long tmp;
  238. regs = task_pt_regs(child);
  239. tmp = 0; /* Default return value. */
  240. switch(regno) {
  241. case REG_AR_BASE ... REG_AR_BASE + XCHAL_NUM_AREGS - 1:
  242. tmp = regs->areg[regno - REG_AR_BASE];
  243. break;
  244. case REG_A_BASE ... REG_A_BASE + 15:
  245. tmp = regs->areg[regno - REG_A_BASE];
  246. break;
  247. case REG_PC:
  248. tmp = regs->pc;
  249. break;
  250. case REG_PS:
  251. /* Note: PS.EXCM is not set while user task is running;
  252. * its being set in regs is for exception handling
  253. * convenience.
  254. */
  255. tmp = (regs->ps & ~(1 << PS_EXCM_BIT));
  256. break;
  257. case REG_WB:
  258. break; /* tmp = 0 */
  259. case REG_WS:
  260. {
  261. unsigned long wb = regs->windowbase;
  262. unsigned long ws = regs->windowstart;
  263. tmp = ((ws >> wb) | (ws << (WSBITS - wb))) &
  264. ((1 << WSBITS) - 1);
  265. break;
  266. }
  267. case REG_LBEG:
  268. tmp = regs->lbeg;
  269. break;
  270. case REG_LEND:
  271. tmp = regs->lend;
  272. break;
  273. case REG_LCOUNT:
  274. tmp = regs->lcount;
  275. break;
  276. case REG_SAR:
  277. tmp = regs->sar;
  278. break;
  279. case SYSCALL_NR:
  280. tmp = regs->syscall;
  281. break;
  282. default:
  283. return -EIO;
  284. }
  285. return put_user(tmp, ret);
  286. }
  287. static int ptrace_pokeusr(struct task_struct *child, long regno, long val)
  288. {
  289. struct pt_regs *regs;
  290. regs = task_pt_regs(child);
  291. switch (regno) {
  292. case REG_AR_BASE ... REG_AR_BASE + XCHAL_NUM_AREGS - 1:
  293. regs->areg[regno - REG_AR_BASE] = val;
  294. break;
  295. case REG_A_BASE ... REG_A_BASE + 15:
  296. regs->areg[regno - REG_A_BASE] = val;
  297. break;
  298. case REG_PC:
  299. regs->pc = val;
  300. break;
  301. case SYSCALL_NR:
  302. regs->syscall = val;
  303. break;
  304. default:
  305. return -EIO;
  306. }
  307. return 0;
  308. }
  309. #ifdef CONFIG_HAVE_HW_BREAKPOINT
  310. static void ptrace_hbptriggered(struct perf_event *bp,
  311. struct perf_sample_data *data,
  312. struct pt_regs *regs)
  313. {
  314. int i;
  315. struct arch_hw_breakpoint *bkpt = counter_arch_bp(bp);
  316. if (bp->attr.bp_type & HW_BREAKPOINT_X) {
  317. for (i = 0; i < XCHAL_NUM_IBREAK; ++i)
  318. if (current->thread.ptrace_bp[i] == bp)
  319. break;
  320. i <<= 1;
  321. } else {
  322. for (i = 0; i < XCHAL_NUM_DBREAK; ++i)
  323. if (current->thread.ptrace_wp[i] == bp)
  324. break;
  325. i = (i << 1) | 1;
  326. }
  327. force_sig_ptrace_errno_trap(i, (void __user *)bkpt->address);
  328. }
  329. static struct perf_event *ptrace_hbp_create(struct task_struct *tsk, int type)
  330. {
  331. struct perf_event_attr attr;
  332. ptrace_breakpoint_init(&attr);
  333. /* Initialise fields to sane defaults. */
  334. attr.bp_addr = 0;
  335. attr.bp_len = 1;
  336. attr.bp_type = type;
  337. attr.disabled = 1;
  338. return register_user_hw_breakpoint(&attr, ptrace_hbptriggered, NULL,
  339. tsk);
  340. }
  341. /*
  342. * Address bit 0 choose instruction (0) or data (1) break register, bits
  343. * 31..1 are the register number.
  344. * Both PTRACE_GETHBPREGS and PTRACE_SETHBPREGS transfer two 32-bit words:
  345. * address (0) and control (1).
  346. * Instruction breakpoint contorl word is 0 to clear breakpoint, 1 to set.
  347. * Data breakpoint control word bit 31 is 'trigger on store', bit 30 is
  348. * 'trigger on load, bits 29..0 are length. Length 0 is used to clear a
  349. * breakpoint. To set a breakpoint length must be a power of 2 in the range
  350. * 1..64 and the address must be length-aligned.
  351. */
  352. static long ptrace_gethbpregs(struct task_struct *child, long addr,
  353. long __user *datap)
  354. {
  355. struct perf_event *bp;
  356. u32 user_data[2] = {0};
  357. bool dbreak = addr & 1;
  358. unsigned idx = addr >> 1;
  359. if ((!dbreak && idx >= XCHAL_NUM_IBREAK) ||
  360. (dbreak && idx >= XCHAL_NUM_DBREAK))
  361. return -EINVAL;
  362. if (dbreak)
  363. bp = child->thread.ptrace_wp[idx];
  364. else
  365. bp = child->thread.ptrace_bp[idx];
  366. if (bp) {
  367. user_data[0] = bp->attr.bp_addr;
  368. user_data[1] = bp->attr.disabled ? 0 : bp->attr.bp_len;
  369. if (dbreak) {
  370. if (bp->attr.bp_type & HW_BREAKPOINT_R)
  371. user_data[1] |= DBREAKC_LOAD_MASK;
  372. if (bp->attr.bp_type & HW_BREAKPOINT_W)
  373. user_data[1] |= DBREAKC_STOR_MASK;
  374. }
  375. }
  376. if (copy_to_user(datap, user_data, sizeof(user_data)))
  377. return -EFAULT;
  378. return 0;
  379. }
  380. static long ptrace_sethbpregs(struct task_struct *child, long addr,
  381. long __user *datap)
  382. {
  383. struct perf_event *bp;
  384. struct perf_event_attr attr;
  385. u32 user_data[2];
  386. bool dbreak = addr & 1;
  387. unsigned idx = addr >> 1;
  388. int bp_type = 0;
  389. if ((!dbreak && idx >= XCHAL_NUM_IBREAK) ||
  390. (dbreak && idx >= XCHAL_NUM_DBREAK))
  391. return -EINVAL;
  392. if (copy_from_user(user_data, datap, sizeof(user_data)))
  393. return -EFAULT;
  394. if (dbreak) {
  395. bp = child->thread.ptrace_wp[idx];
  396. if (user_data[1] & DBREAKC_LOAD_MASK)
  397. bp_type |= HW_BREAKPOINT_R;
  398. if (user_data[1] & DBREAKC_STOR_MASK)
  399. bp_type |= HW_BREAKPOINT_W;
  400. } else {
  401. bp = child->thread.ptrace_bp[idx];
  402. bp_type = HW_BREAKPOINT_X;
  403. }
  404. if (!bp) {
  405. bp = ptrace_hbp_create(child,
  406. bp_type ? bp_type : HW_BREAKPOINT_RW);
  407. if (IS_ERR(bp))
  408. return PTR_ERR(bp);
  409. if (dbreak)
  410. child->thread.ptrace_wp[idx] = bp;
  411. else
  412. child->thread.ptrace_bp[idx] = bp;
  413. }
  414. attr = bp->attr;
  415. attr.bp_addr = user_data[0];
  416. attr.bp_len = user_data[1] & ~(DBREAKC_LOAD_MASK | DBREAKC_STOR_MASK);
  417. attr.bp_type = bp_type;
  418. attr.disabled = !attr.bp_len;
  419. return modify_user_hw_breakpoint(bp, &attr);
  420. }
  421. #endif
  422. long arch_ptrace(struct task_struct *child, long request,
  423. unsigned long addr, unsigned long data)
  424. {
  425. int ret = -EPERM;
  426. void __user *datap = (void __user *) data;
  427. switch (request) {
  428. case PTRACE_PEEKUSR: /* read register specified by addr. */
  429. ret = ptrace_peekusr(child, addr, datap);
  430. break;
  431. case PTRACE_POKEUSR: /* write register specified by addr. */
  432. ret = ptrace_pokeusr(child, addr, data);
  433. break;
  434. case PTRACE_GETREGS:
  435. ret = ptrace_getregs(child, datap);
  436. break;
  437. case PTRACE_SETREGS:
  438. ret = ptrace_setregs(child, datap);
  439. break;
  440. case PTRACE_GETXTREGS:
  441. ret = ptrace_getxregs(child, datap);
  442. break;
  443. case PTRACE_SETXTREGS:
  444. ret = ptrace_setxregs(child, datap);
  445. break;
  446. #ifdef CONFIG_HAVE_HW_BREAKPOINT
  447. case PTRACE_GETHBPREGS:
  448. ret = ptrace_gethbpregs(child, addr, datap);
  449. break;
  450. case PTRACE_SETHBPREGS:
  451. ret = ptrace_sethbpregs(child, addr, datap);
  452. break;
  453. #endif
  454. default:
  455. ret = ptrace_request(child, request, addr, data);
  456. break;
  457. }
  458. return ret;
  459. }
  460. void do_syscall_trace_leave(struct pt_regs *regs);
  461. int do_syscall_trace_enter(struct pt_regs *regs)
  462. {
  463. if (regs->syscall == NO_SYSCALL)
  464. regs->areg[2] = -ENOSYS;
  465. if (test_thread_flag(TIF_SYSCALL_TRACE) &&
  466. tracehook_report_syscall_entry(regs)) {
  467. regs->areg[2] = -ENOSYS;
  468. regs->syscall = NO_SYSCALL;
  469. return 0;
  470. }
  471. if (regs->syscall == NO_SYSCALL ||
  472. secure_computing() == -1) {
  473. do_syscall_trace_leave(regs);
  474. return 0;
  475. }
  476. if (test_thread_flag(TIF_SYSCALL_TRACEPOINT))
  477. trace_sys_enter(regs, syscall_get_nr(current, regs));
  478. audit_syscall_entry(regs->syscall, regs->areg[6],
  479. regs->areg[3], regs->areg[4],
  480. regs->areg[5]);
  481. return 1;
  482. }
  483. void do_syscall_trace_leave(struct pt_regs *regs)
  484. {
  485. int step;
  486. audit_syscall_exit(regs);
  487. if (test_thread_flag(TIF_SYSCALL_TRACEPOINT))
  488. trace_sys_exit(regs, regs_return_value(regs));
  489. step = test_thread_flag(TIF_SINGLESTEP);
  490. if (step || test_thread_flag(TIF_SYSCALL_TRACE))
  491. tracehook_report_syscall_exit(regs, step);
  492. }