Commits

Anonymous committed f46235e

suppress warning about unhandled expr 0x9f (DW_OP_stack_value)

This is a DWARF-4 item that stores the value of the object on
the dwarf expression stack, rather than the address of the object.
We don't have a way to convey this value through to the type resolution
code, which is focused on reading data from memory.

Fixup failed expression evals so that we can render the variable along
with an <optimized out> annotation.

  • Participants
  • Parent commits fc76f96
  • Branches onering

Comments (0)

Files changed (4)

         if (debug) printf("OP_reg%" PRId64 "\n", u64);
         if (!push(&e, &val)) return 0;
         continue;
-       
+
       case DW_OP_dup:
         val = e.stack[e.top];
         if (debug) printf("OP_dup\n");
       case DW_OP_nop:
         continue;
 
+      case DW_OP_stack_value:
+        /* The DW_OP_stack_value operation specifies that the object does not
+         * exist in memory but its value is nonetheless known and is at the top
+         * of the DWARF expression stack. In this form of location description,
+         * the DWARF expression represents the actual value of the object,
+         * rather than its location. The DW_OP_stack_value operation terminates
+         * the expression.
+         *
+         * Unfortunately, we're focused around expressions returning
+         * addresses rather than values, so while it is simple to
+         * break here to obtain the desired value, we have no way to convey
+         * that result back to the caller at this time.
+         */
+        return 0;
+
+      case DW_OP_piece: /* similar reasoning to DW_OP_stack_value above */
       default:
-        fprintf(stderr, "DWARF: expr: unhandled op %02x\n", op);
+        fprintf(stderr, "DWARF: expr: unhandled op 0x%02x\n", op);
         return 0;
     }
   }
       return NULL;
   }
 
-
   if (t) {
     gimli_hash_insert_ptr(file->die_to_type, die, t);
   }
       case DW_FORM_block:
         if (!dw_eval_expr(&frame->cur, (uint8_t*)location->ptr, location->code,
               frame_base, &res, NULL, &is_stack)) {
-          return;
+          res = 0;
         }
         break;
       case DW_FORM_data8:
         if (!dw_calc_location(&frame->cur, comp_unit_base, m,
               location->code, &res, NULL, &is_stack)) {
-          return;
+          res = 0;
         }
         break;
       default:
         printf("Unhandled location form 0x%" PRIx64 "\n", location->form);
-        return;
     }
   } else if (name) {
     /* no location defined, so assume the compiler optimized it away */
 #define DW_OP_lo_user 0xe0   
 #define DW_OP_hi_user 0xff   
 
+// DWARF 4 (seen in the wild!)
+#define DW_OP_stack_value 0x9f // result is on the expr stack
+
 #define DW_ATE_address 0x01 
 #define DW_ATE_boolean 0x02 
 #define DW_ATE_complex_float 0x03 
       }
     }
 
+    if (data->addr == 0) {
+      printf(" <optimized out>%s", data->suffix);
+      goto after;
+    }
+
     t = gimli_type_resolve(t);
 
     switch (gimli_type_kind(t)) {
     }
   }
 
+after:
   gimli_hash_iter(data->proc->files, after_print_var, data);
 
   return GIMLI_ITER_CONT;