1 //===-- DWARFExpression.cpp -------------------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #include "lldb/Expression/DWARFExpression.h" 11 12 #include <vector> 13 14 #include "lldb/Core/dwarf.h" 15 #include "lldb/Core/Log.h" 16 #include "lldb/Core/StreamString.h" 17 #include "lldb/Core/Scalar.h" 18 #include "lldb/Core/Value.h" 19 #include "lldb/Core/VMRange.h" 20 21 #include "lldb/Expression/ClangExpressionDeclMap.h" 22 #include "lldb/Expression/ClangExpressionVariable.h" 23 24 #include "lldb/Host/Host.h" 25 26 #include "lldb/lldb-private-log.h" 27 28 #include "lldb/Symbol/ClangASTType.h" 29 #include "lldb/Symbol/ClangASTContext.h" 30 #include "lldb/Symbol/Type.h" 31 32 #include "lldb/Target/ExecutionContext.h" 33 #include "lldb/Target/Process.h" 34 #include "lldb/Target/RegisterContext.h" 35 #include "lldb/Target/StackFrame.h" 36 37 using namespace lldb; 38 using namespace lldb_private; 39 40 const char * 41 DW_OP_value_to_name (uint32_t val) 42 { 43 static char invalid[100]; 44 switch (val) { 45 case 0x03: return "DW_OP_addr"; 46 case 0x06: return "DW_OP_deref"; 47 case 0x08: return "DW_OP_const1u"; 48 case 0x09: return "DW_OP_const1s"; 49 case 0x0a: return "DW_OP_const2u"; 50 case 0x0b: return "DW_OP_const2s"; 51 case 0x0c: return "DW_OP_const4u"; 52 case 0x0d: return "DW_OP_const4s"; 53 case 0x0e: return "DW_OP_const8u"; 54 case 0x0f: return "DW_OP_const8s"; 55 case 0x10: return "DW_OP_constu"; 56 case 0x11: return "DW_OP_consts"; 57 case 0x12: return "DW_OP_dup"; 58 case 0x13: return "DW_OP_drop"; 59 case 0x14: return "DW_OP_over"; 60 case 0x15: return "DW_OP_pick"; 61 case 0x16: return "DW_OP_swap"; 62 case 0x17: return "DW_OP_rot"; 63 case 0x18: return "DW_OP_xderef"; 64 case 0x19: return "DW_OP_abs"; 65 case 0x1a: return "DW_OP_and"; 66 case 0x1b: return "DW_OP_div"; 67 case 0x1c: return "DW_OP_minus"; 68 case 0x1d: return "DW_OP_mod"; 69 case 0x1e: return "DW_OP_mul"; 70 case 0x1f: return "DW_OP_neg"; 71 case 0x20: return "DW_OP_not"; 72 case 0x21: return "DW_OP_or"; 73 case 0x22: return "DW_OP_plus"; 74 case 0x23: return "DW_OP_plus_uconst"; 75 case 0x24: return "DW_OP_shl"; 76 case 0x25: return "DW_OP_shr"; 77 case 0x26: return "DW_OP_shra"; 78 case 0x27: return "DW_OP_xor"; 79 case 0x2f: return "DW_OP_skip"; 80 case 0x28: return "DW_OP_bra"; 81 case 0x29: return "DW_OP_eq"; 82 case 0x2a: return "DW_OP_ge"; 83 case 0x2b: return "DW_OP_gt"; 84 case 0x2c: return "DW_OP_le"; 85 case 0x2d: return "DW_OP_lt"; 86 case 0x2e: return "DW_OP_ne"; 87 case 0x30: return "DW_OP_lit0"; 88 case 0x31: return "DW_OP_lit1"; 89 case 0x32: return "DW_OP_lit2"; 90 case 0x33: return "DW_OP_lit3"; 91 case 0x34: return "DW_OP_lit4"; 92 case 0x35: return "DW_OP_lit5"; 93 case 0x36: return "DW_OP_lit6"; 94 case 0x37: return "DW_OP_lit7"; 95 case 0x38: return "DW_OP_lit8"; 96 case 0x39: return "DW_OP_lit9"; 97 case 0x3a: return "DW_OP_lit10"; 98 case 0x3b: return "DW_OP_lit11"; 99 case 0x3c: return "DW_OP_lit12"; 100 case 0x3d: return "DW_OP_lit13"; 101 case 0x3e: return "DW_OP_lit14"; 102 case 0x3f: return "DW_OP_lit15"; 103 case 0x40: return "DW_OP_lit16"; 104 case 0x41: return "DW_OP_lit17"; 105 case 0x42: return "DW_OP_lit18"; 106 case 0x43: return "DW_OP_lit19"; 107 case 0x44: return "DW_OP_lit20"; 108 case 0x45: return "DW_OP_lit21"; 109 case 0x46: return "DW_OP_lit22"; 110 case 0x47: return "DW_OP_lit23"; 111 case 0x48: return "DW_OP_lit24"; 112 case 0x49: return "DW_OP_lit25"; 113 case 0x4a: return "DW_OP_lit26"; 114 case 0x4b: return "DW_OP_lit27"; 115 case 0x4c: return "DW_OP_lit28"; 116 case 0x4d: return "DW_OP_lit29"; 117 case 0x4e: return "DW_OP_lit30"; 118 case 0x4f: return "DW_OP_lit31"; 119 case 0x50: return "DW_OP_reg0"; 120 case 0x51: return "DW_OP_reg1"; 121 case 0x52: return "DW_OP_reg2"; 122 case 0x53: return "DW_OP_reg3"; 123 case 0x54: return "DW_OP_reg4"; 124 case 0x55: return "DW_OP_reg5"; 125 case 0x56: return "DW_OP_reg6"; 126 case 0x57: return "DW_OP_reg7"; 127 case 0x58: return "DW_OP_reg8"; 128 case 0x59: return "DW_OP_reg9"; 129 case 0x5a: return "DW_OP_reg10"; 130 case 0x5b: return "DW_OP_reg11"; 131 case 0x5c: return "DW_OP_reg12"; 132 case 0x5d: return "DW_OP_reg13"; 133 case 0x5e: return "DW_OP_reg14"; 134 case 0x5f: return "DW_OP_reg15"; 135 case 0x60: return "DW_OP_reg16"; 136 case 0x61: return "DW_OP_reg17"; 137 case 0x62: return "DW_OP_reg18"; 138 case 0x63: return "DW_OP_reg19"; 139 case 0x64: return "DW_OP_reg20"; 140 case 0x65: return "DW_OP_reg21"; 141 case 0x66: return "DW_OP_reg22"; 142 case 0x67: return "DW_OP_reg23"; 143 case 0x68: return "DW_OP_reg24"; 144 case 0x69: return "DW_OP_reg25"; 145 case 0x6a: return "DW_OP_reg26"; 146 case 0x6b: return "DW_OP_reg27"; 147 case 0x6c: return "DW_OP_reg28"; 148 case 0x6d: return "DW_OP_reg29"; 149 case 0x6e: return "DW_OP_reg30"; 150 case 0x6f: return "DW_OP_reg31"; 151 case 0x70: return "DW_OP_breg0"; 152 case 0x71: return "DW_OP_breg1"; 153 case 0x72: return "DW_OP_breg2"; 154 case 0x73: return "DW_OP_breg3"; 155 case 0x74: return "DW_OP_breg4"; 156 case 0x75: return "DW_OP_breg5"; 157 case 0x76: return "DW_OP_breg6"; 158 case 0x77: return "DW_OP_breg7"; 159 case 0x78: return "DW_OP_breg8"; 160 case 0x79: return "DW_OP_breg9"; 161 case 0x7a: return "DW_OP_breg10"; 162 case 0x7b: return "DW_OP_breg11"; 163 case 0x7c: return "DW_OP_breg12"; 164 case 0x7d: return "DW_OP_breg13"; 165 case 0x7e: return "DW_OP_breg14"; 166 case 0x7f: return "DW_OP_breg15"; 167 case 0x80: return "DW_OP_breg16"; 168 case 0x81: return "DW_OP_breg17"; 169 case 0x82: return "DW_OP_breg18"; 170 case 0x83: return "DW_OP_breg19"; 171 case 0x84: return "DW_OP_breg20"; 172 case 0x85: return "DW_OP_breg21"; 173 case 0x86: return "DW_OP_breg22"; 174 case 0x87: return "DW_OP_breg23"; 175 case 0x88: return "DW_OP_breg24"; 176 case 0x89: return "DW_OP_breg25"; 177 case 0x8a: return "DW_OP_breg26"; 178 case 0x8b: return "DW_OP_breg27"; 179 case 0x8c: return "DW_OP_breg28"; 180 case 0x8d: return "DW_OP_breg29"; 181 case 0x8e: return "DW_OP_breg30"; 182 case 0x8f: return "DW_OP_breg31"; 183 case 0x90: return "DW_OP_regx"; 184 case 0x91: return "DW_OP_fbreg"; 185 case 0x92: return "DW_OP_bregx"; 186 case 0x93: return "DW_OP_piece"; 187 case 0x94: return "DW_OP_deref_size"; 188 case 0x95: return "DW_OP_xderef_size"; 189 case 0x96: return "DW_OP_nop"; 190 case 0x97: return "DW_OP_push_object_address"; 191 case 0x98: return "DW_OP_call2"; 192 case 0x99: return "DW_OP_call4"; 193 case 0x9a: return "DW_OP_call_ref"; 194 case DW_OP_APPLE_array_ref: return "DW_OP_APPLE_array_ref"; 195 case DW_OP_APPLE_extern: return "DW_OP_APPLE_extern"; 196 case DW_OP_APPLE_uninit: return "DW_OP_APPLE_uninit"; 197 case DW_OP_APPLE_assign: return "DW_OP_APPLE_assign"; 198 case DW_OP_APPLE_address_of: return "DW_OP_APPLE_address_of"; 199 case DW_OP_APPLE_value_of: return "DW_OP_APPLE_value_of"; 200 case DW_OP_APPLE_deref_type: return "DW_OP_APPLE_deref_type"; 201 case DW_OP_APPLE_expr_local: return "DW_OP_APPLE_expr_local"; 202 case DW_OP_APPLE_constf: return "DW_OP_APPLE_constf"; 203 case DW_OP_APPLE_scalar_cast: return "DW_OP_APPLE_scalar_cast"; 204 case DW_OP_APPLE_clang_cast: return "DW_OP_APPLE_clang_cast"; 205 case DW_OP_APPLE_clear: return "DW_OP_APPLE_clear"; 206 case DW_OP_APPLE_error: return "DW_OP_APPLE_error"; 207 default: 208 snprintf (invalid, sizeof(invalid), "Unknown DW_OP constant: 0x%x", val); 209 return invalid; 210 } 211 } 212 213 214 //---------------------------------------------------------------------- 215 // DWARFExpression constructor 216 //---------------------------------------------------------------------- 217 DWARFExpression::DWARFExpression() : 218 m_data(), 219 m_reg_kind (eRegisterKindDWARF), 220 m_loclist_slide (LLDB_INVALID_ADDRESS), 221 m_expr_locals (NULL), 222 m_decl_map (NULL) 223 { 224 } 225 226 DWARFExpression::DWARFExpression(const DWARFExpression& rhs) : 227 m_data(rhs.m_data), 228 m_reg_kind (rhs.m_reg_kind), 229 m_loclist_slide(rhs.m_loclist_slide), 230 m_expr_locals (rhs.m_expr_locals), 231 m_decl_map (rhs.m_decl_map) 232 { 233 } 234 235 236 DWARFExpression::DWARFExpression(const DataExtractor& data, uint32_t data_offset, uint32_t data_length) : 237 m_data(data, data_offset, data_length), 238 m_reg_kind (eRegisterKindDWARF), 239 m_loclist_slide(LLDB_INVALID_ADDRESS), 240 m_expr_locals (NULL), 241 m_decl_map (NULL) 242 { 243 } 244 245 //---------------------------------------------------------------------- 246 // Destructor 247 //---------------------------------------------------------------------- 248 DWARFExpression::~DWARFExpression() 249 { 250 } 251 252 253 bool 254 DWARFExpression::IsValid() const 255 { 256 return m_data.GetByteSize() > 0; 257 } 258 259 260 void 261 DWARFExpression::SetExpressionLocalVariableList (ClangExpressionVariableList *locals) 262 { 263 m_expr_locals = locals; 264 } 265 266 void 267 DWARFExpression::SetExpressionDeclMap (ClangExpressionDeclMap *decl_map) 268 { 269 m_decl_map = decl_map; 270 } 271 272 void 273 DWARFExpression::SetOpcodeData (const DataExtractor& data) 274 { 275 m_data = data; 276 } 277 278 void 279 DWARFExpression::SetOpcodeData (const DataExtractor& data, uint32_t data_offset, uint32_t data_length) 280 { 281 m_data.SetData(data, data_offset, data_length); 282 } 283 284 void 285 DWARFExpression::DumpLocation (Stream *s, uint32_t offset, uint32_t length, lldb::DescriptionLevel level) const 286 { 287 if (!m_data.ValidOffsetForDataOfSize(offset, length)) 288 return; 289 const uint32_t start_offset = offset; 290 const uint32_t end_offset = offset + length; 291 while (m_data.ValidOffset(offset) && offset < end_offset) 292 { 293 const uint32_t op_offset = offset; 294 const uint8_t op = m_data.GetU8(&offset); 295 296 switch (level) 297 { 298 default: 299 break; 300 301 case lldb::eDescriptionLevelBrief: 302 if (offset > start_offset) 303 s->PutChar(' '); 304 break; 305 306 case lldb::eDescriptionLevelFull: 307 case lldb::eDescriptionLevelVerbose: 308 if (offset > start_offset) 309 s->EOL(); 310 s->Indent(); 311 if (level == lldb::eDescriptionLevelFull) 312 break; 313 // Fall through for verbose and print offset and DW_OP prefix.. 314 s->Printf("0x%8.8x: %s", op_offset, op >= DW_OP_APPLE_uninit ? "DW_OP_APPLE_" : "DW_OP_"); 315 break; 316 } 317 318 switch (op) 319 { 320 case DW_OP_addr: *s << "addr(" << m_data.GetAddress(&offset) << ") "; break; // 0x03 1 address 321 case DW_OP_deref: *s << "deref"; break; // 0x06 322 case DW_OP_const1u: s->Printf("const1u(0x%2.2x) ", m_data.GetU8(&offset)); break; // 0x08 1 1-byte constant 323 case DW_OP_const1s: s->Printf("const1s(0x%2.2x) ", m_data.GetU8(&offset)); break; // 0x09 1 1-byte constant 324 case DW_OP_const2u: s->Printf("const2u(0x%4.4x) ", m_data.GetU16(&offset)); break; // 0x0a 1 2-byte constant 325 case DW_OP_const2s: s->Printf("const2s(0x%4.4x) ", m_data.GetU16(&offset)); break; // 0x0b 1 2-byte constant 326 case DW_OP_const4u: s->Printf("const4u(0x%8.8x) ", m_data.GetU32(&offset)); break; // 0x0c 1 4-byte constant 327 case DW_OP_const4s: s->Printf("const4s(0x%8.8x) ", m_data.GetU32(&offset)); break; // 0x0d 1 4-byte constant 328 case DW_OP_const8u: s->Printf("const8u(0x%16.16llx) ", m_data.GetU64(&offset)); break; // 0x0e 1 8-byte constant 329 case DW_OP_const8s: s->Printf("const8s(0x%16.16llx) ", m_data.GetU64(&offset)); break; // 0x0f 1 8-byte constant 330 case DW_OP_constu: s->Printf("constu(0x%x) ", m_data.GetULEB128(&offset)); break; // 0x10 1 ULEB128 constant 331 case DW_OP_consts: s->Printf("consts(0x%x) ", m_data.GetSLEB128(&offset)); break; // 0x11 1 SLEB128 constant 332 case DW_OP_dup: s->PutCString("dup"); break; // 0x12 333 case DW_OP_drop: s->PutCString("drop"); break; // 0x13 334 case DW_OP_over: s->PutCString("over"); break; // 0x14 335 case DW_OP_pick: s->Printf("pick(0x%2.2x) ", m_data.GetU8(&offset)); break; // 0x15 1 1-byte stack index 336 case DW_OP_swap: s->PutCString("swap"); break; // 0x16 337 case DW_OP_rot: s->PutCString("rot"); break; // 0x17 338 case DW_OP_xderef: s->PutCString("xderef"); break; // 0x18 339 case DW_OP_abs: s->PutCString("abs"); break; // 0x19 340 case DW_OP_and: s->PutCString("and"); break; // 0x1a 341 case DW_OP_div: s->PutCString("div"); break; // 0x1b 342 case DW_OP_minus: s->PutCString("minus"); break; // 0x1c 343 case DW_OP_mod: s->PutCString("mod"); break; // 0x1d 344 case DW_OP_mul: s->PutCString("mul"); break; // 0x1e 345 case DW_OP_neg: s->PutCString("neg"); break; // 0x1f 346 case DW_OP_not: s->PutCString("not"); break; // 0x20 347 case DW_OP_or: s->PutCString("or"); break; // 0x21 348 case DW_OP_plus: s->PutCString("plus"); break; // 0x22 349 case DW_OP_plus_uconst: // 0x23 1 ULEB128 addend 350 s->Printf("plus_uconst(0x%x) ", m_data.GetULEB128(&offset)); 351 break; 352 353 case DW_OP_shl: s->PutCString("shl"); break; // 0x24 354 case DW_OP_shr: s->PutCString("shr"); break; // 0x25 355 case DW_OP_shra: s->PutCString("shra"); break; // 0x26 356 case DW_OP_xor: s->PutCString("xor"); break; // 0x27 357 case DW_OP_skip: s->Printf("skip(0x%4.4x)", m_data.GetU16(&offset)); break; // 0x2f 1 signed 2-byte constant 358 case DW_OP_bra: s->Printf("bra(0x%4.4x)", m_data.GetU16(&offset)); break; // 0x28 1 signed 2-byte constant 359 case DW_OP_eq: s->PutCString("eq"); break; // 0x29 360 case DW_OP_ge: s->PutCString("ge"); break; // 0x2a 361 case DW_OP_gt: s->PutCString("gt"); break; // 0x2b 362 case DW_OP_le: s->PutCString("le"); break; // 0x2c 363 case DW_OP_lt: s->PutCString("lt"); break; // 0x2d 364 case DW_OP_ne: s->PutCString("ne"); break; // 0x2e 365 366 case DW_OP_lit0: // 0x30 367 case DW_OP_lit1: // 0x31 368 case DW_OP_lit2: // 0x32 369 case DW_OP_lit3: // 0x33 370 case DW_OP_lit4: // 0x34 371 case DW_OP_lit5: // 0x35 372 case DW_OP_lit6: // 0x36 373 case DW_OP_lit7: // 0x37 374 case DW_OP_lit8: // 0x38 375 case DW_OP_lit9: // 0x39 376 case DW_OP_lit10: // 0x3A 377 case DW_OP_lit11: // 0x3B 378 case DW_OP_lit12: // 0x3C 379 case DW_OP_lit13: // 0x3D 380 case DW_OP_lit14: // 0x3E 381 case DW_OP_lit15: // 0x3F 382 case DW_OP_lit16: // 0x40 383 case DW_OP_lit17: // 0x41 384 case DW_OP_lit18: // 0x42 385 case DW_OP_lit19: // 0x43 386 case DW_OP_lit20: // 0x44 387 case DW_OP_lit21: // 0x45 388 case DW_OP_lit22: // 0x46 389 case DW_OP_lit23: // 0x47 390 case DW_OP_lit24: // 0x48 391 case DW_OP_lit25: // 0x49 392 case DW_OP_lit26: // 0x4A 393 case DW_OP_lit27: // 0x4B 394 case DW_OP_lit28: // 0x4C 395 case DW_OP_lit29: // 0x4D 396 case DW_OP_lit30: // 0x4E 397 case DW_OP_lit31: s->Printf("lit%i", op - DW_OP_lit0); break; // 0x4f 398 399 case DW_OP_reg0: // 0x50 400 case DW_OP_reg1: // 0x51 401 case DW_OP_reg2: // 0x52 402 case DW_OP_reg3: // 0x53 403 case DW_OP_reg4: // 0x54 404 case DW_OP_reg5: // 0x55 405 case DW_OP_reg6: // 0x56 406 case DW_OP_reg7: // 0x57 407 case DW_OP_reg8: // 0x58 408 case DW_OP_reg9: // 0x59 409 case DW_OP_reg10: // 0x5A 410 case DW_OP_reg11: // 0x5B 411 case DW_OP_reg12: // 0x5C 412 case DW_OP_reg13: // 0x5D 413 case DW_OP_reg14: // 0x5E 414 case DW_OP_reg15: // 0x5F 415 case DW_OP_reg16: // 0x60 416 case DW_OP_reg17: // 0x61 417 case DW_OP_reg18: // 0x62 418 case DW_OP_reg19: // 0x63 419 case DW_OP_reg20: // 0x64 420 case DW_OP_reg21: // 0x65 421 case DW_OP_reg22: // 0x66 422 case DW_OP_reg23: // 0x67 423 case DW_OP_reg24: // 0x68 424 case DW_OP_reg25: // 0x69 425 case DW_OP_reg26: // 0x6A 426 case DW_OP_reg27: // 0x6B 427 case DW_OP_reg28: // 0x6C 428 case DW_OP_reg29: // 0x6D 429 case DW_OP_reg30: // 0x6E 430 case DW_OP_reg31: s->Printf("reg%i", op - DW_OP_reg0); break; // 0x6f 431 432 case DW_OP_breg0: 433 case DW_OP_breg1: 434 case DW_OP_breg2: 435 case DW_OP_breg3: 436 case DW_OP_breg4: 437 case DW_OP_breg5: 438 case DW_OP_breg6: 439 case DW_OP_breg7: 440 case DW_OP_breg8: 441 case DW_OP_breg9: 442 case DW_OP_breg10: 443 case DW_OP_breg11: 444 case DW_OP_breg12: 445 case DW_OP_breg13: 446 case DW_OP_breg14: 447 case DW_OP_breg15: 448 case DW_OP_breg16: 449 case DW_OP_breg17: 450 case DW_OP_breg18: 451 case DW_OP_breg19: 452 case DW_OP_breg20: 453 case DW_OP_breg21: 454 case DW_OP_breg22: 455 case DW_OP_breg23: 456 case DW_OP_breg24: 457 case DW_OP_breg25: 458 case DW_OP_breg26: 459 case DW_OP_breg27: 460 case DW_OP_breg28: 461 case DW_OP_breg29: 462 case DW_OP_breg30: 463 case DW_OP_breg31: s->Printf("breg%i(0x%x)", op - DW_OP_breg0, m_data.GetULEB128(&offset)); break; 464 465 case DW_OP_regx: // 0x90 1 ULEB128 register 466 s->Printf("regx(0x%x)", m_data.GetULEB128(&offset)); 467 break; 468 case DW_OP_fbreg: // 0x91 1 SLEB128 offset 469 s->Printf("fbreg(0x%x)",m_data.GetSLEB128(&offset)); 470 break; 471 case DW_OP_bregx: // 0x92 2 ULEB128 register followed by SLEB128 offset 472 s->Printf("bregx(0x%x, 0x%x)", m_data.GetULEB128(&offset), m_data.GetSLEB128(&offset)); 473 break; 474 case DW_OP_piece: // 0x93 1 ULEB128 size of piece addressed 475 s->Printf("piece(0x%x)", m_data.GetULEB128(&offset)); 476 break; 477 case DW_OP_deref_size: // 0x94 1 1-byte size of data retrieved 478 s->Printf("deref_size(0x%2.2x)", m_data.GetU8(&offset)); 479 break; 480 case DW_OP_xderef_size: // 0x95 1 1-byte size of data retrieved 481 s->Printf("xderef_size(0x%2.2x)", m_data.GetU8(&offset)); 482 break; 483 case DW_OP_nop: s->PutCString("nop"); break; // 0x96 484 case DW_OP_push_object_address: s->PutCString("push_object_address"); break; // 0x97 DWARF3 485 case DW_OP_call2: // 0x98 DWARF3 1 2-byte offset of DIE 486 s->Printf("call2(0x%4.4x)", m_data.GetU16(&offset)); 487 break; 488 case DW_OP_call4: // 0x99 DWARF3 1 4-byte offset of DIE 489 s->Printf("call4(0x%8.8x)", m_data.GetU32(&offset)); 490 break; 491 case DW_OP_call_ref: // 0x9a DWARF3 1 4- or 8-byte offset of DIE 492 s->Printf("call_ref(0x%8.8llx)", m_data.GetAddress(&offset)); 493 break; 494 // case DW_OP_form_tls_address: s << "form_tls_address"; break; // 0x9b DWARF3 495 // case DW_OP_call_frame_cfa: s << "call_frame_cfa"; break; // 0x9c DWARF3 496 // case DW_OP_bit_piece: // 0x9d DWARF3 2 497 // s->Printf("bit_piece(0x%x, 0x%x)", m_data.GetULEB128(&offset), m_data.GetULEB128(&offset)); 498 // break; 499 // case DW_OP_lo_user: s->PutCString("lo_user"); break; // 0xe0 500 // case DW_OP_hi_user: s->PutCString("hi_user"); break; // 0xff 501 case DW_OP_APPLE_extern: 502 s->Printf("extern(%u)", m_data.GetULEB128(&offset)); 503 break; 504 case DW_OP_APPLE_array_ref: 505 s->PutCString("array_ref"); 506 break; 507 case DW_OP_APPLE_uninit: 508 s->PutCString("uninit"); // 0xF0 509 break; 510 case DW_OP_APPLE_assign: // 0xF1 - pops value off and assigns it to second item on stack (2nd item must have assignable context) 511 s->PutCString("assign"); 512 break; 513 case DW_OP_APPLE_address_of: // 0xF2 - gets the address of the top stack item (top item must be a variable, or have value_type that is an address already) 514 s->PutCString("address_of"); 515 break; 516 case DW_OP_APPLE_value_of: // 0xF3 - pops the value off the stack and pushes the value of that object (top item must be a variable, or expression local) 517 s->PutCString("value_of"); 518 break; 519 case DW_OP_APPLE_deref_type: // 0xF4 - gets the address of the top stack item (top item must be a variable, or a clang type) 520 s->PutCString("deref_type"); 521 break; 522 case DW_OP_APPLE_expr_local: // 0xF5 - ULEB128 expression local index 523 s->Printf("expr_local(%u)", m_data.GetULEB128(&offset)); 524 break; 525 case DW_OP_APPLE_constf: // 0xF6 - 1 byte float size, followed by constant float data 526 { 527 uint8_t float_length = m_data.GetU8(&offset); 528 s->Printf("constf(<%u> ", float_length); 529 m_data.Dump(s, offset, eFormatHex, float_length, 1, UINT32_MAX, DW_INVALID_ADDRESS, 0, 0); 530 s->PutChar(')'); 531 // Consume the float data 532 m_data.GetData(&offset, float_length); 533 } 534 break; 535 case DW_OP_APPLE_scalar_cast: 536 s->Printf("scalar_cast(%s)", Scalar::GetValueTypeAsCString ((Scalar::Type)m_data.GetU8(&offset))); 537 break; 538 case DW_OP_APPLE_clang_cast: 539 { 540 clang::Type *clang_type = (clang::Type *)m_data.GetMaxU64(&offset, sizeof(void*)); 541 s->Printf("clang_cast(%p)", clang_type); 542 } 543 break; 544 case DW_OP_APPLE_clear: 545 s->PutCString("clear"); 546 break; 547 case DW_OP_APPLE_error: // 0xFF - Stops expression evaluation and returns an error (no args) 548 s->PutCString("error"); 549 break; 550 } 551 } 552 } 553 554 void 555 DWARFExpression::SetLocationListSlide (addr_t slide) 556 { 557 m_loclist_slide = slide; 558 } 559 560 int 561 DWARFExpression::GetRegisterKind () 562 { 563 return m_reg_kind; 564 } 565 566 void 567 DWARFExpression::SetRegisterKind (int reg_kind) 568 { 569 m_reg_kind = reg_kind; 570 } 571 572 bool 573 DWARFExpression::IsLocationList() const 574 { 575 return m_loclist_slide != LLDB_INVALID_ADDRESS; 576 } 577 578 void 579 DWARFExpression::GetDescription (Stream *s, lldb::DescriptionLevel level, addr_t location_list_base_addr) const 580 { 581 if (IsLocationList()) 582 { 583 // We have a location list 584 uint32_t offset = 0; 585 uint32_t count = 0; 586 addr_t curr_base_addr = location_list_base_addr; 587 while (m_data.ValidOffset(offset)) 588 { 589 lldb::addr_t begin_addr_offset = m_data.GetAddress(&offset); 590 lldb::addr_t end_addr_offset = m_data.GetAddress(&offset); 591 if (begin_addr_offset < end_addr_offset) 592 { 593 if (count > 0) 594 s->PutCString(", "); 595 VMRange addr_range(curr_base_addr + begin_addr_offset, curr_base_addr + end_addr_offset); 596 addr_range.Dump(s, 0, 8); 597 s->PutChar('{'); 598 uint32_t location_length = m_data.GetU16(&offset); 599 DumpLocation (s, offset, location_length, level); 600 s->PutChar('}'); 601 offset += location_length; 602 } 603 else if (begin_addr_offset == 0 && end_addr_offset == 0) 604 { 605 // The end of the location list is marked by both the start and end offset being zero 606 break; 607 } 608 else 609 { 610 if (m_data.GetAddressByteSize() == 4 && begin_addr_offset == 0xFFFFFFFFull || 611 m_data.GetAddressByteSize() == 8 && begin_addr_offset == 0xFFFFFFFFFFFFFFFFull) 612 { 613 curr_base_addr = end_addr_offset + location_list_base_addr; 614 // We have a new base address 615 if (count > 0) 616 s->PutCString(", "); 617 *s << "base_addr = " << end_addr_offset; 618 } 619 } 620 621 count++; 622 } 623 } 624 else 625 { 626 // We have a normal location that contains DW_OP location opcodes 627 DumpLocation (s, 0, m_data.GetByteSize(), level); 628 } 629 } 630 631 static bool 632 ReadRegisterValueAsScalar 633 ( 634 ExecutionContext *exe_ctx, 635 uint32_t reg_kind, 636 uint32_t reg_num, 637 Error *error_ptr, 638 Value &value 639 ) 640 { 641 if (exe_ctx && exe_ctx->frame) 642 { 643 RegisterContext *reg_context = exe_ctx->frame->GetRegisterContext(); 644 645 if (reg_context == NULL) 646 { 647 if (error_ptr) 648 error_ptr->SetErrorStringWithFormat("No register context in frame.\n"); 649 } 650 else 651 { 652 uint32_t native_reg = reg_context->ConvertRegisterKindToRegisterNumber(reg_kind, reg_num); 653 if (native_reg == LLDB_INVALID_REGNUM) 654 { 655 if (error_ptr) 656 error_ptr->SetErrorStringWithFormat("Unable to convert register kind=%u reg_num=%u to a native register number.\n", reg_kind, reg_num); 657 } 658 else 659 { 660 value.SetValueType (Value::eValueTypeScalar); 661 value.SetContext (Value::eContextTypeDCRegisterInfo, const_cast<RegisterInfo *>(reg_context->GetRegisterInfoAtIndex(native_reg))); 662 663 if (reg_context->ReadRegisterValue (native_reg, value.GetScalar())) 664 return true; 665 666 if (error_ptr) 667 error_ptr->SetErrorStringWithFormat("Failed to read register %u.\n", native_reg); 668 } 669 } 670 } 671 else 672 { 673 if (error_ptr) 674 error_ptr->SetErrorStringWithFormat("Invalid frame in execution context.\n"); 675 } 676 return false; 677 } 678 679 //bool 680 //DWARFExpression::LocationListContainsLoadAddress (Process* process, const Address &addr) const 681 //{ 682 // return LocationListContainsLoadAddress(process, addr.GetLoadAddress(process)); 683 //} 684 // 685 //bool 686 //DWARFExpression::LocationListContainsLoadAddress (Process* process, addr_t load_addr) const 687 //{ 688 // if (load_addr == LLDB_INVALID_ADDRESS) 689 // return false; 690 // 691 // if (IsLocationList()) 692 // { 693 // uint32_t offset = 0; 694 // 695 // addr_t loc_list_base_addr = m_loclist_slide.GetLoadAddress(process); 696 // 697 // if (loc_list_base_addr == LLDB_INVALID_ADDRESS) 698 // return false; 699 // 700 // while (m_data.ValidOffset(offset)) 701 // { 702 // // We need to figure out what the value is for the location. 703 // addr_t lo_pc = m_data.GetAddress(&offset); 704 // addr_t hi_pc = m_data.GetAddress(&offset); 705 // if (lo_pc == 0 && hi_pc == 0) 706 // break; 707 // else 708 // { 709 // lo_pc += loc_list_base_addr; 710 // hi_pc += loc_list_base_addr; 711 // 712 // if (lo_pc <= load_addr && load_addr < hi_pc) 713 // return true; 714 // 715 // offset += m_data.GetU16(&offset); 716 // } 717 // } 718 // } 719 // return false; 720 //} 721 722 bool 723 DWARFExpression::LocationListContainsAddress (lldb::addr_t loclist_base_addr, lldb::addr_t addr) const 724 { 725 if (addr == LLDB_INVALID_ADDRESS) 726 return false; 727 728 if (IsLocationList()) 729 { 730 uint32_t offset = 0; 731 732 if (loclist_base_addr == LLDB_INVALID_ADDRESS) 733 return false; 734 735 while (m_data.ValidOffset(offset)) 736 { 737 // We need to figure out what the value is for the location. 738 addr_t lo_pc = m_data.GetAddress(&offset); 739 addr_t hi_pc = m_data.GetAddress(&offset); 740 if (lo_pc == 0 && hi_pc == 0) 741 break; 742 else 743 { 744 lo_pc += loclist_base_addr - m_loclist_slide; 745 hi_pc += loclist_base_addr - m_loclist_slide; 746 747 if (lo_pc <= addr && addr < hi_pc) 748 return true; 749 750 offset += m_data.GetU16(&offset); 751 } 752 } 753 } 754 return false; 755 } 756 757 bool 758 DWARFExpression::Evaluate 759 ( 760 ExecutionContextScope *exe_scope, 761 clang::ASTContext *ast_context, 762 lldb::addr_t loclist_base_load_addr, 763 const Value* initial_value_ptr, 764 Value& result, 765 Error *error_ptr 766 ) const 767 { 768 ExecutionContext exe_ctx (exe_scope); 769 return Evaluate(&exe_ctx, ast_context, loclist_base_load_addr, initial_value_ptr, result, error_ptr); 770 } 771 772 bool 773 DWARFExpression::Evaluate 774 ( 775 ExecutionContext *exe_ctx, 776 clang::ASTContext *ast_context, 777 lldb::addr_t loclist_base_load_addr, 778 const Value* initial_value_ptr, 779 Value& result, 780 Error *error_ptr 781 ) const 782 { 783 if (IsLocationList()) 784 { 785 uint32_t offset = 0; 786 addr_t pc = exe_ctx->frame->GetRegisterContext()->GetPC(); 787 788 if (loclist_base_load_addr != LLDB_INVALID_ADDRESS) 789 { 790 if (pc == LLDB_INVALID_ADDRESS) 791 { 792 if (error_ptr) 793 error_ptr->SetErrorString("Invalid PC in frame."); 794 return false; 795 } 796 797 addr_t curr_loclist_base_load_addr = loclist_base_load_addr; 798 799 while (m_data.ValidOffset(offset)) 800 { 801 // We need to figure out what the value is for the location. 802 addr_t lo_pc = m_data.GetAddress(&offset); 803 addr_t hi_pc = m_data.GetAddress(&offset); 804 if (lo_pc == 0 && hi_pc == 0) 805 { 806 break; 807 } 808 else 809 { 810 lo_pc += curr_loclist_base_load_addr - m_loclist_slide; 811 hi_pc += curr_loclist_base_load_addr - m_loclist_slide; 812 813 uint16_t length = m_data.GetU16(&offset); 814 815 if (length > 0 && lo_pc <= pc && pc < hi_pc) 816 { 817 return DWARFExpression::Evaluate (exe_ctx, ast_context, m_data, m_expr_locals, m_decl_map, offset, length, m_reg_kind, initial_value_ptr, result, error_ptr); 818 } 819 offset += length; 820 } 821 } 822 } 823 if (error_ptr) 824 error_ptr->SetErrorStringWithFormat("Out of scope."); 825 return false; 826 } 827 828 // Not a location list, just a single expression. 829 return DWARFExpression::Evaluate (exe_ctx, ast_context, m_data, m_expr_locals, m_decl_map, 0, m_data.GetByteSize(), m_reg_kind, initial_value_ptr, result, error_ptr); 830 } 831 832 833 834 bool 835 DWARFExpression::Evaluate 836 ( 837 ExecutionContext *exe_ctx, 838 clang::ASTContext *ast_context, 839 const DataExtractor& opcodes, 840 ClangExpressionVariableList *expr_locals, 841 ClangExpressionDeclMap *decl_map, 842 const uint32_t opcodes_offset, 843 const uint32_t opcodes_length, 844 const uint32_t reg_kind, 845 const Value* initial_value_ptr, 846 Value& result, 847 Error *error_ptr 848 ) 849 { 850 std::vector<Value> stack; 851 852 if (initial_value_ptr) 853 stack.push_back(*initial_value_ptr); 854 855 uint32_t offset = opcodes_offset; 856 const uint32_t end_offset = opcodes_offset + opcodes_length; 857 Value tmp; 858 uint32_t reg_num; 859 860 // Make sure all of the data is available in opcodes. 861 if (!opcodes.ValidOffsetForDataOfSize(opcodes_offset, opcodes_length)) 862 { 863 if (error_ptr) 864 error_ptr->SetErrorString ("Invalid offset and/or length for opcodes buffer."); 865 return false; 866 } 867 Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS); 868 869 870 while (opcodes.ValidOffset(offset) && offset < end_offset) 871 { 872 const uint32_t op_offset = offset; 873 const uint8_t op = opcodes.GetU8(&offset); 874 875 if (log) 876 { 877 size_t count = stack.size(); 878 log->Printf("Stack before operation has %d values:", count); 879 for (size_t i=0; i<count; ++i) 880 { 881 StreamString new_value; 882 new_value.Printf("[%zu]", i); 883 stack[i].Dump(&new_value); 884 log->Printf(" %s", new_value.GetData()); 885 } 886 log->Printf("0x%8.8x: %s", op_offset, DW_OP_value_to_name(op)); 887 } 888 switch (op) 889 { 890 //---------------------------------------------------------------------- 891 // The DW_OP_addr operation has a single operand that encodes a machine 892 // address and whose size is the size of an address on the target machine. 893 //---------------------------------------------------------------------- 894 case DW_OP_addr: 895 stack.push_back(opcodes.GetAddress(&offset)); 896 stack.back().SetValueType (Value::eValueTypeFileAddress); 897 break; 898 899 //---------------------------------------------------------------------- 900 // The DW_OP_addr_sect_offset4 is used for any location expressions in 901 // shared libraries that have a location like: 902 // DW_OP_addr(0x1000) 903 // If this address resides in a shared library, then this virtual 904 // address won't make sense when it is evaluated in the context of a 905 // running process where shared libraries have been slid. To account for 906 // this, this new address type where we can store the section pointer 907 // and a 4 byte offset. 908 //---------------------------------------------------------------------- 909 // case DW_OP_addr_sect_offset4: 910 // { 911 // result_type = eResultTypeFileAddress; 912 // lldb::Section *sect = (lldb::Section *)opcodes.GetMaxU64(&offset, sizeof(void *)); 913 // lldb::addr_t sect_offset = opcodes.GetU32(&offset); 914 // 915 // Address so_addr (sect, sect_offset); 916 // lldb::addr_t load_addr = so_addr.GetLoadAddress(); 917 // if (load_addr != LLDB_INVALID_ADDRESS) 918 // { 919 // // We successfully resolve a file address to a load 920 // // address. 921 // stack.push_back(load_addr); 922 // break; 923 // } 924 // else 925 // { 926 // // We were able 927 // if (error_ptr) 928 // error_ptr->SetErrorStringWithFormat ("Section %s in %s is not currently loaded.\n", sect->GetName().AsCString(), sect->GetModule()->GetFileSpec().GetFilename().AsCString()); 929 // return false; 930 // } 931 // } 932 // break; 933 934 //---------------------------------------------------------------------- 935 // OPCODE: DW_OP_deref 936 // OPERANDS: none 937 // DESCRIPTION: Pops the top stack entry and treats it as an address. 938 // The value retrieved from that address is pushed. The size of the 939 // data retrieved from the dereferenced address is the size of an 940 // address on the target machine. 941 //---------------------------------------------------------------------- 942 case DW_OP_deref: 943 { 944 Value::ValueType value_type = stack.back().GetValueType(); 945 switch (value_type) 946 { 947 case Value::eValueTypeHostAddress: 948 { 949 void *src = (void *)stack.back().GetScalar().ULongLong(); 950 intptr_t ptr; 951 ::memcpy (&ptr, src, sizeof(void *)); 952 stack.back().GetScalar() = ptr; 953 stack.back().ClearContext(); 954 } 955 break; 956 case Value::eValueTypeLoadAddress: 957 if (exe_ctx) 958 { 959 if (exe_ctx->process) 960 { 961 lldb::addr_t pointer_addr = stack.back().GetScalar().ULongLong(LLDB_INVALID_ADDRESS); 962 uint8_t addr_bytes[sizeof(lldb::addr_t)]; 963 uint32_t addr_size = exe_ctx->process->GetAddressByteSize(); 964 Error error; 965 if (exe_ctx->process->ReadMemory(pointer_addr, &addr_bytes, addr_size, error) == addr_size) 966 { 967 DataExtractor addr_data(addr_bytes, sizeof(addr_bytes), exe_ctx->process->GetByteOrder(), addr_size); 968 uint32_t addr_data_offset = 0; 969 stack.back().GetScalar() = addr_data.GetPointer(&addr_data_offset); 970 stack.back().ClearContext(); 971 } 972 else 973 { 974 if (error_ptr) 975 error_ptr->SetErrorStringWithFormat ("Failed to dereference pointer from 0x%llx for DW_OP_deref: %s\n", 976 pointer_addr, 977 error.AsCString()); 978 return false; 979 } 980 } 981 else 982 { 983 if (error_ptr) 984 error_ptr->SetErrorStringWithFormat ("NULL process for DW_OP_deref.\n"); 985 return false; 986 } 987 } 988 else 989 { 990 if (error_ptr) 991 error_ptr->SetErrorStringWithFormat ("NULL execution context for DW_OP_deref.\n"); 992 return false; 993 } 994 break; 995 996 default: 997 break; 998 } 999 1000 } 1001 break; 1002 1003 //---------------------------------------------------------------------- 1004 // OPCODE: DW_OP_deref_size 1005 // OPERANDS: 1 1006 // 1 - uint8_t that specifies the size of the data to dereference. 1007 // DESCRIPTION: Behaves like the DW_OP_deref operation: it pops the top 1008 // stack entry and treats it as an address. The value retrieved from that 1009 // address is pushed. In the DW_OP_deref_size operation, however, the 1010 // size in bytes of the data retrieved from the dereferenced address is 1011 // specified by the single operand. This operand is a 1-byte unsigned 1012 // integral constant whose value may not be larger than the size of an 1013 // address on the target machine. The data retrieved is zero extended 1014 // to the size of an address on the target machine before being pushed 1015 // on the expression stack. 1016 //---------------------------------------------------------------------- 1017 case DW_OP_deref_size: 1018 if (error_ptr) 1019 error_ptr->SetErrorString("Unimplemented opcode: DW_OP_deref_size."); 1020 return false; 1021 1022 //---------------------------------------------------------------------- 1023 // OPCODE: DW_OP_xderef_size 1024 // OPERANDS: 1 1025 // 1 - uint8_t that specifies the size of the data to dereference. 1026 // DESCRIPTION: Behaves like the DW_OP_xderef operation: the entry at 1027 // the top of the stack is treated as an address. The second stack 1028 // entry is treated as an "address space identifier" for those 1029 // architectures that support multiple address spaces. The top two 1030 // stack elements are popped, a data item is retrieved through an 1031 // implementation-defined address calculation and pushed as the new 1032 // stack top. In the DW_OP_xderef_size operation, however, the size in 1033 // bytes of the data retrieved from the dereferenced address is 1034 // specified by the single operand. This operand is a 1-byte unsigned 1035 // integral constant whose value may not be larger than the size of an 1036 // address on the target machine. The data retrieved is zero extended 1037 // to the size of an address on the target machine before being pushed 1038 // on the expression stack. 1039 //---------------------------------------------------------------------- 1040 case DW_OP_xderef_size: 1041 if (error_ptr) 1042 error_ptr->SetErrorString("Unimplemented opcode: DW_OP_xderef_size."); 1043 return false; 1044 //---------------------------------------------------------------------- 1045 // OPCODE: DW_OP_xderef 1046 // OPERANDS: none 1047 // DESCRIPTION: Provides an extended dereference mechanism. The entry at 1048 // the top of the stack is treated as an address. The second stack entry 1049 // is treated as an "address space identifier" for those architectures 1050 // that support multiple address spaces. The top two stack elements are 1051 // popped, a data item is retrieved through an implementation-defined 1052 // address calculation and pushed as the new stack top. The size of the 1053 // data retrieved from the dereferenced address is the size of an address 1054 // on the target machine. 1055 //---------------------------------------------------------------------- 1056 case DW_OP_xderef: 1057 if (error_ptr) 1058 error_ptr->SetErrorString("Unimplemented opcode: DW_OP_xderef."); 1059 return false; 1060 1061 //---------------------------------------------------------------------- 1062 // All DW_OP_constXXX opcodes have a single operand as noted below: 1063 // 1064 // Opcode Operand 1 1065 // --------------- ---------------------------------------------------- 1066 // DW_OP_const1u 1-byte unsigned integer constant 1067 // DW_OP_const1s 1-byte signed integer constant 1068 // DW_OP_const2u 2-byte unsigned integer constant 1069 // DW_OP_const2s 2-byte signed integer constant 1070 // DW_OP_const4u 4-byte unsigned integer constant 1071 // DW_OP_const4s 4-byte signed integer constant 1072 // DW_OP_const8u 8-byte unsigned integer constant 1073 // DW_OP_const8s 8-byte signed integer constant 1074 // DW_OP_constu unsigned LEB128 integer constant 1075 // DW_OP_consts signed LEB128 integer constant 1076 //---------------------------------------------------------------------- 1077 case DW_OP_const1u : stack.push_back(( uint8_t)opcodes.GetU8(&offset)); break; 1078 case DW_OP_const1s : stack.push_back(( int8_t)opcodes.GetU8(&offset)); break; 1079 case DW_OP_const2u : stack.push_back((uint16_t)opcodes.GetU16(&offset)); break; 1080 case DW_OP_const2s : stack.push_back(( int16_t)opcodes.GetU16(&offset)); break; 1081 case DW_OP_const4u : stack.push_back((uint32_t)opcodes.GetU32(&offset)); break; 1082 case DW_OP_const4s : stack.push_back(( int32_t)opcodes.GetU32(&offset)); break; 1083 case DW_OP_const8u : stack.push_back((uint64_t)opcodes.GetU64(&offset)); break; 1084 case DW_OP_const8s : stack.push_back(( int64_t)opcodes.GetU64(&offset)); break; 1085 case DW_OP_constu : stack.push_back(opcodes.GetULEB128(&offset)); break; 1086 case DW_OP_consts : stack.push_back(opcodes.GetSLEB128(&offset)); break; 1087 1088 //---------------------------------------------------------------------- 1089 // OPCODE: DW_OP_dup 1090 // OPERANDS: none 1091 // DESCRIPTION: duplicates the value at the top of the stack 1092 //---------------------------------------------------------------------- 1093 case DW_OP_dup: 1094 if (stack.empty()) 1095 { 1096 if (error_ptr) 1097 error_ptr->SetErrorString("Expression stack empty for DW_OP_dup."); 1098 return false; 1099 } 1100 else 1101 stack.push_back(stack.back()); 1102 break; 1103 1104 //---------------------------------------------------------------------- 1105 // OPCODE: DW_OP_drop 1106 // OPERANDS: none 1107 // DESCRIPTION: pops the value at the top of the stack 1108 //---------------------------------------------------------------------- 1109 case DW_OP_drop: 1110 if (stack.empty()) 1111 { 1112 if (error_ptr) 1113 error_ptr->SetErrorString("Expression stack empty for DW_OP_drop."); 1114 return false; 1115 } 1116 else 1117 stack.pop_back(); 1118 break; 1119 1120 //---------------------------------------------------------------------- 1121 // OPCODE: DW_OP_over 1122 // OPERANDS: none 1123 // DESCRIPTION: Duplicates the entry currently second in the stack at 1124 // the top of the stack. 1125 //---------------------------------------------------------------------- 1126 case DW_OP_over: 1127 if (stack.size() < 2) 1128 { 1129 if (error_ptr) 1130 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_over."); 1131 return false; 1132 } 1133 else 1134 stack.push_back(stack[stack.size() - 2]); 1135 break; 1136 1137 1138 //---------------------------------------------------------------------- 1139 // OPCODE: DW_OP_pick 1140 // OPERANDS: uint8_t index into the current stack 1141 // DESCRIPTION: The stack entry with the specified index (0 through 255, 1142 // inclusive) is pushed on the stack 1143 //---------------------------------------------------------------------- 1144 case DW_OP_pick: 1145 { 1146 uint8_t pick_idx = opcodes.GetU8(&offset); 1147 if (pick_idx < stack.size()) 1148 stack.push_back(stack[pick_idx]); 1149 else 1150 { 1151 if (error_ptr) 1152 error_ptr->SetErrorStringWithFormat("Index %u out of range for DW_OP_pick.\n", pick_idx); 1153 return false; 1154 } 1155 } 1156 break; 1157 1158 //---------------------------------------------------------------------- 1159 // OPCODE: DW_OP_swap 1160 // OPERANDS: none 1161 // DESCRIPTION: swaps the top two stack entries. The entry at the top 1162 // of the stack becomes the second stack entry, and the second entry 1163 // becomes the top of the stack 1164 //---------------------------------------------------------------------- 1165 case DW_OP_swap: 1166 if (stack.size() < 2) 1167 { 1168 if (error_ptr) 1169 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_swap."); 1170 return false; 1171 } 1172 else 1173 { 1174 tmp = stack.back(); 1175 stack.back() = stack[stack.size() - 2]; 1176 stack[stack.size() - 2] = tmp; 1177 } 1178 break; 1179 1180 //---------------------------------------------------------------------- 1181 // OPCODE: DW_OP_rot 1182 // OPERANDS: none 1183 // DESCRIPTION: Rotates the first three stack entries. The entry at 1184 // the top of the stack becomes the third stack entry, the second 1185 // entry becomes the top of the stack, and the third entry becomes 1186 // the second entry. 1187 //---------------------------------------------------------------------- 1188 case DW_OP_rot: 1189 if (stack.size() < 3) 1190 { 1191 if (error_ptr) 1192 error_ptr->SetErrorString("Expression stack needs at least 3 items for DW_OP_rot."); 1193 return false; 1194 } 1195 else 1196 { 1197 size_t last_idx = stack.size() - 1; 1198 Value old_top = stack[last_idx]; 1199 stack[last_idx] = stack[last_idx - 1]; 1200 stack[last_idx - 1] = stack[last_idx - 2]; 1201 stack[last_idx - 2] = old_top; 1202 } 1203 break; 1204 1205 //---------------------------------------------------------------------- 1206 // OPCODE: DW_OP_abs 1207 // OPERANDS: none 1208 // DESCRIPTION: pops the top stack entry, interprets it as a signed 1209 // value and pushes its absolute value. If the absolute value can not be 1210 // represented, the result is undefined. 1211 //---------------------------------------------------------------------- 1212 case DW_OP_abs: 1213 if (stack.empty()) 1214 { 1215 if (error_ptr) 1216 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_abs."); 1217 return false; 1218 } 1219 else if (stack.back().ResolveValue(exe_ctx, ast_context).AbsoluteValue() == false) 1220 { 1221 if (error_ptr) 1222 error_ptr->SetErrorString("Failed to take the absolute value of the first stack item."); 1223 return false; 1224 } 1225 break; 1226 1227 //---------------------------------------------------------------------- 1228 // OPCODE: DW_OP_and 1229 // OPERANDS: none 1230 // DESCRIPTION: pops the top two stack values, performs a bitwise and 1231 // operation on the two, and pushes the result. 1232 //---------------------------------------------------------------------- 1233 case DW_OP_and: 1234 if (stack.size() < 2) 1235 { 1236 if (error_ptr) 1237 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_and."); 1238 return false; 1239 } 1240 else 1241 { 1242 tmp = stack.back(); 1243 stack.pop_back(); 1244 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) & tmp.ResolveValue(exe_ctx, ast_context); 1245 } 1246 break; 1247 1248 //---------------------------------------------------------------------- 1249 // OPCODE: DW_OP_div 1250 // OPERANDS: none 1251 // DESCRIPTION: pops the top two stack values, divides the former second 1252 // entry by the former top of the stack using signed division, and 1253 // pushes the result. 1254 //---------------------------------------------------------------------- 1255 case DW_OP_div: 1256 if (stack.size() < 2) 1257 { 1258 if (error_ptr) 1259 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_div."); 1260 return false; 1261 } 1262 else 1263 { 1264 tmp = stack.back(); 1265 if (tmp.ResolveValue(exe_ctx, ast_context).IsZero()) 1266 { 1267 if (error_ptr) 1268 error_ptr->SetErrorString("Divide by zero."); 1269 return false; 1270 } 1271 else 1272 { 1273 stack.pop_back(); 1274 stack.back() = stack.back().ResolveValue(exe_ctx, ast_context) / tmp.ResolveValue(exe_ctx, ast_context); 1275 if (!stack.back().ResolveValue(exe_ctx, ast_context).IsValid()) 1276 { 1277 if (error_ptr) 1278 error_ptr->SetErrorString("Divide failed."); 1279 return false; 1280 } 1281 } 1282 } 1283 break; 1284 1285 //---------------------------------------------------------------------- 1286 // OPCODE: DW_OP_minus 1287 // OPERANDS: none 1288 // DESCRIPTION: pops the top two stack values, subtracts the former top 1289 // of the stack from the former second entry, and pushes the result. 1290 //---------------------------------------------------------------------- 1291 case DW_OP_minus: 1292 if (stack.size() < 2) 1293 { 1294 if (error_ptr) 1295 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_minus."); 1296 return false; 1297 } 1298 else 1299 { 1300 tmp = stack.back(); 1301 stack.pop_back(); 1302 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) - tmp.ResolveValue(exe_ctx, ast_context); 1303 } 1304 break; 1305 1306 //---------------------------------------------------------------------- 1307 // OPCODE: DW_OP_mod 1308 // OPERANDS: none 1309 // DESCRIPTION: pops the top two stack values and pushes the result of 1310 // the calculation: former second stack entry modulo the former top of 1311 // the stack. 1312 //---------------------------------------------------------------------- 1313 case DW_OP_mod: 1314 if (stack.size() < 2) 1315 { 1316 if (error_ptr) 1317 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_mod."); 1318 return false; 1319 } 1320 else 1321 { 1322 tmp = stack.back(); 1323 stack.pop_back(); 1324 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) % tmp.ResolveValue(exe_ctx, ast_context); 1325 } 1326 break; 1327 1328 1329 //---------------------------------------------------------------------- 1330 // OPCODE: DW_OP_mul 1331 // OPERANDS: none 1332 // DESCRIPTION: pops the top two stack entries, multiplies them 1333 // together, and pushes the result. 1334 //---------------------------------------------------------------------- 1335 case DW_OP_mul: 1336 if (stack.size() < 2) 1337 { 1338 if (error_ptr) 1339 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_mul."); 1340 return false; 1341 } 1342 else 1343 { 1344 tmp = stack.back(); 1345 stack.pop_back(); 1346 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) * tmp.ResolveValue(exe_ctx, ast_context); 1347 } 1348 break; 1349 1350 //---------------------------------------------------------------------- 1351 // OPCODE: DW_OP_neg 1352 // OPERANDS: none 1353 // DESCRIPTION: pops the top stack entry, and pushes its negation. 1354 //---------------------------------------------------------------------- 1355 case DW_OP_neg: 1356 if (stack.empty()) 1357 { 1358 if (error_ptr) 1359 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_neg."); 1360 return false; 1361 } 1362 else 1363 { 1364 if (stack.back().ResolveValue(exe_ctx, ast_context).UnaryNegate() == false) 1365 { 1366 if (error_ptr) 1367 error_ptr->SetErrorString("Unary negate failed."); 1368 return false; 1369 } 1370 } 1371 break; 1372 1373 //---------------------------------------------------------------------- 1374 // OPCODE: DW_OP_not 1375 // OPERANDS: none 1376 // DESCRIPTION: pops the top stack entry, and pushes its bitwise 1377 // complement 1378 //---------------------------------------------------------------------- 1379 case DW_OP_not: 1380 if (stack.empty()) 1381 { 1382 if (error_ptr) 1383 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_not."); 1384 return false; 1385 } 1386 else 1387 { 1388 if (stack.back().ResolveValue(exe_ctx, ast_context).OnesComplement() == false) 1389 { 1390 if (error_ptr) 1391 error_ptr->SetErrorString("Logical NOT failed."); 1392 return false; 1393 } 1394 } 1395 break; 1396 1397 //---------------------------------------------------------------------- 1398 // OPCODE: DW_OP_or 1399 // OPERANDS: none 1400 // DESCRIPTION: pops the top two stack entries, performs a bitwise or 1401 // operation on the two, and pushes the result. 1402 //---------------------------------------------------------------------- 1403 case DW_OP_or: 1404 if (stack.size() < 2) 1405 { 1406 if (error_ptr) 1407 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_or."); 1408 return false; 1409 } 1410 else 1411 { 1412 tmp = stack.back(); 1413 stack.pop_back(); 1414 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) | tmp.ResolveValue(exe_ctx, ast_context); 1415 } 1416 break; 1417 1418 //---------------------------------------------------------------------- 1419 // OPCODE: DW_OP_plus 1420 // OPERANDS: none 1421 // DESCRIPTION: pops the top two stack entries, adds them together, and 1422 // pushes the result. 1423 //---------------------------------------------------------------------- 1424 case DW_OP_plus: 1425 if (stack.size() < 2) 1426 { 1427 if (error_ptr) 1428 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_plus."); 1429 return false; 1430 } 1431 else 1432 { 1433 tmp = stack.back(); 1434 stack.pop_back(); 1435 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) + tmp.ResolveValue(exe_ctx, ast_context); 1436 } 1437 break; 1438 1439 //---------------------------------------------------------------------- 1440 // OPCODE: DW_OP_plus_uconst 1441 // OPERANDS: none 1442 // DESCRIPTION: pops the top stack entry, adds it to the unsigned LEB128 1443 // constant operand and pushes the result. 1444 //---------------------------------------------------------------------- 1445 case DW_OP_plus_uconst: 1446 if (stack.empty()) 1447 { 1448 if (error_ptr) 1449 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_plus_uconst."); 1450 return false; 1451 } 1452 else 1453 { 1454 uint32_t uconst_value = opcodes.GetULEB128(&offset); 1455 // Implicit conversion from a UINT to a Scalar... 1456 stack.back().ResolveValue(exe_ctx, ast_context) += uconst_value; 1457 if (!stack.back().ResolveValue(exe_ctx, ast_context).IsValid()) 1458 { 1459 if (error_ptr) 1460 error_ptr->SetErrorString("DW_OP_plus_uconst failed."); 1461 return false; 1462 } 1463 } 1464 break; 1465 1466 //---------------------------------------------------------------------- 1467 // OPCODE: DW_OP_shl 1468 // OPERANDS: none 1469 // DESCRIPTION: pops the top two stack entries, shifts the former 1470 // second entry left by the number of bits specified by the former top 1471 // of the stack, and pushes the result. 1472 //---------------------------------------------------------------------- 1473 case DW_OP_shl: 1474 if (stack.size() < 2) 1475 { 1476 if (error_ptr) 1477 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_shl."); 1478 return false; 1479 } 1480 else 1481 { 1482 tmp = stack.back(); 1483 stack.pop_back(); 1484 stack.back().ResolveValue(exe_ctx, ast_context) <<= tmp.ResolveValue(exe_ctx, ast_context); 1485 } 1486 break; 1487 1488 //---------------------------------------------------------------------- 1489 // OPCODE: DW_OP_shr 1490 // OPERANDS: none 1491 // DESCRIPTION: pops the top two stack entries, shifts the former second 1492 // entry right logically (filling with zero bits) by the number of bits 1493 // specified by the former top of the stack, and pushes the result. 1494 //---------------------------------------------------------------------- 1495 case DW_OP_shr: 1496 if (stack.size() < 2) 1497 { 1498 if (error_ptr) 1499 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_shr."); 1500 return false; 1501 } 1502 else 1503 { 1504 tmp = stack.back(); 1505 stack.pop_back(); 1506 if (stack.back().ResolveValue(exe_ctx, ast_context).ShiftRightLogical(tmp.ResolveValue(exe_ctx, ast_context)) == false) 1507 { 1508 if (error_ptr) 1509 error_ptr->SetErrorString("DW_OP_shr failed."); 1510 return false; 1511 } 1512 } 1513 break; 1514 1515 //---------------------------------------------------------------------- 1516 // OPCODE: DW_OP_shra 1517 // OPERANDS: none 1518 // DESCRIPTION: pops the top two stack entries, shifts the former second 1519 // entry right arithmetically (divide the magnitude by 2, keep the same 1520 // sign for the result) by the number of bits specified by the former 1521 // top of the stack, and pushes the result. 1522 //---------------------------------------------------------------------- 1523 case DW_OP_shra: 1524 if (stack.size() < 2) 1525 { 1526 if (error_ptr) 1527 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_shra."); 1528 return false; 1529 } 1530 else 1531 { 1532 tmp = stack.back(); 1533 stack.pop_back(); 1534 stack.back().ResolveValue(exe_ctx, ast_context) >>= tmp.ResolveValue(exe_ctx, ast_context); 1535 } 1536 break; 1537 1538 //---------------------------------------------------------------------- 1539 // OPCODE: DW_OP_xor 1540 // OPERANDS: none 1541 // DESCRIPTION: pops the top two stack entries, performs the bitwise 1542 // exclusive-or operation on the two, and pushes the result. 1543 //---------------------------------------------------------------------- 1544 case DW_OP_xor: 1545 if (stack.size() < 2) 1546 { 1547 if (error_ptr) 1548 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_xor."); 1549 return false; 1550 } 1551 else 1552 { 1553 tmp = stack.back(); 1554 stack.pop_back(); 1555 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) ^ tmp.ResolveValue(exe_ctx, ast_context); 1556 } 1557 break; 1558 1559 1560 //---------------------------------------------------------------------- 1561 // OPCODE: DW_OP_skip 1562 // OPERANDS: int16_t 1563 // DESCRIPTION: An unconditional branch. Its single operand is a 2-byte 1564 // signed integer constant. The 2-byte constant is the number of bytes 1565 // of the DWARF expression to skip forward or backward from the current 1566 // operation, beginning after the 2-byte constant. 1567 //---------------------------------------------------------------------- 1568 case DW_OP_skip: 1569 { 1570 int16_t skip_offset = (int16_t)opcodes.GetU16(&offset); 1571 uint32_t new_offset = offset + skip_offset; 1572 if (new_offset >= opcodes_offset && new_offset < end_offset) 1573 offset = new_offset; 1574 else 1575 { 1576 if (error_ptr) 1577 error_ptr->SetErrorString("Invalid opcode offset in DW_OP_skip."); 1578 return false; 1579 } 1580 } 1581 break; 1582 1583 //---------------------------------------------------------------------- 1584 // OPCODE: DW_OP_bra 1585 // OPERANDS: int16_t 1586 // DESCRIPTION: A conditional branch. Its single operand is a 2-byte 1587 // signed integer constant. This operation pops the top of stack. If 1588 // the value popped is not the constant 0, the 2-byte constant operand 1589 // is the number of bytes of the DWARF expression to skip forward or 1590 // backward from the current operation, beginning after the 2-byte 1591 // constant. 1592 //---------------------------------------------------------------------- 1593 case DW_OP_bra: 1594 { 1595 tmp = stack.back(); 1596 stack.pop_back(); 1597 int16_t bra_offset = (int16_t)opcodes.GetU16(&offset); 1598 Scalar zero(0); 1599 if (tmp.ResolveValue(exe_ctx, ast_context) != zero) 1600 { 1601 uint32_t new_offset = offset + bra_offset; 1602 if (new_offset >= opcodes_offset && new_offset < end_offset) 1603 offset = new_offset; 1604 else 1605 { 1606 if (error_ptr) 1607 error_ptr->SetErrorString("Invalid opcode offset in DW_OP_bra."); 1608 return false; 1609 } 1610 } 1611 } 1612 break; 1613 1614 //---------------------------------------------------------------------- 1615 // OPCODE: DW_OP_eq 1616 // OPERANDS: none 1617 // DESCRIPTION: pops the top two stack values, compares using the 1618 // equals (==) operator. 1619 // STACK RESULT: push the constant value 1 onto the stack if the result 1620 // of the operation is true or the constant value 0 if the result of the 1621 // operation is false. 1622 //---------------------------------------------------------------------- 1623 case DW_OP_eq: 1624 if (stack.size() < 2) 1625 { 1626 if (error_ptr) 1627 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_eq."); 1628 return false; 1629 } 1630 else 1631 { 1632 tmp = stack.back(); 1633 stack.pop_back(); 1634 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) == tmp.ResolveValue(exe_ctx, ast_context); 1635 } 1636 break; 1637 1638 //---------------------------------------------------------------------- 1639 // OPCODE: DW_OP_ge 1640 // OPERANDS: none 1641 // DESCRIPTION: pops the top two stack values, compares using the 1642 // greater than or equal to (>=) operator. 1643 // STACK RESULT: push the constant value 1 onto the stack if the result 1644 // of the operation is true or the constant value 0 if the result of the 1645 // operation is false. 1646 //---------------------------------------------------------------------- 1647 case DW_OP_ge: 1648 if (stack.size() < 2) 1649 { 1650 if (error_ptr) 1651 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_ge."); 1652 return false; 1653 } 1654 else 1655 { 1656 tmp = stack.back(); 1657 stack.pop_back(); 1658 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) >= tmp.ResolveValue(exe_ctx, ast_context); 1659 } 1660 break; 1661 1662 //---------------------------------------------------------------------- 1663 // OPCODE: DW_OP_gt 1664 // OPERANDS: none 1665 // DESCRIPTION: pops the top two stack values, compares using the 1666 // greater than (>) operator. 1667 // STACK RESULT: push the constant value 1 onto the stack if the result 1668 // of the operation is true or the constant value 0 if the result of the 1669 // operation is false. 1670 //---------------------------------------------------------------------- 1671 case DW_OP_gt: 1672 if (stack.size() < 2) 1673 { 1674 if (error_ptr) 1675 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_gt."); 1676 return false; 1677 } 1678 else 1679 { 1680 tmp = stack.back(); 1681 stack.pop_back(); 1682 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) > tmp.ResolveValue(exe_ctx, ast_context); 1683 } 1684 break; 1685 1686 //---------------------------------------------------------------------- 1687 // OPCODE: DW_OP_le 1688 // OPERANDS: none 1689 // DESCRIPTION: pops the top two stack values, compares using the 1690 // less than or equal to (<=) operator. 1691 // STACK RESULT: push the constant value 1 onto the stack if the result 1692 // of the operation is true or the constant value 0 if the result of the 1693 // operation is false. 1694 //---------------------------------------------------------------------- 1695 case DW_OP_le: 1696 if (stack.size() < 2) 1697 { 1698 if (error_ptr) 1699 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_le."); 1700 return false; 1701 } 1702 else 1703 { 1704 tmp = stack.back(); 1705 stack.pop_back(); 1706 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) <= tmp.ResolveValue(exe_ctx, ast_context); 1707 } 1708 break; 1709 1710 //---------------------------------------------------------------------- 1711 // OPCODE: DW_OP_lt 1712 // OPERANDS: none 1713 // DESCRIPTION: pops the top two stack values, compares using the 1714 // less than (<) operator. 1715 // STACK RESULT: push the constant value 1 onto the stack if the result 1716 // of the operation is true or the constant value 0 if the result of the 1717 // operation is false. 1718 //---------------------------------------------------------------------- 1719 case DW_OP_lt: 1720 if (stack.size() < 2) 1721 { 1722 if (error_ptr) 1723 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_lt."); 1724 return false; 1725 } 1726 else 1727 { 1728 tmp = stack.back(); 1729 stack.pop_back(); 1730 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) < tmp.ResolveValue(exe_ctx, ast_context); 1731 } 1732 break; 1733 1734 //---------------------------------------------------------------------- 1735 // OPCODE: DW_OP_ne 1736 // OPERANDS: none 1737 // DESCRIPTION: pops the top two stack values, compares using the 1738 // not equal (!=) operator. 1739 // STACK RESULT: push the constant value 1 onto the stack if the result 1740 // of the operation is true or the constant value 0 if the result of the 1741 // operation is false. 1742 //---------------------------------------------------------------------- 1743 case DW_OP_ne: 1744 if (stack.size() < 2) 1745 { 1746 if (error_ptr) 1747 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_ne."); 1748 return false; 1749 } 1750 else 1751 { 1752 tmp = stack.back(); 1753 stack.pop_back(); 1754 stack.back().ResolveValue(exe_ctx, ast_context) = stack.back().ResolveValue(exe_ctx, ast_context) != tmp.ResolveValue(exe_ctx, ast_context); 1755 } 1756 break; 1757 1758 //---------------------------------------------------------------------- 1759 // OPCODE: DW_OP_litn 1760 // OPERANDS: none 1761 // DESCRIPTION: encode the unsigned literal values from 0 through 31. 1762 // STACK RESULT: push the unsigned literal constant value onto the top 1763 // of the stack. 1764 //---------------------------------------------------------------------- 1765 case DW_OP_lit0: 1766 case DW_OP_lit1: 1767 case DW_OP_lit2: 1768 case DW_OP_lit3: 1769 case DW_OP_lit4: 1770 case DW_OP_lit5: 1771 case DW_OP_lit6: 1772 case DW_OP_lit7: 1773 case DW_OP_lit8: 1774 case DW_OP_lit9: 1775 case DW_OP_lit10: 1776 case DW_OP_lit11: 1777 case DW_OP_lit12: 1778 case DW_OP_lit13: 1779 case DW_OP_lit14: 1780 case DW_OP_lit15: 1781 case DW_OP_lit16: 1782 case DW_OP_lit17: 1783 case DW_OP_lit18: 1784 case DW_OP_lit19: 1785 case DW_OP_lit20: 1786 case DW_OP_lit21: 1787 case DW_OP_lit22: 1788 case DW_OP_lit23: 1789 case DW_OP_lit24: 1790 case DW_OP_lit25: 1791 case DW_OP_lit26: 1792 case DW_OP_lit27: 1793 case DW_OP_lit28: 1794 case DW_OP_lit29: 1795 case DW_OP_lit30: 1796 case DW_OP_lit31: 1797 stack.push_back(op - DW_OP_lit0); 1798 break; 1799 1800 //---------------------------------------------------------------------- 1801 // OPCODE: DW_OP_regN 1802 // OPERANDS: none 1803 // DESCRIPTION: Push the value in register n on the top of the stack. 1804 //---------------------------------------------------------------------- 1805 case DW_OP_reg0: 1806 case DW_OP_reg1: 1807 case DW_OP_reg2: 1808 case DW_OP_reg3: 1809 case DW_OP_reg4: 1810 case DW_OP_reg5: 1811 case DW_OP_reg6: 1812 case DW_OP_reg7: 1813 case DW_OP_reg8: 1814 case DW_OP_reg9: 1815 case DW_OP_reg10: 1816 case DW_OP_reg11: 1817 case DW_OP_reg12: 1818 case DW_OP_reg13: 1819 case DW_OP_reg14: 1820 case DW_OP_reg15: 1821 case DW_OP_reg16: 1822 case DW_OP_reg17: 1823 case DW_OP_reg18: 1824 case DW_OP_reg19: 1825 case DW_OP_reg20: 1826 case DW_OP_reg21: 1827 case DW_OP_reg22: 1828 case DW_OP_reg23: 1829 case DW_OP_reg24: 1830 case DW_OP_reg25: 1831 case DW_OP_reg26: 1832 case DW_OP_reg27: 1833 case DW_OP_reg28: 1834 case DW_OP_reg29: 1835 case DW_OP_reg30: 1836 case DW_OP_reg31: 1837 { 1838 reg_num = op - DW_OP_reg0; 1839 1840 if (ReadRegisterValueAsScalar (exe_ctx, reg_kind, reg_num, error_ptr, tmp)) 1841 stack.push_back(tmp); 1842 else 1843 return false; 1844 } 1845 break; 1846 //---------------------------------------------------------------------- 1847 // OPCODE: DW_OP_regx 1848 // OPERANDS: 1849 // ULEB128 literal operand that encodes the register. 1850 // DESCRIPTION: Push the value in register on the top of the stack. 1851 //---------------------------------------------------------------------- 1852 case DW_OP_regx: 1853 { 1854 reg_num = opcodes.GetULEB128(&offset); 1855 if (ReadRegisterValueAsScalar (exe_ctx, reg_kind, reg_num, error_ptr, tmp)) 1856 stack.push_back(tmp); 1857 else 1858 return false; 1859 } 1860 break; 1861 1862 //---------------------------------------------------------------------- 1863 // OPCODE: DW_OP_bregN 1864 // OPERANDS: 1865 // SLEB128 offset from register N 1866 // DESCRIPTION: Value is in memory at the address specified by register 1867 // N plus an offset. 1868 //---------------------------------------------------------------------- 1869 case DW_OP_breg0: 1870 case DW_OP_breg1: 1871 case DW_OP_breg2: 1872 case DW_OP_breg3: 1873 case DW_OP_breg4: 1874 case DW_OP_breg5: 1875 case DW_OP_breg6: 1876 case DW_OP_breg7: 1877 case DW_OP_breg8: 1878 case DW_OP_breg9: 1879 case DW_OP_breg10: 1880 case DW_OP_breg11: 1881 case DW_OP_breg12: 1882 case DW_OP_breg13: 1883 case DW_OP_breg14: 1884 case DW_OP_breg15: 1885 case DW_OP_breg16: 1886 case DW_OP_breg17: 1887 case DW_OP_breg18: 1888 case DW_OP_breg19: 1889 case DW_OP_breg20: 1890 case DW_OP_breg21: 1891 case DW_OP_breg22: 1892 case DW_OP_breg23: 1893 case DW_OP_breg24: 1894 case DW_OP_breg25: 1895 case DW_OP_breg26: 1896 case DW_OP_breg27: 1897 case DW_OP_breg28: 1898 case DW_OP_breg29: 1899 case DW_OP_breg30: 1900 case DW_OP_breg31: 1901 { 1902 reg_num = op - DW_OP_breg0; 1903 1904 if (ReadRegisterValueAsScalar (exe_ctx, reg_kind, reg_num, error_ptr, tmp)) 1905 { 1906 int64_t breg_offset = opcodes.GetSLEB128(&offset); 1907 tmp.ResolveValue(exe_ctx, ast_context) += (uint64_t)breg_offset; 1908 stack.push_back(tmp); 1909 stack.back().SetValueType (Value::eValueTypeLoadAddress); 1910 } 1911 else 1912 return false; 1913 } 1914 break; 1915 //---------------------------------------------------------------------- 1916 // OPCODE: DW_OP_bregx 1917 // OPERANDS: 2 1918 // ULEB128 literal operand that encodes the register. 1919 // SLEB128 offset from register N 1920 // DESCRIPTION: Value is in memory at the address specified by register 1921 // N plus an offset. 1922 //---------------------------------------------------------------------- 1923 case DW_OP_bregx: 1924 { 1925 reg_num = opcodes.GetULEB128(&offset); 1926 1927 if (ReadRegisterValueAsScalar (exe_ctx, reg_kind, reg_num, error_ptr, tmp)) 1928 { 1929 int64_t breg_offset = opcodes.GetSLEB128(&offset); 1930 tmp.ResolveValue(exe_ctx, ast_context) += (uint64_t)breg_offset; 1931 stack.push_back(tmp); 1932 stack.back().SetValueType (Value::eValueTypeLoadAddress); 1933 } 1934 else 1935 return false; 1936 } 1937 break; 1938 1939 case DW_OP_fbreg: 1940 if (exe_ctx && exe_ctx->frame) 1941 { 1942 Scalar value; 1943 if (exe_ctx->frame->GetFrameBaseValue(value, error_ptr)) 1944 { 1945 int64_t fbreg_offset = opcodes.GetSLEB128(&offset); 1946 value += fbreg_offset; 1947 stack.push_back(value); 1948 stack.back().SetValueType (Value::eValueTypeLoadAddress); 1949 } 1950 else 1951 return false; 1952 } 1953 else 1954 { 1955 if (error_ptr) 1956 error_ptr->SetErrorString ("Invalid stack frame in context for DW_OP_fbreg opcode."); 1957 return false; 1958 } 1959 break; 1960 1961 //---------------------------------------------------------------------- 1962 // OPCODE: DW_OP_nop 1963 // OPERANDS: none 1964 // DESCRIPTION: A place holder. It has no effect on the location stack 1965 // or any of its values. 1966 //---------------------------------------------------------------------- 1967 case DW_OP_nop: 1968 break; 1969 1970 //---------------------------------------------------------------------- 1971 // OPCODE: DW_OP_piece 1972 // OPERANDS: 1 1973 // ULEB128: byte size of the piece 1974 // DESCRIPTION: The operand describes the size in bytes of the piece of 1975 // the object referenced by the DWARF expression whose result is at the 1976 // top of the stack. If the piece is located in a register, but does not 1977 // occupy the entire register, the placement of the piece within that 1978 // register is defined by the ABI. 1979 // 1980 // Many compilers store a single variable in sets of registers, or store 1981 // a variable partially in memory and partially in registers. 1982 // DW_OP_piece provides a way of describing how large a part of a 1983 // variable a particular DWARF expression refers to. 1984 //---------------------------------------------------------------------- 1985 case DW_OP_piece: 1986 if (error_ptr) 1987 error_ptr->SetErrorString ("Unimplemented opcode DW_OP_piece."); 1988 return false; 1989 1990 //---------------------------------------------------------------------- 1991 // OPCODE: DW_OP_push_object_address 1992 // OPERANDS: none 1993 // DESCRIPTION: Pushes the address of the object currently being 1994 // evaluated as part of evaluation of a user presented expression. 1995 // This object may correspond to an independent variable described by 1996 // its own DIE or it may be a component of an array, structure, or class 1997 // whose address has been dynamically determined by an earlier step 1998 // during user expression evaluation. 1999 //---------------------------------------------------------------------- 2000 case DW_OP_push_object_address: 2001 if (error_ptr) 2002 error_ptr->SetErrorString ("Unimplemented opcode DW_OP_push_object_address."); 2003 return false; 2004 2005 //---------------------------------------------------------------------- 2006 // OPCODE: DW_OP_call2 2007 // OPERANDS: 2008 // uint16_t compile unit relative offset of a DIE 2009 // DESCRIPTION: Performs subroutine calls during evaluation 2010 // of a DWARF expression. The operand is the 2-byte unsigned offset 2011 // of a debugging information entry in the current compilation unit. 2012 // 2013 // Operand interpretation is exactly like that for DW_FORM_ref2. 2014 // 2015 // This operation transfers control of DWARF expression evaluation 2016 // to the DW_AT_location attribute of the referenced DIE. If there is 2017 // no such attribute, then there is no effect. Execution of the DWARF 2018 // expression of a DW_AT_location attribute may add to and/or remove from 2019 // values on the stack. Execution returns to the point following the call 2020 // when the end of the attribute is reached. Values on the stack at the 2021 // time of the call may be used as parameters by the called expression 2022 // and values left on the stack by the called expression may be used as 2023 // return values by prior agreement between the calling and called 2024 // expressions. 2025 //---------------------------------------------------------------------- 2026 case DW_OP_call2: 2027 if (error_ptr) 2028 error_ptr->SetErrorString ("Unimplemented opcode DW_OP_call2."); 2029 return false; 2030 //---------------------------------------------------------------------- 2031 // OPCODE: DW_OP_call4 2032 // OPERANDS: 1 2033 // uint32_t compile unit relative offset of a DIE 2034 // DESCRIPTION: Performs a subroutine call during evaluation of a DWARF 2035 // expression. For DW_OP_call4, the operand is a 4-byte unsigned offset 2036 // of a debugging information entry in the current compilation unit. 2037 // 2038 // Operand interpretation DW_OP_call4 is exactly like that for 2039 // DW_FORM_ref4. 2040 // 2041 // This operation transfers control of DWARF expression evaluation 2042 // to the DW_AT_location attribute of the referenced DIE. If there is 2043 // no such attribute, then there is no effect. Execution of the DWARF 2044 // expression of a DW_AT_location attribute may add to and/or remove from 2045 // values on the stack. Execution returns to the point following the call 2046 // when the end of the attribute is reached. Values on the stack at the 2047 // time of the call may be used as parameters by the called expression 2048 // and values left on the stack by the called expression may be used as 2049 // return values by prior agreement between the calling and called 2050 // expressions. 2051 //---------------------------------------------------------------------- 2052 case DW_OP_call4: 2053 if (error_ptr) 2054 error_ptr->SetErrorString ("Unimplemented opcode DW_OP_call4."); 2055 return false; 2056 2057 2058 //---------------------------------------------------------------------- 2059 // OPCODE: DW_OP_call_ref 2060 // OPERANDS: 2061 // uint32_t absolute DIE offset for 32-bit DWARF or a uint64_t 2062 // absolute DIE offset for 64 bit DWARF. 2063 // DESCRIPTION: Performs a subroutine call during evaluation of a DWARF 2064 // expression. Takes a single operand. In the 32-bit DWARF format, the 2065 // operand is a 4-byte unsigned value; in the 64-bit DWARF format, it 2066 // is an 8-byte unsigned value. The operand is used as the offset of a 2067 // debugging information entry in a .debug_info section which may be 2068 // contained in a shared object for executable other than that 2069 // containing the operator. For references from one shared object or 2070 // executable to another, the relocation must be performed by the 2071 // consumer. 2072 // 2073 // Operand interpretation of DW_OP_call_ref is exactly like that for 2074 // DW_FORM_ref_addr. 2075 // 2076 // This operation transfers control of DWARF expression evaluation 2077 // to the DW_AT_location attribute of the referenced DIE. If there is 2078 // no such attribute, then there is no effect. Execution of the DWARF 2079 // expression of a DW_AT_location attribute may add to and/or remove from 2080 // values on the stack. Execution returns to the point following the call 2081 // when the end of the attribute is reached. Values on the stack at the 2082 // time of the call may be used as parameters by the called expression 2083 // and values left on the stack by the called expression may be used as 2084 // return values by prior agreement between the calling and called 2085 // expressions. 2086 //---------------------------------------------------------------------- 2087 case DW_OP_call_ref: 2088 if (error_ptr) 2089 error_ptr->SetErrorString ("Unimplemented opcode DW_OP_call_ref."); 2090 return false; 2091 2092 //---------------------------------------------------------------------- 2093 // OPCODE: DW_OP_APPLE_array_ref 2094 // OPERANDS: none 2095 // DESCRIPTION: Pops a value off the stack and uses it as the array 2096 // index. Pops a second value off the stack and uses it as the array 2097 // itself. Pushes a value onto the stack representing the element of 2098 // the array specified by the index. 2099 //---------------------------------------------------------------------- 2100 case DW_OP_APPLE_array_ref: 2101 { 2102 if (stack.size() < 2) 2103 { 2104 if (error_ptr) 2105 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_APPLE_array_ref."); 2106 return false; 2107 } 2108 2109 Value index_val = stack.back(); 2110 stack.pop_back(); 2111 Value array_val = stack.back(); 2112 stack.pop_back(); 2113 2114 Scalar &index_scalar = index_val.ResolveValue(exe_ctx, ast_context); 2115 int64_t index = index_scalar.SLongLong(LONG_LONG_MAX); 2116 2117 if (index == LONG_LONG_MAX) 2118 { 2119 if (error_ptr) 2120 error_ptr->SetErrorString("Invalid array index."); 2121 return false; 2122 } 2123 2124 if (array_val.GetContextType() != Value::eContextTypeOpaqueClangQualType) 2125 { 2126 if (error_ptr) 2127 error_ptr->SetErrorString("Arrays without Clang types are unhandled at this time."); 2128 return false; 2129 } 2130 2131 if (array_val.GetValueType() != Value::eValueTypeLoadAddress && 2132 array_val.GetValueType() != Value::eValueTypeHostAddress) 2133 { 2134 if (error_ptr) 2135 error_ptr->SetErrorString("Array must be stored in memory."); 2136 return false; 2137 } 2138 2139 void *array_type = array_val.GetClangType(); 2140 2141 void *member_type; 2142 uint64_t size = 0; 2143 2144 if ((!ClangASTContext::IsPointerType(array_type, &member_type)) && 2145 (!ClangASTContext::IsArrayType(array_type, &member_type, &size))) 2146 { 2147 if (error_ptr) 2148 error_ptr->SetErrorString("Array reference from something that is neither a pointer nor an array."); 2149 return false; 2150 } 2151 2152 if (size && (index >= size || index < 0)) 2153 { 2154 if (error_ptr) 2155 error_ptr->SetErrorStringWithFormat("Out of bounds array access. %lld is not in [0, %llu]", index, size); 2156 return false; 2157 } 2158 2159 uint64_t member_bit_size = ClangASTType::GetClangTypeBitWidth(ast_context, member_type); 2160 uint64_t member_bit_align = ClangASTType::GetTypeBitAlign(ast_context, member_type); 2161 uint64_t member_bit_incr = ((member_bit_size + member_bit_align - 1) / member_bit_align) * member_bit_align; 2162 if (member_bit_incr % 8) 2163 { 2164 if (error_ptr) 2165 error_ptr->SetErrorStringWithFormat("Array increment is not byte aligned", index, size); 2166 return false; 2167 } 2168 int64_t member_offset = (int64_t)(member_bit_incr / 8) * index; 2169 2170 Value member; 2171 2172 member.SetContext(Value::eContextTypeOpaqueClangQualType, member_type); 2173 member.SetValueType(array_val.GetValueType()); 2174 2175 addr_t array_base = (addr_t)array_val.GetScalar().ULongLong(LLDB_INVALID_ADDRESS); 2176 addr_t member_loc = array_base + member_offset; 2177 member.GetScalar() = (uint64_t)member_loc; 2178 2179 stack.push_back(member); 2180 } 2181 break; 2182 2183 //---------------------------------------------------------------------- 2184 // OPCODE: DW_OP_APPLE_uninit 2185 // OPERANDS: none 2186 // DESCRIPTION: Lets us know that the value is currently not initialized 2187 //---------------------------------------------------------------------- 2188 case DW_OP_APPLE_uninit: 2189 //return eResultTypeErrorUninitialized; 2190 break; // Ignore this as we have seen cases where this value is incorrectly added 2191 2192 //---------------------------------------------------------------------- 2193 // OPCODE: DW_OP_APPLE_assign 2194 // OPERANDS: none 2195 // DESCRIPTION: Pops a value off of the stack and assigns it to the next 2196 // item on the stack which must be something assignable (inferior 2197 // Variable, inferior Type with address, inferior register, or 2198 // expression local variable. 2199 //---------------------------------------------------------------------- 2200 case DW_OP_APPLE_assign: 2201 if (stack.size() < 2) 2202 { 2203 if (error_ptr) 2204 error_ptr->SetErrorString("Expression stack needs at least 2 items for DW_OP_APPLE_assign."); 2205 return false; 2206 } 2207 else 2208 { 2209 tmp = stack.back(); 2210 stack.pop_back(); 2211 Value::ContextType context_type = stack.back().GetContextType(); 2212 StreamString new_value(Stream::eBinary, 4, eByteOrderHost); 2213 switch (context_type) 2214 { 2215 case Value::eContextTypeOpaqueClangQualType: 2216 { 2217 void *clang_type = stack.back().GetClangType(); 2218 2219 if (ClangASTContext::IsAggregateType (clang_type)) 2220 { 2221 Value::ValueType source_value_type = tmp.GetValueType(); 2222 Value::ValueType target_value_type = stack.back().GetValueType(); 2223 2224 addr_t source_addr = (addr_t)tmp.GetScalar().ULongLong(); 2225 addr_t target_addr = (addr_t)stack.back().GetScalar().ULongLong(); 2226 2227 size_t byte_size = (ClangASTType::GetClangTypeBitWidth(ast_context, clang_type) + 7) / 8; 2228 2229 switch (source_value_type) 2230 { 2231 case Value::eValueTypeLoadAddress: 2232 switch (target_value_type) 2233 { 2234 case Value::eValueTypeLoadAddress: 2235 { 2236 DataBufferHeap data; 2237 data.SetByteSize(byte_size); 2238 2239 Error error; 2240 if (exe_ctx->process->ReadMemory (source_addr, data.GetBytes(), byte_size, error) != byte_size) 2241 { 2242 if (error_ptr) 2243 error_ptr->SetErrorStringWithFormat ("Couldn't read a composite type from the target: %s", error.AsCString()); 2244 return false; 2245 } 2246 2247 if (exe_ctx->process->WriteMemory (target_addr, data.GetBytes(), byte_size, error) != byte_size) 2248 { 2249 if (error_ptr) 2250 error_ptr->SetErrorStringWithFormat ("Couldn't write a composite type to the target: %s", error.AsCString()); 2251 return false; 2252 } 2253 } 2254 break; 2255 case Value::eValueTypeHostAddress: 2256 if (exe_ctx->process->GetByteOrder() != Host::GetByteOrder()) 2257 { 2258 if (error_ptr) 2259 error_ptr->SetErrorStringWithFormat ("Copy of composite types between incompatible byte orders is unimplemented"); 2260 return false; 2261 } 2262 else 2263 { 2264 Error error; 2265 if (exe_ctx->process->ReadMemory (source_addr, (uint8_t*)target_addr, byte_size, error) != byte_size) 2266 { 2267 if (error_ptr) 2268 error_ptr->SetErrorStringWithFormat ("Couldn't read a composite type from the target: %s", error.AsCString()); 2269 return false; 2270 } 2271 } 2272 break; 2273 default: 2274 return false; 2275 } 2276 break; 2277 case Value::eValueTypeHostAddress: 2278 switch (target_value_type) 2279 { 2280 case Value::eValueTypeLoadAddress: 2281 if (exe_ctx->process->GetByteOrder() != Host::GetByteOrder()) 2282 { 2283 if (error_ptr) 2284 error_ptr->SetErrorStringWithFormat ("Copy of composite types between incompatible byte orders is unimplemented"); 2285 return false; 2286 } 2287 else 2288 { 2289 Error error; 2290 if (exe_ctx->process->WriteMemory (target_addr, (uint8_t*)source_addr, byte_size, error) != byte_size) 2291 { 2292 if (error_ptr) 2293 error_ptr->SetErrorStringWithFormat ("Couldn't write a composite type to the target: %s", error.AsCString()); 2294 return false; 2295 } 2296 } 2297 case Value::eValueTypeHostAddress: 2298 memcpy ((uint8_t*)target_addr, (uint8_t*)source_addr, byte_size); 2299 break; 2300 default: 2301 return false; 2302 } 2303 } 2304 } 2305 else 2306 { 2307 if (!ClangASTType::SetValueFromScalar (ast_context, 2308 clang_type, 2309 tmp.ResolveValue(exe_ctx, ast_context), 2310 new_value)) 2311 { 2312 if (error_ptr) 2313 error_ptr->SetErrorStringWithFormat ("Couldn't extract a value from an integral type.\n"); 2314 return false; 2315 } 2316 2317 Value::ValueType value_type = stack.back().GetValueType(); 2318 2319 switch (value_type) 2320 { 2321 case Value::eValueTypeLoadAddress: 2322 case Value::eValueTypeHostAddress: 2323 { 2324 lldb::AddressType address_type = (value_type == Value::eValueTypeLoadAddress ? eAddressTypeLoad : eAddressTypeHost); 2325 lldb::addr_t addr = stack.back().GetScalar().ULongLong(LLDB_INVALID_ADDRESS); 2326 if (!ClangASTType::WriteToMemory (ast_context, 2327 clang_type, 2328 exe_ctx, 2329 addr, 2330 address_type, 2331 new_value)) 2332 { 2333 if (error_ptr) 2334 error_ptr->SetErrorStringWithFormat ("Failed to write value to memory at 0x%llx.\n", addr); 2335 return false; 2336 } 2337 } 2338 break; 2339 2340 default: 2341 break; 2342 } 2343 } 2344 } 2345 break; 2346 2347 default: 2348 if (error_ptr) 2349 error_ptr->SetErrorString ("Assign failed."); 2350 return false; 2351 } 2352 } 2353 break; 2354 2355 //---------------------------------------------------------------------- 2356 // OPCODE: DW_OP_APPLE_address_of 2357 // OPERANDS: none 2358 // DESCRIPTION: Pops a value off of the stack and pushed its address. 2359 // The top item on the stack must be a variable, or already be a memory 2360 // location. 2361 //---------------------------------------------------------------------- 2362 case DW_OP_APPLE_address_of: 2363 if (stack.empty()) 2364 { 2365 if (error_ptr) 2366 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_APPLE_address_of."); 2367 return false; 2368 } 2369 else 2370 { 2371 Value::ValueType value_type = stack.back().GetValueType(); 2372 switch (value_type) 2373 { 2374 default: 2375 case Value::eValueTypeScalar: // raw scalar value 2376 if (error_ptr) 2377 error_ptr->SetErrorString("Top stack item isn't a memory based object."); 2378 return false; 2379 2380 case Value::eValueTypeLoadAddress: // load address value 2381 case Value::eValueTypeFileAddress: // file address value 2382 case Value::eValueTypeHostAddress: // host address value (for memory in the process that is using liblldb) 2383 // Taking the address of an object reduces it to the address 2384 // of the value and removes any extra context it had. 2385 //stack.back().SetValueType(Value::eValueTypeScalar); 2386 stack.back().ClearContext(); 2387 break; 2388 } 2389 } 2390 break; 2391 2392 //---------------------------------------------------------------------- 2393 // OPCODE: DW_OP_APPLE_value_of 2394 // OPERANDS: none 2395 // DESCRIPTION: Pops a value off of the stack and pushed its value. 2396 // The top item on the stack must be a variable, expression variable. 2397 //---------------------------------------------------------------------- 2398 case DW_OP_APPLE_value_of: 2399 if (stack.empty()) 2400 { 2401 if (error_ptr) 2402 error_ptr->SetErrorString("Expression stack needs at least 1 items for DW_OP_APPLE_value_of."); 2403 return false; 2404 } 2405 else if (!stack.back().ValueOf(exe_ctx, ast_context)) 2406 { 2407 if (error_ptr) 2408 error_ptr->SetErrorString ("Top stack item isn't a valid candidate for DW_OP_APPLE_value_of."); 2409 return false; 2410 } 2411 break; 2412 2413 //---------------------------------------------------------------------- 2414 // OPCODE: DW_OP_APPLE_deref_type 2415 // OPERANDS: none 2416 // DESCRIPTION: gets the value pointed to by the top stack item 2417 //---------------------------------------------------------------------- 2418 case DW_OP_APPLE_deref_type: 2419 { 2420 if (stack.empty()) 2421 { 2422 if (error_ptr) 2423 error_ptr->SetErrorString("Expression stack needs at least 1 items for DW_OP_APPLE_deref_type."); 2424 return false; 2425 } 2426 2427 tmp = stack.back(); 2428 stack.pop_back(); 2429 2430 if (tmp.GetContextType() != Value::eContextTypeOpaqueClangQualType) 2431 { 2432 if (error_ptr) 2433 error_ptr->SetErrorString("Item at top of expression stack must have a Clang type"); 2434 return false; 2435 } 2436 2437 void *ptr_type = tmp.GetClangType(); 2438 void *target_type; 2439 2440 if (!ClangASTContext::IsPointerType(ptr_type, &target_type)) 2441 { 2442 if (error_ptr) 2443 error_ptr->SetErrorString("Dereferencing a non-pointer type"); 2444 return false; 2445 } 2446 2447 // TODO do we want all pointers to be dereferenced as load addresses? 2448 Value::ValueType value_type = tmp.GetValueType(); 2449 2450 tmp.ResolveValue(exe_ctx, ast_context); 2451 2452 tmp.SetValueType(value_type); 2453 tmp.SetContext(Value::eContextTypeOpaqueClangQualType, target_type); 2454 2455 stack.push_back(tmp); 2456 } 2457 break; 2458 2459 //---------------------------------------------------------------------- 2460 // OPCODE: DW_OP_APPLE_expr_local 2461 // OPERANDS: ULEB128 2462 // DESCRIPTION: pushes the expression local variable index onto the 2463 // stack and set the appropriate context so we know the stack item is 2464 // an expression local variable index. 2465 //---------------------------------------------------------------------- 2466 case DW_OP_APPLE_expr_local: 2467 { 2468 /* 2469 uint32_t idx = opcodes.GetULEB128(&offset); 2470 if (expr_locals == NULL) 2471 { 2472 if (error_ptr) 2473 error_ptr->SetErrorStringWithFormat ("DW_OP_APPLE_expr_local(%u) opcode encountered with no local variable list.\n", idx); 2474 return false; 2475 } 2476 Value *expr_local_variable = expr_locals->GetVariableAtIndex(idx); 2477 if (expr_local_variable == NULL) 2478 { 2479 if (error_ptr) 2480 error_ptr->SetErrorStringWithFormat ("DW_OP_APPLE_expr_local(%u) with invalid index %u.\n", idx, idx); 2481 return false; 2482 } 2483 Value *proxy = expr_local_variable->CreateProxy(); 2484 stack.push_back(*proxy); 2485 delete proxy; 2486 //stack.back().SetContext (Value::eContextTypeOpaqueClangQualType, expr_local_variable->GetClangType()); 2487 */ 2488 } 2489 break; 2490 2491 //---------------------------------------------------------------------- 2492 // OPCODE: DW_OP_APPLE_extern 2493 // OPERANDS: ULEB128 2494 // DESCRIPTION: pushes a proxy for the extern object index onto the 2495 // stack. 2496 //---------------------------------------------------------------------- 2497 case DW_OP_APPLE_extern: 2498 { 2499 /* 2500 uint32_t idx = opcodes.GetULEB128(&offset); 2501 if (!decl_map) 2502 { 2503 if (error_ptr) 2504 error_ptr->SetErrorStringWithFormat ("DW_OP_APPLE_extern(%u) opcode encountered with no decl map.\n", idx); 2505 return false; 2506 } 2507 Value *extern_var = decl_map->GetValueForIndex(idx); 2508 if (!extern_var) 2509 { 2510 if (error_ptr) 2511 error_ptr->SetErrorStringWithFormat ("DW_OP_APPLE_extern(%u) with invalid index %u.\n", idx, idx); 2512 return false; 2513 } 2514 Value *proxy = extern_var->CreateProxy(); 2515 stack.push_back(*proxy); 2516 delete proxy; 2517 */ 2518 } 2519 break; 2520 2521 case DW_OP_APPLE_scalar_cast: 2522 if (stack.empty()) 2523 { 2524 if (error_ptr) 2525 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_APPLE_scalar_cast."); 2526 return false; 2527 } 2528 else 2529 { 2530 // Simple scalar cast 2531 if (!stack.back().ResolveValue(exe_ctx, ast_context).Cast((Scalar::Type)opcodes.GetU8(&offset))) 2532 { 2533 if (error_ptr) 2534 error_ptr->SetErrorString("Cast failed."); 2535 return false; 2536 } 2537 } 2538 break; 2539 2540 2541 case DW_OP_APPLE_clang_cast: 2542 if (stack.empty()) 2543 { 2544 if (error_ptr) 2545 error_ptr->SetErrorString("Expression stack needs at least 1 item for DW_OP_APPLE_clang_cast."); 2546 return false; 2547 } 2548 else 2549 { 2550 void *clang_type = (void *)opcodes.GetMaxU64(&offset, sizeof(void*)); 2551 stack.back().SetContext (Value::eContextTypeOpaqueClangQualType, clang_type); 2552 } 2553 break; 2554 //---------------------------------------------------------------------- 2555 // OPCODE: DW_OP_APPLE_constf 2556 // OPERANDS: 1 byte float length, followed by that many bytes containing 2557 // the constant float data. 2558 // DESCRIPTION: Push a float value onto the expression stack. 2559 //---------------------------------------------------------------------- 2560 case DW_OP_APPLE_constf: // 0xF6 - 1 byte float size, followed by constant float data 2561 { 2562 uint8_t float_length = opcodes.GetU8(&offset); 2563 if (sizeof(float) == float_length) 2564 tmp.ResolveValue(exe_ctx, ast_context) = opcodes.GetFloat (&offset); 2565 else if (sizeof(double) == float_length) 2566 tmp.ResolveValue(exe_ctx, ast_context) = opcodes.GetDouble (&offset); 2567 else if (sizeof(long double) == float_length) 2568 tmp.ResolveValue(exe_ctx, ast_context) = opcodes.GetLongDouble (&offset); 2569 else 2570 { 2571 StreamString new_value; 2572 opcodes.Dump(&new_value, offset, eFormatBytes, 1, float_length, UINT32_MAX, DW_INVALID_ADDRESS, 0, 0); 2573 2574 if (error_ptr) 2575 error_ptr->SetErrorStringWithFormat ("DW_OP_APPLE_constf(<%u> %s) unsupported float size.\n", float_length, new_value.GetData()); 2576 return false; 2577 } 2578 tmp.SetValueType(Value::eValueTypeScalar); 2579 tmp.ClearContext(); 2580 stack.push_back(tmp); 2581 } 2582 break; 2583 //---------------------------------------------------------------------- 2584 // OPCODE: DW_OP_APPLE_clear 2585 // OPERANDS: none 2586 // DESCRIPTION: Clears the expression stack. 2587 //---------------------------------------------------------------------- 2588 case DW_OP_APPLE_clear: 2589 stack.clear(); 2590 break; 2591 2592 //---------------------------------------------------------------------- 2593 // OPCODE: DW_OP_APPLE_error 2594 // OPERANDS: none 2595 // DESCRIPTION: Pops a value off of the stack and pushed its value. 2596 // The top item on the stack must be a variable, expression variable. 2597 //---------------------------------------------------------------------- 2598 case DW_OP_APPLE_error: // 0xFF - Stops expression evaluation and returns an error (no args) 2599 if (error_ptr) 2600 error_ptr->SetErrorString ("Generic error."); 2601 return false; 2602 } 2603 } 2604 2605 if (stack.empty()) 2606 { 2607 if (error_ptr) 2608 error_ptr->SetErrorString ("Stack empty after evaluation."); 2609 return false; 2610 } 2611 else if (log) 2612 { 2613 size_t count = stack.size(); 2614 log->Printf("Stack after operation has %d values:", count); 2615 for (size_t i=0; i<count; ++i) 2616 { 2617 StreamString new_value; 2618 new_value.Printf("[%zu]", i); 2619 stack[i].Dump(&new_value); 2620 log->Printf(" %s", new_value.GetData()); 2621 } 2622 } 2623 2624 result = stack.back(); 2625 return true; // Return true on success 2626 } 2627 2628