OLD | NEW |
1 /* Target-dependent code for GNU/Linux on MIPS processors. | 1 /* Target-dependent code for GNU/Linux on MIPS processors. |
2 | 2 |
3 Copyright (C) 2001-2002, 2004-2012 Free Software Foundation, Inc. | 3 Copyright (C) 2001-2002, 2004-2012 Free Software Foundation, Inc. |
4 | 4 |
5 This file is part of GDB. | 5 This file is part of GDB. |
6 | 6 |
7 This program is free software; you can redistribute it and/or modify | 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 | 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 | 9 the Free Software Foundation; either version 3 of the License, or |
10 (at your option) any later version. | 10 (at your option) any later version. |
(...skipping 22 matching lines...) Expand all Loading... |
33 #include "solib.h" | 33 #include "solib.h" |
34 #include "solib-svr4.h" | 34 #include "solib-svr4.h" |
35 #include "solist.h" | 35 #include "solist.h" |
36 #include "symtab.h" | 36 #include "symtab.h" |
37 #include "target-descriptions.h" | 37 #include "target-descriptions.h" |
38 #include "regset.h" | 38 #include "regset.h" |
39 #include "mips-linux-tdep.h" | 39 #include "mips-linux-tdep.h" |
40 #include "glibc-tdep.h" | 40 #include "glibc-tdep.h" |
41 #include "linux-tdep.h" | 41 #include "linux-tdep.h" |
42 #include "xml-syscall.h" | 42 #include "xml-syscall.h" |
| 43 #include "gdb_signals.h" |
43 | 44 |
44 static struct target_so_ops mips_svr4_so_ops; | 45 static struct target_so_ops mips_svr4_so_ops; |
45 | 46 |
46 /* Figure out where the longjmp will land. | 47 /* Figure out where the longjmp will land. |
47 We expect the first arg to be a pointer to the jmp_buf structure | 48 We expect the first arg to be a pointer to the jmp_buf structure |
48 from which we extract the pc (MIPS_LINUX_JB_PC) that we will land | 49 from which we extract the pc (MIPS_LINUX_JB_PC) that we will land |
49 at. The pc is copied into PC. This routine returns 1 on | 50 at. The pc is copied into PC. This routine returns 1 on |
50 success. */ | 51 success. */ |
51 | 52 |
52 #define MIPS_LINUX_JB_ELEMENT_SIZE 4 | 53 #define MIPS_LINUX_JB_ELEMENT_SIZE 4 |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
112 supply_32bit_reg (regcache, mips_regnum (gdbarch)->hi, regp + EF_HI); | 113 supply_32bit_reg (regcache, mips_regnum (gdbarch)->hi, regp + EF_HI); |
113 | 114 |
114 supply_32bit_reg (regcache, mips_regnum (gdbarch)->pc, | 115 supply_32bit_reg (regcache, mips_regnum (gdbarch)->pc, |
115 regp + EF_CP0_EPC); | 116 regp + EF_CP0_EPC); |
116 supply_32bit_reg (regcache, mips_regnum (gdbarch)->badvaddr, | 117 supply_32bit_reg (regcache, mips_regnum (gdbarch)->badvaddr, |
117 regp + EF_CP0_BADVADDR); | 118 regp + EF_CP0_BADVADDR); |
118 supply_32bit_reg (regcache, MIPS_PS_REGNUM, regp + EF_CP0_STATUS); | 119 supply_32bit_reg (regcache, MIPS_PS_REGNUM, regp + EF_CP0_STATUS); |
119 supply_32bit_reg (regcache, mips_regnum (gdbarch)->cause, | 120 supply_32bit_reg (regcache, mips_regnum (gdbarch)->cause, |
120 regp + EF_CP0_CAUSE); | 121 regp + EF_CP0_CAUSE); |
121 | 122 |
122 /* Fill inaccessible registers with zero. */ | 123 /* Fill the inaccessible zero register with zero. */ |
123 regcache_raw_supply (regcache, MIPS_ZERO_REGNUM, zerobuf); | 124 regcache_raw_supply (regcache, MIPS_ZERO_REGNUM, zerobuf); |
124 regcache_raw_supply (regcache, MIPS_UNUSED_REGNUM, zerobuf); | |
125 for (regi = MIPS_FIRST_EMBED_REGNUM; | |
126 regi <= MIPS_LAST_EMBED_REGNUM; | |
127 regi++) | |
128 regcache_raw_supply (regcache, regi, zerobuf); | |
129 } | 125 } |
130 | 126 |
131 static void | 127 static void |
132 mips_supply_gregset_wrapper (const struct regset *regset, | 128 mips_supply_gregset_wrapper (const struct regset *regset, |
133 struct regcache *regcache, | 129 struct regcache *regcache, |
134 int regnum, const void *gregs, size_t len) | 130 int regnum, const void *gregs, size_t len) |
135 { | 131 { |
136 gdb_assert (len == sizeof (mips_elf_gregset_t)); | 132 gdb_assert (len == sizeof (mips_elf_gregset_t)); |
137 | 133 |
138 mips_supply_gregset (regcache, (const mips_elf_gregset_t *)gregs); | 134 mips_supply_gregset (regcache, (const mips_elf_gregset_t *)gregs); |
(...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
244 } | 240 } |
245 | 241 |
246 /* Likewise, pack one or all floating point registers into an | 242 /* Likewise, pack one or all floating point registers into an |
247 elf_fpregset_t. */ | 243 elf_fpregset_t. */ |
248 | 244 |
249 void | 245 void |
250 mips_fill_fpregset (const struct regcache *regcache, | 246 mips_fill_fpregset (const struct regcache *regcache, |
251 mips_elf_fpregset_t *fpregsetp, int regno) | 247 mips_elf_fpregset_t *fpregsetp, int regno) |
252 { | 248 { |
253 struct gdbarch *gdbarch = get_regcache_arch (regcache); | 249 struct gdbarch *gdbarch = get_regcache_arch (regcache); |
254 char *from, *to; | 250 char *to; |
255 | 251 |
256 if ((regno >= gdbarch_fp0_regnum (gdbarch)) | 252 if ((regno >= gdbarch_fp0_regnum (gdbarch)) |
257 && (regno < gdbarch_fp0_regnum (gdbarch) + 32)) | 253 && (regno < gdbarch_fp0_regnum (gdbarch) + 32)) |
258 { | 254 { |
259 to = (char *) (*fpregsetp + regno - gdbarch_fp0_regnum (gdbarch)); | 255 to = (char *) (*fpregsetp + regno - gdbarch_fp0_regnum (gdbarch)); |
260 regcache_raw_collect (regcache, regno, to); | 256 regcache_raw_collect (regcache, regno, to); |
261 } | 257 } |
262 else if (regno == mips_regnum (gdbarch)->fp_control_status) | 258 else if (regno == mips_regnum (gdbarch)->fp_control_status) |
263 { | 259 { |
264 to = (char *) (*fpregsetp + 32); | 260 to = (char *) (*fpregsetp + 32); |
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
367 | 363 |
368 supply_64bit_reg (regcache, mips_regnum (gdbarch)->pc, | 364 supply_64bit_reg (regcache, mips_regnum (gdbarch)->pc, |
369 (const gdb_byte *) (regp + MIPS64_EF_CP0_EPC)); | 365 (const gdb_byte *) (regp + MIPS64_EF_CP0_EPC)); |
370 supply_64bit_reg (regcache, mips_regnum (gdbarch)->badvaddr, | 366 supply_64bit_reg (regcache, mips_regnum (gdbarch)->badvaddr, |
371 (const gdb_byte *) (regp + MIPS64_EF_CP0_BADVADDR)); | 367 (const gdb_byte *) (regp + MIPS64_EF_CP0_BADVADDR)); |
372 supply_64bit_reg (regcache, MIPS_PS_REGNUM, | 368 supply_64bit_reg (regcache, MIPS_PS_REGNUM, |
373 (const gdb_byte *) (regp + MIPS64_EF_CP0_STATUS)); | 369 (const gdb_byte *) (regp + MIPS64_EF_CP0_STATUS)); |
374 supply_64bit_reg (regcache, mips_regnum (gdbarch)->cause, | 370 supply_64bit_reg (regcache, mips_regnum (gdbarch)->cause, |
375 (const gdb_byte *) (regp + MIPS64_EF_CP0_CAUSE)); | 371 (const gdb_byte *) (regp + MIPS64_EF_CP0_CAUSE)); |
376 | 372 |
377 /* Fill inaccessible registers with zero. */ | 373 /* Fill the inaccessible zero register with zero. */ |
378 regcache_raw_supply (regcache, MIPS_ZERO_REGNUM, zerobuf); | 374 regcache_raw_supply (regcache, MIPS_ZERO_REGNUM, zerobuf); |
379 regcache_raw_supply (regcache, MIPS_UNUSED_REGNUM, zerobuf); | |
380 for (regi = MIPS_FIRST_EMBED_REGNUM; | |
381 regi <= MIPS_LAST_EMBED_REGNUM; | |
382 regi++) | |
383 regcache_raw_supply (regcache, regi, zerobuf); | |
384 } | 375 } |
385 | 376 |
386 static void | 377 static void |
387 mips64_supply_gregset_wrapper (const struct regset *regset, | 378 mips64_supply_gregset_wrapper (const struct regset *regset, |
388 struct regcache *regcache, | 379 struct regcache *regcache, |
389 int regnum, const void *gregs, size_t len) | 380 int regnum, const void *gregs, size_t len) |
390 { | 381 { |
391 gdb_assert (len == sizeof (mips64_elf_gregset_t)); | 382 gdb_assert (len == sizeof (mips64_elf_gregset_t)); |
392 | 383 |
393 mips64_supply_gregset (regcache, (const mips64_elf_gregset_t *)gregs); | 384 mips64_supply_gregset (regcache, (const mips64_elf_gregset_t *)gregs); |
(...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
584 static void | 575 static void |
585 mips64_fill_fpregset_wrapper (const struct regset *regset, | 576 mips64_fill_fpregset_wrapper (const struct regset *regset, |
586 const struct regcache *regcache, | 577 const struct regcache *regcache, |
587 int regnum, void *gregs, size_t len) | 578 int regnum, void *gregs, size_t len) |
588 { | 579 { |
589 gdb_assert (len == sizeof (mips64_elf_fpregset_t)); | 580 gdb_assert (len == sizeof (mips64_elf_fpregset_t)); |
590 | 581 |
591 mips64_fill_fpregset (regcache, (mips64_elf_fpregset_t *)gregs, regnum); | 582 mips64_fill_fpregset (regcache, (mips64_elf_fpregset_t *)gregs, regnum); |
592 } | 583 } |
593 | 584 |
594 const struct regset * | 585 static const struct regset * |
595 mips_linux_regset_from_core_section (struct gdbarch *gdbarch, | 586 mips_linux_regset_from_core_section (struct gdbarch *gdbarch, |
596 const char *sect_name, size_t sect_size) | 587 const char *sect_name, size_t sect_size) |
597 { | 588 { |
598 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); | 589 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); |
599 mips_elf_gregset_t gregset; | 590 mips_elf_gregset_t gregset; |
600 mips_elf_fpregset_t fpregset; | 591 mips_elf_fpregset_t fpregset; |
601 mips64_elf_gregset_t gregset64; | 592 mips64_elf_gregset_t gregset64; |
602 mips64_elf_fpregset_t fpregset64; | 593 mips64_elf_fpregset_t fpregset64; |
603 | 594 |
604 if (strcmp (sect_name, ".reg") == 0) | 595 if (strcmp (sect_name, ".reg") == 0) |
(...skipping 267 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
872 /* The unwinder for o32 signal frames. The legacy structures look | 863 /* The unwinder for o32 signal frames. The legacy structures look |
873 like this: | 864 like this: |
874 | 865 |
875 struct sigframe { | 866 struct sigframe { |
876 u32 sf_ass[4]; [argument save space for o32] | 867 u32 sf_ass[4]; [argument save space for o32] |
877 u32 sf_code[2]; [signal trampoline or fill] | 868 u32 sf_code[2]; [signal trampoline or fill] |
878 struct sigcontext sf_sc; | 869 struct sigcontext sf_sc; |
879 sigset_t sf_mask; | 870 sigset_t sf_mask; |
880 }; | 871 }; |
881 | 872 |
| 873 Pre-2.6.12 sigcontext: |
| 874 |
882 struct sigcontext { | 875 struct sigcontext { |
883 unsigned int sc_regmask; [Unused] | 876 unsigned int sc_regmask; [Unused] |
884 unsigned int sc_status; | 877 unsigned int sc_status; |
885 unsigned long long sc_pc; | 878 unsigned long long sc_pc; |
886 unsigned long long sc_regs[32]; | 879 unsigned long long sc_regs[32]; |
887 unsigned long long sc_fpregs[32]; | 880 unsigned long long sc_fpregs[32]; |
888 unsigned int sc_ownedfp; | 881 unsigned int sc_ownedfp; |
889 unsigned int sc_fpc_csr; | 882 unsigned int sc_fpc_csr; |
890 unsigned int sc_fpc_eir; [Unused] | 883 unsigned int sc_fpc_eir; [Unused] |
891 unsigned int sc_used_math; | 884 unsigned int sc_used_math; |
892 unsigned int sc_ssflags; [Unused] | 885 unsigned int sc_ssflags; [Unused] |
893 [Alignment hole of four bytes] | 886 [Alignment hole of four bytes] |
894 unsigned long long sc_mdhi; | 887 unsigned long long sc_mdhi; |
895 unsigned long long sc_mdlo; | 888 unsigned long long sc_mdlo; |
896 | 889 |
897 unsigned int sc_cause; [Unused] | 890 unsigned int sc_cause; [Unused] |
898 unsigned int sc_badvaddr; [Unused] | 891 unsigned int sc_badvaddr; [Unused] |
899 | 892 |
900 unsigned long sc_sigset[4]; [kernel's sigset_t] | 893 unsigned long sc_sigset[4]; [kernel's sigset_t] |
901 }; | 894 }; |
902 | 895 |
| 896 Post-2.6.12 sigcontext (SmartMIPS/DSP support added): |
| 897 |
| 898 struct sigcontext { |
| 899 unsigned int sc_regmask; [Unused] |
| 900 unsigned int sc_status; [Unused] |
| 901 unsigned long long sc_pc; |
| 902 unsigned long long sc_regs[32]; |
| 903 unsigned long long sc_fpregs[32]; |
| 904 unsigned int sc_acx; |
| 905 unsigned int sc_fpc_csr; |
| 906 unsigned int sc_fpc_eir; [Unused] |
| 907 unsigned int sc_used_math; |
| 908 unsigned int sc_dsp; |
| 909 [Alignment hole of four bytes] |
| 910 unsigned long long sc_mdhi; |
| 911 unsigned long long sc_mdlo; |
| 912 unsigned long sc_hi1; |
| 913 unsigned long sc_lo1; |
| 914 unsigned long sc_hi2; |
| 915 unsigned long sc_lo2; |
| 916 unsigned long sc_hi3; |
| 917 unsigned long sc_lo3; |
| 918 }; |
| 919 |
903 The RT signal frames look like this: | 920 The RT signal frames look like this: |
904 | 921 |
905 struct rt_sigframe { | 922 struct rt_sigframe { |
906 u32 rs_ass[4]; [argument save space for o32] | 923 u32 rs_ass[4]; [argument save space for o32] |
907 u32 rs_code[2] [signal trampoline or fill] | 924 u32 rs_code[2] [signal trampoline or fill] |
908 struct siginfo rs_info; | 925 struct siginfo rs_info; |
909 struct ucontext rs_uc; | 926 struct ucontext rs_uc; |
910 }; | 927 }; |
911 | 928 |
912 struct ucontext { | 929 struct ucontext { |
(...skipping 12 matching lines...) Expand all Loading... |
925 #define STACK_T_SIZE (3 * 4) | 942 #define STACK_T_SIZE (3 * 4) |
926 #define UCONTEXT_SIGCONTEXT_OFFSET (2 * 4 + STACK_T_SIZE + 4) | 943 #define UCONTEXT_SIGCONTEXT_OFFSET (2 * 4 + STACK_T_SIZE + 4) |
927 #define RTSIGFRAME_SIGCONTEXT_OFFSET (SIGFRAME_SIGCONTEXT_OFFSET \ | 944 #define RTSIGFRAME_SIGCONTEXT_OFFSET (SIGFRAME_SIGCONTEXT_OFFSET \ |
928 + RTSIGFRAME_SIGINFO_SIZE \ | 945 + RTSIGFRAME_SIGINFO_SIZE \ |
929 + UCONTEXT_SIGCONTEXT_OFFSET) | 946 + UCONTEXT_SIGCONTEXT_OFFSET) |
930 | 947 |
931 #define SIGCONTEXT_PC (1 * 8) | 948 #define SIGCONTEXT_PC (1 * 8) |
932 #define SIGCONTEXT_REGS (2 * 8) | 949 #define SIGCONTEXT_REGS (2 * 8) |
933 #define SIGCONTEXT_FPREGS (34 * 8) | 950 #define SIGCONTEXT_FPREGS (34 * 8) |
934 #define SIGCONTEXT_FPCSR (66 * 8 + 4) | 951 #define SIGCONTEXT_FPCSR (66 * 8 + 4) |
| 952 #define SIGCONTEXT_DSPCTL (68 * 8 + 0) |
935 #define SIGCONTEXT_HI (69 * 8) | 953 #define SIGCONTEXT_HI (69 * 8) |
936 #define SIGCONTEXT_LO (70 * 8) | 954 #define SIGCONTEXT_LO (70 * 8) |
937 #define SIGCONTEXT_CAUSE (71 * 8 + 0) | 955 #define SIGCONTEXT_CAUSE (71 * 8 + 0) |
938 #define SIGCONTEXT_BADVADDR (71 * 8 + 4) | 956 #define SIGCONTEXT_BADVADDR (71 * 8 + 4) |
| 957 #define SIGCONTEXT_HI1 (71 * 8 + 0) |
| 958 #define SIGCONTEXT_LO1 (71 * 8 + 4) |
| 959 #define SIGCONTEXT_HI2 (72 * 8 + 0) |
| 960 #define SIGCONTEXT_LO2 (72 * 8 + 4) |
| 961 #define SIGCONTEXT_HI3 (73 * 8 + 0) |
| 962 #define SIGCONTEXT_LO3 (73 * 8 + 4) |
939 | 963 |
940 #define SIGCONTEXT_REG_SIZE 8 | 964 #define SIGCONTEXT_REG_SIZE 8 |
941 | 965 |
942 static void | 966 static void |
943 mips_linux_o32_sigframe_init (const struct tramp_frame *self, | 967 mips_linux_o32_sigframe_init (const struct tramp_frame *self, |
944 struct frame_info *this_frame, | 968 struct frame_info *this_frame, |
945 struct trad_frame_cache *this_cache, | 969 struct trad_frame_cache *this_cache, |
946 CORE_ADDR func) | 970 CORE_ADDR func) |
947 { | 971 { |
948 struct gdbarch *gdbarch = get_frame_arch (this_frame); | 972 struct gdbarch *gdbarch = get_frame_arch (this_frame); |
949 int ireg, reg_position; | 973 int ireg; |
950 CORE_ADDR frame_sp = get_frame_sp (this_frame); | 974 CORE_ADDR frame_sp = get_frame_sp (this_frame); |
951 CORE_ADDR sigcontext_base; | 975 CORE_ADDR sigcontext_base; |
952 const struct mips_regnum *regs = mips_regnum (gdbarch); | 976 const struct mips_regnum *regs = mips_regnum (gdbarch); |
953 CORE_ADDR regs_base; | 977 CORE_ADDR regs_base; |
954 | 978 |
955 if (self == &mips_linux_o32_sigframe) | 979 if (self == &mips_linux_o32_sigframe) |
956 sigcontext_base = frame_sp + SIGFRAME_SIGCONTEXT_OFFSET; | 980 sigcontext_base = frame_sp + SIGFRAME_SIGCONTEXT_OFFSET; |
957 else | 981 else |
958 sigcontext_base = frame_sp + RTSIGFRAME_SIGCONTEXT_OFFSET; | 982 sigcontext_base = frame_sp + RTSIGFRAME_SIGCONTEXT_OFFSET; |
959 | 983 |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1003 + (ireg & ~1) * SIGCONTEXT_REG_SIZE); | 1027 + (ireg & ~1) * SIGCONTEXT_REG_SIZE); |
1004 | 1028 |
1005 trad_frame_set_reg_addr (this_cache, | 1029 trad_frame_set_reg_addr (this_cache, |
1006 regs->pc + gdbarch_num_regs (gdbarch), | 1030 regs->pc + gdbarch_num_regs (gdbarch), |
1007 regs_base + SIGCONTEXT_PC); | 1031 regs_base + SIGCONTEXT_PC); |
1008 | 1032 |
1009 trad_frame_set_reg_addr (this_cache, | 1033 trad_frame_set_reg_addr (this_cache, |
1010 regs->fp_control_status | 1034 regs->fp_control_status |
1011 + gdbarch_num_regs (gdbarch), | 1035 + gdbarch_num_regs (gdbarch), |
1012 sigcontext_base + SIGCONTEXT_FPCSR); | 1036 sigcontext_base + SIGCONTEXT_FPCSR); |
| 1037 |
| 1038 if (regs->dspctl != -1) |
| 1039 trad_frame_set_reg_addr (this_cache, |
| 1040 regs->dspctl + gdbarch_num_regs (gdbarch), |
| 1041 sigcontext_base + SIGCONTEXT_DSPCTL); |
| 1042 |
1013 trad_frame_set_reg_addr (this_cache, | 1043 trad_frame_set_reg_addr (this_cache, |
1014 regs->hi + gdbarch_num_regs (gdbarch), | 1044 regs->hi + gdbarch_num_regs (gdbarch), |
1015 regs_base + SIGCONTEXT_HI); | 1045 regs_base + SIGCONTEXT_HI); |
1016 trad_frame_set_reg_addr (this_cache, | 1046 trad_frame_set_reg_addr (this_cache, |
1017 regs->lo + gdbarch_num_regs (gdbarch), | 1047 regs->lo + gdbarch_num_regs (gdbarch), |
1018 regs_base + SIGCONTEXT_LO); | 1048 regs_base + SIGCONTEXT_LO); |
1019 trad_frame_set_reg_addr (this_cache, | 1049 |
1020 » » » regs->cause + gdbarch_num_regs (gdbarch), | 1050 if (regs->dspacc != -1) |
1021 » » » sigcontext_base + SIGCONTEXT_CAUSE); | 1051 { |
1022 trad_frame_set_reg_addr (this_cache, | 1052 trad_frame_set_reg_addr (this_cache, |
1023 » » » regs->badvaddr + gdbarch_num_regs (gdbarch), | 1053 » » » regs->dspacc + 0 + gdbarch_num_regs (gdbarch), |
1024 » » » sigcontext_base + SIGCONTEXT_BADVADDR); | 1054 » » » sigcontext_base + SIGCONTEXT_HI1); |
| 1055 trad_frame_set_reg_addr (this_cache, |
| 1056 » » » regs->dspacc + 1 + gdbarch_num_regs (gdbarch), |
| 1057 » » » sigcontext_base + SIGCONTEXT_LO1); |
| 1058 trad_frame_set_reg_addr (this_cache, |
| 1059 » » » regs->dspacc + 2 + gdbarch_num_regs (gdbarch), |
| 1060 » » » sigcontext_base + SIGCONTEXT_HI2); |
| 1061 trad_frame_set_reg_addr (this_cache, |
| 1062 » » » regs->dspacc + 3 + gdbarch_num_regs (gdbarch), |
| 1063 » » » sigcontext_base + SIGCONTEXT_LO2); |
| 1064 trad_frame_set_reg_addr (this_cache, |
| 1065 » » » regs->dspacc + 4 + gdbarch_num_regs (gdbarch), |
| 1066 » » » sigcontext_base + SIGCONTEXT_HI3); |
| 1067 trad_frame_set_reg_addr (this_cache, |
| 1068 » » » regs->dspacc + 5 + gdbarch_num_regs (gdbarch), |
| 1069 » » » sigcontext_base + SIGCONTEXT_LO3); |
| 1070 } |
| 1071 else |
| 1072 { |
| 1073 trad_frame_set_reg_addr (this_cache, |
| 1074 » » » regs->cause + gdbarch_num_regs (gdbarch), |
| 1075 » » » sigcontext_base + SIGCONTEXT_CAUSE); |
| 1076 trad_frame_set_reg_addr (this_cache, |
| 1077 » » » regs->badvaddr + gdbarch_num_regs (gdbarch), |
| 1078 » » » sigcontext_base + SIGCONTEXT_BADVADDR); |
| 1079 } |
1025 | 1080 |
1026 /* Choice of the bottom of the sigframe is somewhat arbitrary. */ | 1081 /* Choice of the bottom of the sigframe is somewhat arbitrary. */ |
1027 trad_frame_set_id (this_cache, frame_id_build (frame_sp, func)); | 1082 trad_frame_set_id (this_cache, frame_id_build (frame_sp, func)); |
1028 } | 1083 } |
1029 | 1084 |
1030 /* *INDENT-OFF* */ | 1085 /* *INDENT-OFF* */ |
1031 /* For N32/N64 things look different. There is no non-rt signal frame. | 1086 /* For N32/N64 things look different. There is no non-rt signal frame. |
1032 | 1087 |
1033 struct rt_sigframe_n32 { | 1088 struct rt_sigframe_n32 { |
1034 u32 rs_ass[4]; [ argument save space for o32 ] | 1089 u32 rs_ass[4]; [ argument save space for o32 ] |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1092 #define N32_SIGFRAME_SIGCONTEXT_OFFSET (SIGFRAME_SIGCONTEXT_OFFSET \ | 1147 #define N32_SIGFRAME_SIGCONTEXT_OFFSET (SIGFRAME_SIGCONTEXT_OFFSET \ |
1093 + RTSIGFRAME_SIGINFO_SIZE \ | 1148 + RTSIGFRAME_SIGINFO_SIZE \ |
1094 + N32_UCONTEXT_SIGCONTEXT_OFFSET) | 1149 + N32_UCONTEXT_SIGCONTEXT_OFFSET) |
1095 #define N64_SIGFRAME_SIGCONTEXT_OFFSET (SIGFRAME_SIGCONTEXT_OFFSET \ | 1150 #define N64_SIGFRAME_SIGCONTEXT_OFFSET (SIGFRAME_SIGCONTEXT_OFFSET \ |
1096 + RTSIGFRAME_SIGINFO_SIZE \ | 1151 + RTSIGFRAME_SIGINFO_SIZE \ |
1097 + N64_UCONTEXT_SIGCONTEXT_OFFSET) | 1152 + N64_UCONTEXT_SIGCONTEXT_OFFSET) |
1098 | 1153 |
1099 #define N64_SIGCONTEXT_REGS (0 * 8) | 1154 #define N64_SIGCONTEXT_REGS (0 * 8) |
1100 #define N64_SIGCONTEXT_FPREGS (32 * 8) | 1155 #define N64_SIGCONTEXT_FPREGS (32 * 8) |
1101 #define N64_SIGCONTEXT_HI (64 * 8) | 1156 #define N64_SIGCONTEXT_HI (64 * 8) |
| 1157 #define N64_SIGCONTEXT_HI1 (65 * 8) |
| 1158 #define N64_SIGCONTEXT_HI2 (66 * 8) |
| 1159 #define N64_SIGCONTEXT_HI3 (67 * 8) |
1102 #define N64_SIGCONTEXT_LO (68 * 8) | 1160 #define N64_SIGCONTEXT_LO (68 * 8) |
| 1161 #define N64_SIGCONTEXT_LO1 (69 * 8) |
| 1162 #define N64_SIGCONTEXT_LO2 (70 * 8) |
| 1163 #define N64_SIGCONTEXT_LO3 (71 * 8) |
1103 #define N64_SIGCONTEXT_PC (72 * 8) | 1164 #define N64_SIGCONTEXT_PC (72 * 8) |
1104 #define N64_SIGCONTEXT_FPCSR (73 * 8) | 1165 #define N64_SIGCONTEXT_FPCSR (73 * 8 + 0) |
| 1166 #define N64_SIGCONTEXT_DSPCTL (74 * 8 + 0) |
1105 | 1167 |
1106 #define N64_SIGCONTEXT_REG_SIZE 8 | 1168 #define N64_SIGCONTEXT_REG_SIZE 8 |
1107 | 1169 |
1108 static void | 1170 static void |
1109 mips_linux_n32n64_sigframe_init (const struct tramp_frame *self, | 1171 mips_linux_n32n64_sigframe_init (const struct tramp_frame *self, |
1110 struct frame_info *this_frame, | 1172 struct frame_info *this_frame, |
1111 struct trad_frame_cache *this_cache, | 1173 struct trad_frame_cache *this_cache, |
1112 CORE_ADDR func) | 1174 CORE_ADDR func) |
1113 { | 1175 { |
1114 struct gdbarch *gdbarch = get_frame_arch (this_frame); | 1176 struct gdbarch *gdbarch = get_frame_arch (this_frame); |
1115 int ireg, reg_position; | 1177 int ireg; |
1116 CORE_ADDR frame_sp = get_frame_sp (this_frame); | 1178 CORE_ADDR frame_sp = get_frame_sp (this_frame); |
1117 CORE_ADDR sigcontext_base; | 1179 CORE_ADDR sigcontext_base; |
1118 const struct mips_regnum *regs = mips_regnum (gdbarch); | 1180 const struct mips_regnum *regs = mips_regnum (gdbarch); |
1119 | 1181 |
1120 if (self == &mips_linux_n32_rt_sigframe) | 1182 if (self == &mips_linux_n32_rt_sigframe) |
1121 sigcontext_base = frame_sp + N32_SIGFRAME_SIGCONTEXT_OFFSET; | 1183 sigcontext_base = frame_sp + N32_SIGFRAME_SIGCONTEXT_OFFSET; |
1122 else | 1184 else |
1123 sigcontext_base = frame_sp + N64_SIGFRAME_SIGCONTEXT_OFFSET; | 1185 sigcontext_base = frame_sp + N64_SIGFRAME_SIGCONTEXT_OFFSET; |
1124 | 1186 |
1125 if (mips_linux_restart_reg_p (gdbarch)) | 1187 if (mips_linux_restart_reg_p (gdbarch)) |
(...skipping 17 matching lines...) Expand all Loading... |
1143 + ireg * N64_SIGCONTEXT_REG_SIZE); | 1205 + ireg * N64_SIGCONTEXT_REG_SIZE); |
1144 | 1206 |
1145 trad_frame_set_reg_addr (this_cache, | 1207 trad_frame_set_reg_addr (this_cache, |
1146 regs->pc + gdbarch_num_regs (gdbarch), | 1208 regs->pc + gdbarch_num_regs (gdbarch), |
1147 sigcontext_base + N64_SIGCONTEXT_PC); | 1209 sigcontext_base + N64_SIGCONTEXT_PC); |
1148 | 1210 |
1149 trad_frame_set_reg_addr (this_cache, | 1211 trad_frame_set_reg_addr (this_cache, |
1150 regs->fp_control_status | 1212 regs->fp_control_status |
1151 + gdbarch_num_regs (gdbarch), | 1213 + gdbarch_num_regs (gdbarch), |
1152 sigcontext_base + N64_SIGCONTEXT_FPCSR); | 1214 sigcontext_base + N64_SIGCONTEXT_FPCSR); |
| 1215 |
1153 trad_frame_set_reg_addr (this_cache, | 1216 trad_frame_set_reg_addr (this_cache, |
1154 regs->hi + gdbarch_num_regs (gdbarch), | 1217 regs->hi + gdbarch_num_regs (gdbarch), |
1155 sigcontext_base + N64_SIGCONTEXT_HI); | 1218 sigcontext_base + N64_SIGCONTEXT_HI); |
1156 trad_frame_set_reg_addr (this_cache, | 1219 trad_frame_set_reg_addr (this_cache, |
1157 regs->lo + gdbarch_num_regs (gdbarch), | 1220 regs->lo + gdbarch_num_regs (gdbarch), |
1158 sigcontext_base + N64_SIGCONTEXT_LO); | 1221 sigcontext_base + N64_SIGCONTEXT_LO); |
1159 | 1222 |
| 1223 if (regs->dspacc != -1) |
| 1224 { |
| 1225 trad_frame_set_reg_addr (this_cache, |
| 1226 regs->dspacc + 0 + gdbarch_num_regs (gdbarch), |
| 1227 sigcontext_base + N64_SIGCONTEXT_HI1); |
| 1228 trad_frame_set_reg_addr (this_cache, |
| 1229 regs->dspacc + 1 + gdbarch_num_regs (gdbarch), |
| 1230 sigcontext_base + N64_SIGCONTEXT_LO1); |
| 1231 trad_frame_set_reg_addr (this_cache, |
| 1232 regs->dspacc + 2 + gdbarch_num_regs (gdbarch), |
| 1233 sigcontext_base + N64_SIGCONTEXT_HI2); |
| 1234 trad_frame_set_reg_addr (this_cache, |
| 1235 regs->dspacc + 3 + gdbarch_num_regs (gdbarch), |
| 1236 sigcontext_base + N64_SIGCONTEXT_LO2); |
| 1237 trad_frame_set_reg_addr (this_cache, |
| 1238 regs->dspacc + 4 + gdbarch_num_regs (gdbarch), |
| 1239 sigcontext_base + N64_SIGCONTEXT_HI3); |
| 1240 trad_frame_set_reg_addr (this_cache, |
| 1241 regs->dspacc + 5 + gdbarch_num_regs (gdbarch), |
| 1242 sigcontext_base + N64_SIGCONTEXT_LO3); |
| 1243 } |
| 1244 if (regs->dspctl != -1) |
| 1245 trad_frame_set_reg_addr (this_cache, |
| 1246 regs->dspctl + gdbarch_num_regs (gdbarch), |
| 1247 sigcontext_base + N64_SIGCONTEXT_DSPCTL); |
| 1248 |
1160 /* Choice of the bottom of the sigframe is somewhat arbitrary. */ | 1249 /* Choice of the bottom of the sigframe is somewhat arbitrary. */ |
1161 trad_frame_set_id (this_cache, frame_id_build (frame_sp, func)); | 1250 trad_frame_set_id (this_cache, frame_id_build (frame_sp, func)); |
1162 } | 1251 } |
1163 | 1252 |
| 1253 /* Implement the "write_pc" gdbarch method. */ |
| 1254 |
1164 static void | 1255 static void |
1165 mips_linux_write_pc (struct regcache *regcache, CORE_ADDR pc) | 1256 mips_linux_write_pc (struct regcache *regcache, CORE_ADDR pc) |
1166 { | 1257 { |
1167 struct gdbarch *gdbarch = get_regcache_arch (regcache); | 1258 struct gdbarch *gdbarch = get_regcache_arch (regcache); |
1168 regcache_cooked_write_unsigned (regcache, gdbarch_pc_regnum (gdbarch), pc); | 1259 |
| 1260 mips_write_pc (regcache, pc); |
1169 | 1261 |
1170 /* Clear the syscall restart flag. */ | 1262 /* Clear the syscall restart flag. */ |
1171 if (mips_linux_restart_reg_p (gdbarch)) | 1263 if (mips_linux_restart_reg_p (gdbarch)) |
1172 regcache_cooked_write_unsigned (regcache, MIPS_RESTART_REGNUM, 0); | 1264 regcache_cooked_write_unsigned (regcache, MIPS_RESTART_REGNUM, 0); |
1173 } | 1265 } |
1174 | 1266 |
1175 /* Return 1 if MIPS_RESTART_REGNUM is usable. */ | 1267 /* Return 1 if MIPS_RESTART_REGNUM is usable. */ |
1176 | 1268 |
1177 int | 1269 int |
1178 mips_linux_restart_reg_p (struct gdbarch *gdbarch) | 1270 mips_linux_restart_reg_p (struct gdbarch *gdbarch) |
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1232 | 1324 |
1233 /* Getting the system call number from the register. | 1325 /* Getting the system call number from the register. |
1234 syscall number is in v0 or $2. */ | 1326 syscall number is in v0 or $2. */ |
1235 regcache_cooked_read (regcache, MIPS_V0_REGNUM, buf); | 1327 regcache_cooked_read (regcache, MIPS_V0_REGNUM, buf); |
1236 | 1328 |
1237 ret = extract_signed_integer (buf, regsize, byte_order); | 1329 ret = extract_signed_integer (buf, regsize, byte_order); |
1238 | 1330 |
1239 return ret; | 1331 return ret; |
1240 } | 1332 } |
1241 | 1333 |
| 1334 /* Translate signals based on MIPS signal values. |
| 1335 Adapted from gdb/common/signals.c. */ |
| 1336 |
| 1337 static enum gdb_signal |
| 1338 mips_gdb_signal_from_target (struct gdbarch *gdbarch, int signo) |
| 1339 { |
| 1340 switch (signo) |
| 1341 { |
| 1342 case 0: |
| 1343 return GDB_SIGNAL_0; |
| 1344 case MIPS_SIGHUP: |
| 1345 return GDB_SIGNAL_HUP; |
| 1346 case MIPS_SIGINT: |
| 1347 return GDB_SIGNAL_INT; |
| 1348 case MIPS_SIGQUIT: |
| 1349 return GDB_SIGNAL_QUIT; |
| 1350 case MIPS_SIGILL: |
| 1351 return GDB_SIGNAL_ILL; |
| 1352 case MIPS_SIGTRAP: |
| 1353 return GDB_SIGNAL_TRAP; |
| 1354 case MIPS_SIGABRT: |
| 1355 return GDB_SIGNAL_ABRT; |
| 1356 case MIPS_SIGEMT: |
| 1357 return GDB_SIGNAL_EMT; |
| 1358 case MIPS_SIGFPE: |
| 1359 return GDB_SIGNAL_FPE; |
| 1360 case MIPS_SIGKILL: |
| 1361 return GDB_SIGNAL_KILL; |
| 1362 case MIPS_SIGBUS: |
| 1363 return GDB_SIGNAL_BUS; |
| 1364 case MIPS_SIGSEGV: |
| 1365 return GDB_SIGNAL_SEGV; |
| 1366 case MIPS_SIGSYS: |
| 1367 return GDB_SIGNAL_SYS; |
| 1368 case MIPS_SIGPIPE: |
| 1369 return GDB_SIGNAL_PIPE; |
| 1370 case MIPS_SIGALRM: |
| 1371 return GDB_SIGNAL_ALRM; |
| 1372 case MIPS_SIGTERM: |
| 1373 return GDB_SIGNAL_TERM; |
| 1374 case MIPS_SIGUSR1: |
| 1375 return GDB_SIGNAL_USR1; |
| 1376 case MIPS_SIGUSR2: |
| 1377 return GDB_SIGNAL_USR2; |
| 1378 case MIPS_SIGCHLD: |
| 1379 return GDB_SIGNAL_CHLD; |
| 1380 case MIPS_SIGPWR: |
| 1381 return GDB_SIGNAL_PWR; |
| 1382 case MIPS_SIGWINCH: |
| 1383 return GDB_SIGNAL_WINCH; |
| 1384 case MIPS_SIGURG: |
| 1385 return GDB_SIGNAL_URG; |
| 1386 case MIPS_SIGPOLL: |
| 1387 return GDB_SIGNAL_POLL; |
| 1388 case MIPS_SIGSTOP: |
| 1389 return GDB_SIGNAL_STOP; |
| 1390 case MIPS_SIGTSTP: |
| 1391 return GDB_SIGNAL_TSTP; |
| 1392 case MIPS_SIGCONT: |
| 1393 return GDB_SIGNAL_CONT; |
| 1394 case MIPS_SIGTTIN: |
| 1395 return GDB_SIGNAL_TTIN; |
| 1396 case MIPS_SIGTTOU: |
| 1397 return GDB_SIGNAL_TTOU; |
| 1398 case MIPS_SIGVTALRM: |
| 1399 return GDB_SIGNAL_VTALRM; |
| 1400 case MIPS_SIGPROF: |
| 1401 return GDB_SIGNAL_PROF; |
| 1402 case MIPS_SIGXCPU: |
| 1403 return GDB_SIGNAL_XCPU; |
| 1404 case MIPS_SIGXFSZ: |
| 1405 return GDB_SIGNAL_XFSZ; |
| 1406 } |
| 1407 |
| 1408 if (signo >= MIPS_SIGRTMIN && signo <= MIPS_SIGRTMAX) |
| 1409 { |
| 1410 /* GDB_SIGNAL_REALTIME values are not contiguous, map parts of |
| 1411 the MIPS block to the respective GDB_SIGNAL_REALTIME blocks. */ |
| 1412 signo -= MIPS_SIGRTMIN; |
| 1413 if (signo == 0) |
| 1414 return GDB_SIGNAL_REALTIME_32; |
| 1415 else if (signo < 32) |
| 1416 return ((enum gdb_signal) (signo - 1 + (int) GDB_SIGNAL_REALTIME_33)); |
| 1417 else |
| 1418 return ((enum gdb_signal) (signo - 32 + (int) GDB_SIGNAL_REALTIME_64)); |
| 1419 } |
| 1420 |
| 1421 return GDB_SIGNAL_UNKNOWN; |
| 1422 } |
| 1423 |
1242 /* Initialize one of the GNU/Linux OS ABIs. */ | 1424 /* Initialize one of the GNU/Linux OS ABIs. */ |
1243 | 1425 |
1244 static void | 1426 static void |
1245 mips_linux_init_abi (struct gdbarch_info info, | 1427 mips_linux_init_abi (struct gdbarch_info info, |
1246 struct gdbarch *gdbarch) | 1428 struct gdbarch *gdbarch) |
1247 { | 1429 { |
1248 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); | 1430 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); |
1249 enum mips_abi abi = mips_abi (gdbarch); | 1431 enum mips_abi abi = mips_abi (gdbarch); |
1250 struct tdesc_arch_data *tdesc_data = (void *) info.tdep_info; | 1432 struct tdesc_arch_data *tdesc_data = (void *) info.tdep_info; |
1251 | 1433 |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1316 set_solib_ops (gdbarch, &mips_svr4_so_ops); | 1498 set_solib_ops (gdbarch, &mips_svr4_so_ops); |
1317 | 1499 |
1318 set_gdbarch_write_pc (gdbarch, mips_linux_write_pc); | 1500 set_gdbarch_write_pc (gdbarch, mips_linux_write_pc); |
1319 | 1501 |
1320 set_gdbarch_core_read_description (gdbarch, | 1502 set_gdbarch_core_read_description (gdbarch, |
1321 mips_linux_core_read_description); | 1503 mips_linux_core_read_description); |
1322 | 1504 |
1323 set_gdbarch_regset_from_core_section (gdbarch, | 1505 set_gdbarch_regset_from_core_section (gdbarch, |
1324 mips_linux_regset_from_core_section); | 1506 mips_linux_regset_from_core_section); |
1325 | 1507 |
| 1508 set_gdbarch_gdb_signal_from_target (gdbarch, |
| 1509 mips_gdb_signal_from_target); |
| 1510 |
1326 tdep->syscall_next_pc = mips_linux_syscall_next_pc; | 1511 tdep->syscall_next_pc = mips_linux_syscall_next_pc; |
1327 | 1512 |
1328 if (tdesc_data) | 1513 if (tdesc_data) |
1329 { | 1514 { |
1330 const struct tdesc_feature *feature; | 1515 const struct tdesc_feature *feature; |
1331 | 1516 |
1332 /* If we have target-described registers, then we can safely | 1517 /* If we have target-described registers, then we can safely |
1333 reserve a number for MIPS_RESTART_REGNUM (whether it is | 1518 reserve a number for MIPS_RESTART_REGNUM (whether it is |
1334 described or not). */ | 1519 described or not). */ |
1335 gdb_assert (gdbarch_num_regs (gdbarch) <= MIPS_RESTART_REGNUM); | 1520 gdb_assert (gdbarch_num_regs (gdbarch) <= MIPS_RESTART_REGNUM); |
1336 set_gdbarch_num_regs (gdbarch, MIPS_RESTART_REGNUM + 1); | 1521 set_gdbarch_num_regs (gdbarch, MIPS_RESTART_REGNUM + 1); |
| 1522 set_gdbarch_num_pseudo_regs (gdbarch, MIPS_RESTART_REGNUM + 1); |
1337 | 1523 |
1338 /* If it's present, then assign it to the reserved number. */ | 1524 /* If it's present, then assign it to the reserved number. */ |
1339 feature = tdesc_find_feature (info.target_desc, | 1525 feature = tdesc_find_feature (info.target_desc, |
1340 "org.gnu.gdb.mips.linux"); | 1526 "org.gnu.gdb.mips.linux"); |
1341 if (feature != NULL) | 1527 if (feature != NULL) |
1342 tdesc_numbered_register (feature, tdesc_data, MIPS_RESTART_REGNUM, | 1528 tdesc_numbered_register (feature, tdesc_data, MIPS_RESTART_REGNUM, |
1343 "restart"); | 1529 "restart"); |
1344 } | 1530 } |
1345 } | 1531 } |
1346 | 1532 |
1347 /* Provide a prototype to silence -Wmissing-prototypes. */ | 1533 /* Provide a prototype to silence -Wmissing-prototypes. */ |
1348 extern initialize_file_ftype _initialize_mips_linux_tdep; | 1534 extern initialize_file_ftype _initialize_mips_linux_tdep; |
1349 | 1535 |
1350 void | 1536 void |
1351 _initialize_mips_linux_tdep (void) | 1537 _initialize_mips_linux_tdep (void) |
1352 { | 1538 { |
1353 const struct bfd_arch_info *arch_info; | 1539 const struct bfd_arch_info *arch_info; |
1354 | 1540 |
1355 for (arch_info = bfd_lookup_arch (bfd_arch_mips, 0); | 1541 for (arch_info = bfd_lookup_arch (bfd_arch_mips, 0); |
1356 arch_info != NULL; | 1542 arch_info != NULL; |
1357 arch_info = arch_info->next) | 1543 arch_info = arch_info->next) |
1358 { | 1544 { |
1359 gdbarch_register_osabi (bfd_arch_mips, arch_info->mach, | 1545 gdbarch_register_osabi (bfd_arch_mips, arch_info->mach, |
1360 GDB_OSABI_LINUX, | 1546 GDB_OSABI_LINUX, |
1361 mips_linux_init_abi); | 1547 mips_linux_init_abi); |
1362 } | 1548 } |
1363 } | 1549 } |
OLD | NEW |