GDB (API)
/home/stan/gdb/src/gdb/armbsd-tdep.c
Go to the documentation of this file.
00001 /* Target-dependent code for ARM BSD's.
00002 
00003    Copyright (C) 2006-2013 Free Software Foundation, Inc.
00004 
00005    This file is part of GDB.
00006 
00007    This program is free software; you can redistribute it and/or modify
00008    it under the terms of the GNU General Public License as published by
00009    the Free Software Foundation; either version 3 of the License, or
00010    (at your option) any later version.
00011 
00012    This program is distributed in the hope that it will be useful,
00013    but WITHOUT ANY WARRANTY; without even the implied warranty of
00014    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015    GNU General Public License for more details.
00016 
00017    You should have received a copy of the GNU General Public License
00018    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
00019 
00020 #include "defs.h"
00021 #include "osabi.h"
00022 #include "regcache.h"
00023 #include "regset.h"
00024 
00025 #include "gdb_assert.h"
00026 #include "gdb_string.h"
00027 
00028 #include "arm-tdep.h"
00029 
00030 /* Core file support.  */
00031 
00032 /* Sizeof `struct reg' in <machine/reg.h>.  */
00033 #define ARMBSD_SIZEOF_GREGS     (17 * 4)
00034 
00035 /* Sizeof `struct fpreg' in <machine/reg.h.  */
00036 #define ARMBSD_SIZEOF_FPREGS    ((1 + (8 * 3)) * 4)
00037 
00038 static int
00039 armbsd_fpreg_offset (int regnum)
00040 {
00041   if (regnum == ARM_FPS_REGNUM)
00042     return 0;
00043 
00044   return 4 + (regnum - ARM_F0_REGNUM) * 12;
00045 }
00046 
00047 /* Supply register REGNUM from the buffer specified by FPREGS and LEN
00048    in the floating-point register set REGSET to register cache
00049    REGCACHE.  If REGNUM is -1, do this for all registers in REGSET.  */
00050 
00051 static void
00052 armbsd_supply_fpregset (const struct regset *regset,
00053                         struct regcache *regcache,
00054                         int regnum, const void *fpregs, size_t len)
00055 {
00056   const gdb_byte *regs = fpregs;
00057   int i;
00058 
00059   gdb_assert (len >= ARMBSD_SIZEOF_FPREGS);
00060 
00061   for (i = ARM_F0_REGNUM; i <= ARM_FPS_REGNUM; i++)
00062     {
00063       if (regnum == i || regnum == -1)
00064         regcache_raw_supply (regcache, i, regs + armbsd_fpreg_offset (i));
00065     }
00066 }
00067 
00068 /* Supply register REGNUM from the buffer specified by GREGS and LEN
00069    in the general-purpose register set REGSET to register cache
00070    REGCACHE.  If REGNUM is -1, do this for all registers in REGSET.  */
00071 
00072 static void
00073 armbsd_supply_gregset (const struct regset *regset,
00074                        struct regcache *regcache,
00075                        int regnum, const void *gregs, size_t len)
00076 {
00077   const gdb_byte *regs = gregs;
00078   int i;
00079 
00080   gdb_assert (len >= ARMBSD_SIZEOF_GREGS);
00081 
00082   for (i = ARM_A1_REGNUM; i <= ARM_PC_REGNUM; i++)
00083     {
00084       if (regnum == i || regnum == -1)
00085         regcache_raw_supply (regcache, i, regs + i * 4);
00086     }
00087 
00088   if (regnum == ARM_PS_REGNUM || regnum == -1)
00089     regcache_raw_supply (regcache, i, regs + 16 * 4);
00090 
00091   if (len >= ARMBSD_SIZEOF_GREGS + ARMBSD_SIZEOF_FPREGS)
00092     {
00093       regs += ARMBSD_SIZEOF_GREGS;
00094       len -= ARMBSD_SIZEOF_GREGS;
00095       armbsd_supply_fpregset (regset, regcache, regnum, regs, len);
00096     }
00097 }
00098 
00099 /* ARM register sets.  */
00100 
00101 static struct regset armbsd_gregset =
00102 {
00103   NULL,
00104   armbsd_supply_gregset
00105 };
00106 
00107 static struct regset armbsd_fpregset =
00108 {
00109   NULL,
00110   armbsd_supply_fpregset
00111 };
00112 
00113 /* Return the appropriate register set for the core section identified
00114    by SECT_NAME and SECT_SIZE.  */
00115 
00116 const struct regset *
00117 armbsd_regset_from_core_section (struct gdbarch *gdbarch,
00118                                  const char *sect_name, size_t sect_size)
00119 {
00120   if (strcmp (sect_name, ".reg") == 0 && sect_size >= ARMBSD_SIZEOF_GREGS)
00121     return &armbsd_gregset;
00122 
00123   if (strcmp (sect_name, ".reg2") == 0 && sect_size >= ARMBSD_SIZEOF_FPREGS)
00124     return &armbsd_fpregset;
00125 
00126   return NULL;
00127 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines