packaging: support aarch64 build
[platform/upstream/binutils.git] / gdb / dwarf2-frame.c
index b53c015..80e5903 100644 (file)
@@ -1,6 +1,6 @@
 /* Frame unwinder for frames with DWARF Call Frame Information.
 
-   Copyright (C) 2003-2013 Free Software Foundation, Inc.
+   Copyright (C) 2003-2014 Free Software Foundation, Inc.
 
    Contributed by Mark Kettenis.
 
 #include "objfiles.h"
 #include "regcache.h"
 #include "value.h"
-
-#include "gdb_assert.h"
-#include "gdb_string.h"
+#include "record.h"
 
 #include "complaints.h"
 #include "dwarf2-frame.h"
 #include "ax.h"
 #include "dwarf2loc.h"
-#include "exceptions.h"
 #include "dwarf2-frame-tailcall.h"
 
 struct comp_unit;
@@ -290,20 +287,9 @@ read_addr_from_reg (void *baton, int reg)
 {
   struct frame_info *this_frame = (struct frame_info *) baton;
   struct gdbarch *gdbarch = get_frame_arch (this_frame);
-  int regnum;
-  gdb_byte *buf;
-
-  regnum = gdbarch_dwarf2_reg_to_regnum (gdbarch, reg);
-
-  buf = alloca (register_size (gdbarch, regnum));
-  get_frame_register (this_frame, regnum, buf);
+  int regnum = gdbarch_dwarf2_reg_to_regnum (gdbarch, reg);
 
-  /* Convert the register to an integer.  This returns a LONGEST
-     rather than a CORE_ADDR, but unpack_pointer does the same thing
-     under the covers, and this makes more sense for non-pointer
-     registers.  Maybe read_addr_from_reg and the associated interfaces
-     should deal with "struct value" instead of CORE_ADDR.  */
-  return unpack_long (register_type (gdbarch, regnum), buf);
+  return address_from_register (regnum, this_frame);
 }
 
 /* Implement struct dwarf_expr_context_funcs' "get_reg_value" callback.  */
@@ -523,7 +509,7 @@ execute_cfa_program (struct dwarf2_fde *fde, const gdb_byte *insn_ptr,
              {
                struct dwarf2_frame_state_reg_info *new_rs;
 
-               new_rs = XMALLOC (struct dwarf2_frame_state_reg_info);
+               new_rs = XNEW (struct dwarf2_frame_state_reg_info);
                *new_rs = fs->regs;
                fs->regs.reg = dwarf2_frame_state_copy_regs (&fs->regs);
                fs->regs.prev = new_rs;
@@ -998,12 +984,22 @@ struct dwarf2_frame_cache
   /* The .text offset.  */
   CORE_ADDR text_offset;
 
+  /* True if we already checked whether this frame is the bottom frame
+     of a virtual tail call frame chain.  */
+  int checked_tailcall_bottom;
+
   /* If not NULL then this frame is the bottom frame of a TAILCALL_FRAME
      sequence.  If NULL then it is a normal case with no TAILCALL_FRAME
      involved.  Non-bottom frames of a virtual tail call frames chain use
      dwarf2_tailcall_frame_unwind unwinder so this field does not apply for
      them.  */
   void *tailcall_cache;
+
+  /* The number of bytes to subtract from TAILCALL_FRAME frames frame
+     base to get the SP, to simulate the return address pushed on the
+     stack.  */
+  LONGEST entry_cfa_sp_offset;
+  int entry_cfa_sp_offset_p;
 };
 
 /* A cleanup that sets a pointer to NULL.  */
@@ -1028,8 +1024,6 @@ dwarf2_frame_cache (struct frame_info *this_frame, void **this_cache)
   struct dwarf2_fde *fde;
   volatile struct gdb_exception ex;
   CORE_ADDR entry_pc;
-  LONGEST entry_cfa_sp_offset;
-  int entry_cfa_sp_offset_p = 0;
   const gdb_byte *instr;
 
   if (*this_cache)
@@ -1042,7 +1036,7 @@ dwarf2_frame_cache (struct frame_info *this_frame, void **this_cache)
   reset_cache_cleanup = make_cleanup (clear_pointer_cleanup, this_cache);
 
   /* Allocate and initialize the frame state.  */
-  fs = XZALLOC (struct dwarf2_frame_state);
+  fs = XCNEW (struct dwarf2_frame_state);
   old_chain = make_cleanup (dwarf2_frame_state_free, fs);
 
   /* Unwind the PC.
@@ -1094,8 +1088,8 @@ dwarf2_frame_cache (struct frame_info *this_frame, void **this_cache)
          && (gdbarch_dwarf2_reg_to_regnum (gdbarch, fs->regs.cfa_reg)
              == gdbarch_sp_regnum (gdbarch)))
        {
-         entry_cfa_sp_offset = fs->regs.cfa_offset;
-         entry_cfa_sp_offset_p = 1;
+         cache->entry_cfa_sp_offset = fs->regs.cfa_offset;
+         cache->entry_cfa_sp_offset_p = 1;
        }
     }
   else
@@ -1244,13 +1238,6 @@ incomplete CFI data; unspecified registers (e.g., %s) at %s"),
     cache->undefined_retaddr = 1;
 
   do_cleanups (old_chain);
-
-  /* Try to find a virtual tail call frames chain with bottom (callee) frame
-     starting at THIS_FRAME.  */
-  dwarf2_tailcall_sniffer_first (this_frame, &cache->tailcall_cache,
-                                (entry_cfa_sp_offset_p
-                                 ? &entry_cfa_sp_offset : NULL));
-
   discard_cleanups (reset_cache_cleanup);
   return cache;
 }
