Path: blob/main/contrib/llvm-project/lldb/source/Plugins/Language/ObjC/CFBasicHash.cpp
39644 views
#include "CFBasicHash.h"12#include "lldb/Utility/Endian.h"34using namespace lldb;5using namespace lldb_private;67bool CFBasicHash::IsValid() const {8if (m_address != LLDB_INVALID_ADDRESS) {9if (m_ptr_size == 4 && m_ht_32)10return true;11else if (m_ptr_size == 8 && m_ht_64)12return true;13else14return false;15}16return false;17}1819bool CFBasicHash::Update(addr_t addr, ExecutionContextRef exe_ctx_rf) {20if (addr == LLDB_INVALID_ADDRESS || !addr)21return false;2223m_address = addr;24m_exe_ctx_ref = exe_ctx_rf;25m_ptr_size =26m_exe_ctx_ref.GetTargetSP()->GetArchitecture().GetAddressByteSize();27m_byte_order = m_exe_ctx_ref.GetTargetSP()->GetArchitecture().GetByteOrder();2829if (m_ptr_size == 4)30return UpdateFor(m_ht_32);31else if (m_ptr_size == 8)32return UpdateFor(m_ht_64);33return false;3435llvm_unreachable(36"Unsupported architecture. Only 32bits and 64bits supported.");37}3839template <typename T>40bool CFBasicHash::UpdateFor(std::unique_ptr<__CFBasicHash<T>> &m_ht) {41if (m_byte_order != endian::InlHostByteOrder())42return false;4344Status error;45Target *target = m_exe_ctx_ref.GetTargetSP().get();46addr_t addr = m_address.GetLoadAddress(target);47size_t size = sizeof(typename __CFBasicHash<T>::RuntimeBase) +48sizeof(typename __CFBasicHash<T>::Bits);4950m_ht = std::make_unique<__CFBasicHash<T>>();51m_exe_ctx_ref.GetProcessSP()->ReadMemory(addr, m_ht.get(),52size, error);53if (error.Fail())54return false;5556m_mutable = !(m_ht->base.cfinfoa & (1 << 6));57m_multi = m_ht->bits.counts_offset;58m_type = static_cast<HashType>(m_ht->bits.keys_offset);59addr_t ptr_offset = addr + size;60size_t ptr_count = GetPointerCount();61size = ptr_count * sizeof(T);6263m_exe_ctx_ref.GetProcessSP()->ReadMemory(ptr_offset, m_ht->pointers, size,64error);6566if (error.Fail()) {67m_ht = nullptr;68return false;69}7071return true;72}7374size_t CFBasicHash::GetCount() const {75if (!IsValid())76return 0;7778if (!m_multi)79return (m_ptr_size == 4) ? m_ht_32->bits.used_buckets80: m_ht_64->bits.used_buckets;8182// FIXME: Add support for multi83return 0;84}8586size_t CFBasicHash::GetPointerCount() const {87if (!IsValid())88return 0;8990if (m_multi)91return 3; // Bits::counts_offset;92return (m_type == HashType::dict) + 1;93}9495addr_t CFBasicHash::GetKeyPointer() const {96if (!IsValid())97return LLDB_INVALID_ADDRESS;9899if (m_ptr_size == 4)100return m_ht_32->pointers[m_ht_32->bits.keys_offset];101102return m_ht_64->pointers[m_ht_64->bits.keys_offset];103}104105addr_t CFBasicHash::GetValuePointer() const {106if (!IsValid())107return LLDB_INVALID_ADDRESS;108109if (m_ptr_size == 4)110return m_ht_32->pointers[0];111112return m_ht_64->pointers[0];113}114115116