~ubuntu-branches/ubuntu/raring/cell-gdb/raring

« back to all changes in this revision

Viewing changes to debian/patches/ppu/diff-combined-gdb-gdbserver

  • Committer: Bazaar Package Importer
  • Author(s): Matthias Klose
  • Date: 2007-06-13 19:50:12 UTC
  • Revision ID: james.westby@ubuntu.com-20070613195012-5b131ubeqq7tstzt
Tags: 6.6-1ubuntu1
Upload to gutsy.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
diff -urN gdb-orig/gdb/gdbserver/linux-low.c gdb-6.6/gdb/gdbserver/linux-low.c
 
2
--- gdb-orig/gdb/gdbserver/linux-low.c  2006-10-17 18:02:27.000000000 +0200
 
3
+++ gdb-6.6/gdb/gdbserver/linux-low.c   2006-12-13 21:37:42.965524856 +0100
 
4
@@ -37,6 +37,13 @@
 
5
 #include <unistd.h>
 
6
 #include <errno.h>
 
7
 #include <sys/syscall.h>
 
8
+#include <sys/types.h>
 
9
+#include <sys/stat.h>
 
10
+#include <sys/vfs.h>
 
11
+
 
12
+#ifndef SPUFS_MAGIC
 
13
+#define SPUFS_MAGIC 0x23c9b64e
 
14
+#endif
 
15
 
 
16
 #ifndef PTRACE_GETSIGINFO
 
17
 # define PTRACE_GETSIGINFO 0x4202
 
18
@@ -1631,6 +1638,115 @@
 
19
 }
 
20
 #endif
 
21
 
 
22
+
 
23
+/* Enumerate spufs IDs for process PID.  */
 
24
+static int
 
25
+spu_enumerate_spu_ids (long pid, unsigned char *buf, CORE_ADDR offset, int len)
 
26
+{
 
27
+  int pos = 0;
 
28
+  int written = 0;
 
29
+  char path[128];
 
30
+  DIR *dir;
 
31
+  struct dirent *entry;
 
32
+
 
33
+  sprintf (path, "/proc/%ld/fd", pid);
 
34
+  dir = opendir (path);
 
35
+  if (!dir)
 
36
+    return -1;
 
37
+
 
38
+  rewinddir (dir);
 
39
+  while ((entry = readdir (dir)) != NULL)
 
40
+    {
 
41
+      struct stat st;
 
42
+      struct statfs stfs;
 
43
+      int fd;
 
44
+
 
45
+      fd = atoi (entry->d_name);
 
46
+      if (!fd)
 
47
+        continue;
 
48
+
 
49
+      sprintf (path, "/proc/%ld/fd/%d", pid, fd);
 
50
+      if (stat (path, &st) != 0)
 
51
+        continue;
 
52
+      if (!S_ISDIR (st.st_mode))
 
53
+        continue;
 
54
+
 
55
+      if (statfs (path, &stfs) != 0)
 
56
+        continue;
 
57
+      if (stfs.f_type != SPUFS_MAGIC)
 
58
+        continue;
 
59
+
 
60
+      if (pos >= offset && pos + 4 <= offset + len)
 
61
+        {
 
62
+          *(unsigned int *)(buf + pos - offset) = fd;
 
63
+          written += 4;
 
64
+        }
 
65
+      pos += 4;
 
66
+    }
 
67
+
 
68
+  closedir (dir);
 
69
+  return written;
 
70
+}
 
71
+
 
72
+/* Implements the to_xfer_partial interface for the TARGET_OBJECT_SPU
 
73
+   object type, using the /proc file system */
 
74
+static int
 
75
+linux_spu_qxfer_partial (const char *annex, unsigned char *readbuf,
 
76
+                         unsigned const char *writebuf, 
 
77
+                         CORE_ADDR offset, int len)
 
