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