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