78
+{
 
79
+  char buf[128];
 
80
+  int fd = 0;
 
81
+  int ret = 0;
 
82
+
 
83
+  if (!writebuf && !readbuf)
 
84
+    return -1;
 
85
+
 
86
+  if (!*annex)
 
87
+    {
 
88
+      if (!readbuf)
 
89
+        return -1;
 
90
+      else
 
91
+        return spu_enumerate_spu_ids (inferior_pid, readbuf, offset, len);
 
92
+    }
 
93
+
 
94
+  sprintf (buf, "/proc/%ld/fd/%s", inferior_pid, annex);
 
95
+  if (debug_threads)
 
96
+    printf ("access [%s] |offset [%lld] | len [%d]\n", buf, offset, len);
 
97
+
 
98
+  fd = open (buf, writebuf? O_WRONLY : O_RDONLY);
 
99
+  if (fd <= 0)
 
100
+    return -1;
 
101
+
 
102
+  if (offset != 0
 
103
+      && lseek (fd, (off_t) offset, SEEK_SET) != (off_t) offset)
 
104
+    {
 
105
+      close (fd);
 
106
+      return 0;
 
107
+    }
 
108
+
 
109
+  if (writebuf) 
 
110
+    ret = write (fd, writebuf, (size_t) len);
 
111
+  else
 
112
+    ret = read (fd, readbuf, (size_t) len);
 
113
+
 
114
+  close (fd);
 
115
+  return ret;
 
116
+}
 
117
+
 
118
+/* Implements the to_xfer_partial interface */
 
119
+static int
 
120
+linux_qxfer_partial (const char *object_name, const char *annex, 
 
121
+                     unsigned char *readbuf, unsigned const char *writebuf, 
 
122
+                     CORE_ADDR offset, int len)
 
123
+{
 
124
+  if (strncmp (object_name, "spu", 3) == 0)
 
125
+    return linux_spu_qxfer_partial 
 
126
+      (annex, readbuf, writebuf, offset, len);
 
127
+
 
128
+  return -1;
 
129
+}
 
130
+
 
131
 static struct target_ops linux_target_ops = {
 
132
   linux_create_inferior,
 
133
   linux_attach,
 
134
@@ -1660,6 +1776,7 @@
 
135
 #else
 
136
   NULL,
 
137
 #endif
 
138
+  linux_qxfer_partial,
 
139
 };
 
140
 
 
141
 static void
 
142
diff -urN gdb-orig/gdb/gdbserver/linux-ppc64-low.c gdb-6.6/gdb/gdbserver/linux-ppc64-low.c
 
143
--- gdb-orig/gdb/gdbserver/linux-ppc64-low.c    2006-12-13 21:36:19.942498256 +0100
 
144
+++ gdb-6.6/gdb/gdbserver/linux-ppc64-low.c     2006-12-13 21:36:28.193575472 +0100
 
145
@@ -70,21 +70,75 @@
 
146
   return 0;
 
147
 }
 
148
 
 
149
+
 
150
+#define INSTR_SC        0x44000002
 
151
+#define NR_spu_run      0x0116
 
152
+
 
153
+/* If the PPU thread is currently stopped on a spu_run system call,
 
154
+   return to FD and ADDR the file handle and NPC parameter address
 
155
+   used with the system call.  Return non-zero if successful.  */
 
156
+static int
 
157
+parse_spufs_run (int *fd, CORE_ADDR *addr)
 
158
+{
 
159
+  unsigned int insn;
 
160
+  unsigned long pc, r0, r3, r4;
 
161
+  collect_register_by_name ("pc", &pc);
 
162
+
 
163
+  /* Fetch instruction preceding current NIP.  */
 
164
+  if ((*the_target->read_memory) (pc - 4, (unsigned char *) &insn, 4) != 0)
 
165
+    return 0;
 
166
+  /* It should be a "sc" instruction.  */
 
167
+  if (insn != INSTR_SC)
 
168
+    return 0;
 
169
+  /* System call number should be NR_spu_run.  */
 
170
+  collect_register_by_name ("r0", &r0);
 
171
+  if (r0 != NR_spu_run)
 
172
+    return 0;
 
173
+
 
174
+  /* Register 3 contains fd, register 4 the NPC param pointer.  */
 
175
+  collect_register_by_name ("orig_r3", &r3);
 
176
+  collect_register_by_name ("r4", &r4);
 
177
+  *fd = (int) r3;
 
178
+  *addr = (CORE_ADDR) r4;
 
179
+  return 1;
 
180
+}
 
