Initialize gdb::optional empty payload to quiet false -Wmaybe-uninitialized warnings
[deliverable/binutils-gdb.git] / gdb / dwarf2-frame.c
index 200b04469a40c236e9281c4dcb1524ceea58aa9b..f8dd1df739d024e73bf2756d033773393bc4ec4b 100644 (file)
@@ -1,6 +1,6 @@
 /* Frame unwinder for frames with DWARF Call Frame Information.
 
-   Copyright (C) 2003-2015 Free Software Foundation, Inc.
+   Copyright (C) 2003-2017 Free Software Foundation, Inc.
 
    Contributed by Mark Kettenis.
 
@@ -288,33 +288,14 @@ dwarf2_frame_state_free (void *p)
 /* Helper functions for execute_stack_op.  */
 
 static CORE_ADDR
-read_addr_from_reg (void *baton, int reg)
+read_addr_from_reg (struct frame_info *this_frame, int reg)
 {
-  struct frame_info *this_frame = (struct frame_info *) baton;
   struct gdbarch *gdbarch = get_frame_arch (this_frame);
-  int regnum = gdbarch_dwarf2_reg_to_regnum (gdbarch, reg);
+  int regnum = dwarf_reg_to_regnum_or_error (gdbarch, reg);
 
   return address_from_register (regnum, this_frame);
 }
 
-/* Implement struct dwarf_expr_context_funcs' "get_reg_value" callback.  */
-
-static struct value *
-get_reg_value (void *baton, struct type *type, int reg)
-{
-  struct frame_info *this_frame = (struct frame_info *) baton;
-  struct gdbarch *gdbarch = get_frame_arch (this_frame);
-  int regnum = gdbarch_dwarf2_reg_to_regnum (gdbarch, reg);
-
-  return value_from_register (type, regnum, this_frame);
-}
-
-static void
-read_mem (void *baton, gdb_byte *buf, CORE_ADDR addr, size_t len)
-{
-  read_memory (addr, buf, len);
-}
-
 /* Execute the required actions for both the DW_CFA_restore and
 DW_CFA_restore_extended instructions.  */
 static void
@@ -336,30 +317,84 @@ dwarf2_restore_rule (struct gdbarch *gdbarch, ULONGEST reg_num,
     fs->regs.reg[reg].how = DWARF2_FRAME_REG_UNSPECIFIED;
 
   if (fs->regs.reg[reg].how == DWARF2_FRAME_REG_UNSPECIFIED)
-    complaint (&symfile_complaints, _("\
+    {
+      int regnum = dwarf_reg_to_regnum (gdbarch, reg);
+
+      complaint (&symfile_complaints, _("\
 incomplete CFI data; DW_CFA_restore unspecified\n\
 register %s (#%d) at %s"),
-                      gdbarch_register_name
-                      (gdbarch, gdbarch_dwarf2_reg_to_regnum (gdbarch, reg)),
-                      gdbarch_dwarf2_reg_to_regnum (gdbarch, reg),
-                      paddress (gdbarch, fs->pc));
+                gdbarch_register_name (gdbarch, regnum), regnum,
+                paddress (gdbarch, fs->pc));
+    }
 }
 
