Example #1
0
CORE_ADDR
get_pc_function_start (CORE_ADDR pc)
{
  struct block *bl;
  struct minimal_symbol *msymbol;

  bl = block_for_pc (pc);
  if (bl)
    {
      struct symbol *symbol = block_linkage_function (bl);

      if (symbol)
	{
	  bl = SYMBOL_BLOCK_VALUE (symbol);
	  return BLOCK_START (bl);
	}
    }

  msymbol = lookup_minimal_symbol_by_pc (pc);
  if (msymbol)
    {
      CORE_ADDR fstart = SYMBOL_VALUE_ADDRESS (msymbol);

      if (find_pc_section (fstart))
	return fstart;
    }

  return 0;
}
/* Return the innermost lexical block containing the specified pc value,
   or 0 if there is none.  */
PyObject *
gdbpy_block_for_pc (PyObject *self, PyObject *args)
{
  unsigned PY_LONG_LONG pc;
  struct block *block;
  struct obj_section *section;
  struct symtab *symtab;

  if (!PyArg_ParseTuple (args, "K", &pc))
    return NULL;

  section = find_pc_mapped_section (pc);
  symtab = find_pc_sect_symtab (pc, section);
  if (!symtab || symtab->objfile == NULL)
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _("Cannot locate object file for block."));
      return NULL;
    }

  block = block_for_pc (pc);
  if (block)
    return block_to_block_object (block, symtab->objfile);

  Py_RETURN_NONE;
}
Example #3
0
static struct mdebug_extra_func_info *
find_proc_desc (CORE_ADDR pc)
{
  struct block *b = block_for_pc (pc);
  struct mdebug_extra_func_info *proc_desc = NULL;
  struct symbol *sym = NULL;

  if (b)
    {
      CORE_ADDR startaddr;
      find_pc_partial_function (pc, NULL, &startaddr, NULL);

      if (startaddr > BLOCK_START (b))
	/* This is the "pathological" case referred to in a comment in
	   print_frame_info.  It might be better to move this check into
	   symbol reading.  */
	sym = NULL;
      else
	sym = lookup_symbol (MDEBUG_EFI_SYMBOL_NAME, b, LABEL_DOMAIN, 0, NULL);
    }

  if (sym)
    {
      proc_desc = (struct mdebug_extra_func_info *) SYMBOL_VALUE (sym);

      /* If we never found a PDR for this function in symbol reading,
	 then examine prologues to find the information.  */
      if (proc_desc->pdr.framereg == -1)
	proc_desc = NULL;
    }

  return proc_desc;
}
Example #4
0
/* Implementation of
   gdb.lookup_symbol (name [, block] [, domain]) -> (symbol, is_field_of_this)
   A tuple with 2 elements is always returned.  The first is the symbol
   object or None, the second is a boolean with the value of
   is_a_field_of_this (see comment in lookup_symbol_in_language).  */