181
+
 
182
 static CORE_ADDR
 
183
 ppc_get_pc (void)
 
184
 {
 
185
-  unsigned long pc;
 
186
+  CORE_ADDR addr;
 
187
+  int fd;
 
188
 
 
189
-  collect_register_by_name ("pc", &pc);
 
190
-  return (CORE_ADDR) pc;
 
191
+  if (parse_spufs_run (&fd, &addr))
 
192
+    {
 
193
+      unsigned int pc;
 
194
+      (*the_target->read_memory) (addr, (unsigned char *) &pc, 4);
 
195
+      return ((CORE_ADDR)1 << 63) | ((CORE_ADDR)fd << 32) | (CORE_ADDR) (pc - 4);
 
196
+    }
 
197
+  else
 
198
+    {
 
199
+      unsigned long pc;
 
200
+      collect_register_by_name ("pc", &pc);
 
201
+      return (CORE_ADDR) pc;
 
202
+    }
 
203
 }
 
204
 
 
205
 static void
 
206
 ppc_set_pc (CORE_ADDR pc)
 
207
 {
 
208
-  unsigned long newpc = pc;
 
209
+  CORE_ADDR addr;
 
210
+  int fd;
 
211
 
 
212
-  supply_register_by_name ("pc", &newpc);
 
213
+  if (parse_spufs_run (&fd, &addr))
 
214
+    {
 
215
+      unsigned int newpc = pc;
 
216
+      (*the_target->write_memory) (addr, (unsigned char *) &newpc, 4);
 
217
+    }
 
218
+  else
 
219
+    {
 
220
+      unsigned long newpc = pc;
 
221
+      supply_register_by_name ("pc", &newpc);
 
222
+    }
 
223
 }
 
224
 
 
225
 /* Correct in either endianness.
 
226
@@ -98,14 +152,28 @@
 
227
 {
 
228
   unsigned int insn;
 
229
 
 
230
-  (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
 
231
-  if (insn == ppc_breakpoint)
 
232
-    return 1;
 
233
-  /* If necessary, recognize more trap instructions here.  GDB only uses the
 
234
-     one.  */
 
235
+  if (where & ((CORE_ADDR)1 << 63))
 
236
+    {
 
237
+      char mem_annex[32];
 
238
+      sprintf (mem_annex, "%d/mem", (int)((where >> 32) & 0x7fffffff));
 
239
+      (*the_target->qxfer_partial) ("spu", mem_annex, (unsigned char *) &insn,
 
240
+                                   NULL, where & 0xffffffff, 4);
 
241
+      if (insn == 0x3fff)
 
242
+       return 1;
 
243
+    }
 
244
+  else
 
245
+    {
 
246
+      (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
 
247
+      if (insn == ppc_breakpoint)
 
248
+       return 1;
 
249
+      /* If necessary, recognize more trap instructions here.  GDB only uses
 
250
+        the one.  */
 
251
+    }
 
252
+
 
253
   return 0;
 
254
 }
 
255
 
 
256
+
 
257
 /* Provide only a fill function for the general register set.  ps_lgetregs
 
258
    will use this for NPTL support.  */
 
259
 
 
260
diff -urN gdb-orig/gdb/gdbserver/linux-ppc-low.c gdb-6.6/gdb/gdbserver/linux-ppc-low.c
 
261
--- gdb-orig/gdb/gdbserver/linux-ppc-low.c      2006-12-13 21:36:19.946497648 +0100
 
262
+++ gdb-6.6/gdb/gdbserver/linux-ppc-low.c       2006-12-13 21:36:28.197574864 +0100
 
263
@@ -73,21 +73,74 @@
 
264
   return 0;
 
265
 }
 
266
 
 
267
+
 
268
+#define INSTR_SC        0x44000002
 
269
+#define NR_spu_run      0x0116
 
270
+
 
271
+/* If the PPU thread is currently stopped on a spu_run system call,
 
272
+   return to FD and ADDR the file handle and NPC parameter address
 
273
+   used with the system call.  Return non-zero if successful.  */
 
274
+static int
 
