Introduce gdbarch_num_cooked_regs
[external/binutils.git] / gdb / mn10300-linux-tdep.c
1 /* Target-dependent code for the Matsushita MN10300 for GDB, the GNU debugger.
2
3    Copyright (C) 2003-2018 Free Software Foundation, Inc.
4
5    This file is part of GDB.
6
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 3 of the License, or
10    (at your option) any later version.
11
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16
17    You should have received a copy of the GNU General Public License
18    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
19
20 #include "defs.h"
21 #include "gdbcore.h"
22 #include "regcache.h"
23 #include "mn10300-tdep.h"
24 #include "bfd.h"
25 #include "elf-bfd.h"
26 #include "osabi.h"
27 #include "regset.h"
28 #include "solib-svr4.h"
29 #include "frame.h"
30 #include "trad-frame.h"
31 #include "tramp-frame.h"
32 #include "linux-tdep.h"
33
34 /* Transliterated from <asm-mn10300/elf.h>...  */
35 #define MN10300_ELF_NGREG 28
36 #define MN10300_ELF_NFPREG 32
37
38 typedef gdb_byte   mn10300_elf_greg_t[4];
39 typedef mn10300_elf_greg_t mn10300_elf_gregset_t[MN10300_ELF_NGREG];
40
41 typedef gdb_byte   mn10300_elf_fpreg_t[4];
42 typedef struct
43 {
44   mn10300_elf_fpreg_t fpregs[MN10300_ELF_NFPREG];
45   gdb_byte    fpcr[4];
46 } mn10300_elf_fpregset_t;
47
48 /* elf_gregset_t register indices stolen from include/asm-mn10300/ptrace.h.  */
49 #define MN10300_ELF_GREGSET_T_REG_INDEX_A3      0
50 #define MN10300_ELF_GREGSET_T_REG_INDEX_A2      1
51 #define MN10300_ELF_GREGSET_T_REG_INDEX_D3      2
52 #define MN10300_ELF_GREGSET_T_REG_INDEX_D2      3
53 #define MN10300_ELF_GREGSET_T_REG_INDEX_MCVF    4
54 #define MN10300_ELF_GREGSET_T_REG_INDEX_MCRL    5
55 #define MN10300_ELF_GREGSET_T_REG_INDEX_MCRH    6
56 #define MN10300_ELF_GREGSET_T_REG_INDEX_MDRQ    7
57 #define MN10300_ELF_GREGSET_T_REG_INDEX_E1      8
58 #define MN10300_ELF_GREGSET_T_REG_INDEX_E0      9
59 #define MN10300_ELF_GREGSET_T_REG_INDEX_E7      10
60 #define MN10300_ELF_GREGSET_T_REG_INDEX_E6      11
61 #define MN10300_ELF_GREGSET_T_REG_INDEX_E5      12
62 #define MN10300_ELF_GREGSET_T_REG_INDEX_E4      13
63 #define MN10300_ELF_GREGSET_T_REG_INDEX_E3      14
64 #define MN10300_ELF_GREGSET_T_REG_INDEX_E2      15
65 #define MN10300_ELF_GREGSET_T_REG_INDEX_SP      16
66 #define MN10300_ELF_GREGSET_T_REG_INDEX_LAR     17
67 #define MN10300_ELF_GREGSET_T_REG_INDEX_LIR     18
68 #define MN10300_ELF_GREGSET_T_REG_INDEX_MDR     19
69 #define MN10300_ELF_GREGSET_T_REG_INDEX_A1      20
70 #define MN10300_ELF_GREGSET_T_REG_INDEX_A0      21
71 #define MN10300_ELF_GREGSET_T_REG_INDEX_D1      22
72 #define MN10300_ELF_GREGSET_T_REG_INDEX_D0      23
73 #define MN10300_ELF_GREGSET_T_REG_INDEX_ORIG_D0 24
74 #define MN10300_ELF_GREGSET_T_REG_INDEX_EPSW    25
75 #define MN10300_ELF_GREGSET_T_REG_INDEX_PC      26
76
77 /* New gdbarch API for corefile registers.
78    Given a section name and size, create a struct reg object
79    with a supply_register and a collect_register method.  */
80
81 /* Copy register value of REGNUM from regset to regcache.
82    If REGNUM is -1, do this for all gp registers in regset.  */
83
84 static void
85 am33_supply_gregset_method (const struct regset *regset, 
86                             struct regcache *regcache, 
87                             int regnum, const void *gregs, size_t len)
88 {
89   const mn10300_elf_greg_t *regp = (const mn10300_elf_greg_t *) gregs;
90   int i;
91
92   gdb_assert (len >= sizeof (mn10300_elf_gregset_t));
93
94   switch (regnum) {
95   case E_D0_REGNUM:
96     regcache->raw_supply (E_D0_REGNUM, 
97                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D0));
98     break;
99   case E_D1_REGNUM:
100     regcache->raw_supply (E_D1_REGNUM, 
101                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D1));
102     break;
103   case E_D2_REGNUM:
104     regcache->raw_supply (E_D2_REGNUM, 
105                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D2));
106     break;
107   case E_D3_REGNUM:
108     regcache->raw_supply (E_D3_REGNUM, 
109                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D3));
110     break;
111   case E_A0_REGNUM:
112     regcache->raw_supply (E_A0_REGNUM, 
113                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A0));
114     break;
115   case E_A1_REGNUM:
116     regcache->raw_supply (E_A1_REGNUM, 
117                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A1));
118     break;
119   case E_A2_REGNUM:
120     regcache->raw_supply (E_A2_REGNUM, 
121                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A2));
122     break;
123   case E_A3_REGNUM:
124     regcache->raw_supply (E_A3_REGNUM, 
125                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A3));
126     break;
127   case E_SP_REGNUM:
128     regcache->raw_supply (E_SP_REGNUM, 
129                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_SP));
130     break;
131   case E_PC_REGNUM:
132     regcache->raw_supply (E_PC_REGNUM, 
133                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_PC));
134     break;
135   case E_MDR_REGNUM:
136     regcache->raw_supply (E_MDR_REGNUM, 
137                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MDR));
138     break;
139   case E_PSW_REGNUM:
140     regcache->raw_supply (E_PSW_REGNUM, 
141                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_EPSW));
142     break;
143   case E_LIR_REGNUM:
144     regcache->raw_supply (E_LIR_REGNUM, 
145                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_LIR));
146     break;
147   case E_LAR_REGNUM:
148     regcache->raw_supply (E_LAR_REGNUM, 
149                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_LAR));
150     break;
151   case E_MDRQ_REGNUM:
152     regcache->raw_supply (E_MDRQ_REGNUM, 
153                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MDRQ));
154     break;
155   case E_E0_REGNUM:
156     regcache->raw_supply (E_E0_REGNUM,   
157                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E0));
158     break;
159   case E_E1_REGNUM:
160     regcache->raw_supply (E_E1_REGNUM,
161                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E1));
162     break;
163   case E_E2_REGNUM:
164     regcache->raw_supply (E_E2_REGNUM, 
165                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E2));
166     break;
167   case E_E3_REGNUM:
168     regcache->raw_supply (E_E3_REGNUM, 
169                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E3));
170     break;
171   case E_E4_REGNUM:
172     regcache->raw_supply (E_E4_REGNUM, 
173                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E4));
174     break;
175   case E_E5_REGNUM:
176     regcache->raw_supply (E_E5_REGNUM, 
177                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E5));
178     break;
179   case E_E6_REGNUM:
180     regcache->raw_supply (E_E6_REGNUM, 
181                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E6));
182     break;
183   case E_E7_REGNUM:
184     regcache->raw_supply (E_E7_REGNUM, 
185                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E7));
186     break;
187
188     /* ssp, msp, and usp are inaccessible.  */
189   case E_E8_REGNUM:
190     regcache->raw_supply_zeroed (E_E8_REGNUM);
191     break;
192   case E_E9_REGNUM:
193     regcache->raw_supply_zeroed (E_E9_REGNUM);
194     break;
195   case E_E10_REGNUM:
196     regcache->raw_supply_zeroed (E_E10_REGNUM);
197     break;
198   case E_MCRH_REGNUM:
199     regcache->raw_supply (E_MCRH_REGNUM, 
200                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MCRH));
201     break;
202   case E_MCRL_REGNUM:
203     regcache->raw_supply (E_MCRL_REGNUM, 
204                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MCRL));
205     break;
206   case E_MCVF_REGNUM:
207     regcache->raw_supply (E_MCVF_REGNUM, 
208                           (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MCVF));
209     break;
210   case E_FPCR_REGNUM:
211     /* FPCR is numbered among the GP regs, but handled as an FP reg.
212        Do nothing.  */
213     break;
214   case E_FPCR_REGNUM + 1:
215     /* The two unused registers beyond fpcr are inaccessible.  */
216     regcache->raw_supply_zeroed (E_FPCR_REGNUM + 1);
217     break;
218   case E_FPCR_REGNUM + 2:
219     regcache->raw_supply_zeroed (E_FPCR_REGNUM + 2);
220     break;
221   default:      /* An error, obviously, but should we error out?  */
222     break;
223   case -1:
224     for (i = 0; i < MN10300_ELF_NGREG; i++)
225       am33_supply_gregset_method (regset, regcache, i, gregs, len);
226     break;
227   }
228   return;
229 }
230
231 /* Copy fp register value of REGNUM from regset to regcache.
232    If REGNUM is -1, do this for all fp registers in regset.  */
233
234 static void
235 am33_supply_fpregset_method (const struct regset *regset, 
236                              struct regcache *regcache, 
237                              int regnum, const void *fpregs, size_t len)
238 {
239   const mn10300_elf_fpregset_t *fpregset
240     = (const mn10300_elf_fpregset_t *) fpregs;
241
242   gdb_assert (len >= sizeof (mn10300_elf_fpregset_t));
243
244   if (regnum == -1)
245     {
246       int i;
247
248       for (i = 0; i < MN10300_ELF_NFPREG; i++)
249         am33_supply_fpregset_method (regset, regcache,
250                                      E_FS0_REGNUM + i, fpregs, len);
251       am33_supply_fpregset_method (regset, regcache, 
252                                    E_FPCR_REGNUM, fpregs, len);
253     }
254   else if (regnum == E_FPCR_REGNUM)
255     regcache->raw_supply (E_FPCR_REGNUM, &fpregset->fpcr);
256   else if (E_FS0_REGNUM <= regnum
257            && regnum < E_FS0_REGNUM + MN10300_ELF_NFPREG)
258     regcache->raw_supply (regnum, &fpregset->fpregs[regnum - E_FS0_REGNUM]);
259
260   return;
261 }
262
263 /* Copy register values from regcache to regset.  */
264
265 static void
266 am33_collect_gregset_method (const struct regset *regset, 
267                              const struct regcache *regcache, 
268                              int regnum, void *gregs, size_t len)
269 {
270   mn10300_elf_gregset_t *regp = (gdb_byte (*)[28][4]) gregs;
271   int i;
272
273   gdb_assert (len >= sizeof (mn10300_elf_gregset_t));
274
275   switch (regnum) {
276   case E_D0_REGNUM:
277     regcache->raw_collect (E_D0_REGNUM,
278                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D0));
279     break;
280   case E_D1_REGNUM:
281     regcache->raw_collect (E_D1_REGNUM, 
282                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D1));
283     break;
284   case E_D2_REGNUM:
285     regcache->raw_collect (E_D2_REGNUM, 
286                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D2));
287     break;
288   case E_D3_REGNUM:
289     regcache->raw_collect (E_D3_REGNUM, 
290                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_D3));
291     break;
292   case E_A0_REGNUM:
293     regcache->raw_collect (E_A0_REGNUM, 
294                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A0));
295     break;
296   case E_A1_REGNUM:
297     regcache->raw_collect (E_A1_REGNUM, 
298                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A1));
299     break;
300   case E_A2_REGNUM:
301     regcache->raw_collect (E_A2_REGNUM, 
302                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A2));
303     break;
304   case E_A3_REGNUM:
305     regcache->raw_collect (E_A3_REGNUM, 
306                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_A3));
307     break;
308   case E_SP_REGNUM:
309     regcache->raw_collect (E_SP_REGNUM, 
310                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_SP));
311     break;
312   case E_PC_REGNUM:
313     regcache->raw_collect (E_PC_REGNUM, 
314                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_PC));
315     break;
316   case E_MDR_REGNUM:
317     regcache->raw_collect (E_MDR_REGNUM, 
318                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MDR));
319     break;
320   case E_PSW_REGNUM:
321     regcache->raw_collect (E_PSW_REGNUM, 
322                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_EPSW));
323     break;
324   case E_LIR_REGNUM:
325     regcache->raw_collect (E_LIR_REGNUM, 
326                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_LIR));
327     break;
328   case E_LAR_REGNUM:
329     regcache->raw_collect (E_LAR_REGNUM, 
330                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_LAR));
331     break;
332   case E_MDRQ_REGNUM:
333     regcache->raw_collect (E_MDRQ_REGNUM, 
334                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MDRQ));
335     break;
336   case E_E0_REGNUM:
337     regcache->raw_collect (E_E0_REGNUM,   
338                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E0));
339     break;
340   case E_E1_REGNUM:
341     regcache->raw_collect (E_E1_REGNUM,
342                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E1));
343     break;
344   case E_E2_REGNUM:
345     regcache->raw_collect (E_E2_REGNUM, 
346                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E2));
347     break;
348   case E_E3_REGNUM:
349     regcache->raw_collect (E_E3_REGNUM, 
350                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E3));
351     break;
352   case E_E4_REGNUM:
353     regcache->raw_collect (E_E4_REGNUM, 
354                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E4));
355     break;
356   case E_E5_REGNUM:
357     regcache->raw_collect (E_E5_REGNUM, 
358                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E5));
359     break;
360   case E_E6_REGNUM:
361     regcache->raw_collect (E_E6_REGNUM, 
362                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E6));
363     break;
364   case E_E7_REGNUM:
365     regcache->raw_collect (E_E7_REGNUM, 
366                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_E7));
367     break;
368
369     /* ssp, msp, and usp are inaccessible.  */
370   case E_E8_REGNUM:
371     /* The gregset struct has noplace to put this: do nothing.  */
372     break;
373   case E_E9_REGNUM:
374     /* The gregset struct has noplace to put this: do nothing.  */
375     break;
376   case E_E10_REGNUM:
377     /* The gregset struct has noplace to put this: do nothing.  */
378     break;
379   case E_MCRH_REGNUM:
380     regcache->raw_collect (E_MCRH_REGNUM, 
381                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MCRH));
382     break;
383   case E_MCRL_REGNUM:
384     regcache->raw_collect (E_MCRL_REGNUM, 
385                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MCRL));
386     break;
387   case E_MCVF_REGNUM:
388     regcache->raw_collect (E_MCVF_REGNUM, 
389                            (regp + MN10300_ELF_GREGSET_T_REG_INDEX_MCVF));
390     break;
391   case E_FPCR_REGNUM:
392     /* FPCR is numbered among the GP regs, but handled as an FP reg.
393        Do nothing.  */
394     break;
395   case E_FPCR_REGNUM + 1:
396     /* The gregset struct has noplace to put this: do nothing.  */
397     break;
398   case E_FPCR_REGNUM + 2:
399     /* The gregset struct has noplace to put this: do nothing.  */
400     break;
401   default:      /* An error, obviously, but should we error out?  */
402     break;
403   case -1:
404     for (i = 0; i < MN10300_ELF_NGREG; i++)
405       am33_collect_gregset_method (regset, regcache, i, gregs, len);
406     break;
407   }
408   return;
409 }
410
411 /* Copy fp register values from regcache to regset.  */
412
413 static void
414 am33_collect_fpregset_method (const struct regset *regset, 
415                               const struct regcache *regcache, 
416                               int regnum, void *fpregs, size_t len)
417 {
418   mn10300_elf_fpregset_t *fpregset = (mn10300_elf_fpregset_t *) fpregs;
419
420   gdb_assert (len >= sizeof (mn10300_elf_fpregset_t));
421
422   if (regnum == -1)
423     {
424       int i;
425       for (i = 0; i < MN10300_ELF_NFPREG; i++)
426         am33_collect_fpregset_method (regset, regcache, E_FS0_REGNUM + i,
427                                       fpregs, len);
428       am33_collect_fpregset_method (regset, regcache, 
429                                     E_FPCR_REGNUM, fpregs, len);
430     }
431   else if (regnum == E_FPCR_REGNUM)
432     regcache->raw_collect (E_FPCR_REGNUM, &fpregset->fpcr);
433   else if (E_FS0_REGNUM <= regnum
434            && regnum < E_FS0_REGNUM + MN10300_ELF_NFPREG)
435     regcache->raw_collect (regnum, &fpregset->fpregs[regnum - E_FS0_REGNUM]);
436
437   return;
438 }
439
440 static const struct regset am33_gregset =
441   {
442     NULL, am33_supply_gregset_method, am33_collect_gregset_method
443   };
444
445 static const struct regset am33_fpregset =
446   {
447     NULL, am33_supply_fpregset_method, am33_collect_fpregset_method
448   };
449
450 /* Iterate over core file register note sections.  */
451
452 static void
453 am33_iterate_over_regset_sections (struct gdbarch *gdbarch,
454                                    iterate_over_regset_sections_cb *cb,
455                                    void *cb_data,
456                                    const struct regcache *regcache)
457 {
458   cb (".reg", sizeof (mn10300_elf_gregset_t), sizeof (mn10300_elf_gregset_t),
459       &am33_gregset, NULL, cb_data);
460   cb (".reg2", sizeof (mn10300_elf_fpregset_t), sizeof (mn10300_elf_fpregset_t),
461       &am33_fpregset, NULL, cb_data);
462 }
463 \f
464 static void
465 am33_linux_sigframe_cache_init (const struct tramp_frame *self,
466                                 struct frame_info *this_frame,
467                                 struct trad_frame_cache *this_cache,
468                                 CORE_ADDR func);
469
470 static const struct tramp_frame am33_linux_sigframe = {
471   SIGTRAMP_FRAME,
472   1,
473   {
474     /* mov     119,d0 */
475     { 0x2c, ULONGEST_MAX },
476     { 0x77, ULONGEST_MAX },
477     { 0x00, ULONGEST_MAX },
478     /* syscall 0 */
479     { 0xf0, ULONGEST_MAX },
480     { 0xe0, ULONGEST_MAX },
481     { TRAMP_SENTINEL_INSN, ULONGEST_MAX }
482   },
483   am33_linux_sigframe_cache_init
484 };
485
486 static const struct tramp_frame am33_linux_rt_sigframe = {
487   SIGTRAMP_FRAME,
488   1,
489   {
490     /* mov     173,d0 */
491     { 0x2c, ULONGEST_MAX },
492     { 0xad, ULONGEST_MAX },
493     { 0x00, ULONGEST_MAX },
494     /* syscall 0 */
495     { 0xf0, ULONGEST_MAX },
496     { 0xe0, ULONGEST_MAX },
497     { TRAMP_SENTINEL_INSN, ULONGEST_MAX }
498   },
499   am33_linux_sigframe_cache_init
500 };
501
502 /* Relevant struct definitions for signal handling...
503
504 From arch/mn10300/kernel/sigframe.h:
505
506 struct sigframe
507 {
508         void (*pretcode)(void);
509         int sig;
510         struct sigcontext *psc;
511         struct sigcontext sc;
512         struct fpucontext fpuctx;
513         unsigned long extramask[_NSIG_WORDS-1];
514         char retcode[8];
515 };
516
517 struct rt_sigframe
518 {
519         void (*pretcode)(void);
520         int sig;
521         struct siginfo *pinfo;
522         void *puc;
523         struct siginfo info;
524         struct ucontext uc;
525         struct fpucontext fpuctx;
526         char retcode[8];
527 };
528
529 From include/asm-mn10300/ucontext.h:
530
531 struct ucontext {
532         unsigned long     uc_flags;
533         struct ucontext  *uc_link;
534         stack_t           uc_stack;
535         struct sigcontext uc_mcontext;
536         sigset_t          uc_sigmask;
537 };
538
539 From include/asm-mn10300/sigcontext.h:
540
541 struct fpucontext {
542         unsigned long   fs[32];
543         unsigned long   fpcr;
544 };
545
546 struct sigcontext {
547         unsigned long   d0;
548         unsigned long   d1;
549         unsigned long   d2;
550         unsigned long   d3;
551         unsigned long   a0;
552         unsigned long   a1;
553         unsigned long   a2;
554         unsigned long   a3;
555         unsigned long   e0;
556         unsigned long   e1;
557         unsigned long   e2;
558         unsigned long   e3;
559         unsigned long   e4;
560         unsigned long   e5;
561         unsigned long   e6;
562         unsigned long   e7;
563         unsigned long   lar;
564         unsigned long   lir;
565         unsigned long   mdr;
566         unsigned long   mcvf;
567         unsigned long   mcrl;
568         unsigned long   mcrh;
569         unsigned long   mdrq;
570         unsigned long   sp;
571         unsigned long   epsw;
572         unsigned long   pc;
573         struct fpucontext *fpucontext;
574         unsigned long   oldmask;
575 }; */
576
577
578 #define AM33_SIGCONTEXT_D0 0
579 #define AM33_SIGCONTEXT_D1 4
580 #define AM33_SIGCONTEXT_D2 8
581 #define AM33_SIGCONTEXT_D3 12
582 #define AM33_SIGCONTEXT_A0 16
583 #define AM33_SIGCONTEXT_A1 20
584 #define AM33_SIGCONTEXT_A2 24
585 #define AM33_SIGCONTEXT_A3 28
586 #define AM33_SIGCONTEXT_E0 32
587 #define AM33_SIGCONTEXT_E1 36
588 #define AM33_SIGCONTEXT_E2 40
589 #define AM33_SIGCONTEXT_E3 44
590 #define AM33_SIGCONTEXT_E4 48
591 #define AM33_SIGCONTEXT_E5 52
592 #define AM33_SIGCONTEXT_E6 56
593 #define AM33_SIGCONTEXT_E7 60
594 #define AM33_SIGCONTEXT_LAR 64
595 #define AM33_SIGCONTEXT_LIR 68
596 #define AM33_SIGCONTEXT_MDR 72
597 #define AM33_SIGCONTEXT_MCVF 76
598 #define AM33_SIGCONTEXT_MCRL 80
599 #define AM33_SIGCONTEXT_MCRH 84
600 #define AM33_SIGCONTEXT_MDRQ 88
601 #define AM33_SIGCONTEXT_SP 92
602 #define AM33_SIGCONTEXT_EPSW 96
603 #define AM33_SIGCONTEXT_PC 100
604 #define AM33_SIGCONTEXT_FPUCONTEXT 104
605
606
607 static void
608 am33_linux_sigframe_cache_init (const struct tramp_frame *self,
609                                 struct frame_info *this_frame,
610                                 struct trad_frame_cache *this_cache,
611                                 CORE_ADDR func)
612 {
613   CORE_ADDR sc_base, fpubase;
614   int i;
615
616   sc_base = get_frame_register_unsigned (this_frame, E_SP_REGNUM);
617   if (self == &am33_linux_sigframe)
618     {
619       sc_base += 8;
620       sc_base = get_frame_memory_unsigned (this_frame, sc_base, 4);
621     }
622   else
623     {
624       sc_base += 12;
625       sc_base = get_frame_memory_unsigned (this_frame, sc_base, 4);
626       sc_base += 20;
627     }
628
629   trad_frame_set_reg_addr (this_cache, E_D0_REGNUM,
630                            sc_base + AM33_SIGCONTEXT_D0);
631   trad_frame_set_reg_addr (this_cache, E_D1_REGNUM,
632                            sc_base + AM33_SIGCONTEXT_D1);
633   trad_frame_set_reg_addr (this_cache, E_D2_REGNUM,
634                            sc_base + AM33_SIGCONTEXT_D2);
635   trad_frame_set_reg_addr (this_cache, E_D3_REGNUM,
636                            sc_base + AM33_SIGCONTEXT_D3);
637
638   trad_frame_set_reg_addr (this_cache, E_A0_REGNUM,
639                            sc_base + AM33_SIGCONTEXT_A0);
640   trad_frame_set_reg_addr (this_cache, E_A1_REGNUM,
641                            sc_base + AM33_SIGCONTEXT_A1);
642   trad_frame_set_reg_addr (this_cache, E_A2_REGNUM,
643                            sc_base + AM33_SIGCONTEXT_A2);
644   trad_frame_set_reg_addr (this_cache, E_A3_REGNUM,
645                            sc_base + AM33_SIGCONTEXT_A3);
646
647   trad_frame_set_reg_addr (this_cache, E_E0_REGNUM,
648                            sc_base + AM33_SIGCONTEXT_E0);
649   trad_frame_set_reg_addr (this_cache, E_E1_REGNUM,
650                            sc_base + AM33_SIGCONTEXT_E1);
651   trad_frame_set_reg_addr (this_cache, E_E2_REGNUM,
652                            sc_base + AM33_SIGCONTEXT_E2);
653   trad_frame_set_reg_addr (this_cache, E_E3_REGNUM,
654                            sc_base + AM33_SIGCONTEXT_E3);
655   trad_frame_set_reg_addr (this_cache, E_E4_REGNUM,
656                            sc_base + AM33_SIGCONTEXT_E4);
657   trad_frame_set_reg_addr (this_cache, E_E5_REGNUM,
658                            sc_base + AM33_SIGCONTEXT_E5);
659   trad_frame_set_reg_addr (this_cache, E_E6_REGNUM,
660                            sc_base + AM33_SIGCONTEXT_E6);
661   trad_frame_set_reg_addr (this_cache, E_E7_REGNUM,
662                            sc_base + AM33_SIGCONTEXT_E7);
663
664   trad_frame_set_reg_addr (this_cache, E_LAR_REGNUM,
665                            sc_base + AM33_SIGCONTEXT_LAR);
666   trad_frame_set_reg_addr (this_cache, E_LIR_REGNUM,
667                            sc_base + AM33_SIGCONTEXT_LIR);
668   trad_frame_set_reg_addr (this_cache, E_MDR_REGNUM,
669                            sc_base + AM33_SIGCONTEXT_MDR);
670   trad_frame_set_reg_addr (this_cache, E_MCVF_REGNUM,
671                            sc_base + AM33_SIGCONTEXT_MCVF);
672   trad_frame_set_reg_addr (this_cache, E_MCRL_REGNUM,
673                            sc_base + AM33_SIGCONTEXT_MCRL);
674   trad_frame_set_reg_addr (this_cache, E_MDRQ_REGNUM,
675                            sc_base + AM33_SIGCONTEXT_MDRQ);
676
677   trad_frame_set_reg_addr (this_cache, E_SP_REGNUM,
678                            sc_base + AM33_SIGCONTEXT_SP);
679   trad_frame_set_reg_addr (this_cache, E_PSW_REGNUM,
680                            sc_base + AM33_SIGCONTEXT_EPSW);
681   trad_frame_set_reg_addr (this_cache, E_PC_REGNUM,
682                            sc_base + AM33_SIGCONTEXT_PC);
683
684   fpubase = get_frame_memory_unsigned (this_frame,
685                                        sc_base + AM33_SIGCONTEXT_FPUCONTEXT,
686                                        4);
687   if (fpubase)
688     {
689       for (i = 0; i < 32; i++)
690         {
691           trad_frame_set_reg_addr (this_cache, E_FS0_REGNUM + i,
692                                    fpubase + 4 * i);
693         }
694       trad_frame_set_reg_addr (this_cache, E_FPCR_REGNUM, fpubase + 4 * 32);
695     }
696
697   trad_frame_set_id (this_cache, frame_id_build (sc_base, func));
698 }
699 \f
700 /* AM33 GNU/Linux osabi has been recognized.
701    Now's our chance to register our corefile handling.  */
702
703 static void
704 am33_linux_init_osabi (struct gdbarch_info info, struct gdbarch *gdbarch)
705 {
706   linux_init_abi (info, gdbarch);
707
708   set_gdbarch_iterate_over_regset_sections
709     (gdbarch, am33_iterate_over_regset_sections);
710   set_solib_svr4_fetch_link_map_offsets
711     (gdbarch, svr4_ilp32_fetch_link_map_offsets);
712
713   tramp_frame_prepend_unwinder (gdbarch, &am33_linux_sigframe);
714   tramp_frame_prepend_unwinder (gdbarch, &am33_linux_rt_sigframe);
715 }
716
717 void
718 _initialize_mn10300_linux_tdep (void)
719 {
720   gdbarch_register_osabi (bfd_arch_mn10300, 0,
721                           GDB_OSABI_LINUX, am33_linux_init_osabi);
722 }
723