Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
ptrace_64.c
Go to the documentation of this file.
1 /*
2  * Copyright 2003 PathScale, Inc.
3  * Copyright (C) 2003 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com)
4  *
5  * Licensed under the GPL
6  */
7 
8 #include <linux/mm.h>
9 #include <linux/sched.h>
10 #include <linux/errno.h>
11 #define __FRAME_OFFSETS
12 #include <asm/ptrace.h>
13 #include <asm/uaccess.h>
14 
15 /*
16  * determines which flags the user has access to.
17  * 1 = access 0 = no access
18  */
19 #define FLAG_MASK 0x44dd5UL
20 
21 static const int reg_offsets[] =
22 {
23  [R8 >> 3] = HOST_R8,
24  [R9 >> 3] = HOST_R9,
25  [R10 >> 3] = HOST_R10,
26  [R11 >> 3] = HOST_R11,
27  [R12 >> 3] = HOST_R12,
28  [R13 >> 3] = HOST_R13,
29  [R14 >> 3] = HOST_R14,
30  [R15 >> 3] = HOST_R15,
31  [RIP >> 3] = HOST_IP,
32  [RSP >> 3] = HOST_SP,
33  [RAX >> 3] = HOST_AX,
34  [RBX >> 3] = HOST_BX,
35  [RCX >> 3] = HOST_CX,
36  [RDX >> 3] = HOST_DX,
37  [RSI >> 3] = HOST_SI,
38  [RDI >> 3] = HOST_DI,
39  [RBP >> 3] = HOST_BP,
40  [CS >> 3] = HOST_CS,
41  [SS >> 3] = HOST_SS,
42  [FS_BASE >> 3] = HOST_FS_BASE,
43  [GS_BASE >> 3] = HOST_GS_BASE,
44  [DS >> 3] = HOST_DS,
45  [ES >> 3] = HOST_ES,
46  [FS >> 3] = HOST_FS,
47  [GS >> 3] = HOST_GS,
48  [EFLAGS >> 3] = HOST_EFLAGS,
49  [ORIG_RAX >> 3] = HOST_ORIG_AX,
50 };
51 
52 int putreg(struct task_struct *child, int regno, unsigned long value)
53 {
54 #ifdef TIF_IA32
55  /*
56  * Some code in the 64bit emulation may not be 64bit clean.
57  * Don't take any chances.
58  */
59  if (test_tsk_thread_flag(child, TIF_IA32))
60  value &= 0xffffffff;
61 #endif
62  switch (regno) {
63  case R8:
64  case R9:
65  case R10:
66  case R11:
67  case R12:
68  case R13:
69  case R14:
70  case R15:
71  case RIP:
72  case RSP:
73  case RAX:
74  case RBX:
75  case RCX:
76  case RDX:
77  case RSI:
78  case RDI:
79  case RBP:
80  case ORIG_RAX:
81  break;
82 
83  case FS:
84  case GS:
85  case DS:
86  case ES:
87  case SS:
88  case CS:
89  if (value && (value & 3) != 3)
90  return -EIO;
91  value &= 0xffff;
92  break;
93 
94  case FS_BASE:
95  case GS_BASE:
96  if (!((value >> 48) == 0 || (value >> 48) == 0xffff))
97  return -EIO;
98  break;
99 
100  case EFLAGS:
101  value &= FLAG_MASK;
102  child->thread.regs.regs.gp[HOST_EFLAGS] |= value;
103  return 0;
104 
105  default:
106  panic("Bad register in putreg(): %d\n", regno);
107  }
108 
109  child->thread.regs.regs.gp[reg_offsets[regno >> 3]] = value;
110  return 0;
111 }
112 
113 int poke_user(struct task_struct *child, long addr, long data)
114 {
115  if ((addr & 3) || addr < 0)
116  return -EIO;
117 
118  if (addr < MAX_REG_OFFSET)
119  return putreg(child, addr, data);
120  else if ((addr >= offsetof(struct user, u_debugreg[0])) &&
121  (addr <= offsetof(struct user, u_debugreg[7]))) {
122  addr -= offsetof(struct user, u_debugreg[0]);
123  addr = addr >> 2;
124  if ((addr == 4) || (addr == 5))
125  return -EIO;
126  child->thread.arch.debugregs[addr] = data;
127  return 0;
128  }
129  return -EIO;
130 }
131 
132 unsigned long getreg(struct task_struct *child, int regno)
133 {
134  unsigned long mask = ~0UL;
135 #ifdef TIF_IA32
136  if (test_tsk_thread_flag(child, TIF_IA32))
137  mask = 0xffffffff;
138 #endif
139  switch (regno) {
140  case R8:
141  case R9:
142  case R10:
143  case R11:
144  case R12:
145  case R13:
146  case R14:
147  case R15:
148  case RIP:
149  case RSP:
150  case RAX:
151  case RBX:
152  case RCX:
153  case RDX:
154  case RSI:
155  case RDI:
156  case RBP:
157  case ORIG_RAX:
158  case EFLAGS:
159  case FS_BASE:
160  case GS_BASE:
161  break;
162  case FS:
163  case GS:
164  case DS:
165  case ES:
166  case SS:
167  case CS:
168  mask = 0xffff;
169  break;
170  default:
171  panic("Bad register in getreg: %d\n", regno);
172  }
173  return mask & child->thread.regs.regs.gp[reg_offsets[regno >> 3]];
174 }
175 
176 int peek_user(struct task_struct *child, long addr, long data)
177 {
178  /* read the word at location addr in the USER area. */
179  unsigned long tmp;
180 
181  if ((addr & 3) || addr < 0)
182  return -EIO;
183 
184  tmp = 0; /* Default return condition */
185  if (addr < MAX_REG_OFFSET)
186  tmp = getreg(child, addr);
187  else if ((addr >= offsetof(struct user, u_debugreg[0])) &&
188  (addr <= offsetof(struct user, u_debugreg[7]))) {
189  addr -= offsetof(struct user, u_debugreg[0]);
190  addr = addr >> 2;
191  tmp = child->thread.arch.debugregs[addr];
192  }
193  return put_user(tmp, (unsigned long *) data);
194 }
195 
196 /* XXX Mostly copied from sys-i386 */
197 int is_syscall(unsigned long addr)
198 {
199  unsigned short instr;
200  int n;
201 
202  n = copy_from_user(&instr, (void __user *) addr, sizeof(instr));
203  if (n) {
204  /*
205  * access_process_vm() grants access to vsyscall and stub,
206  * while copy_from_user doesn't. Maybe access_process_vm is
207  * slow, but that doesn't matter, since it will be called only
208  * in case of singlestepping, if copy_from_user failed.
209  */
210  n = access_process_vm(current, addr, &instr, sizeof(instr), 0);
211  if (n != sizeof(instr)) {
212  printk("is_syscall : failed to read instruction from "
213  "0x%lx\n", addr);
214  return 1;
215  }
216  }
217  /* sysenter */
218  return instr == 0x050f;
219 }
220 
221 static int get_fpregs(struct user_i387_struct __user *buf, struct task_struct *child)
222 {
223  int err, n, cpu = ((struct thread_info *) child->stack)->cpu;
224  long fpregs[HOST_FP_SIZE];
225 
226  BUG_ON(sizeof(*buf) != sizeof(fpregs));
227  err = save_fp_registers(userspace_pid[cpu], fpregs);
228  if (err)
229  return err;
230 
231  n = copy_to_user(buf, fpregs, sizeof(fpregs));
232  if (n > 0)
233  return -EFAULT;
234 
235  return n;
236 }
237 
238 static int set_fpregs(struct user_i387_struct __user *buf, struct task_struct *child)
239 {
240  int n, cpu = ((struct thread_info *) child->stack)->cpu;
241  long fpregs[HOST_FP_SIZE];
242 
243  BUG_ON(sizeof(*buf) != sizeof(fpregs));
244  n = copy_from_user(fpregs, buf, sizeof(fpregs));
245  if (n > 0)
246  return -EFAULT;
247 
248  return restore_fp_registers(userspace_pid[cpu], fpregs);
249 }
250 
251 long subarch_ptrace(struct task_struct *child, long request,
252  unsigned long addr, unsigned long data)
253 {
254  int ret = -EIO;
255  void __user *datap = (void __user *) data;
256 
257  switch (request) {
258  case PTRACE_GETFPREGS: /* Get the child FPU state. */
259  ret = get_fpregs(datap, child);
260  break;
261  case PTRACE_SETFPREGS: /* Set the child FPU state. */
262  ret = set_fpregs(datap, child);
263  break;
264  case PTRACE_ARCH_PRCTL:
265  /* XXX Calls ptrace on the host - needs some SMP thinking */
266  ret = arch_prctl(child, data, (void __user *) addr);
267  break;
268  }
269 
270  return ret;
271 }