@@ -1279,12 +1266,11 @@ dwarf2_frame_this_id (struct frame_info *this_frame, void **this_cache,
     dwarf2_frame_cache (this_frame, this_cache);
 
   if (cache->unavailable_retaddr)
+    (*this_id) = frame_id_build_unavailable_stack (get_frame_func (this_frame));
+  else if (cache->undefined_retaddr)
     return;
-
-  if (cache->undefined_retaddr)
-    return;
-
-  (*this_id) = frame_id_build (cache->cfa, get_frame_func (this_frame));
+  else
+    (*this_id) = frame_id_build (cache->cfa, get_frame_func (this_frame));
 }
 
 static struct value *
@@ -1297,6 +1283,16 @@ dwarf2_frame_prev_register (struct frame_info *this_frame, void **this_cache,
   CORE_ADDR addr;
   int realnum;
 
+  /* Check whether THIS_FRAME is the bottom frame of a virtual tail
+     call frame chain.  */
+  if (!cache->checked_tailcall_bottom)
+    {
+      cache->checked_tailcall_bottom = 1;
+      dwarf2_tailcall_sniffer_first (this_frame, &cache->tailcall_cache,
+                                    (cache->entry_cfa_sp_offset_p
+                                     ? &cache->entry_cfa_sp_offset : NULL));
+    }
+
   /* Non-bottom frames of a virtual tail call frames chain use
      dwarf2_tailcall_frame_unwind unwinder so this code does not apply for
      them.  If dwarf2_tailcall_prev_register_first does not have specific value
@@ -1423,10 +1419,6 @@ dwarf2_frame_sniffer (const struct frame_unwind *self,
   if (self->type != NORMAL_FRAME)
     return 0;
 
-  /* Preinitializa the cache so that TAILCALL_FRAME can find the record by
-     dwarf2_tailcall_sniffer_first.  */
-  dwarf2_frame_cache (this_frame, this_cache);
-
   return 1;
 }
 
@@ -1509,18 +1501,23 @@ dwarf2_frame_base_sniffer (struct frame_info *this_frame)
 CORE_ADDR
 dwarf2_frame_cfa (struct frame_info *this_frame)
 {
+  if (frame_unwinder_is (this_frame, &record_btrace_tailcall_frame_unwind)
+      || frame_unwinder_is (this_frame, &record_btrace_frame_unwind))
+    throw_error (NOT_AVAILABLE_ERROR,
+                _("cfa not available for record btrace target"));
+
   while (get_frame_type (this_frame) == INLINE_FRAME)
     this_frame = get_prev_frame (this_frame);
+  if (get_frame_unwind_stop_reason (this_frame) == UNWIND_UNAVAILABLE)
+    throw_error (NOT_AVAILABLE_ERROR,
+                _("can't compute CFA for this frame: "
+                  "required registers or memory are unavailable"));
   /* This restriction could be lifted if other unwinders are known to
      compute the frame base in a way compatible with the DWARF
      unwinder.  */
   if (!frame_unwinder_is (this_frame, &dwarf2_frame_unwind)
       && !frame_unwinder_is (this_frame, &dwarf2_tailcall_frame_unwind))
     error (_("can't compute CFA for this frame"));
-  if (get_frame_unwind_stop_reason (this_frame) == UNWIND_UNAVAILABLE)
-    throw_error (NOT_AVAILABLE_ERROR,
-                _("can't compute CFA for this frame: "
-                  "required registers or memory are unavailable"));
   return get_frame_base (this_frame);
 }
 \f