-/* Virtual method table for execute_stack_op below.  */
-
-static const struct dwarf_expr_context_funcs dwarf2_frame_ctx_funcs =
+class dwarf_expr_executor : public dwarf_expr_context
 {
-  read_addr_from_reg,
-  get_reg_value,
-  read_mem,
-  ctx_no_get_frame_base,
-  ctx_no_get_frame_cfa,
-  ctx_no_get_frame_pc,
-  ctx_no_get_tls_address,
-  ctx_no_dwarf_call,
-  ctx_no_get_base_type,
-  ctx_no_push_dwarf_reg_entry_value,
-  ctx_no_get_addr_index
+ public:
+
+  struct frame_info *this_frame;
+
+  CORE_ADDR read_addr_from_reg (int reg) OVERRIDE
+  {
+    return ::read_addr_from_reg (this_frame, reg);
+  }
+
+  struct value *get_reg_value (struct type *type, int reg) OVERRIDE
+  {
+    struct gdbarch *gdbarch = get_frame_arch (this_frame);
+    int regnum = dwarf_reg_to_regnum_or_error (gdbarch, reg);
+
+    return value_from_register (type, regnum, this_frame);
+  }
+
+  void read_mem (gdb_byte *buf, CORE_ADDR addr, size_t len) OVERRIDE
+  {
+    read_memory (addr, buf, len);
+  }
+
+  void get_frame_base (const gdb_byte **start, size_t *length) OVERRIDE
+  {
+    invalid ("DW_OP_fbreg");
+  }
+
+  void push_dwarf_reg_entry_value (enum call_site_parameter_kind kind,
+                                  union call_site_parameter_u kind_u,
+                                  int deref_size) OVERRIDE
+  {
+    invalid ("DW_OP_entry_value");
+  }
+
+  CORE_ADDR get_object_address () OVERRIDE
+  {
+    invalid ("DW_OP_push_object_address");
+  }
+
+  CORE_ADDR get_frame_cfa () OVERRIDE
+  {
+    invalid ("DW_OP_call_frame_cfa");
+  }
+
+  CORE_ADDR get_tls_address (CORE_ADDR offset) OVERRIDE
+  {
+    invalid ("DW_OP_form_tls_address");
+  }
+
+  void dwarf_call (cu_offset die_offset) OVERRIDE
+  {
+    invalid ("DW_OP_call*");
+  }
+
+  CORE_ADDR get_addr_index (unsigned int index)
+  {
+    invalid ("DW_OP_GNU_addr_index");
+  }
+
+ private:
+
+  void invalid (const char *op) ATTRIBUTE_NORETURN
+  {
+    error (_("%s is invalid in this context"), op);
+  }
 };
 
 static CORE_ADDR