PyObject *
gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw)
{
    int domain = VAR_DOMAIN, is_a_field_of_this = 0;
    const char *name;
    static char *keywords[] = { "name", "block", "domain", NULL };
    struct symbol *symbol;
    PyObject *block_obj = NULL, *ret_tuple, *sym_obj, *bool_obj;
    struct block *block = NULL;

    if (! PyArg_ParseTupleAndKeywords (args, kw, "s|O!i", keywords, &name,
                                       &block_object_type, &block_obj, &domain))
        return NULL;

    if (block_obj)
        block = block_object_to_block (block_obj);
    else
    {
        struct frame_info *selected_frame;
        volatile struct gdb_exception except;

        TRY_CATCH (except, RETURN_MASK_ALL)
        {
            selected_frame  = get_selected_frame (_("No frame selected."));
            block = block_for_pc (get_frame_address_in_block (selected_frame));
        }
        GDB_PY_HANDLE_EXCEPTION (except);
    }
Example #5
0
struct block *
get_frame_block (struct frame_info *frame, CORE_ADDR *addr_in_block)
{
  CORE_ADDR pc;
  struct block *bl;
  int inline_count;

  if (!get_frame_address_in_block_if_available (frame, &pc))
    return NULL;

  if (addr_in_block)
    *addr_in_block = pc;

  bl = block_for_pc (pc);
  if (bl == NULL)
    return NULL;

  inline_count = frame_inlined_callees (frame);

  while (inline_count > 0)
    {
      if (block_inlined_p (bl))
	inline_count--;

      bl = BLOCK_SUPERBLOCK (bl);
      gdb_assert (bl != NULL);
    }

  return bl;
}
Example #6
0
CORE_ADDR
get_pc_function_start (CORE_ADDR pc)
{
  struct block *bl;
  struct minimal_symbol *msymbol;

  bl = block_for_pc (pc);
  if (bl)
    {
      struct symbol *symbol = block_function (bl);

      if (symbol)
	{
	  bl = SYMBOL_BLOCK_VALUE (symbol);
	  /* APPLE LOCAL begin address ranges  */
	  return BLOCK_LOWEST_PC (bl);
	  /* APPLE LOCAL end address ranges  */
	}
    }

  msymbol = lookup_minimal_symbol_by_pc (pc);
  if (msymbol)
    {
      CORE_ADDR fstart = SYMBOL_VALUE_ADDRESS (msymbol);

      if (find_pc_section (fstart))
	return fstart;
    }

  return 0;
}
Example #7
0
struct block *
get_frame_block (struct frame_info *frame, CORE_ADDR *addr_in_block)
{
  const CORE_ADDR pc = get_frame_address_in_block (frame);

  if (addr_in_block)
    *addr_in_block = pc;

  return block_for_pc (pc);
}
Example #8
0
static int
wrap_block_for_pc (char *opaque_arg)
{
  struct gdb_wrapper_arguments **args = (struct gdb_wrapper_arguments **) opaque_arg;
  CORE_ADDR pc;

  pc = *(CORE_ADDR *) (*args)->args[0].ptr;
  (*args)->result.cstptr = block_for_pc (pc);
  return 1;
}
Example #9
0
struct block *
get_frame_block (struct frame_info *frame)
{
  CORE_ADDR pc;

  pc = frame->pc;
  if (frame->next != 0 && frame->next->signal_handler_caller == 0)
    /* We are not in the innermost frame and we were not interrupted
       by a signal.  We need to subtract one to get the correct block,
       in case the call instruction was the last instruction of the block.
       If there are any machines on which the saved pc does not point to
       after the call insn, we probably want to make frame->pc point after
       the call insn anyway.  */
    --pc;
  return block_for_pc (pc);
}
Example #10
0
static struct mdebug_extra_func_info *
find_proc_desc (CORE_ADDR pc)
{
  const struct block *b = block_for_pc (pc);
  struct mdebug_extra_func_info *proc_desc = NULL;
  struct symbol *sym = NULL;
  const char *sh_name = NULL;

  if (b)
    {
      CORE_ADDR startaddr;
      find_pc_partial_function (pc, &sh_name, &startaddr, NULL);

      if (startaddr > BLOCK_START (b))
	/* This is the "pathological" case referred to in a comment in
	   print_frame_info.  It might be better to move this check into
	   symbol reading.  */
	sym = NULL;
      else
	sym = lookup_symbol (MDEBUG_EFI_SYMBOL_NAME, b, LABEL_DOMAIN,
			     0).symbol;
    }

  if (sym)
    {
      proc_desc = (struct mdebug_extra_func_info *) SYMBOL_VALUE_BYTES (sym);

      /* Correct incorrect setjmp procedure descriptor from the library
         to make backtrace through setjmp work.  */
      if (proc_desc->pdr.pcreg == 0
	  && strcmp (sh_name, "setjmp") == 0)
	{
	  proc_desc->pdr.pcreg = ALPHA_RA_REGNUM;
	  proc_desc->pdr.regmask = 0x80000000;
	  proc_desc->pdr.regoffset = -4;
	}

      /* If we never found a PDR for this function in symbol reading,
	 then examine prologues to find the information.  */
      if (proc_desc->pdr.framereg == -1)
	proc_desc = NULL;
    }

  return proc_desc;
}
Example #11
0
/* Return the innermost lexical block containing the specified pc value,
   or 0 if there is none.  */
PyObject *
gdbpy_block_for_pc (PyObject *self, PyObject *args)
{
  gdb_py_ulongest pc;
  const struct block *block = NULL;
  struct compunit_symtab *cust = NULL;
  volatile struct gdb_exception except;

  if (!PyArg_ParseTuple (args, GDB_PY_LLU_ARG, &pc))
    return NULL;

  TRY_CATCH (except, RETURN_MASK_ALL)
    {
      cust = find_pc_compunit_symtab (pc);

      if (cust != NULL && COMPUNIT_OBJFILE (cust) != NULL)
	block = block_for_pc (pc);
    }
Example #12
0
/* Return the innermost lexical block containing the specified pc value,
   or 0 if there is none.  */
PyObject *
gdbpy_block_for_pc (PyObject *self, PyObject *args)
{
  gdb_py_ulongest pc;
  struct block *block = NULL;
  struct obj_section *section = NULL;
  struct symtab *symtab = NULL;
  volatile struct gdb_exception except;

  if (!PyArg_ParseTuple (args, GDB_PY_LLU_ARG, &pc))
    return NULL;

  TRY_CATCH (except, RETURN_MASK_ALL)
    {
      section = find_pc_mapped_section (pc);
      symtab = find_pc_sect_symtab (pc, section);

      if (symtab != NULL && symtab->objfile != NULL)
	block = block_for_pc (pc);
    }
Example #13
0
CORE_ADDR
get_pc_function_start (CORE_ADDR pc)
{
  register struct block *bl;
  register struct symbol *symbol;
  register struct minimal_symbol *msymbol;
  CORE_ADDR fstart;

  if ((bl = block_for_pc (pc)) != NULL &&
      (symbol = block_function (bl)) != NULL)
    {
      bl = SYMBOL_BLOCK_VALUE (symbol);
      fstart = BLOCK_START (bl);
    }
  else if ((msymbol = lookup_minimal_symbol_by_pc (pc)) != NULL)
    {
      fstart = SYMBOL_VALUE_ADDRESS (msymbol);
    }
  else
    {
      fstart = 0;
    }
  return (fstart);
}
Example #14
0
static struct mdebug_extra_func_info *
non_heuristic_proc_desc (CORE_ADDR pc, CORE_ADDR *addrptr)
{
    CORE_ADDR startaddr;
    struct mdebug_extra_func_info *proc_desc;
    struct block *b = block_for_pc (pc);
    struct symbol *sym;
    struct obj_section *sec;
    struct mips_objfile_private *priv;

    find_pc_partial_function (pc, NULL, &startaddr, NULL);
    if (addrptr)
        *addrptr = startaddr;

    priv = NULL;

    sec = find_pc_section (pc);
    if (sec != NULL)
    {
        priv = (struct mips_objfile_private *) objfile_data (sec->objfile, mips_pdr_data);

        /* Search the ".pdr" section generated by GAS.  This includes most of
           the information normally found in ECOFF PDRs.  */

        the_bfd = sec->objfile->obfd;
        if (priv == NULL
                && (the_bfd->format == bfd_object
                    && bfd_get_flavour (the_bfd) == bfd_target_elf_flavour
                    && elf_elfheader (the_bfd)->e_ident[EI_CLASS] == ELFCLASS64))
        {
            /* Right now GAS only outputs the address as a four-byte sequence.
               This means that we should not bother with this method on 64-bit
               targets (until that is fixed).  */

            priv = obstack_alloc (&sec->objfile->objfile_obstack,
                                  sizeof (struct mips_objfile_private));
            priv->size = 0;
            set_objfile_data (sec->objfile, mips_pdr_data, priv);
        }
        else if (priv == NULL)
        {
            asection *bfdsec;

            priv = obstack_alloc (&sec->objfile->objfile_obstack,
                                  sizeof (struct mips_objfile_private));

            bfdsec = bfd_get_section_by_name (sec->objfile->obfd, ".pdr");
            if (bfdsec != NULL)
            {
                priv->size = bfd_section_size (sec->objfile->obfd, bfdsec);
                priv->contents = obstack_alloc (&sec->objfile->objfile_obstack,
                                                priv->size);
                bfd_get_section_contents (sec->objfile->obfd, bfdsec,
                                          priv->contents, 0, priv->size);

                /* In general, the .pdr section is sorted.  However, in the
                   presence of multiple code sections (and other corner cases)
                   it can become unsorted.  Sort it so that we can use a faster
                   binary search.  */
                qsort (priv->contents, priv->size / 32, 32,
                       compare_pdr_entries);
            }
            else
                priv->size = 0;

            set_objfile_data (sec->objfile, mips_pdr_data, priv);
        }
        the_bfd = NULL;

        if (priv->size != 0)
        {
            int low, mid, high;
            char *ptr;
            CORE_ADDR pdr_pc;

            low = 0;
            high = priv->size / 32;

            /* We've found a .pdr section describing this objfile.  We want to
               find the entry which describes this code address.  The .pdr
               information is not very descriptive; we have only a function
               start address.  We have to look for the closest entry, because
               the local symbol at the beginning of this function may have
               been stripped - so if we ask the symbol table for the start
               address we may get a preceding global function.  */

            /* First, find the last .pdr entry starting at or before PC.  */
            do
            {
                mid = (low + high) / 2;

                ptr = priv->contents + mid * 32;
                pdr_pc = bfd_get_signed_32 (sec->objfile->obfd, ptr);
                pdr_pc += ANOFFSET (sec->objfile->section_offsets,
                                    SECT_OFF_TEXT (sec->objfile));

                if (pdr_pc > pc)
                    high = mid;
                else
                    low = mid + 1;
            }
            while (low != high);

            /* Both low and high point one past the PDR of interest.  If
               both are zero, that means this PC is before any region
               covered by a PDR, i.e. pdr_pc for the first PDR entry is
               greater than PC.  */
            if (low > 0)
            {
                ptr = priv->contents + (low - 1) * 32;
                pdr_pc = bfd_get_signed_32 (sec->objfile->obfd, ptr);
                pdr_pc += ANOFFSET (sec->objfile->section_offsets,
                                    SECT_OFF_TEXT (sec->objfile));
            }

            /* We don't have a range, so we have no way to know for sure
               whether we're in the correct PDR or a PDR for a preceding
               function and the current function was a stripped local
               symbol.  But if the PDR's PC is at least as great as the
               best guess from the symbol table, assume that it does cover
               the right area; if a .pdr section is present at all then
               nearly every function will have an entry.  The biggest exception
               will be the dynamic linker stubs; conveniently these are
               placed before .text instead of after.  */

            if (pc >= pdr_pc && pdr_pc >= startaddr)
            {
                struct symbol *sym = find_pc_function (pc);

                if (addrptr)
                    *addrptr = pdr_pc;

                /* Fill in what we need of the proc_desc.  */
                proc_desc = (struct mdebug_extra_func_info *)
                            obstack_alloc (&sec->objfile->objfile_obstack,
                                           sizeof (struct mdebug_extra_func_info));
                PROC_LOW_ADDR (proc_desc) = pdr_pc;

                PROC_FRAME_OFFSET (proc_desc)
                    = bfd_get_signed_32 (sec->objfile->obfd, ptr + 20);
                PROC_FRAME_REG (proc_desc) = bfd_get_32 (sec->objfile->obfd,
                                             ptr + 24);
                PROC_REG_MASK (proc_desc) = bfd_get_32 (sec->objfile->obfd,
                                                        ptr + 4);
                PROC_FREG_MASK (proc_desc) = bfd_get_32 (sec->objfile->obfd,
                                             ptr + 12);
                PROC_REG_OFFSET (proc_desc)
                    = bfd_get_signed_32 (sec->objfile->obfd, ptr + 8);
                PROC_FREG_OFFSET (proc_desc)
                    = bfd_get_signed_32 (sec->objfile->obfd, ptr + 16);
                PROC_PC_REG (proc_desc) = bfd_get_32 (sec->objfile->obfd,
                                                      ptr + 28);
                proc_desc->pdr.isym = (long) sym;

                return proc_desc;
            }
        }
    }

    if (b == NULL)
        return NULL;

    if (startaddr > BLOCK_START (b))
    {
        /* This is the "pathological" case referred to in a comment in
           print_frame_info.  It might be better to move this check into
           symbol reading.  */
        return NULL;
    }

    sym = lookup_symbol (MDEBUG_EFI_SYMBOL_NAME, b, LABEL_DOMAIN, 0);

    /* If we never found a PDR for this function in symbol reading, then
       examine prologues to find the information.  */
    if (sym)
    {
        proc_desc = (struct mdebug_extra_func_info *) SYMBOL_VALUE (sym);
        if (PROC_FRAME_REG (proc_desc) == -1)
            return NULL;
        else
            return proc_desc;
    }
    else
        return NULL;
}
Example #15
0
struct block *
get_current_block (void)
{
  return block_for_pc (read_pc ());
}