]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
Dwarf: Fix dynamic properties with neg. value.
authorBernhard Heckel <bernhard.heckel@intel.com>
Tue, 6 Sep 2016 07:00:54 +0000 (09:00 +0200)
committerBernhard Heckel <bernhard.heckel@intel.com>
Wed, 7 Sep 2016 10:07:39 +0000 (12:07 +0200)
Evaluating of neg. value of 32bit inferiours running on 64bit plattform
causes issues because of the missing sign bits.

Bernhard Heckel  <bernhard.heckel@intel.com>

gdb/Changelog
* dwarf2loc.h: Declare
* dwarf2loc.c (dwarf2_evaluate_property_signed): New.
  (dwarf2_evaluate_property): Delegate tasks to
  dwarf2_evaluate_property_signed.

Change-Id: I3e8f67ecd0d78c579253f67cdf836bd8129a1a26

gdb/dwarf2loc.c
gdb/dwarf2loc.h

index 548e4683a61d20c9e52c44e89b84d80566cf2015..560e16f4658b984e976541692cbb3662804057c7 100644 (file)
@@ -2601,11 +2601,14 @@ dwarf2_locexpr_baton_eval (const struct dwarf2_locexpr_baton *dlbaton,
 /* See dwarf2loc.h.  */
 
 int
-dwarf2_evaluate_property (const struct dynamic_prop *prop,
+dwarf2_evaluate_property_signed (const struct dynamic_prop *prop,
                          struct frame_info *frame,
                          struct property_addr_info *addr_stack,
-                         CORE_ADDR *value)
+                         CORE_ADDR *value,
+                         int is_signed)
 {
+  int rc = 0;
+
   if (prop == NULL)
     return 0;
 
@@ -2629,7 +2632,7 @@ dwarf2_evaluate_property (const struct dynamic_prop *prop,
 
                *value = value_as_address (val);
              }
-           return 1;
+           rc = 1;
          }
       }
       break;
@@ -2651,7 +2654,7 @@ dwarf2_evaluate_property (const struct dynamic_prop *prop,
            if (!value_optimized_out (val))
              {
                *value = value_as_address (val);
-               return 1;
+               rc = 1;
              }
          }
       }
@@ -2659,8 +2662,8 @@ dwarf2_evaluate_property (const struct dynamic_prop *prop,
 
     case PROP_CONST:
       *value = prop->data.const_val;
-      return 1;
-
+      rc = 1;
+      break;
     case PROP_ADDR_OFFSET:
       {
        struct dwarf2_property_baton *baton
@@ -2681,11 +2684,38 @@ dwarf2_evaluate_property (const struct dynamic_prop *prop,
          val = value_at (baton->offset_info.type,
                          pinfo->addr + baton->offset_info.offset);
        *value = value_as_address (val);
-       return 1;
+       rc = 1;
       }
+      break;
     }
 
-  return 0;
+  if (rc == 1 && is_signed == 1)
+    {
+      /* If we have a valid return candidate and it's value is signed,
+         we have to sign-extend the value because CORE_ADDR on 64bit machine has
+         8 bytes but address size of an 32bit application is 4 bytes.  */
+      struct gdbarch * gdbarch = target_gdbarch ();
+      const int addr_bit = gdbarch_addr_bit (gdbarch);
+      const CORE_ADDR neg_mask = ((~0) <<  (addr_bit - 1));
+
+      /* Check if signed bit is set and sign-extend values.  */
+      if (*value & (neg_mask))
+       *value |= (neg_mask );
+    }
+  return rc;
+}
+
+int
+dwarf2_evaluate_property (const struct dynamic_prop *prop,
+                         struct frame_info *frame,
+                         struct property_addr_info *addr_stack,
+                         CORE_ADDR *value)
+{
+  return dwarf2_evaluate_property_signed (prop,
+                                  frame,
+                                  addr_stack,
+                                  value,
+                                  0);
 }
 
 /* See dwarf2loc.h.  */
index fa83459cc87ca473a373d19aa60d9ca50c9b9ca9..da6b9cd44f18a4cb5bb6920e508e5c9be207d52c 100644 (file)
@@ -138,6 +138,12 @@ int dwarf2_evaluate_property (const struct dynamic_prop *prop,
                              struct property_addr_info *addr_stack,
                              CORE_ADDR *value);
 
+int dwarf2_evaluate_property_signed (const struct dynamic_prop *prop,
+                             struct frame_info *frame,
+                             struct property_addr_info *addr_stack,
+                             CORE_ADDR *value,
+                             int is_signed);
+
 /* A helper for the compiler interface that compiles a single dynamic
    property to C code.