@@ -367,29 +402,24 @@ execute_stack_op (const gdb_byte *exp, ULONGEST len, int addr_size,
                  CORE_ADDR offset, struct frame_info *this_frame,
                  CORE_ADDR initial, int initial_in_stack_memory)
 {
-  struct dwarf_expr_context *ctx;
   CORE_ADDR result;
-  struct cleanup *old_chain;
-
-  ctx = new_dwarf_expr_context ();
-  old_chain = make_cleanup_free_dwarf_expr_context (ctx);
-  make_cleanup_value_free_to_mark (value_mark ());
-
-  ctx->gdbarch = get_frame_arch (this_frame);
-  ctx->addr_size = addr_size;
-  ctx->ref_addr_size = -1;
-  ctx->offset = offset;
-  ctx->baton = this_frame;
-  ctx->funcs = &dwarf2_frame_ctx_funcs;
-
-  dwarf_expr_push_address (ctx, initial, initial_in_stack_memory);
-  dwarf_expr_eval (ctx, exp, len);
-
-  if (ctx->location == DWARF_VALUE_MEMORY)
-    result = dwarf_expr_fetch_address (ctx, 0);
-  else if (ctx->location == DWARF_VALUE_REGISTER)
-    result = read_addr_from_reg (this_frame,
-                                value_as_long (dwarf_expr_fetch (ctx, 0)));
+
+  dwarf_expr_executor ctx;
+  scoped_value_mark free_values;
+
+  ctx.this_frame = this_frame;
+  ctx.gdbarch = get_frame_arch (this_frame);
+  ctx.addr_size = addr_size;
+  ctx.ref_addr_size = -1;
+  ctx.offset = offset;
+
+  ctx.push_address (initial, initial_in_stack_memory);
+  ctx.eval (exp, len);
+
+  if (ctx.location == DWARF_VALUE_MEMORY)
+    result = ctx.fetch_address (0);
+  else if (ctx.location == DWARF_VALUE_REGISTER)
+    result = ctx.read_addr_from_reg (value_as_long (ctx.fetch (0)));
   else
     {
       /* This is actually invalid DWARF, but if we ever do run across
@@ -399,8 +429,6 @@ execute_stack_op (const gdb_byte *exp, ULONGEST len, int addr_size,
 Not implemented: computing unwound register using explicit value operator"));
     }
 
-  do_cleanups (old_chain);
-
   return result;
 }
 \f
@@ -906,7 +934,6 @@ dwarf2_fetch_cfa_info (struct gdbarch *gdbarch, CORE_ADDR pc,
   struct dwarf2_fde *fde;
   CORE_ADDR text_offset;
   struct dwarf2_frame_state fs;
-  int addr_size;
 
   memset (&fs, 0, sizeof (struct dwarf2_frame_state));
 
@@ -921,7 +948,6 @@ dwarf2_fetch_cfa_info (struct gdbarch *gdbarch, CORE_ADDR pc,
   fs.data_align = fde->cie->data_alignment_factor;
   fs.code_align = fde->cie->code_alignment_factor;
   fs.retaddr_column = fde->cie->return_address_register;
-  addr_size = fde->cie->addr_size;
 
   /* Check for "quirks" - known bugs in producers.  */
   dwarf2_frame_find_quirks (&fs, fde);
@@ -942,11 +968,7 @@ dwarf2_fetch_cfa_info (struct gdbarch *gdbarch, CORE_ADDR pc,
     {
     case CFA_REG_OFFSET:
       {
-       int regnum = gdbarch_dwarf2_reg_to_regnum (gdbarch, fs.regs.cfa_reg);
-
-       if (regnum == -1)
-         error (_("Unable to access DWARF register number %d"),
-                (int) fs.regs.cfa_reg); /* FIXME */
+       int regnum = dwarf_reg_to_regnum_or_error (gdbarch, fs.regs.cfa_reg);
 
        *regnum_out = regnum;
        if (fs.armcc_cfa_offsets_reversed)
@@ -1093,7 +1115,7 @@ dwarf2_frame_cache (struct frame_info *this_frame, void **this_cache)
                                   entry_pc, fs);
 
       if (fs->regs.cfa_how == CFA_REG_OFFSET
-         && (gdbarch_dwarf2_reg_to_regnum (gdbarch, fs->regs.cfa_reg)
+         && (dwarf_reg_to_regnum (gdbarch, fs->regs.cfa_reg)
              == gdbarch_sp_regnum (gdbarch)))
        {
          cache->entry_cfa_sp_offset = fs->regs.cfa_offset;
@@ -1156,19 +1178,16 @@ dwarf2_frame_cache (struct frame_info *this_frame, void **this_cache)
   /* Go through the DWARF2 CFI generated table and save its register
      location information in the cache.  Note that we don't skip the
      return address column; it's perfectly all right for it to
-     correspond to a real register.  If it doesn't correspond to a
-     real register, or if we shouldn't treat it as such,
-     gdbarch_dwarf2_reg_to_regnum should be defined to return a number outside
-     the range [0, gdbarch_num_regs).  */
+     correspond to a real register.  */
   {
     int column;                /* CFI speak for "register number".  */
 
     for (column = 0; column < fs->regs.num_regs; column++)
       {
        /* Use the GDB register number as the destination index.  */
-       int regnum = gdbarch_dwarf2_reg_to_regnum (gdbarch, column);
+       int regnum = dwarf_reg_to_regnum (gdbarch, column);
 
-       /* If there's no corresponding GDB register, ignore it.  */
+       /* Protect against a target returning a bad register.  */
        if (regnum < 0 || regnum >= num_regs)
          continue;
 
@@ -1330,8 +1349,8 @@ dwarf2_frame_prev_register (struct frame_info *this_frame, void **this_cache,
       return frame_unwind_got_memory (this_frame, regnum, addr);
 
     case DWARF2_FRAME_REG_SAVED_REG:
-      realnum
-       = gdbarch_dwarf2_reg_to_regnum (gdbarch, cache->reg[regnum].loc.reg);
+      realnum = dwarf_reg_to_regnum_or_error
+       (gdbarch, cache->reg[regnum].loc.reg);
       return frame_unwind_got_register (this_frame, regnum, realnum);
 
     case DWARF2_FRAME_REG_SAVED_EXP:
@@ -1374,7 +1393,7 @@ dwarf2_frame_prev_register (struct frame_info *this_frame, void **this_cache,
 
     case DWARF2_FRAME_REG_RA_OFFSET:
       addr = cache->reg[regnum].loc.offset;
-      regnum = gdbarch_dwarf2_reg_to_regnum
+      regnum = dwarf_reg_to_regnum_or_error
        (gdbarch, cache->retaddr_reg.loc.reg);
       addr += get_frame_register_unsigned (this_frame, regnum);
       return frame_unwind_got_address (this_frame, regnum, addr);
This page took 0.0284 seconds and 4 git commands to generate.