1 //===-- Value.cpp ---------------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "lldb/Core/Value.h"
10 
11 #include "lldb/Core/Address.h"
12 #include "lldb/Core/Module.h"
13 #include "lldb/Symbol/CompilerType.h"
14 #include "lldb/Symbol/ObjectFile.h"
15 #include "lldb/Symbol/SymbolContext.h"
16 #include "lldb/Symbol/Type.h"
17 #include "lldb/Symbol/Variable.h"
18 #include "lldb/Target/ExecutionContext.h"
19 #include "lldb/Target/Process.h"
20 #include "lldb/Target/SectionLoadList.h"
21 #include "lldb/Target/Target.h"
22 #include "lldb/Utility/ConstString.h"
23 #include "lldb/Utility/DataBufferHeap.h"
24 #include "lldb/Utility/DataExtractor.h"
25 #include "lldb/Utility/Endian.h"
26 #include "lldb/Utility/FileSpec.h"
27 #include "lldb/Utility/State.h"
28 #include "lldb/Utility/Stream.h"
29 #include "lldb/lldb-defines.h"
30 #include "lldb/lldb-forward.h"
31 #include "lldb/lldb-types.h"
32 
33 #include <memory>
34 #include <string>
35 
36 #include <cinttypes>
37 
38 using namespace lldb;
39 using namespace lldb_private;
40 
41 Value::Value() : m_value(), m_compiler_type(), m_data_buffer() {}
42 
43 Value::Value(const Scalar &scalar)
44     : m_value(scalar), m_compiler_type(), m_data_buffer() {}
45 
46 Value::Value(const void *bytes, int len)
47     : m_value(), m_compiler_type(), m_value_type(ValueType::HostAddress),
48       m_data_buffer() {
49   SetBytes(bytes, len);
50 }
51 
52 Value::Value(const Value &v)
53     : m_value(v.m_value), m_compiler_type(v.m_compiler_type),
54       m_context(v.m_context), m_value_type(v.m_value_type),
55       m_context_type(v.m_context_type), m_data_buffer() {
56   const uintptr_t rhs_value =
57       (uintptr_t)v.m_value.ULongLong(LLDB_INVALID_ADDRESS);
58   if ((rhs_value != 0) &&
59       (rhs_value == (uintptr_t)v.m_data_buffer.GetBytes())) {
60     m_data_buffer.CopyData(v.m_data_buffer.GetBytes(),
61                            v.m_data_buffer.GetByteSize());
62 
63     m_value = (uintptr_t)m_data_buffer.GetBytes();
64   }
65 }
66 
67 Value &Value::operator=(const Value &rhs) {
68   if (this != &rhs) {
69     m_value = rhs.m_value;
70     m_compiler_type = rhs.m_compiler_type;
71     m_context = rhs.m_context;
72     m_value_type = rhs.m_value_type;
73     m_context_type = rhs.m_context_type;
74     const uintptr_t rhs_value =
75         (uintptr_t)rhs.m_value.ULongLong(LLDB_INVALID_ADDRESS);
76     if ((rhs_value != 0) &&
77         (rhs_value == (uintptr_t)rhs.m_data_buffer.GetBytes())) {
78       m_data_buffer.CopyData(rhs.m_data_buffer.GetBytes(),
79                              rhs.m_data_buffer.GetByteSize());
80 
81       m_value = (uintptr_t)m_data_buffer.GetBytes();
82     }
83   }
84   return *this;
85 }
86 
87 void Value::SetBytes(const void *bytes, int len) {
88   m_value_type = ValueType::HostAddress;
89   m_data_buffer.CopyData(bytes, len);
90   m_value = (uintptr_t)m_data_buffer.GetBytes();
91 }
92 
93 void Value::AppendBytes(const void *bytes, int len) {
94   m_value_type = ValueType::HostAddress;
95   m_data_buffer.AppendData(bytes, len);
96   m_value = (uintptr_t)m_data_buffer.GetBytes();
97 }
98 
99 void Value::Dump(Stream *strm) {
100   m_value.GetValue(strm, true);
101   strm->Printf(", value_type = %s, context = %p, context_type = %s",
102                Value::GetValueTypeAsCString(m_value_type), m_context,
103                Value::GetContextTypeAsCString(m_context_type));
104 }
105 
106 Value::ValueType Value::GetValueType() const { return m_value_type; }
107 
108 AddressType Value::GetValueAddressType() const {
109   switch (m_value_type) {
110   case ValueType::Invalid:
111   case ValueType::Scalar:
112     break;
113   case ValueType::LoadAddress:
114     return eAddressTypeLoad;
115   case ValueType::FileAddress:
116     return eAddressTypeFile;
117   case ValueType::HostAddress:
118     return eAddressTypeHost;
119   }
120   return eAddressTypeInvalid;
121 }
122 
123 RegisterInfo *Value::GetRegisterInfo() const {
124   if (m_context_type == ContextType::RegisterInfo)
125     return static_cast<RegisterInfo *>(m_context);
126   return nullptr;
127 }
128 
129 Type *Value::GetType() {
130   if (m_context_type == ContextType::LLDBType)
131     return static_cast<Type *>(m_context);
132   return nullptr;
133 }
134 
135 size_t Value::AppendDataToHostBuffer(const Value &rhs) {
136   if (this == &rhs)
137     return 0;
138 
139   size_t curr_size = m_data_buffer.GetByteSize();
140   Status error;
141   switch (rhs.GetValueType()) {
142   case ValueType::Invalid:
143     return 0;
144   case ValueType::Scalar: {
145     const size_t scalar_size = rhs.m_value.GetByteSize();
146     if (scalar_size > 0) {
147       const size_t new_size = curr_size + scalar_size;
148       if (ResizeData(new_size) == new_size) {
149         rhs.m_value.GetAsMemoryData(m_data_buffer.GetBytes() + curr_size,
150                                     scalar_size, endian::InlHostByteOrder(),
151                                     error);
152         return scalar_size;
153       }
154     }
155   } break;
156   case ValueType::FileAddress:
157   case ValueType::LoadAddress:
158   case ValueType::HostAddress: {
159     const uint8_t *src = rhs.GetBuffer().GetBytes();
160     const size_t src_len = rhs.GetBuffer().GetByteSize();
161     if (src && src_len > 0) {
162       const size_t new_size = curr_size + src_len;
163       if (ResizeData(new_size) == new_size) {
164         ::memcpy(m_data_buffer.GetBytes() + curr_size, src, src_len);
165         return src_len;
166       }
167     }
168   } break;
169   }
170   return 0;
171 }
172 
173 size_t Value::ResizeData(size_t len) {
174   m_value_type = ValueType::HostAddress;
175   m_data_buffer.SetByteSize(len);
176   m_value = (uintptr_t)m_data_buffer.GetBytes();
177   return m_data_buffer.GetByteSize();
178 }
179 
180 bool Value::ValueOf(ExecutionContext *exe_ctx) {
181   switch (m_context_type) {
182   case ContextType::Invalid:
183   case ContextType::RegisterInfo: // RegisterInfo *
184   case ContextType::LLDBType:     // Type *
185     break;
186 
187   case ContextType::Variable: // Variable *
188     ResolveValue(exe_ctx);
189     return true;
190   }
191   return false;
192 }
193 
194 uint64_t Value::GetValueByteSize(Status *error_ptr, ExecutionContext *exe_ctx) {
195   switch (m_context_type) {
196   case ContextType::RegisterInfo: // RegisterInfo *
197     if (GetRegisterInfo()) {
198       if (error_ptr)
199         error_ptr->Clear();
200       return GetRegisterInfo()->byte_size;
201     }
202     break;
203 
204   case ContextType::Invalid:
205   case ContextType::LLDBType: // Type *
206   case ContextType::Variable: // Variable *
207   {
208     auto *scope = exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr;
209     if (llvm::Optional<uint64_t> size = GetCompilerType().GetByteSize(scope)) {
210       if (error_ptr)
211         error_ptr->Clear();
212       return *size;
213     }
214     break;
215   }
216   }
217   if (error_ptr && error_ptr->Success())
218     error_ptr->SetErrorString("Unable to determine byte size.");
219   return 0;
220 }
221 
222 const CompilerType &Value::GetCompilerType() {
223   if (!m_compiler_type.IsValid()) {
224     switch (m_context_type) {
225     case ContextType::Invalid:
226       break;
227 
228     case ContextType::RegisterInfo:
229       break; // TODO: Eventually convert into a compiler type?
230 
231     case ContextType::LLDBType: {
232       Type *lldb_type = GetType();
233       if (lldb_type)
234         m_compiler_type = lldb_type->GetForwardCompilerType();
235     } break;
236 
237     case ContextType::Variable: {
238       Variable *variable = GetVariable();
239       if (variable) {
240         Type *variable_type = variable->GetType();
241         if (variable_type)
242           m_compiler_type = variable_type->GetForwardCompilerType();
243       }
244     } break;
245     }
246   }
247 
248   return m_compiler_type;
249 }
250 
251 void Value::SetCompilerType(const CompilerType &compiler_type) {
252   m_compiler_type = compiler_type;
253 }
254 
255 lldb::Format Value::GetValueDefaultFormat() {
256   switch (m_context_type) {
257   case ContextType::RegisterInfo:
258     if (GetRegisterInfo())
259       return GetRegisterInfo()->format;
260     break;
261 
262   case ContextType::Invalid:
263   case ContextType::LLDBType:
264   case ContextType::Variable: {
265     const CompilerType &ast_type = GetCompilerType();
266     if (ast_type.IsValid())
267       return ast_type.GetFormat();
268   } break;
269   }
270 
271   // Return a good default in case we can't figure anything out
272   return eFormatHex;
273 }
274 
275 bool Value::GetData(DataExtractor &data) {
276   switch (m_value_type) {
277   case ValueType::Invalid:
278     return false;
279   case ValueType::Scalar:
280     if (m_value.GetData(data))
281       return true;
282     break;
283 
284   case ValueType::LoadAddress:
285   case ValueType::FileAddress:
286   case ValueType::HostAddress:
287     if (m_data_buffer.GetByteSize()) {
288       data.SetData(m_data_buffer.GetBytes(), m_data_buffer.GetByteSize(),
289                    data.GetByteOrder());
290       return true;
291     }
292     break;
293   }
294 
295   return false;
296 }
297 
298 Status Value::GetValueAsData(ExecutionContext *exe_ctx, DataExtractor &data,
299                              Module *module) {
300   data.Clear();
301 
302   Status error;
303   lldb::addr_t address = LLDB_INVALID_ADDRESS;
304   AddressType address_type = eAddressTypeFile;
305   Address file_so_addr;
306   const CompilerType &ast_type = GetCompilerType();
307   llvm::Optional<uint64_t> type_size = ast_type.GetByteSize(
308       exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr);
309   // Nothing to be done for a zero-sized type.
310   if (type_size && *type_size == 0)
311     return error;
312 
313   switch (m_value_type) {
314   case ValueType::Invalid:
315     error.SetErrorString("invalid value");
316     break;
317   case ValueType::Scalar: {
318     data.SetByteOrder(endian::InlHostByteOrder());
319     if (ast_type.IsValid())
320       data.SetAddressByteSize(ast_type.GetPointerByteSize());
321     else
322       data.SetAddressByteSize(sizeof(void *));
323 
324     uint32_t limit_byte_size = UINT32_MAX;
325 
326     if (type_size)
327       limit_byte_size = *type_size;
328 
329     if (limit_byte_size <= m_value.GetByteSize()) {
330       if (m_value.GetData(data, limit_byte_size))
331         return error; // Success;
332     }
333 
334     error.SetErrorString("extracting data from value failed");
335     break;
336   }
337   case ValueType::LoadAddress:
338     if (exe_ctx == nullptr) {
339       error.SetErrorString("can't read load address (no execution context)");
340     } else {
341       Process *process = exe_ctx->GetProcessPtr();
342       if (process == nullptr || !process->IsAlive()) {
343         Target *target = exe_ctx->GetTargetPtr();
344         if (target) {
345           // Allow expressions to run and evaluate things when the target has
346           // memory sections loaded. This allows you to use "target modules
347           // load" to load your executable and any shared libraries, then
348           // execute commands where you can look at types in data sections.
349           const SectionLoadList &target_sections = target->GetSectionLoadList();
350           if (!target_sections.IsEmpty()) {
351             address = m_value.ULongLong(LLDB_INVALID_ADDRESS);
352             if (target_sections.ResolveLoadAddress(address, file_so_addr)) {
353               address_type = eAddressTypeLoad;
354               data.SetByteOrder(target->GetArchitecture().GetByteOrder());
355               data.SetAddressByteSize(
356                   target->GetArchitecture().GetAddressByteSize());
357             } else
358               address = LLDB_INVALID_ADDRESS;
359           }
360         } else {
361           error.SetErrorString("can't read load address (invalid process)");
362         }
363       } else {
364         address = m_value.ULongLong(LLDB_INVALID_ADDRESS);
365         address_type = eAddressTypeLoad;
366         data.SetByteOrder(
367             process->GetTarget().GetArchitecture().GetByteOrder());
368         data.SetAddressByteSize(
369             process->GetTarget().GetArchitecture().GetAddressByteSize());
370       }
371     }
372     break;
373 
374   case ValueType::FileAddress:
375     if (exe_ctx == nullptr) {
376       error.SetErrorString("can't read file address (no execution context)");
377     } else if (exe_ctx->GetTargetPtr() == nullptr) {
378       error.SetErrorString("can't read file address (invalid target)");
379     } else {
380       address = m_value.ULongLong(LLDB_INVALID_ADDRESS);
381       if (address == LLDB_INVALID_ADDRESS) {
382         error.SetErrorString("invalid file address");
383       } else {
384         if (module == nullptr) {
385           // The only thing we can currently lock down to a module so that we
386           // can resolve a file address, is a variable.
387           Variable *variable = GetVariable();
388           if (variable) {
389             SymbolContext var_sc;
390             variable->CalculateSymbolContext(&var_sc);
391             module = var_sc.module_sp.get();
392           }
393         }
394 
395         if (module) {
396           bool resolved = false;
397           ObjectFile *objfile = module->GetObjectFile();
398           if (objfile) {
399             Address so_addr(address, objfile->GetSectionList());
400             addr_t load_address =
401                 so_addr.GetLoadAddress(exe_ctx->GetTargetPtr());
402             bool process_launched_and_stopped =
403                 exe_ctx->GetProcessPtr()
404                     ? StateIsStoppedState(exe_ctx->GetProcessPtr()->GetState(),
405                                           true /* must_exist */)
406                     : false;
407             // Don't use the load address if the process has exited.
408             if (load_address != LLDB_INVALID_ADDRESS &&
409                 process_launched_and_stopped) {
410               resolved = true;
411               address = load_address;
412               address_type = eAddressTypeLoad;
413               data.SetByteOrder(
414                   exe_ctx->GetTargetRef().GetArchitecture().GetByteOrder());
415               data.SetAddressByteSize(exe_ctx->GetTargetRef()
416                                           .GetArchitecture()
417                                           .GetAddressByteSize());
418             } else {
419               if (so_addr.IsSectionOffset()) {
420                 resolved = true;
421                 file_so_addr = so_addr;
422                 data.SetByteOrder(objfile->GetByteOrder());
423                 data.SetAddressByteSize(objfile->GetAddressByteSize());
424               }
425             }
426           }
427           if (!resolved) {
428             Variable *variable = GetVariable();
429 
430             if (module) {
431               if (variable)
432                 error.SetErrorStringWithFormat(
433                     "unable to resolve the module for file address 0x%" PRIx64
434                     " for variable '%s' in %s",
435                     address, variable->GetName().AsCString(""),
436                     module->GetFileSpec().GetPath().c_str());
437               else
438                 error.SetErrorStringWithFormat(
439                     "unable to resolve the module for file address 0x%" PRIx64
440                     " in %s",
441                     address, module->GetFileSpec().GetPath().c_str());
442             } else {
443               if (variable)
444                 error.SetErrorStringWithFormat(
445                     "unable to resolve the module for file address 0x%" PRIx64
446                     " for variable '%s'",
447                     address, variable->GetName().AsCString(""));
448               else
449                 error.SetErrorStringWithFormat(
450                     "unable to resolve the module for file address 0x%" PRIx64,
451                     address);
452             }
453           }
454         } else {
455           // Can't convert a file address to anything valid without more
456           // context (which Module it came from)
457           error.SetErrorString(
458               "can't read memory from file address without more context");
459         }
460       }
461     }
462     break;
463 
464   case ValueType::HostAddress:
465     address = m_value.ULongLong(LLDB_INVALID_ADDRESS);
466     address_type = eAddressTypeHost;
467     if (exe_ctx) {
468       Target *target = exe_ctx->GetTargetPtr();
469       if (target) {
470         data.SetByteOrder(target->GetArchitecture().GetByteOrder());
471         data.SetAddressByteSize(target->GetArchitecture().GetAddressByteSize());
472         break;
473       }
474     }
475     // fallback to host settings
476     data.SetByteOrder(endian::InlHostByteOrder());
477     data.SetAddressByteSize(sizeof(void *));
478     break;
479   }
480 
481   // Bail if we encountered any errors
482   if (error.Fail())
483     return error;
484 
485   if (address == LLDB_INVALID_ADDRESS) {
486     error.SetErrorStringWithFormat("invalid %s address",
487                                    address_type == eAddressTypeHost ? "host"
488                                                                     : "load");
489     return error;
490   }
491 
492   // If we got here, we need to read the value from memory.
493   size_t byte_size = GetValueByteSize(&error, exe_ctx);
494 
495   // Bail if we encountered any errors getting the byte size.
496   if (error.Fail())
497     return error;
498 
499   // No memory to read for zero-sized types.
500   if (byte_size == 0)
501     return error;
502 
503   // Make sure we have enough room within "data", and if we don't make
504   // something large enough that does
505   if (!data.ValidOffsetForDataOfSize(0, byte_size)) {
506     auto data_sp = std::make_shared<DataBufferHeap>(byte_size, '\0');
507     data.SetData(data_sp);
508   }
509 
510   uint8_t *dst = const_cast<uint8_t *>(data.PeekData(0, byte_size));
511   if (dst != nullptr) {
512     if (address_type == eAddressTypeHost) {
513       // The address is an address in this process, so just copy it.
514       if (address == 0) {
515         error.SetErrorString("trying to read from host address of 0.");
516         return error;
517       }
518       memcpy(dst, reinterpret_cast<uint8_t *>(address), byte_size);
519     } else if ((address_type == eAddressTypeLoad) ||
520                (address_type == eAddressTypeFile)) {
521       if (file_so_addr.IsValid()) {
522         const bool force_live_memory = true;
523         if (exe_ctx->GetTargetRef().ReadMemory(file_so_addr, dst, byte_size,
524                                                error, force_live_memory) !=
525             byte_size) {
526           error.SetErrorStringWithFormat(
527               "read memory from 0x%" PRIx64 " failed", (uint64_t)address);
528         }
529       } else {
530         // The execution context might have a NULL process, but it might have a
531         // valid process in the exe_ctx->target, so use the
532         // ExecutionContext::GetProcess accessor to ensure we get the process
533         // if there is one.
534         Process *process = exe_ctx->GetProcessPtr();
535 
536         if (process) {
537           const size_t bytes_read =
538               process->ReadMemory(address, dst, byte_size, error);
539           if (bytes_read != byte_size)
540             error.SetErrorStringWithFormat(
541                 "read memory from 0x%" PRIx64 " failed (%u of %u bytes read)",
542                 (uint64_t)address, (uint32_t)bytes_read, (uint32_t)byte_size);
543         } else {
544           error.SetErrorStringWithFormat("read memory from 0x%" PRIx64
545                                          " failed (invalid process)",
546                                          (uint64_t)address);
547         }
548       }
549     } else {
550       error.SetErrorStringWithFormat("unsupported AddressType value (%i)",
551                                      address_type);
552     }
553   } else {
554     error.SetErrorString("out of memory");
555   }
556 
557   return error;
558 }
559 
560 Scalar &Value::ResolveValue(ExecutionContext *exe_ctx) {
561   const CompilerType &compiler_type = GetCompilerType();
562   if (compiler_type.IsValid()) {
563     switch (m_value_type) {
564     case ValueType::Invalid:
565     case ValueType::Scalar: // raw scalar value
566       break;
567 
568     case ValueType::FileAddress:
569     case ValueType::LoadAddress: // load address value
570     case ValueType::HostAddress: // host address value (for memory in the process
571                                 // that is using liblldb)
572     {
573       DataExtractor data;
574       lldb::addr_t addr = m_value.ULongLong(LLDB_INVALID_ADDRESS);
575       Status error(GetValueAsData(exe_ctx, data, nullptr));
576       if (error.Success()) {
577         Scalar scalar;
578         if (compiler_type.GetValueAsScalar(
579                 data, 0, data.GetByteSize(), scalar,
580                 exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr)) {
581           m_value = scalar;
582           m_value_type = ValueType::Scalar;
583         } else {
584           if ((uintptr_t)addr != (uintptr_t)m_data_buffer.GetBytes()) {
585             m_value.Clear();
586             m_value_type = ValueType::Scalar;
587           }
588         }
589       } else {
590         if ((uintptr_t)addr != (uintptr_t)m_data_buffer.GetBytes()) {
591           m_value.Clear();
592           m_value_type = ValueType::Scalar;
593         }
594       }
595     } break;
596     }
597   }
598   return m_value;
599 }
600 
601 Variable *Value::GetVariable() {
602   if (m_context_type == ContextType::Variable)
603     return static_cast<Variable *>(m_context);
604   return nullptr;
605 }
606 
607 void Value::Clear() {
608   m_value.Clear();
609   m_compiler_type.Clear();
610   m_value_type = ValueType::Scalar;
611   m_context = nullptr;
612   m_context_type = ContextType::Invalid;
613   m_data_buffer.Clear();
614 }
615 
616 const char *Value::GetValueTypeAsCString(ValueType value_type) {
617   switch (value_type) {
618   case ValueType::Invalid:
619     return "invalid";
620   case ValueType::Scalar:
621     return "scalar";
622   case ValueType::FileAddress:
623     return "file address";
624   case ValueType::LoadAddress:
625     return "load address";
626   case ValueType::HostAddress:
627     return "host address";
628   };
629   llvm_unreachable("enum cases exhausted.");
630 }
631 
632 const char *Value::GetContextTypeAsCString(ContextType context_type) {
633   switch (context_type) {
634   case ContextType::Invalid:
635     return "invalid";
636   case ContextType::RegisterInfo:
637     return "RegisterInfo *";
638   case ContextType::LLDBType:
639     return "Type *";
640   case ContextType::Variable:
641     return "Variable *";
642   };
643   llvm_unreachable("enum cases exhausted.");
644 }
645 
646 void Value::ConvertToLoadAddress(Module *module, Target *target) {
647   if (!module || !target || (GetValueType() != ValueType::FileAddress))
648     return;
649 
650   lldb::addr_t file_addr = GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
651   if (file_addr == LLDB_INVALID_ADDRESS)
652     return;
653 
654   Address so_addr;
655   if (!module->ResolveFileAddress(file_addr, so_addr))
656     return;
657   lldb::addr_t load_addr = so_addr.GetLoadAddress(target);
658   if (load_addr == LLDB_INVALID_ADDRESS)
659     return;
660 
661   SetValueType(Value::ValueType::LoadAddress);
662   GetScalar() = load_addr;
663 }
664 
665 void ValueList::PushValue(const Value &value) { m_values.push_back(value); }
666 
667 size_t ValueList::GetSize() { return m_values.size(); }
668 
669 Value *ValueList::GetValueAtIndex(size_t idx) {
670   if (idx < GetSize()) {
671     return &(m_values[idx]);
672   } else
673     return nullptr;
674 }
675 
676 void ValueList::Clear() { m_values.clear(); }
677