275
+parse_spufs_run (int *fd, CORE_ADDR *addr)
 
276
+{
 
277
+  unsigned long insn, pc, r0, r3, r4;
 
278
+  collect_register_by_name ("pc", &pc);
 
279
+
 
280
+  /* Fetch instruction preceding current NIP.  */
 
281
+  if ((*the_target->read_memory) (pc - 4, (unsigned char *) &insn, 4) != 0)
 
282
+    return 0;
 
283
+  /* It should be a "sc" instruction.  */
 
284
+  if (insn != INSTR_SC)
 
285
+    return 0;
 
286
+  /* System call number should be NR_spu_run.  */
 
287
+  collect_register_by_name ("r0", &r0);
 
288
+  if (r0 != NR_spu_run)
 
289
+    return 0;
 
290
+
 
291
+  /* Register 3 contains fd, register 4 the NPC param pointer.  */
 
292
+  collect_register_by_name ("orig_r3", &r3);
 
293
+  collect_register_by_name ("r4", &r4);
 
294
+  *fd = (int) r3;
 
295
+  *addr = (CORE_ADDR) r4;
 
296
+  return 1;
 
297
+}
 
298
+
 
299
 static CORE_ADDR
 
300
 ppc_get_pc (void)
 
301
 {
 
302
-  unsigned long pc;
 
303
+  CORE_ADDR addr;
 
304
+  int fd;
 
305
 
 
306
-  collect_register_by_name ("pc", &pc);
 
307
-  return (CORE_ADDR) pc;
 
308
+  if (parse_spufs_run (&fd, &addr))
 
309
+    {
 
310
+      unsigned int pc;
 
311
+      (*the_target->read_memory) (addr, (unsigned char *) &pc, 4);
 
312
+      return ((CORE_ADDR)1 << 63) | ((CORE_ADDR)fd << 32) | (CORE_ADDR) (pc - 4);
 
313
+    }
 
314
+  else
 
315
+    {
 
316
+      unsigned long pc;
 
317
+      collect_register_by_name ("pc", &pc);
 
318
+      return (CORE_ADDR) pc;
 
319
+    }
 
320
 }
 
321
 
 
322
 static void
 
323
 ppc_set_pc (CORE_ADDR pc)
 
324
 {
 
325
-  unsigned long newpc = pc;
 
326
+  CORE_ADDR addr;
 
327
+  int fd;
 
328
 
 
329
-  supply_register_by_name ("pc", &newpc);
 
330
+  if (parse_spufs_run (&fd, &addr))
 
331
+    {
 
332
+      unsigned int newpc = pc;
 
333
+      (*the_target->write_memory) (addr, (unsigned char *) &newpc, 4);
 
334
+    }
 
335
+  else
 
336
+    {
 
337
+      unsigned long newpc = pc;
 
338
+      supply_register_by_name ("pc", &newpc);
 
339
+    }
 
340
 }
 
341
 
 
342
 /* Correct in either endianness.  Note that this file is
 
343
@@ -102,11 +155,24 @@
 
344
 {
 
345
   unsigned long insn;
 
346
 
 
347
-  (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
 
348
-  if (insn == ppc_breakpoint)
 
349
-    return 1;
 
350
-  /* If necessary, recognize more trap instructions here.  GDB only uses the
 
351
-     one.  */
 
352
+  if (where & ((CORE_ADDR)1 << 63))
 
353
+    {
 
354
+      char mem_annex[32];
 
355
+      sprintf (mem_annex, "%d/mem", (int)((where >> 32) & 0x7fffffff));
 
356
+      (*the_target->qxfer_partial) ("spu", mem_annex, (unsigned char *) &insn,
 
357
+                                   NULL, where & 0xffffffff, 4);
 
358
+      if (insn == 0x3fff)
 
359
+       return 1;
 
360
+    }
 
361
+  else
 
362
+    {
 
363
+      (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
 
364
+      if (insn == ppc_breakpoint)
 
365
+       return 1;
 
366
+      /* If necessary, recognize more trap instructions here.  GDB only uses
 
367
+        the one.  */
 
368
+    }
 
369
+
 
370
   return 0;
 
371
 }
 
372