diff options
| author | Dimitry Andric <dim@FreeBSD.org> | 2019-01-19 10:06:29 +0000 |
|---|---|---|
| committer | Dimitry Andric <dim@FreeBSD.org> | 2019-01-19 10:06:29 +0000 |
| commit | 94994d372d014ce4c8758b9605d63fae651bd8aa (patch) | |
| tree | 51c0b708bd59f205d6b35cb2a8c24d62f0c33d77 /source/Core | |
| parent | 39be7ce23363d12ae3e49aeb1fdb2bfeb892e836 (diff) | |
Notes
Diffstat (limited to 'source/Core')
48 files changed, 1372 insertions, 6070 deletions
diff --git a/source/Core/Address.cpp b/source/Core/Address.cpp index f183245f7d36..a4dc364b701b 100644 --- a/source/Core/Address.cpp +++ b/source/Core/Address.cpp @@ -10,43 +10,43 @@ #include "lldb/Core/Address.h" #include "lldb/Core/DumpDataExtractor.h" #include "lldb/Core/Module.h" -#include "lldb/Core/ModuleList.h" // for ModuleList +#include "lldb/Core/ModuleList.h" #include "lldb/Core/Section.h" #include "lldb/Symbol/Block.h" -#include "lldb/Symbol/Declaration.h" // for Declaration -#include "lldb/Symbol/LineEntry.h" // for LineEntry +#include "lldb/Symbol/Declaration.h" +#include "lldb/Symbol/LineEntry.h" #include "lldb/Symbol/ObjectFile.h" -#include "lldb/Symbol/Symbol.h" // for Symbol -#include "lldb/Symbol/SymbolContext.h" // for SymbolContext +#include "lldb/Symbol/Symbol.h" +#include "lldb/Symbol/SymbolContext.h" #include "lldb/Symbol/SymbolVendor.h" -#include "lldb/Symbol/Symtab.h" // for Symtab -#include "lldb/Symbol/Type.h" // for Type +#include "lldb/Symbol/Symtab.h" +#include "lldb/Symbol/Type.h" #include "lldb/Symbol/Variable.h" #include "lldb/Symbol/VariableList.h" #include "lldb/Target/ExecutionContext.h" -#include "lldb/Target/ExecutionContextScope.h" // for ExecutionContextScope +#include "lldb/Target/ExecutionContextScope.h" #include "lldb/Target/Process.h" #include "lldb/Target/SectionLoadList.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/Utility/DataExtractor.h" // for DataExtractor -#include "lldb/Utility/Endian.h" // for InlHostByteOrder -#include "lldb/Utility/FileSpec.h" // for FileSpec -#include "lldb/Utility/Status.h" // for Status -#include "lldb/Utility/Stream.h" // for Stream -#include "lldb/Utility/StreamString.h" // for StreamString - -#include "llvm/ADT/StringRef.h" // for StringRef +#include "lldb/Utility/ConstString.h" +#include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/Endian.h" +#include "lldb/Utility/FileSpec.h" +#include "lldb/Utility/Status.h" +#include "lldb/Utility/Stream.h" +#include "lldb/Utility/StreamString.h" + +#include "llvm/ADT/StringRef.h" #include "llvm/ADT/Triple.h" -#include "llvm/Support/Compiler.h" // for LLVM_FALLTHROUGH +#include "llvm/Support/Compiler.h" -#include <cstdint> // for uint8_t, uint32_t -#include <memory> // for shared_ptr, operator!= -#include <vector> // for vector +#include <cstdint> +#include <memory> +#include <vector> -#include <assert.h> // for assert -#include <inttypes.h> // for PRIu64, PRIx64 -#include <string.h> // for size_t, strlen +#include <assert.h> +#include <inttypes.h> +#include <string.h> namespace lldb_private { class CompileUnit; @@ -779,8 +779,9 @@ bool Address::SectionWasDeletedPrivate() const { m_section_wp.owner_before(empty_section_wp); } -uint32_t Address::CalculateSymbolContext(SymbolContext *sc, - uint32_t resolve_scope) const { +uint32_t +Address::CalculateSymbolContext(SymbolContext *sc, + SymbolContextItem resolve_scope) const { sc->Clear(false); // Absolute addresses don't have enough information to reconstruct even their // target. @@ -987,8 +988,10 @@ AddressClass Address::GetAddressClass() const { if (module_sp) { ObjectFile *obj_file = module_sp->GetObjectFile(); if (obj_file) { - // Give the symbol vendor a chance to add to the unified section list. - module_sp->GetSymbolVendor(); + // Give the symbol vendor a chance to add to the unified section list + // and to symtab from symbol file + if (SymbolVendor *vendor = module_sp->GetSymbolVendor()) + vendor->GetSymtab(); return obj_file->GetAddressClass(GetFileAddress()); } } diff --git a/source/Core/AddressRange.cpp b/source/Core/AddressRange.cpp index e125b693d6f6..1afe4fa223db 100644 --- a/source/Core/AddressRange.cpp +++ b/source/Core/AddressRange.cpp @@ -10,16 +10,16 @@ #include "lldb/Core/AddressRange.h" #include "lldb/Core/Module.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/Utility/FileSpec.h" // for FileSpec +#include "lldb/Utility/ConstString.h" +#include "lldb/Utility/FileSpec.h" #include "lldb/Utility/Stream.h" -#include "lldb/lldb-defines.h" // for LLDB_INVALID_ADDRESS +#include "lldb/lldb-defines.h" -#include "llvm/Support/Compiler.h" // for LLVM_FALLTHROUGH +#include "llvm/Support/Compiler.h" -#include <memory> // for shared_ptr +#include <memory> -#include <inttypes.h> // for PRIx64 +#include <inttypes.h> namespace lldb_private { class SectionList; diff --git a/source/Core/AddressResolverFileLine.cpp b/source/Core/AddressResolverFileLine.cpp index 798a9b50079e..203ab2787fe3 100644 --- a/source/Core/AddressResolverFileLine.cpp +++ b/source/Core/AddressResolverFileLine.cpp @@ -9,21 +9,21 @@ #include "lldb/Core/AddressResolverFileLine.h" -#include "lldb/Core/Address.h" // for Address -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/Address.h" +#include "lldb/Core/AddressRange.h" #include "lldb/Symbol/CompileUnit.h" -#include "lldb/Symbol/LineEntry.h" // for LineEntry +#include "lldb/Symbol/LineEntry.h" #include "lldb/Symbol/SymbolContext.h" -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAllCategoriesSet, LIB... -#include "lldb/Utility/Stream.h" // for Stream +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/Stream.h" #include "lldb/Utility/StreamString.h" -#include "lldb/lldb-enumerations.h" // for SymbolContextItem::eSymbolCon... -#include "lldb/lldb-types.h" // for addr_t +#include "lldb/lldb-enumerations.h" +#include "lldb/lldb-types.h" -#include <inttypes.h> // for PRIx64 -#include <vector> // for vector +#include <inttypes.h> +#include <vector> using namespace lldb; using namespace lldb_private; @@ -78,8 +78,8 @@ AddressResolverFileLine::SearchCallback(SearchFilter &filter, return Searcher::eCallbackReturnContinue; } -Searcher::Depth AddressResolverFileLine::GetDepth() { - return Searcher::eDepthCompUnit; +lldb::SearchDepth AddressResolverFileLine::GetDepth() { + return lldb::eSearchDepthCompUnit; } void AddressResolverFileLine::GetDescription(Stream *s) { diff --git a/source/Core/AddressResolverName.cpp b/source/Core/AddressResolverName.cpp index c3dab6d10810..7683e391e0cf 100644 --- a/source/Core/AddressResolverName.cpp +++ b/source/Core/AddressResolverName.cpp @@ -9,25 +9,25 @@ #include "lldb/Core/AddressResolverName.h" -#include "lldb/Core/Address.h" // for Address, operator== -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/Address.h" +#include "lldb/Core/AddressRange.h" #include "lldb/Core/Module.h" #include "lldb/Symbol/Function.h" #include "lldb/Symbol/Symbol.h" #include "lldb/Symbol/SymbolContext.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAllCategoriesSet, LIB... -#include "lldb/Utility/Stream.h" // for Stream -#include "lldb/lldb-enumerations.h" // for SymbolType::eSymbolTypeCode -#include "lldb/lldb-forward.h" // for ModuleSP -#include "lldb/lldb-types.h" // for addr_t -#include "llvm/ADT/StringRef.h" // for StringRef +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/Stream.h" +#include "lldb/lldb-enumerations.h" +#include "lldb/lldb-forward.h" +#include "lldb/lldb-types.h" +#include "llvm/ADT/StringRef.h" -#include <memory> // for shared_ptr -#include <string> // for string -#include <vector> // for vector +#include <memory> +#include <string> +#include <vector> -#include <stdint.h> // for uint32_t +#include <stdint.h> using namespace lldb; using namespace lldb_private; @@ -186,8 +186,8 @@ AddressResolverName::SearchCallback(SearchFilter &filter, return Searcher::eCallbackReturnContinue; } -Searcher::Depth AddressResolverName::GetDepth() { - return Searcher::eDepthModule; +lldb::SearchDepth AddressResolverName::GetDepth() { + return lldb::eSearchDepthModule; } void AddressResolverName::GetDescription(Stream *s) { diff --git a/source/Core/Broadcaster.cpp b/source/Core/Broadcaster.cpp deleted file mode 100644 index 198434b46c29..000000000000 --- a/source/Core/Broadcaster.cpp +++ /dev/null @@ -1,479 +0,0 @@ -//===-- Broadcaster.cpp -----------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "lldb/Core/Broadcaster.h" - -#include "lldb/Core/Event.h" -#include "lldb/Core/Listener.h" -#include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAnyCategoriesSet, Get... -#include "lldb/Utility/Stream.h" // for Stream -#include "lldb/Utility/StreamString.h" - -#include <algorithm> // for find_if -#include <memory> // for make_shared -#include <type_traits> // for move - -#include <assert.h> // for assert -#include <stddef.h> // for size_t - -using namespace lldb; -using namespace lldb_private; - -Broadcaster::Broadcaster(BroadcasterManagerSP manager_sp, const char *name) - : m_broadcaster_sp(std::make_shared<BroadcasterImpl>(*this)), - m_manager_sp(manager_sp), m_broadcaster_name(name) { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT)); - if (log) - log->Printf("%p Broadcaster::Broadcaster(\"%s\")", - static_cast<void *>(this), GetBroadcasterName().AsCString()); -} - -Broadcaster::BroadcasterImpl::BroadcasterImpl(Broadcaster &broadcaster) - : m_broadcaster(broadcaster), m_listeners(), m_listeners_mutex(), - m_hijacking_listeners(), m_hijacking_masks() {} - -Broadcaster::~Broadcaster() { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT)); - if (log) - log->Printf("%p Broadcaster::~Broadcaster(\"%s\")", - static_cast<void *>(this), m_broadcaster_name.AsCString()); - - Clear(); -} - -void Broadcaster::CheckInWithManager() { - if (m_manager_sp) { - m_manager_sp->SignUpListenersForBroadcaster(*this); - } -} - -llvm::SmallVector<std::pair<ListenerSP, uint32_t &>, 4> -Broadcaster::BroadcasterImpl::GetListeners() { - llvm::SmallVector<std::pair<ListenerSP, uint32_t &>, 4> listeners; - listeners.reserve(m_listeners.size()); - - for (auto it = m_listeners.begin(); it != m_listeners.end();) { - lldb::ListenerSP curr_listener_sp(it->first.lock()); - if (curr_listener_sp && it->second) { - listeners.emplace_back(std::move(curr_listener_sp), it->second); - ++it; - } else - it = m_listeners.erase(it); - } - - return listeners; -} - -void Broadcaster::BroadcasterImpl::Clear() { - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - // Make sure the listener forgets about this broadcaster. We do this in the - // broadcaster in case the broadcaster object initiates the removal. - for (auto &pair : GetListeners()) - pair.first->BroadcasterWillDestruct(&m_broadcaster); - - m_listeners.clear(); -} - -Broadcaster *Broadcaster::BroadcasterImpl::GetBroadcaster() { - return &m_broadcaster; -} - -bool Broadcaster::BroadcasterImpl::GetEventNames( - Stream &s, uint32_t event_mask, bool prefix_with_broadcaster_name) const { - uint32_t num_names_added = 0; - if (event_mask && !m_event_names.empty()) { - event_names_map::const_iterator end = m_event_names.end(); - for (uint32_t bit = 1u, mask = event_mask; mask != 0 && bit != 0; - bit <<= 1, mask >>= 1) { - if (mask & 1) { - event_names_map::const_iterator pos = m_event_names.find(bit); - if (pos != end) { - if (num_names_added > 0) - s.PutCString(", "); - - if (prefix_with_broadcaster_name) { - s.PutCString(GetBroadcasterName()); - s.PutChar('.'); - } - s.PutCString(pos->second); - ++num_names_added; - } - } - } - } - return num_names_added > 0; -} - -void Broadcaster::AddInitialEventsToListener( - const lldb::ListenerSP &listener_sp, uint32_t requested_events) {} - -uint32_t -Broadcaster::BroadcasterImpl::AddListener(const lldb::ListenerSP &listener_sp, - uint32_t event_mask) { - if (!listener_sp) - return 0; - - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - // See if we already have this listener, and if so, update its mask - - bool handled = false; - - for (auto &pair : GetListeners()) { - if (pair.first == listener_sp) { - handled = true; - pair.second |= event_mask; - m_broadcaster.AddInitialEventsToListener(listener_sp, event_mask); - break; - } - } - - if (!handled) { - // Grant a new listener the available event bits - m_listeners.push_back( - std::make_pair(lldb::ListenerWP(listener_sp), event_mask)); - - // Individual broadcasters decide whether they have outstanding data when a - // listener attaches, and insert it into the listener with this method. - m_broadcaster.AddInitialEventsToListener(listener_sp, event_mask); - } - - // Return the event bits that were granted to the listener - return event_mask; -} - -bool Broadcaster::BroadcasterImpl::EventTypeHasListeners(uint32_t event_type) { - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - if (!m_hijacking_listeners.empty() && event_type & m_hijacking_masks.back()) - return true; - - for (auto &pair : GetListeners()) { - if (pair.second & event_type) - return true; - } - return false; -} - -bool Broadcaster::BroadcasterImpl::RemoveListener( - lldb_private::Listener *listener, uint32_t event_mask) { - if (!listener) - return false; - - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - for (auto &pair : GetListeners()) { - if (pair.first.get() == listener) { - pair.second &= ~event_mask; - return true; - } - } - return false; -} - -bool Broadcaster::BroadcasterImpl::RemoveListener( - const lldb::ListenerSP &listener_sp, uint32_t event_mask) { - return RemoveListener(listener_sp.get(), event_mask); -} - -void Broadcaster::BroadcasterImpl::BroadcastEvent(EventSP &event_sp) { - return PrivateBroadcastEvent(event_sp, false); -} - -void Broadcaster::BroadcasterImpl::BroadcastEventIfUnique(EventSP &event_sp) { - return PrivateBroadcastEvent(event_sp, true); -} - -void Broadcaster::BroadcasterImpl::PrivateBroadcastEvent(EventSP &event_sp, - bool unique) { - // Can't add a nullptr event... - if (!event_sp) - return; - - // Update the broadcaster on this event - event_sp->SetBroadcaster(&m_broadcaster); - - const uint32_t event_type = event_sp->GetType(); - - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - ListenerSP hijacking_listener_sp; - - if (!m_hijacking_listeners.empty()) { - assert(!m_hijacking_masks.empty()); - hijacking_listener_sp = m_hijacking_listeners.back(); - if ((event_type & m_hijacking_masks.back()) == 0) - hijacking_listener_sp.reset(); - } - - Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_EVENTS)); - if (log) { - StreamString event_description; - event_sp->Dump(&event_description); - log->Printf("%p Broadcaster(\"%s\")::BroadcastEvent (event_sp = {%s}, " - "unique =%i) hijack = %p", - static_cast<void *>(this), GetBroadcasterName(), - event_description.GetData(), unique, - static_cast<void *>(hijacking_listener_sp.get())); - } - - if (hijacking_listener_sp) { - if (unique && - hijacking_listener_sp->PeekAtNextEventForBroadcasterWithType( - &m_broadcaster, event_type)) - return; - hijacking_listener_sp->AddEvent(event_sp); - } else { - for (auto &pair : GetListeners()) { - if (!(pair.second & event_type)) - continue; - if (unique && - pair.first->PeekAtNextEventForBroadcasterWithType(&m_broadcaster, - event_type)) - continue; - - pair.first->AddEvent(event_sp); - } - } -} - -void Broadcaster::BroadcasterImpl::BroadcastEvent(uint32_t event_type, - EventData *event_data) { - auto event_sp = std::make_shared<Event>(event_type, event_data); - PrivateBroadcastEvent(event_sp, false); -} - -void Broadcaster::BroadcasterImpl::BroadcastEvent( - uint32_t event_type, const lldb::EventDataSP &event_data_sp) { - auto event_sp = std::make_shared<Event>(event_type, event_data_sp); - PrivateBroadcastEvent(event_sp, false); -} - -void Broadcaster::BroadcasterImpl::BroadcastEventIfUnique( - uint32_t event_type, EventData *event_data) { - auto event_sp = std::make_shared<Event>(event_type, event_data); - PrivateBroadcastEvent(event_sp, true); -} - -bool Broadcaster::BroadcasterImpl::HijackBroadcaster( - const lldb::ListenerSP &listener_sp, uint32_t event_mask) { - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_EVENTS)); - if (log) - log->Printf( - "%p Broadcaster(\"%s\")::HijackBroadcaster (listener(\"%s\")=%p)", - static_cast<void *>(this), GetBroadcasterName(), - listener_sp->m_name.c_str(), static_cast<void *>(listener_sp.get())); - m_hijacking_listeners.push_back(listener_sp); - m_hijacking_masks.push_back(event_mask); - return true; -} - -bool Broadcaster::BroadcasterImpl::IsHijackedForEvent(uint32_t event_mask) { - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - if (!m_hijacking_listeners.empty()) - return (event_mask & m_hijacking_masks.back()) != 0; - return false; -} - -const char *Broadcaster::BroadcasterImpl::GetHijackingListenerName() { - if (m_hijacking_listeners.size()) { - return m_hijacking_listeners.back()->GetName(); - } else { - return nullptr; - } -} - -void Broadcaster::BroadcasterImpl::RestoreBroadcaster() { - std::lock_guard<std::recursive_mutex> guard(m_listeners_mutex); - - if (!m_hijacking_listeners.empty()) { - Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_EVENTS)); - if (log) { - ListenerSP listener_sp = m_hijacking_listeners.back(); - log->Printf("%p Broadcaster(\"%s\")::RestoreBroadcaster (about to pop " - "listener(\"%s\")=%p)", - static_cast<void *>(this), GetBroadcasterName(), - listener_sp->m_name.c_str(), - static_cast<void *>(listener_sp.get())); - } - m_hijacking_listeners.pop_back(); - } - if (!m_hijacking_masks.empty()) - m_hijacking_masks.pop_back(); -} - -ConstString &Broadcaster::GetBroadcasterClass() const { - static ConstString class_name("lldb.anonymous"); - return class_name; -} - -BroadcastEventSpec::BroadcastEventSpec(const BroadcastEventSpec &rhs) = default; - -bool BroadcastEventSpec::operator<(const BroadcastEventSpec &rhs) const { - if (GetBroadcasterClass() == rhs.GetBroadcasterClass()) { - return GetEventBits() < rhs.GetEventBits(); - } else { - return GetBroadcasterClass() < rhs.GetBroadcasterClass(); - } -} - -BroadcastEventSpec &BroadcastEventSpec:: -operator=(const BroadcastEventSpec &rhs) = default; - -BroadcasterManager::BroadcasterManager() : m_manager_mutex() {} - -lldb::BroadcasterManagerSP BroadcasterManager::MakeBroadcasterManager() { - return lldb::BroadcasterManagerSP(new BroadcasterManager()); -} - -uint32_t BroadcasterManager::RegisterListenerForEvents( - const lldb::ListenerSP &listener_sp, BroadcastEventSpec event_spec) { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - - collection::iterator iter = m_event_map.begin(), end_iter = m_event_map.end(); - uint32_t available_bits = event_spec.GetEventBits(); - - while (iter != end_iter && - (iter = find_if(iter, end_iter, - BroadcasterClassMatches( - event_spec.GetBroadcasterClass()))) != end_iter) { - available_bits &= ~((*iter).first.GetEventBits()); - iter++; - } - - if (available_bits != 0) { - m_event_map.insert(event_listener_key( - BroadcastEventSpec(event_spec.GetBroadcasterClass(), available_bits), - listener_sp)); - m_listeners.insert(listener_sp); - } - - return available_bits; -} - -bool BroadcasterManager::UnregisterListenerForEvents( - const lldb::ListenerSP &listener_sp, BroadcastEventSpec event_spec) { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - bool removed_some = false; - - if (m_listeners.erase(listener_sp) == 0) - return false; - - ListenerMatchesAndSharedBits predicate(event_spec, listener_sp); - std::vector<BroadcastEventSpec> to_be_readded; - uint32_t event_bits_to_remove = event_spec.GetEventBits(); - - // Go through the map and delete the exact matches, and build a list of - // matches that weren't exact to re-add: - while (true) { - collection::iterator iter, end_iter = m_event_map.end(); - iter = find_if(m_event_map.begin(), end_iter, predicate); - if (iter == end_iter) { - break; - } else { - uint32_t iter_event_bits = (*iter).first.GetEventBits(); - removed_some = true; - - if (event_bits_to_remove != iter_event_bits) { - uint32_t new_event_bits = iter_event_bits & ~event_bits_to_remove; - to_be_readded.push_back(BroadcastEventSpec( - event_spec.GetBroadcasterClass(), new_event_bits)); - } - m_event_map.erase(iter); - } - } - - // Okay now add back the bits that weren't completely removed: - for (size_t i = 0; i < to_be_readded.size(); i++) { - m_event_map.insert(event_listener_key(to_be_readded[i], listener_sp)); - } - - return removed_some; -} - -ListenerSP BroadcasterManager::GetListenerForEventSpec( - BroadcastEventSpec event_spec) const { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - - collection::const_iterator iter, end_iter = m_event_map.end(); - iter = find_if(m_event_map.begin(), end_iter, - BroadcastEventSpecMatches(event_spec)); - if (iter != end_iter) - return (*iter).second; - else - return nullptr; -} - -void BroadcasterManager::RemoveListener(Listener *listener) { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - ListenerMatchesPointer predicate(listener); - listener_collection::iterator iter = m_listeners.begin(), - end_iter = m_listeners.end(); - - std::find_if(iter, end_iter, predicate); - if (iter != end_iter) - m_listeners.erase(iter); - - while (true) { - collection::iterator iter, end_iter = m_event_map.end(); - iter = find_if(m_event_map.begin(), end_iter, predicate); - if (iter == end_iter) - break; - else - m_event_map.erase(iter); - } -} - -void BroadcasterManager::RemoveListener(const lldb::ListenerSP &listener_sp) { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - ListenerMatches predicate(listener_sp); - - if (m_listeners.erase(listener_sp) == 0) - return; - - while (true) { - collection::iterator iter, end_iter = m_event_map.end(); - iter = find_if(m_event_map.begin(), end_iter, predicate); - if (iter == end_iter) - break; - else - m_event_map.erase(iter); - } -} - -void BroadcasterManager::SignUpListenersForBroadcaster( - Broadcaster &broadcaster) { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - - collection::iterator iter = m_event_map.begin(), end_iter = m_event_map.end(); - - while (iter != end_iter && - (iter = find_if(iter, end_iter, - BroadcasterClassMatches( - broadcaster.GetBroadcasterClass()))) != end_iter) { - (*iter).second->StartListeningForEvents(&broadcaster, - (*iter).first.GetEventBits()); - iter++; - } -} - -void BroadcasterManager::Clear() { - std::lock_guard<std::recursive_mutex> guard(m_manager_mutex); - listener_collection::iterator end_iter = m_listeners.end(); - - for (listener_collection::iterator iter = m_listeners.begin(); - iter != end_iter; iter++) - (*iter)->BroadcasterManagerWillDestruct(this->shared_from_this()); - m_listeners.clear(); - m_event_map.clear(); -} diff --git a/source/Core/CMakeLists.txt b/source/Core/CMakeLists.txt index 927a0dcc2ec1..15f2dcf6ed99 100644 --- a/source/Core/CMakeLists.txt +++ b/source/Core/CMakeLists.txt @@ -13,7 +13,6 @@ add_lldb_library(lldbCore AddressResolver.cpp AddressResolverFileLine.cpp AddressResolverName.cpp - Broadcaster.cpp Communication.cpp Debugger.cpp Disassembler.cpp @@ -21,24 +20,21 @@ add_lldb_library(lldbCore DumpRegisterValue.cpp DynamicLoader.cpp EmulateInstruction.cpp - Event.cpp FileLineResolver.cpp FileSpecList.cpp FormatEntity.cpp + Highlighter.cpp IOHandler.cpp - Listener.cpp Mangled.cpp Module.cpp ModuleChild.cpp ModuleList.cpp Opcode.cpp PluginManager.cpp - RegisterValue.cpp - Scalar.cpp + RichManglingContext.cpp SearchFilter.cpp Section.cpp SourceManager.cpp - State.cpp StreamAsynchronousIO.cpp StreamFile.cpp UserSettingsController.cpp @@ -81,3 +77,7 @@ add_lldb_library(lldbCore # Needed to properly resolve references in a debug build. # TODO: Remove once we have better layering set_target_properties(lldbCore PROPERTIES LINK_INTERFACE_MULTIPLICITY 4) + +if (NOT LLDB_DISABLE_LIBEDIT) + target_include_directories(lldbCore PRIVATE ${libedit_INCLUDE_DIRS}) +endif() diff --git a/source/Core/Communication.cpp b/source/Core/Communication.cpp index 5ca338639de0..afdabc0c7ce5 100644 --- a/source/Core/Communication.cpp +++ b/source/Core/Communication.cpp @@ -9,28 +9,28 @@ #include "lldb/Core/Communication.h" -#include "lldb/Core/Event.h" -#include "lldb/Core/Listener.h" #include "lldb/Host/HostThread.h" #include "lldb/Host/ThreadLauncher.h" #include "lldb/Utility/Connection.h" -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ConstString.h" +#include "lldb/Utility/Event.h" +#include "lldb/Utility/Listener.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for LogIfAnyCategoriesSet, LIBLLDB... -#include "lldb/Utility/Status.h" // for Status +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/Status.h" -#include "llvm/ADT/None.h" // for None -#include "llvm/ADT/Optional.h" // for Optional -#include "llvm/Support/Compiler.h" // for LLVM_FALLTHROUGH +#include "llvm/ADT/None.h" +#include "llvm/ADT/Optional.h" +#include "llvm/Support/Compiler.h" -#include <algorithm> // for min -#include <chrono> // for duration, seconds +#include <algorithm> +#include <chrono> #include <cstring> -#include <memory> // for shared_ptr +#include <memory> -#include <errno.h> // for EIO -#include <inttypes.h> // for PRIu64 -#include <stdio.h> // for snprintf +#include <errno.h> +#include <inttypes.h> +#include <stdio.h> using namespace lldb; using namespace lldb_private; diff --git a/source/Core/Debugger.cpp b/source/Core/Debugger.cpp index 972d0bc0a6d7..765b59c8865e 100644 --- a/source/Core/Debugger.cpp +++ b/source/Core/Debugger.cpp @@ -9,67 +9,71 @@ #include "lldb/Core/Debugger.h" -#include "lldb/Breakpoint/Breakpoint.h" // for Breakpoint, Brea... -#include "lldb/Core/Event.h" // for Event, EventData... +#include "lldb/Breakpoint/Breakpoint.h" #include "lldb/Core/FormatEntity.h" -#include "lldb/Core/Listener.h" // for Listener -#include "lldb/Core/Mangled.h" // for Mangled -#include "lldb/Core/ModuleList.h" // for Mangled +#include "lldb/Core/Mangled.h" +#include "lldb/Core/ModuleList.h" #include "lldb/Core/PluginManager.h" -#include "lldb/Core/State.h" #include "lldb/Core/StreamAsynchronousIO.h" #include "lldb/Core/StreamFile.h" #include "lldb/DataFormatters/DataVisualization.h" #include "lldb/Expression/REPL.h" -#include "lldb/Host/File.h" // for File, File::kInv... +#include "lldb/Host/File.h" +#include "lldb/Host/FileSystem.h" #include "lldb/Host/HostInfo.h" #include "lldb/Host/Terminal.h" #include "lldb/Host/ThreadLauncher.h" #include "lldb/Interpreter/CommandInterpreter.h" -#include "lldb/Interpreter/OptionValue.h" // for OptionValue, Opt... +#include "lldb/Interpreter/OptionValue.h" #include "lldb/Interpreter/OptionValueProperties.h" #include "lldb/Interpreter/OptionValueSInt64.h" #include "lldb/Interpreter/OptionValueString.h" -#include "lldb/Interpreter/Property.h" // for PropertyDefinition -#include "lldb/Interpreter/ScriptInterpreter.h" // for ScriptInterpreter +#include "lldb/Interpreter/Property.h" +#include "lldb/Interpreter/ScriptInterpreter.h" #include "lldb/Symbol/Function.h" #include "lldb/Symbol/Symbol.h" -#include "lldb/Symbol/SymbolContext.h" // for SymbolContext +#include "lldb/Symbol/SymbolContext.h" #include "lldb/Target/Language.h" #include "lldb/Target/Process.h" #include "lldb/Target/StructuredDataPlugin.h" #include "lldb/Target/Target.h" #include "lldb/Target/TargetList.h" #include "lldb/Target/Thread.h" -#include "lldb/Target/ThreadList.h" // for ThreadList +#include "lldb/Target/ThreadList.h" #include "lldb/Utility/AnsiTerminal.h" -#include "lldb/Utility/Log.h" // for LLDB_LOG_OPTION_... -#include "lldb/Utility/Stream.h" // for Stream +#include "lldb/Utility/Event.h" +#include "lldb/Utility/Listener.h" +#include "lldb/Utility/Log.h" +#include "lldb/Utility/Reproducer.h" +#include "lldb/Utility/State.h" +#include "lldb/Utility/Stream.h" #include "lldb/Utility/StreamCallback.h" #include "lldb/Utility/StreamString.h" #if defined(_WIN32) -#include "lldb/Host/windows/PosixApi.h" // for PATH_MAX +#include "lldb/Host/windows/PosixApi.h" +#include "lldb/Host/windows/windows.h" #endif -#include "llvm/ADT/None.h" // for None -#include "llvm/ADT/STLExtras.h" // for make_unique +#include "llvm/ADT/None.h" +#include "llvm/ADT/STLExtras.h" #include "llvm/ADT/StringRef.h" -#include "llvm/ADT/iterator.h" // for iterator_facade_... +#include "llvm/ADT/iterator.h" #include "llvm/Support/DynamicLibrary.h" #include "llvm/Support/FileSystem.h" +#include "llvm/Support/Process.h" #include "llvm/Support/Threading.h" -#include "llvm/Support/raw_ostream.h" // for raw_fd_ostream +#include "llvm/Support/raw_ostream.h" -#include <list> // for list -#include <memory> // for make_shared +#include <list> +#include <memory> #include <mutex> -#include <set> // for set -#include <stdio.h> // for size_t, NULL -#include <stdlib.h> // for getenv -#include <string.h> // for strcmp -#include <string> // for string -#include <system_error> // for error_code +#include <set> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <string> +#include <system_error> namespace lldb_private { class Address; @@ -89,7 +93,7 @@ static std::recursive_mutex *g_debugger_list_mutex_ptr = static DebuggerList *g_debugger_list_ptr = nullptr; // NOTE: intentional leak to avoid issues with C++ destructor chain -OptionEnumValueElement g_show_disassembly_enum_values[] = { +static constexpr OptionEnumValueElement g_show_disassembly_enum_values[] = { {Debugger::eStopDisassemblyTypeNever, "never", "Never show disassembly when displaying a stop context."}, {Debugger::eStopDisassemblyTypeNoDebugInfo, "no-debuginfo", @@ -98,16 +102,14 @@ OptionEnumValueElement g_show_disassembly_enum_values[] = { "Show disassembly when there is no source information, or the source file " "is missing when displaying a stop context."}, {Debugger::eStopDisassemblyTypeAlways, "always", - "Always show disassembly when displaying a stop context."}, - {0, nullptr, nullptr}}; + "Always show disassembly when displaying a stop context."} }; -OptionEnumValueElement g_language_enumerators[] = { +static constexpr OptionEnumValueElement g_language_enumerators[] = { {eScriptLanguageNone, "none", "Disable scripting languages."}, {eScriptLanguagePython, "python", "Select python as the default scripting language."}, {eScriptLanguageDefault, "default", - "Select the lldb default as the default scripting language."}, - {0, nullptr, nullptr}}; + "Select the lldb default as the default scripting language."} }; #define MODULE_WITH_FUNC \ "{ " \ @@ -119,9 +121,12 @@ OptionEnumValueElement g_language_enumerators[] = { "${module.file.basename}{`${function.name-without-args}" \ "{${frame.no-debug}${function.pc-offset}}}}" -#define FILE_AND_LINE "{ at ${line.file.basename}:${line.number}}" +#define FILE_AND_LINE \ + "{ at ${line.file.basename}:${line.number}{:${line.column}}}" #define IS_OPTIMIZED "{${function.is-optimized} [opt]}" +#define IS_ARTIFICIAL "{${frame.is-artificial} [artificial]}" + #define DEFAULT_THREAD_FORMAT \ "thread #${thread.index}: tid = ${thread.id%tid}" \ "{, ${frame.pc}}" MODULE_WITH_FUNC FILE_AND_LINE \ @@ -146,11 +151,11 @@ OptionEnumValueElement g_language_enumerators[] = { #define DEFAULT_FRAME_FORMAT \ "frame #${frame.index}: ${frame.pc}" MODULE_WITH_FUNC FILE_AND_LINE \ - IS_OPTIMIZED "\\n" + IS_OPTIMIZED IS_ARTIFICIAL "\\n" #define DEFAULT_FRAME_FORMAT_NO_ARGS \ "frame #${frame.index}: ${frame.pc}" MODULE_WITH_FUNC_NO_ARGS FILE_AND_LINE \ - IS_OPTIMIZED "\\n" + IS_OPTIMIZED IS_ARTIFICIAL "\\n" // Three parts to this disassembly format specification: // 1. If this is a new function/symbol (no previous symbol/function), print @@ -162,8 +167,8 @@ OptionEnumValueElement g_language_enumerators[] = { // address <+offset>: #define DEFAULT_DISASSEMBLY_FORMAT \ "{${function.initial-function}{${module.file.basename}`}{${function.name-" \ - "without-args}}:\n}{${function.changed}\n{${module.file.basename}`}{${" \ - "function.name-without-args}}:\n}{${current-pc-arrow} " \ + "without-args}}:\\n}{${function.changed}\\n{${module.file.basename}`}{${" \ + "function.name-without-args}}:\\n}{${current-pc-arrow} " \ "}${addr-file-or-load}{ " \ "<${function.concrete-only-addr-offset-no-padding}>}: " @@ -177,10 +182,7 @@ OptionEnumValueElement g_language_enumerators[] = { // args}}:\n}{${function.changed}\n{${module.file.basename}`}{${function.name- // without-args}}:\n}{${current-pc-arrow} }{${addr-file-or-load}}: -#define DEFAULT_STOP_SHOW_COLUMN_ANSI_PREFIX "${ansi.underline}" -#define DEFAULT_STOP_SHOW_COLUMN_ANSI_SUFFIX "${ansi.normal}" - -static OptionEnumValueElement s_stop_show_column_values[] = { +static constexpr OptionEnumValueElement s_stop_show_column_values[] = { {eStopShowColumnAnsiOrCaret, "ansi-or-caret", "Highlight the stop column with ANSI terminal codes when color/ANSI mode " "is enabled; otherwise, fall back to using a text-only caret (^) as if " @@ -192,98 +194,95 @@ static OptionEnumValueElement s_stop_show_column_values[] = { "Highlight the stop column with a caret character (^) underneath the stop " "column. This method introduces a new line in source listings that " "display thread stop locations."}, - {eStopShowColumnNone, "none", "Do not highlight the stop column."}, - {0, nullptr, nullptr}}; + {eStopShowColumnNone, "none", "Do not highlight the stop column."}}; -static PropertyDefinition g_properties[] = { - {"auto-confirm", OptionValue::eTypeBoolean, true, false, nullptr, nullptr, +static constexpr PropertyDefinition g_properties[] = { + {"auto-confirm", OptionValue::eTypeBoolean, true, false, nullptr, {}, "If true all confirmation prompts will receive their default reply."}, {"disassembly-format", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_DISASSEMBLY_FORMAT, nullptr, + DEFAULT_DISASSEMBLY_FORMAT, {}, "The default disassembly format " "string to use when disassembling " "instruction sequences."}, {"frame-format", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_FRAME_FORMAT, nullptr, + DEFAULT_FRAME_FORMAT, {}, "The default frame format string to use " "when displaying stack frame information " "for threads."}, - {"notify-void", OptionValue::eTypeBoolean, true, false, nullptr, nullptr, + {"notify-void", OptionValue::eTypeBoolean, true, false, nullptr, {}, "Notify the user explicitly if an expression returns void (default: " "false)."}, {"prompt", OptionValue::eTypeString, true, - OptionValueString::eOptionEncodeCharacterEscapeSequences, "(lldb) ", - nullptr, "The debugger command line prompt displayed for the user."}, + OptionValueString::eOptionEncodeCharacterEscapeSequences, "(lldb) ", {}, + "The debugger command line prompt displayed for the user."}, {"script-lang", OptionValue::eTypeEnum, true, eScriptLanguagePython, - nullptr, g_language_enumerators, + nullptr, OptionEnumValues(g_language_enumerators), "The script language to be used for evaluating user-written scripts."}, - {"stop-disassembly-count", OptionValue::eTypeSInt64, true, 4, nullptr, - nullptr, + {"stop-disassembly-count", OptionValue::eTypeSInt64, true, 4, nullptr, {}, "The number of disassembly lines to show when displaying a " "stopped context."}, {"stop-disassembly-display", OptionValue::eTypeEnum, true, Debugger::eStopDisassemblyTypeNoDebugInfo, nullptr, - g_show_disassembly_enum_values, + OptionEnumValues(g_show_disassembly_enum_values), "Control when to display disassembly when displaying a stopped context."}, - {"stop-line-count-after", OptionValue::eTypeSInt64, true, 3, nullptr, - nullptr, + {"stop-line-count-after", OptionValue::eTypeSInt64, true, 3, nullptr, {}, "The number of sources lines to display that come after the " "current source line when displaying a stopped context."}, - {"stop-line-count-before", OptionValue::eTypeSInt64, true, 3, nullptr, - nullptr, + {"stop-line-count-before", OptionValue::eTypeSInt64, true, 3, nullptr, {}, "The number of sources lines to display that come before the " "current source line when displaying a stopped context."}, + {"highlight-source", OptionValue::eTypeBoolean, true, true, nullptr, {}, + "If true, LLDB will highlight the displayed source code."}, {"stop-show-column", OptionValue::eTypeEnum, false, - eStopShowColumnAnsiOrCaret, nullptr, s_stop_show_column_values, + eStopShowColumnAnsiOrCaret, nullptr, OptionEnumValues(s_stop_show_column_values), "If true, LLDB will use the column information from the debug info to " "mark the current position when displaying a stopped context."}, - {"stop-show-column-ansi-prefix", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_STOP_SHOW_COLUMN_ANSI_PREFIX, nullptr, + {"stop-show-column-ansi-prefix", OptionValue::eTypeString, true, 0, + "${ansi.underline}", {}, "When displaying the column marker in a color-enabled (i.e. ANSI) " "terminal, use the ANSI terminal code specified in this format at the " "immediately before the column to be marked."}, - {"stop-show-column-ansi-suffix", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_STOP_SHOW_COLUMN_ANSI_SUFFIX, nullptr, + {"stop-show-column-ansi-suffix", OptionValue::eTypeString, true, 0, + "${ansi.normal}", {}, "When displaying the column marker in a color-enabled (i.e. ANSI) " "terminal, use the ANSI terminal code specified in this format " "immediately after the column to be marked."}, - {"term-width", OptionValue::eTypeSInt64, true, 80, nullptr, nullptr, + {"term-width", OptionValue::eTypeSInt64, true, 80, nullptr, {}, "The maximum number of columns to use for displaying text."}, {"thread-format", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_THREAD_FORMAT, nullptr, + DEFAULT_THREAD_FORMAT, {}, "The default thread format string to use " "when displaying thread information."}, {"thread-stop-format", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_THREAD_STOP_FORMAT, nullptr, + DEFAULT_THREAD_STOP_FORMAT, {}, "The default thread format " "string to use when displaying thread " "information as part of the stop display."}, - {"use-external-editor", OptionValue::eTypeBoolean, true, false, nullptr, - nullptr, "Whether to use an external editor or not."}, - {"use-color", OptionValue::eTypeBoolean, true, true, nullptr, nullptr, + {"use-external-editor", OptionValue::eTypeBoolean, true, false, nullptr, {}, + "Whether to use an external editor or not."}, + {"use-color", OptionValue::eTypeBoolean, true, true, nullptr, {}, "Whether to use Ansi color codes or not."}, {"auto-one-line-summaries", OptionValue::eTypeBoolean, true, true, nullptr, - nullptr, + {}, "If true, LLDB will automatically display small structs in " "one-liner format (default: true)."}, - {"auto-indent", OptionValue::eTypeBoolean, true, true, nullptr, nullptr, + {"auto-indent", OptionValue::eTypeBoolean, true, true, nullptr, {}, "If true, LLDB will auto indent/outdent code. Currently only supported in " "the REPL (default: true)."}, - {"print-decls", OptionValue::eTypeBoolean, true, true, nullptr, nullptr, + {"print-decls", OptionValue::eTypeBoolean, true, true, nullptr, {}, "If true, LLDB will print the values of variables declared in an " "expression. Currently only supported in the REPL (default: true)."}, - {"tab-size", OptionValue::eTypeUInt64, true, 4, nullptr, nullptr, + {"tab-size", OptionValue::eTypeUInt64, true, 4, nullptr, {}, "The tab size to use when indenting code in multi-line input mode " "(default: 4)."}, {"escape-non-printables", OptionValue::eTypeBoolean, true, true, nullptr, - nullptr, + {}, "If true, LLDB will automatically escape non-printable and " "escape characters when formatting strings."}, {"frame-format-unique", OptionValue::eTypeFormatEntity, true, 0, - DEFAULT_FRAME_FORMAT_NO_ARGS, nullptr, + DEFAULT_FRAME_FORMAT_NO_ARGS, {}, "The default frame format string to use when displaying stack frame" - "information for threads from thread backtrace unique."}, - {nullptr, OptionValue::eTypeInvalid, true, 0, nullptr, nullptr, nullptr}}; + "information for threads from thread backtrace unique."}}; enum { ePropertyAutoConfirm = 0, @@ -296,6 +295,7 @@ enum { ePropertyStopDisassemblyDisplay, ePropertyStopLineCountAfter, ePropertyStopLineCountBefore, + ePropertyHighlightSource, ePropertyStopShowColumn, ePropertyStopShowColumnAnsiPrefix, ePropertyStopShowColumnAnsiSuffix, @@ -413,6 +413,11 @@ void Debugger::SetPrompt(llvm::StringRef p) { GetCommandInterpreter().UpdatePrompt(new_prompt); } +llvm::StringRef Debugger::GetReproducerPath() const { + auto &r = repro::Reproducer::Instance(); + return r.GetReproducerPath().GetCString(); +} + const FormatEntity::Entry *Debugger::GetThreadFormat() const { const uint32_t idx = ePropertyThreadFormat; return m_collection_sp->GetPropertyAtIndexAsFormatEntity(nullptr, idx); @@ -470,20 +475,26 @@ bool Debugger::SetUseColor(bool b) { return ret; } +bool Debugger::GetHighlightSource() const { + const uint32_t idx = ePropertyHighlightSource; + return m_collection_sp->GetPropertyAtIndexAsBoolean( + nullptr, idx, g_properties[idx].default_uint_value); +} + StopShowColumn Debugger::GetStopShowColumn() const { const uint32_t idx = ePropertyStopShowColumn; return (lldb::StopShowColumn)m_collection_sp->GetPropertyAtIndexAsEnumeration( nullptr, idx, g_properties[idx].default_uint_value); } -const FormatEntity::Entry *Debugger::GetStopShowColumnAnsiPrefix() const { +llvm::StringRef Debugger::GetStopShowColumnAnsiPrefix() const { const uint32_t idx = ePropertyStopShowColumnAnsiPrefix; - return m_collection_sp->GetPropertyAtIndexAsFormatEntity(nullptr, idx); + return m_collection_sp->GetPropertyAtIndexAsString(nullptr, idx, ""); } -const FormatEntity::Entry *Debugger::GetStopShowColumnAnsiSuffix() const { +llvm::StringRef Debugger::GetStopShowColumnAnsiSuffix() const { const uint32_t idx = ePropertyStopShowColumnAnsiSuffix; - return m_collection_sp->GetPropertyAtIndexAsFormatEntity(nullptr, idx); + return m_collection_sp->GetPropertyAtIndexAsString(nullptr, idx, ""); } uint32_t Debugger::GetStopSourceLineCount(bool before) const { @@ -600,16 +611,16 @@ bool Debugger::LoadPlugin(const FileSpec &spec, Status &error) { return false; } -static FileSpec::EnumerateDirectoryResult +static FileSystem::EnumerateDirectoryResult LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, - const FileSpec &file_spec) { + llvm::StringRef path) { Status error; static ConstString g_dylibext(".dylib"); static ConstString g_solibext(".so"); if (!baton) - return FileSpec::eEnumerateDirectoryResultQuit; + return FileSystem::eEnumerateDirectoryResultQuit; Debugger *debugger = (Debugger *)baton; @@ -620,18 +631,18 @@ LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, // file type information. if (ft == fs::file_type::regular_file || ft == fs::file_type::symlink_file || ft == fs::file_type::type_unknown) { - FileSpec plugin_file_spec(file_spec); - plugin_file_spec.ResolvePath(); + FileSpec plugin_file_spec(path); + FileSystem::Instance().Resolve(plugin_file_spec); if (plugin_file_spec.GetFileNameExtension() != g_dylibext && plugin_file_spec.GetFileNameExtension() != g_solibext) { - return FileSpec::eEnumerateDirectoryResultNext; + return FileSystem::eEnumerateDirectoryResultNext; } Status plugin_load_error; debugger->LoadPlugin(plugin_file_spec, plugin_load_error); - return FileSpec::eEnumerateDirectoryResultNext; + return FileSystem::eEnumerateDirectoryResultNext; } else if (ft == fs::file_type::directory_file || ft == fs::file_type::symlink_file || ft == fs::file_type::type_unknown) { @@ -639,10 +650,10 @@ LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, // also do this for unknown as sometimes the directory enumeration might be // enumerating a file system that doesn't have correct file type // information. - return FileSpec::eEnumerateDirectoryResultEnter; + return FileSystem::eEnumerateDirectoryResultEnter; } - return FileSpec::eEnumerateDirectoryResultNext; + return FileSystem::eEnumerateDirectoryResultNext; } void Debugger::InstanceInitialize() { @@ -651,16 +662,20 @@ void Debugger::InstanceInitialize() { const bool find_other = true; char dir_path[PATH_MAX]; if (FileSpec dir_spec = HostInfo::GetSystemPluginDir()) { - if (dir_spec.Exists() && dir_spec.GetPath(dir_path, sizeof(dir_path))) { - FileSpec::EnumerateDirectory(dir_path, find_directories, find_files, - find_other, LoadPluginCallback, this); + if (FileSystem::Instance().Exists(dir_spec) && + dir_spec.GetPath(dir_path, sizeof(dir_path))) { + FileSystem::Instance().EnumerateDirectory(dir_path, find_directories, + find_files, find_other, + LoadPluginCallback, this); } } if (FileSpec dir_spec = HostInfo::GetUserPluginDir()) { - if (dir_spec.Exists() && dir_spec.GetPath(dir_path, sizeof(dir_path))) { - FileSpec::EnumerateDirectory(dir_path, find_directories, find_files, - find_other, LoadPluginCallback, this); + if (FileSystem::Instance().Exists(dir_spec) && + dir_spec.GetPath(dir_path, sizeof(dir_path))) { + FileSystem::Instance().EnumerateDirectory(dir_path, find_directories, + find_files, find_other, + LoadPluginCallback, this); } } @@ -795,6 +810,15 @@ Debugger::Debugger(lldb::LogOutputCallback log_callback, void *baton) const char *term = getenv("TERM"); if (term && !strcmp(term, "dumb")) SetUseColor(false); + // Turn off use-color if we don't write to a terminal with color support. + if (!m_output_file_sp->GetFile().GetIsTerminalWithColors()) + SetUseColor(false); + +#if defined(_WIN32) && defined(ENABLE_VIRTUAL_TERMINAL_PROCESSING) + // Enabling use of ANSI color codes because LLDB is using them to highlight + // text. + llvm::sys::Process::UseANSIEscapeCodes(true); +#endif } Debugger::~Debugger() { Clear(); } @@ -1068,7 +1092,8 @@ void Debugger::AdoptTopIOHandlerFilesIfInvalid(StreamFileSP &in, } } -void Debugger::PushIOHandler(const IOHandlerSP &reader_sp) { +void Debugger::PushIOHandler(const IOHandlerSP &reader_sp, + bool cancel_top_handler) { if (!reader_sp) return; @@ -1089,7 +1114,8 @@ void Debugger::PushIOHandler(const IOHandlerSP &reader_sp) { // this new input reader take over if (top_reader_sp) { top_reader_sp->Deactivate(); - top_reader_sp->Cancel(); + if (cancel_top_handler) + top_reader_sp->Cancel(); } } diff --git a/source/Core/Disassembler.cpp b/source/Core/Disassembler.cpp index d41a19465280..a34b8038c589 100644 --- a/source/Core/Disassembler.cpp +++ b/source/Core/Disassembler.cpp @@ -9,14 +9,14 @@ #include "lldb/Core/Disassembler.h" -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/AddressRange.h" #include "lldb/Core/Debugger.h" #include "lldb/Core/EmulateInstruction.h" -#include "lldb/Core/Mangled.h" // for Mangled, Mangled... +#include "lldb/Core/Mangled.h" #include "lldb/Core/Module.h" -#include "lldb/Core/ModuleList.h" // for ModuleList +#include "lldb/Core/ModuleList.h" #include "lldb/Core/PluginManager.h" -#include "lldb/Core/SourceManager.h" // for SourceManager +#include "lldb/Core/SourceManager.h" #include "lldb/Host/FileSystem.h" #include "lldb/Interpreter/OptionValue.h" #include "lldb/Interpreter/OptionValueArray.h" @@ -25,31 +25,31 @@ #include "lldb/Interpreter/OptionValueString.h" #include "lldb/Interpreter/OptionValueUInt64.h" #include "lldb/Symbol/Function.h" -#include "lldb/Symbol/Symbol.h" // for Symbol -#include "lldb/Symbol/SymbolContext.h" // for SymbolContext +#include "lldb/Symbol/Symbol.h" +#include "lldb/Symbol/SymbolContext.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/SectionLoadList.h" #include "lldb/Target/StackFrame.h" #include "lldb/Target/Target.h" -#include "lldb/Target/Thread.h" // for Thread +#include "lldb/Target/Thread.h" #include "lldb/Utility/DataBufferHeap.h" #include "lldb/Utility/DataExtractor.h" #include "lldb/Utility/RegularExpression.h" #include "lldb/Utility/Status.h" -#include "lldb/Utility/Stream.h" // for Stream -#include "lldb/Utility/StreamString.h" // for StreamString +#include "lldb/Utility/Stream.h" +#include "lldb/Utility/StreamString.h" #include "lldb/Utility/Timer.h" -#include "lldb/lldb-private-enumerations.h" // for InstructionType:... -#include "lldb/lldb-private-interfaces.h" // for DisassemblerCrea... -#include "lldb/lldb-private-types.h" // for RegisterInfo -#include "llvm/ADT/Triple.h" // for Triple, Triple::... -#include "llvm/Support/Compiler.h" // for LLVM_PRETTY_FUNC... +#include "lldb/lldb-private-enumerations.h" +#include "lldb/lldb-private-interfaces.h" +#include "lldb/lldb-private-types.h" +#include "llvm/ADT/Triple.h" +#include "llvm/Support/Compiler.h" -#include <cstdint> // for uint32_t, UINT32... +#include <cstdint> #include <cstring> -#include <utility> // for pair +#include <utility> -#include <assert.h> // for assert +#include <assert.h> #define DEFAULT_DISASM_BYTE_SIZE 32 @@ -429,9 +429,9 @@ bool Disassembler::PrintInstructions(Disassembler *disasm_ptr, const Address &addr = inst->GetAddress(); ModuleSP module_sp(addr.GetModule()); if (module_sp) { - const uint32_t resolve_mask = eSymbolContextFunction | - eSymbolContextSymbol | - eSymbolContextLineEntry; + const SymbolContextItem resolve_mask = eSymbolContextFunction | + eSymbolContextSymbol | + eSymbolContextLineEntry; uint32_t resolved_mask = module_sp->ResolveSymbolContextForAddress(addr, resolve_mask, sc); if (resolved_mask) { @@ -452,8 +452,7 @@ bool Disassembler::PrintInstructions(Disassembler *disasm_ptr, if (mixed_source_and_assembly && sc.line_entry.IsValid()) { if (sc.symbol != previous_symbol) { SourceLine decl_line = GetFunctionDeclLineEntry(sc); - if (ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, decl_line) == - false) + if (!ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, decl_line)) AddLineToSourceLineTables(decl_line, source_lines_seen); } if (sc.line_entry.IsValid()) { @@ -461,8 +460,7 @@ bool Disassembler::PrintInstructions(Disassembler *disasm_ptr, this_line.file = sc.line_entry.file; this_line.line = sc.line_entry.line; this_line.column = sc.line_entry.column; - if (ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, this_line) == - false) + if (!ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, this_line)) AddLineToSourceLineTables(this_line, source_lines_seen); } } @@ -506,8 +504,8 @@ bool Disassembler::PrintInstructions(Disassembler *disasm_ptr, previous_symbol = sc.symbol; if (sc.function && sc.line_entry.IsValid()) { LineEntry prologue_end_line = sc.line_entry; - if (ElideMixedSourceAndDisassemblyLine( - exe_ctx, sc, prologue_end_line) == false) { + if (!ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, + prologue_end_line)) { FileSpec func_decl_file; uint32_t func_decl_line; sc.function->GetStartLineSourceInfo(func_decl_file, @@ -547,8 +545,8 @@ bool Disassembler::PrintInstructions(Disassembler *disasm_ptr, this_line.file = sc.line_entry.file; this_line.line = sc.line_entry.line; - if (ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, - this_line) == false) { + if (!ElideMixedSourceAndDisassemblyLine(exe_ctx, sc, + this_line)) { // Only print this source line if it is different from the // last source line we printed. There may have been inlined // functions between these lines that we elided, resulting in @@ -934,7 +932,7 @@ bool Instruction::TestEmulation(Stream *out_stream, const char *file_name) { out_stream->Printf("Instruction::TestEmulation: Missing file_name."); return false; } - FILE *test_file = FileSystem::Fopen(file_name, "r"); + FILE *test_file = FileSystem::Instance().Fopen(file_name, "r"); if (!test_file) { out_stream->Printf( "Instruction::TestEmulation: Attempt to open test file failed."); diff --git a/source/Core/DumpDataExtractor.cpp b/source/Core/DumpDataExtractor.cpp index 049f4d3805a1..43a026d0dcb2 100644 --- a/source/Core/DumpDataExtractor.cpp +++ b/source/Core/DumpDataExtractor.cpp @@ -9,12 +9,12 @@ #include "lldb/Core/DumpDataExtractor.h" -#include "lldb/lldb-defines.h" // for LLDB_INVALID_ADDRESS -#include "lldb/lldb-forward.h" // for TargetSP, DisassemblerSP +#include "lldb/lldb-defines.h" +#include "lldb/lldb-forward.h" -#include "lldb/Core/Address.h" // for Address +#include "lldb/Core/Address.h" #include "lldb/Core/Disassembler.h" -#include "lldb/Core/ModuleList.h" // for ModuleList +#include "lldb/Core/ModuleList.h" #include "lldb/Symbol/ClangASTContext.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/ExecutionContextScope.h" @@ -23,22 +23,22 @@ #include "lldb/Utility/DataExtractor.h" #include "lldb/Utility/Stream.h" -#include "clang/AST/ASTContext.h" // for ASTContext -#include "clang/AST/CanonicalType.h" // for CanQualType +#include "clang/AST/ASTContext.h" +#include "clang/AST/CanonicalType.h" -#include "llvm/ADT/APFloat.h" // for APFloat, APFloatBase:... -#include "llvm/ADT/APInt.h" // for APInt -#include "llvm/ADT/ArrayRef.h" // for ArrayRef -#include "llvm/ADT/SmallVector.h" // for SmallVector +#include "llvm/ADT/APFloat.h" +#include "llvm/ADT/APInt.h" +#include "llvm/ADT/ArrayRef.h" +#include "llvm/ADT/SmallVector.h" -#include <limits> // for numeric_limits, numer... -#include <memory> // for shared_ptr -#include <string> // for string, basic_string +#include <limits> +#include <memory> +#include <string> -#include <assert.h> // for assert -#include <ctype.h> // for isprint -#include <inttypes.h> // for PRIu64, PRIx64, PRIX64 -#include <math.h> // for ldexpf +#include <assert.h> +#include <ctype.h> +#include <inttypes.h> +#include <math.h> #include <bitset> #include <sstream> diff --git a/source/Core/DumpRegisterValue.cpp b/source/Core/DumpRegisterValue.cpp index 99334ca78a6d..d7196a585667 100644 --- a/source/Core/DumpRegisterValue.cpp +++ b/source/Core/DumpRegisterValue.cpp @@ -9,8 +9,8 @@ #include "lldb/Core/DumpRegisterValue.h" #include "lldb/Core/DumpDataExtractor.h" -#include "lldb/Core/RegisterValue.h" #include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/RegisterValue.h" #include "lldb/Utility/StreamString.h" #include "lldb/lldb-private-types.h" diff --git a/source/Core/DynamicLoader.cpp b/source/Core/DynamicLoader.cpp index 16f1ffca1a20..72ee3cfd6d5b 100644 --- a/source/Core/DynamicLoader.cpp +++ b/source/Core/DynamicLoader.cpp @@ -10,22 +10,22 @@ #include "lldb/Target/DynamicLoader.h" #include "lldb/Core/Module.h" -#include "lldb/Core/ModuleList.h" // for ModuleList +#include "lldb/Core/ModuleList.h" #include "lldb/Core/ModuleSpec.h" #include "lldb/Core/PluginManager.h" #include "lldb/Core/Section.h" -#include "lldb/Symbol/ObjectFile.h" // for ObjectFile +#include "lldb/Symbol/ObjectFile.h" #include "lldb/Target/MemoryRegionInfo.h" #include "lldb/Target/Process.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/lldb-private-interfaces.h" // for DynamicLoaderCreateInstance +#include "lldb/Utility/ConstString.h" +#include "lldb/lldb-private-interfaces.h" -#include "llvm/ADT/StringRef.h" // for StringRef +#include "llvm/ADT/StringRef.h" -#include <memory> // for shared_ptr, unique_ptr +#include <memory> -#include <assert.h> // for assert +#include <assert.h> using namespace lldb; using namespace lldb_private; @@ -81,7 +81,7 @@ ModuleSP DynamicLoader::GetTargetExecutable() { ModuleSP executable = target.GetExecutableModule(); if (executable) { - if (executable->GetFileSpec().Exists()) { + if (FileSystem::Instance().Exists(executable->GetFileSpec())) { ModuleSpec module_spec(executable->GetFileSpec(), executable->GetArchitecture()); auto module_sp = std::make_shared<Module>(module_spec); @@ -101,8 +101,7 @@ ModuleSP DynamicLoader::GetTargetExecutable() { if (executable.get() != target.GetExecutableModulePointer()) { // Don't load dependent images since we are in dyld where we will // know and find out about all images that are loaded - const bool get_dependent_images = false; - target.SetExecutableModule(executable, get_dependent_images); + target.SetExecutableModule(executable, eLoadDependentsNo); } } } @@ -196,9 +195,8 @@ ModuleSP DynamicLoader::LoadModuleAtAddress(const FileSpec &file, if (error.Success() && memory_info.GetMapped() && memory_info.GetRange().GetRangeBase() == base_addr && !(memory_info.GetName().IsEmpty())) { - ModuleSpec new_module_spec( - FileSpec(memory_info.GetName().AsCString(), false), - target.GetArchitecture()); + ModuleSpec new_module_spec(FileSpec(memory_info.GetName().AsCString()), + target.GetArchitecture()); if ((module_sp = modules.FindFirstModule(new_module_spec))) { UpdateLoadedSections(module_sp, link_map_addr, base_addr, false); diff --git a/source/Core/EmulateInstruction.cpp b/source/Core/EmulateInstruction.cpp index 469022119c9e..0fcb2eb7e8ce 100644 --- a/source/Core/EmulateInstruction.cpp +++ b/source/Core/EmulateInstruction.cpp @@ -12,27 +12,27 @@ #include "lldb/Core/Address.h" #include "lldb/Core/DumpRegisterValue.h" #include "lldb/Core/PluginManager.h" -#include "lldb/Core/RegisterValue.h" #include "lldb/Core/StreamFile.h" #include "lldb/Symbol/UnwindPlan.h" #include "lldb/Target/Process.h" #include "lldb/Target/RegisterContext.h" -#include "lldb/Target/StackFrame.h" // for StackFrame -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Target/StackFrame.h" +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/RegisterValue.h" #include "lldb/Utility/Status.h" -#include "lldb/Utility/Stream.h" // for Stream, Stream::::eBinary +#include "lldb/Utility/Stream.h" #include "lldb/Utility/StreamString.h" -#include "lldb/lldb-forward.h" // for ProcessSP -#include "lldb/lldb-private-interfaces.h" // for EmulateInstructionCreateIn... +#include "lldb/lldb-forward.h" +#include "lldb/lldb-private-interfaces.h" -#include "llvm/ADT/StringRef.h" // for StringRef +#include "llvm/ADT/StringRef.h" #include <cstring> -#include <memory> // for shared_ptr +#include <memory> -#include <inttypes.h> // for PRIx64, PRId64, PRIu64 -#include <stdio.h> // for stdout +#include <inttypes.h> +#include <stdio.h> namespace lldb_private { class Target; diff --git a/source/Core/Event.cpp b/source/Core/Event.cpp deleted file mode 100644 index 3ebad7acdef7..000000000000 --- a/source/Core/Event.cpp +++ /dev/null @@ -1,301 +0,0 @@ -//===-- Event.cpp -----------------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "lldb/Core/Event.h" - -#include "lldb/Core/Broadcaster.h" -#include "lldb/Utility/DataExtractor.h" -#include "lldb/Utility/Endian.h" -#include "lldb/Utility/Stream.h" -#include "lldb/Utility/StreamString.h" // for StreamString -#include "lldb/lldb-enumerations.h" // for Format::eFormatBytes - -#include <algorithm> - -#include <ctype.h> // for isprint - -using namespace lldb; -using namespace lldb_private; - -#pragma mark - -#pragma mark Event - -//------------------------------------------------------------------ -// Event functions -//------------------------------------------------------------------ - -Event::Event(Broadcaster *broadcaster, uint32_t event_type, EventData *data) - : m_broadcaster_wp(broadcaster->GetBroadcasterImpl()), m_type(event_type), - m_data_sp(data) {} - -Event::Event(Broadcaster *broadcaster, uint32_t event_type, - const EventDataSP &event_data_sp) - : m_broadcaster_wp(broadcaster->GetBroadcasterImpl()), m_type(event_type), - m_data_sp(event_data_sp) {} - -Event::Event(uint32_t event_type, EventData *data) - : m_broadcaster_wp(), m_type(event_type), m_data_sp(data) {} - -Event::Event(uint32_t event_type, const EventDataSP &event_data_sp) - : m_broadcaster_wp(), m_type(event_type), m_data_sp(event_data_sp) {} - -Event::~Event() = default; - -void Event::Dump(Stream *s) const { - Broadcaster *broadcaster; - Broadcaster::BroadcasterImplSP broadcaster_impl_sp(m_broadcaster_wp.lock()); - if (broadcaster_impl_sp) - broadcaster = broadcaster_impl_sp->GetBroadcaster(); - else - broadcaster = nullptr; - - if (broadcaster) { - StreamString event_name; - if (broadcaster->GetEventNames(event_name, m_type, false)) - s->Printf("%p Event: broadcaster = %p (%s), type = 0x%8.8x (%s), data = ", - static_cast<const void *>(this), - static_cast<void *>(broadcaster), - broadcaster->GetBroadcasterName().GetCString(), m_type, - event_name.GetData()); - else - s->Printf("%p Event: broadcaster = %p (%s), type = 0x%8.8x, data = ", - static_cast<const void *>(this), - static_cast<void *>(broadcaster), - broadcaster->GetBroadcasterName().GetCString(), m_type); - } else - s->Printf("%p Event: broadcaster = NULL, type = 0x%8.8x, data = ", - static_cast<const void *>(this), m_type); - - if (m_data_sp) { - s->PutChar('{'); - m_data_sp->Dump(s); - s->PutChar('}'); - } else - s->Printf("<NULL>"); -} - -void Event::DoOnRemoval() { - if (m_data_sp) - m_data_sp->DoOnRemoval(this); -} - -#pragma mark - -#pragma mark EventData - -//------------------------------------------------------------------ -// EventData functions -//------------------------------------------------------------------ - -EventData::EventData() = default; - -EventData::~EventData() = default; - -void EventData::Dump(Stream *s) const { s->PutCString("Generic Event Data"); } - -#pragma mark - -#pragma mark EventDataBytes - -//------------------------------------------------------------------ -// EventDataBytes functions -//------------------------------------------------------------------ - -EventDataBytes::EventDataBytes() : m_bytes() {} - -EventDataBytes::EventDataBytes(const char *cstr) : m_bytes() { - SetBytesFromCString(cstr); -} - -EventDataBytes::EventDataBytes(llvm::StringRef str) : m_bytes() { - SetBytes(str.data(), str.size()); -} - -EventDataBytes::EventDataBytes(const void *src, size_t src_len) : m_bytes() { - SetBytes(src, src_len); -} - -EventDataBytes::~EventDataBytes() = default; - -const ConstString &EventDataBytes::GetFlavorString() { - static ConstString g_flavor("EventDataBytes"); - return g_flavor; -} - -const ConstString &EventDataBytes::GetFlavor() const { - return EventDataBytes::GetFlavorString(); -} - -void EventDataBytes::Dump(Stream *s) const { - size_t num_printable_chars = - std::count_if(m_bytes.begin(), m_bytes.end(), isprint); - if (num_printable_chars == m_bytes.size()) - s->Format("\"{0}\"", m_bytes); - else - s->Format("{0:$[ ]@[x-2]}", llvm::make_range( - reinterpret_cast<const uint8_t *>(m_bytes.data()), - reinterpret_cast<const uint8_t *>(m_bytes.data() + - m_bytes.size()))); -} - -const void *EventDataBytes::GetBytes() const { - return (m_bytes.empty() ? nullptr : m_bytes.data()); -} - -size_t EventDataBytes::GetByteSize() const { return m_bytes.size(); } - -void EventDataBytes::SetBytes(const void *src, size_t src_len) { - if (src != nullptr && src_len > 0) - m_bytes.assign((const char *)src, src_len); - else - m_bytes.clear(); -} - -void EventDataBytes::SetBytesFromCString(const char *cstr) { - if (cstr != nullptr && cstr[0]) - m_bytes.assign(cstr); - else - m_bytes.clear(); -} - -const void *EventDataBytes::GetBytesFromEvent(const Event *event_ptr) { - const EventDataBytes *e = GetEventDataFromEvent(event_ptr); - if (e != nullptr) - return e->GetBytes(); - return nullptr; -} - -size_t EventDataBytes::GetByteSizeFromEvent(const Event *event_ptr) { - const EventDataBytes *e = GetEventDataFromEvent(event_ptr); - if (e != nullptr) - return e->GetByteSize(); - return 0; -} - -const EventDataBytes * -EventDataBytes::GetEventDataFromEvent(const Event *event_ptr) { - if (event_ptr != nullptr) { - const EventData *event_data = event_ptr->GetData(); - if (event_data && - event_data->GetFlavor() == EventDataBytes::GetFlavorString()) - return static_cast<const EventDataBytes *>(event_data); - } - return nullptr; -} - -void EventDataBytes::SwapBytes(std::string &new_bytes) { - m_bytes.swap(new_bytes); -} - -#pragma mark - -#pragma mark EventStructuredData - -//------------------------------------------------------------------ -// EventDataStructuredData definitions -//------------------------------------------------------------------ - -EventDataStructuredData::EventDataStructuredData() - : EventData(), m_process_sp(), m_object_sp(), m_plugin_sp() {} - -EventDataStructuredData::EventDataStructuredData( - const ProcessSP &process_sp, const StructuredData::ObjectSP &object_sp, - const lldb::StructuredDataPluginSP &plugin_sp) - : EventData(), m_process_sp(process_sp), m_object_sp(object_sp), - m_plugin_sp(plugin_sp) {} - -EventDataStructuredData::~EventDataStructuredData() {} - -//------------------------------------------------------------------ -// EventDataStructuredData member functions -//------------------------------------------------------------------ - -const ConstString &EventDataStructuredData::GetFlavor() const { - return EventDataStructuredData::GetFlavorString(); -} - -void EventDataStructuredData::Dump(Stream *s) const { - if (!s) - return; - - if (m_object_sp) - m_object_sp->Dump(*s); -} - -const ProcessSP &EventDataStructuredData::GetProcess() const { - return m_process_sp; -} - -const StructuredData::ObjectSP &EventDataStructuredData::GetObject() const { - return m_object_sp; -} - -const lldb::StructuredDataPluginSP & -EventDataStructuredData::GetStructuredDataPlugin() const { - return m_plugin_sp; -} - -void EventDataStructuredData::SetProcess(const ProcessSP &process_sp) { - m_process_sp = process_sp; -} - -void EventDataStructuredData::SetObject( - const StructuredData::ObjectSP &object_sp) { - m_object_sp = object_sp; -} - -void EventDataStructuredData::SetStructuredDataPlugin( - const lldb::StructuredDataPluginSP &plugin_sp) { - m_plugin_sp = plugin_sp; -} - -//------------------------------------------------------------------ -// EventDataStructuredData static functions -//------------------------------------------------------------------ - -const EventDataStructuredData * -EventDataStructuredData::GetEventDataFromEvent(const Event *event_ptr) { - if (event_ptr == nullptr) - return nullptr; - - const EventData *event_data = event_ptr->GetData(); - if (!event_data || - event_data->GetFlavor() != EventDataStructuredData::GetFlavorString()) - return nullptr; - - return static_cast<const EventDataStructuredData *>(event_data); -} - -ProcessSP EventDataStructuredData::GetProcessFromEvent(const Event *event_ptr) { - auto event_data = EventDataStructuredData::GetEventDataFromEvent(event_ptr); - if (event_data) - return event_data->GetProcess(); - else - return ProcessSP(); -} - -StructuredData::ObjectSP -EventDataStructuredData::GetObjectFromEvent(const Event *event_ptr) { - auto event_data = EventDataStructuredData::GetEventDataFromEvent(event_ptr); - if (event_data) - return event_data->GetObject(); - else - return StructuredData::ObjectSP(); -} - -lldb::StructuredDataPluginSP -EventDataStructuredData::GetPluginFromEvent(const Event *event_ptr) { - auto event_data = EventDataStructuredData::GetEventDataFromEvent(event_ptr); - if (event_data) - return event_data->GetStructuredDataPlugin(); - else - return StructuredDataPluginSP(); -} - -const ConstString &EventDataStructuredData::GetFlavorString() { - static ConstString s_flavor("EventDataStructuredData"); - return s_flavor; -} diff --git a/source/Core/FileLineResolver.cpp b/source/Core/FileLineResolver.cpp index 7f0f440252e7..0f4120711b24 100644 --- a/source/Core/FileLineResolver.cpp +++ b/source/Core/FileLineResolver.cpp @@ -9,14 +9,13 @@ #include "lldb/Core/FileLineResolver.h" -// Project includes -#include "lldb/Core/FileSpecList.h" // for FileSpecList +#include "lldb/Core/FileSpecList.h" #include "lldb/Symbol/CompileUnit.h" #include "lldb/Symbol/LineTable.h" -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/Utility/Stream.h" // for Stream +#include "lldb/Utility/ConstString.h" +#include "lldb/Utility/Stream.h" -#include <string> // for string +#include <string> namespace lldb_private { class Address; @@ -68,8 +67,8 @@ FileLineResolver::SearchCallback(SearchFilter &filter, SymbolContext &context, return Searcher::eCallbackReturnContinue; } -Searcher::Depth FileLineResolver::GetDepth() { - return Searcher::eDepthCompUnit; +lldb::SearchDepth FileLineResolver::GetDepth() { + return lldb::eSearchDepthCompUnit; } void FileLineResolver::GetDescription(Stream *s) { diff --git a/source/Core/FileSpecList.cpp b/source/Core/FileSpecList.cpp index 66e27b197447..ae4831b6efa6 100644 --- a/source/Core/FileSpecList.cpp +++ b/source/Core/FileSpecList.cpp @@ -9,12 +9,12 @@ #include "lldb/Core/FileSpecList.h" -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/Stream.h" -#include <utility> // for find +#include <utility> -#include <stdint.h> // for UINT32_MAX +#include <stdint.h> using namespace lldb_private; using namespace std; diff --git a/source/Core/FormatEntity.cpp b/source/Core/FormatEntity.cpp index 743c7c404994..200008dcff5f 100644 --- a/source/Core/FormatEntity.cpp +++ b/source/Core/FormatEntity.cpp @@ -10,29 +10,28 @@ #include "lldb/Core/FormatEntity.h" #include "lldb/Core/Address.h" -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/AddressRange.h" #include "lldb/Core/Debugger.h" #include "lldb/Core/DumpRegisterValue.h" #include "lldb/Core/Module.h" -#include "lldb/Core/RegisterValue.h" // for RegisterValue #include "lldb/Core/ValueObject.h" #include "lldb/Core/ValueObjectVariable.h" #include "lldb/DataFormatters/DataVisualization.h" -#include "lldb/DataFormatters/FormatClasses.h" // for TypeNameSpecifier... +#include "lldb/DataFormatters/FormatClasses.h" #include "lldb/DataFormatters/FormatManager.h" -#include "lldb/DataFormatters/TypeSummary.h" // for TypeSummaryImpl::... +#include "lldb/DataFormatters/TypeSummary.h" #include "lldb/Expression/ExpressionVariable.h" #include "lldb/Interpreter/CommandInterpreter.h" #include "lldb/Symbol/Block.h" #include "lldb/Symbol/CompileUnit.h" -#include "lldb/Symbol/CompilerType.h" // for CompilerType +#include "lldb/Symbol/CompilerType.h" #include "lldb/Symbol/Function.h" #include "lldb/Symbol/LineEntry.h" #include "lldb/Symbol/Symbol.h" -#include "lldb/Symbol/SymbolContext.h" // for SymbolContext +#include "lldb/Symbol/SymbolContext.h" #include "lldb/Symbol/VariableList.h" #include "lldb/Target/ExecutionContext.h" -#include "lldb/Target/ExecutionContextScope.h" // for ExecutionContextS... +#include "lldb/Target/ExecutionContextScope.h" #include "lldb/Target/Language.h" #include "lldb/Target/Process.h" #include "lldb/Target/RegisterContext.h" @@ -42,31 +41,32 @@ #include "lldb/Target/Target.h" #include "lldb/Target/Thread.h" #include "lldb/Utility/AnsiTerminal.h" -#include "lldb/Utility/ArchSpec.h" // for ArchSpec -#include "lldb/Utility/ConstString.h" // for ConstString, oper... +#include "lldb/Utility/ArchSpec.h" +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/FileSpec.h" -#include "lldb/Utility/Log.h" // for Log -#include "lldb/Utility/Logging.h" // for GetLogIfAllCatego... -#include "lldb/Utility/SharingPtr.h" // for SharingPtr +#include "lldb/Utility/Log.h" +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/RegisterValue.h" +#include "lldb/Utility/SharingPtr.h" #include "lldb/Utility/Stream.h" #include "lldb/Utility/StreamString.h" -#include "lldb/Utility/StringList.h" // for StringList -#include "lldb/Utility/StructuredData.h" // for StructuredData::O... -#include "lldb/lldb-defines.h" // for LLDB_INVALID_ADDRESS -#include "lldb/lldb-forward.h" // for ValueObjectSP +#include "lldb/Utility/StringList.h" +#include "lldb/Utility/StructuredData.h" +#include "lldb/lldb-defines.h" +#include "lldb/lldb-forward.h" #include "llvm/ADT/STLExtras.h" #include "llvm/ADT/StringRef.h" -#include "llvm/ADT/Triple.h" // for Triple, Triple::O... -#include "llvm/Support/Compiler.h" // for LLVM_FALLTHROUGH - -#include <ctype.h> // for isxdigit -#include <inttypes.h> // for PRIu64, PRIx64 -#include <memory> // for shared_ptr, opera... -#include <stdio.h> // for sprintf -#include <stdlib.h> // for strtoul -#include <string.h> // for size_t, strchr -#include <type_traits> // for move -#include <utility> // for pair +#include "llvm/ADT/Triple.h" +#include "llvm/Support/Compiler.h" + +#include <ctype.h> +#include <inttypes.h> +#include <memory> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <type_traits> +#include <utility> namespace lldb_private { class ScriptInterpreter; @@ -128,6 +128,7 @@ static FormatEntity::Entry::Definition g_frame_child_entries[] = { ENTRY("flags", FrameRegisterFlags, UInt64), ENTRY("no-debug", FrameNoDebug, None), ENTRY_CHILDREN("reg", FrameRegisterByName, UInt64, g_string_entry), + ENTRY("is-artificial", FrameIsArtificial, UInt32), }; static FormatEntity::Entry::Definition g_function_child_entries[] = { @@ -146,6 +147,7 @@ static FormatEntity::Entry::Definition g_function_child_entries[] = { static FormatEntity::Entry::Definition g_line_child_entries[] = { ENTRY_CHILDREN("file", LineEntryFile, None, g_file_child_entries), ENTRY("number", LineEntryLineNumber, UInt32), + ENTRY("column", LineEntryColumn, UInt32), ENTRY("start-addr", LineEntryStartAddress, UInt64), ENTRY("end-addr", LineEntryEndAddress, UInt64), }; @@ -356,6 +358,7 @@ const char *FormatEntity::Entry::TypeToCString(Type t) { ENUM_TO_CSTR(FrameRegisterFP); ENUM_TO_CSTR(FrameRegisterFlags); ENUM_TO_CSTR(FrameRegisterByName); + ENUM_TO_CSTR(FrameIsArtificial); ENUM_TO_CSTR(ScriptFrame); ENUM_TO_CSTR(FunctionID); ENUM_TO_CSTR(FunctionDidChange); @@ -372,6 +375,7 @@ const char *FormatEntity::Entry::TypeToCString(Type t) { ENUM_TO_CSTR(FunctionIsOptimized); ENUM_TO_CSTR(LineEntryFile); ENUM_TO_CSTR(LineEntryLineNumber); + ENUM_TO_CSTR(LineEntryColumn); ENUM_TO_CSTR(LineEntryStartAddress); ENUM_TO_CSTR(LineEntryEndAddress); ENUM_TO_CSTR(CurrentPCArrow); @@ -1487,6 +1491,13 @@ bool FormatEntity::Format(const Entry &entry, Stream &s, } return false; + case Entry::Type::FrameIsArtificial: { + if (exe_ctx) + if (StackFrame *frame = exe_ctx->GetFramePtr()) + return frame->IsArtificial(); + return false; + } + case Entry::Type::ScriptFrame: if (exe_ctx) { StackFrame *frame = exe_ctx->GetFramePtr(); @@ -1814,6 +1825,16 @@ bool FormatEntity::Format(const Entry &entry, Stream &s, } return false; + case Entry::Type::LineEntryColumn: + if (sc && sc->line_entry.IsValid() && sc->line_entry.column) { + const char *format = "%" PRIu32; + if (!entry.printf_format.empty()) + format = entry.printf_format.c_str(); + s.Printf(format, sc->line_entry.column); + return true; + } + return false; + case Entry::Type::LineEntryStartAddress: case Entry::Type::LineEntryEndAddress: if (sc && sc->line_entry.range.GetBaseAddress().IsValid()) { diff --git a/source/Core/Highlighter.cpp b/source/Core/Highlighter.cpp new file mode 100644 index 000000000000..c7dd0db83645 --- /dev/null +++ b/source/Core/Highlighter.cpp @@ -0,0 +1,81 @@ +//===-- Highlighter.cpp -----------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "lldb/Core/Highlighter.h" + +#include "lldb/Target/Language.h" +#include "lldb/Utility/AnsiTerminal.h" +#include "lldb/Utility/StreamString.h" + +using namespace lldb_private; + +void HighlightStyle::ColorStyle::Apply(Stream &s, llvm::StringRef value) const { + s << m_prefix << value << m_suffix; +} + +void HighlightStyle::ColorStyle::Set(llvm::StringRef prefix, + llvm::StringRef suffix) { + m_prefix = lldb_utility::ansi::FormatAnsiTerminalCodes(prefix); + m_suffix = lldb_utility::ansi::FormatAnsiTerminalCodes(suffix); +} + +void DefaultHighlighter::Highlight(const HighlightStyle &options, + llvm::StringRef line, + llvm::Optional<size_t> cursor_pos, + llvm::StringRef previous_lines, + Stream &s) const { + // If we don't have a valid cursor, then we just print the line as-is. + if (!cursor_pos || *cursor_pos >= line.size()) { + s << line; + return; + } + + // If we have a valid cursor, we have to apply the 'selected' style around + // the character below the cursor. + + // Split the line around the character which is below the cursor. + size_t column = *cursor_pos; + // Print the characters before the cursor. + s << line.substr(0, column); + // Print the selected character with the defined color codes. + options.selected.Apply(s, line.substr(column, 1)); + // Print the rest of the line. + s << line.substr(column + 1U); +} + +static HighlightStyle::ColorStyle GetColor(const char *c) { + return HighlightStyle::ColorStyle(c, "${ansi.normal}"); +} + +HighlightStyle HighlightStyle::MakeVimStyle() { + HighlightStyle result; + result.comment = GetColor("${ansi.fg.purple}"); + result.scalar_literal = GetColor("${ansi.fg.red}"); + result.keyword = GetColor("${ansi.fg.green}"); + return result; +} + +const Highlighter & +HighlighterManager::getHighlighterFor(lldb::LanguageType language_type, + llvm::StringRef path) const { + Language *language = lldb_private::Language::FindPlugin(language_type, path); + if (language && language->GetHighlighter()) + return *language->GetHighlighter(); + return m_default; +} + +std::string Highlighter::Highlight(const HighlightStyle &options, + llvm::StringRef line, + llvm::Optional<size_t> cursor_pos, + llvm::StringRef previous_lines) const { + StreamString s; + Highlight(options, line, cursor_pos, previous_lines, s); + s.Flush(); + return s.GetString().str(); +} diff --git a/source/Core/IOHandler.cpp b/source/Core/IOHandler.cpp index e7ebeea1b88d..5c0eea5ea1a3 100644 --- a/source/Core/IOHandler.cpp +++ b/source/Core/IOHandler.cpp @@ -9,28 +9,24 @@ #include "lldb/Core/IOHandler.h" -// C Includes #ifndef LLDB_DISABLE_CURSES #include <curses.h> #include <panel.h> #endif -// C++ Includes #if defined(__APPLE__) #include <deque> #endif #include <string> -// Other libraries and framework includes -// Project includes #include "lldb/Core/Debugger.h" #include "lldb/Core/StreamFile.h" -#include "lldb/Host/File.h" // for File -#include "lldb/Host/Predicate.h" // for Predicate, ::eBroad... -#include "lldb/Utility/Status.h" // for Status -#include "lldb/Utility/StreamString.h" // for StreamString -#include "lldb/Utility/StringList.h" // for StringList -#include "lldb/lldb-forward.h" // for StreamFileSP +#include "lldb/Host/File.h" +#include "lldb/Utility/Predicate.h" +#include "lldb/Utility/Status.h" +#include "lldb/Utility/StreamString.h" +#include "lldb/Utility/StringList.h" +#include "lldb/lldb-forward.h" #ifndef LLDB_DISABLE_LIBEDIT #include "lldb/Host/Editline.h" @@ -40,7 +36,6 @@ #ifndef LLDB_DISABLE_CURSES #include "lldb/Breakpoint/BreakpointLocation.h" #include "lldb/Core/Module.h" -#include "lldb/Core/State.h" #include "lldb/Core/ValueObject.h" #include "lldb/Core/ValueObjectRegister.h" #include "lldb/Symbol/Block.h" @@ -53,25 +48,26 @@ #include "lldb/Target/StopInfo.h" #include "lldb/Target/Target.h" #include "lldb/Target/Thread.h" +#include "lldb/Utility/State.h" #endif -#include "llvm/ADT/StringRef.h" // for StringRef +#include "llvm/ADT/StringRef.h" #ifdef _MSC_VER #include "lldb/Host/windows/windows.h" #endif -#include <memory> // for shared_ptr -#include <mutex> // for recursive_mutex +#include <memory> +#include <mutex> -#include <assert.h> // for assert -#include <ctype.h> // for isspace -#include <errno.h> // for EINTR, errno -#include <locale.h> // for setlocale -#include <stdint.h> // for uint32_t, UINT32_MAX -#include <stdio.h> // for size_t, fprintf, feof -#include <string.h> // for strlen -#include <type_traits> // for move +#include <assert.h> +#include <ctype.h> +#include <errno.h> +#include <locale.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> +#include <type_traits> using namespace lldb; using namespace lldb_private; @@ -172,12 +168,10 @@ IOHandlerConfirm::IOHandlerConfirm(Debugger &debugger, llvm::StringRef prompt, IOHandlerConfirm::~IOHandlerConfirm() = default; -int IOHandlerConfirm::IOHandlerComplete(IOHandler &io_handler, - const char *current_line, - const char *cursor, - const char *last_char, - int skip_first_n_matches, - int max_matches, StringList &matches) { +int IOHandlerConfirm::IOHandlerComplete( + IOHandler &io_handler, const char *current_line, const char *cursor, + const char *last_char, int skip_first_n_matches, int max_matches, + StringList &matches, StringList &descriptions) { if (current_line == cursor) { if (m_default_response) { matches.AppendString("y"); @@ -223,12 +217,10 @@ void IOHandlerConfirm::IOHandlerInputComplete(IOHandler &io_handler, } } -int IOHandlerDelegate::IOHandlerComplete(IOHandler &io_handler, - const char *current_line, - const char *cursor, - const char *last_char, - int skip_first_n_matches, - int max_matches, StringList &matches) { +int IOHandlerDelegate::IOHandlerComplete( + IOHandler &io_handler, const char *current_line, const char *cursor, + const char *last_char, int skip_first_n_matches, int max_matches, + StringList &matches, StringList &descriptions) { switch (m_completion) { case Completion::None: break; @@ -236,14 +228,16 @@ int IOHandlerDelegate::IOHandlerComplete(IOHandler &io_handler, case Completion::LLDBCommand: return io_handler.GetDebugger().GetCommandInterpreter().HandleCompletion( current_line, cursor, last_char, skip_first_n_matches, max_matches, - matches); - + matches, descriptions); case Completion::Expression: { + CompletionResult result; CompletionRequest request(current_line, current_line - cursor, - skip_first_n_matches, max_matches, matches); + skip_first_n_matches, max_matches, result); CommandCompletions::InvokeCommonCompletionCallbacks( io_handler.GetDebugger().GetCommandInterpreter(), CommandCompletions::eVariablePathCompletion, request, nullptr); + result.GetMatches(matches); + result.GetDescriptions(descriptions); size_t num_matches = request.GetNumberOfMatches(); if (num_matches > 0) { @@ -432,17 +426,15 @@ int IOHandlerEditline::FixIndentationCallback(Editline *editline, *editline_reader, lines, cursor_position); } -int IOHandlerEditline::AutoCompleteCallback(const char *current_line, - const char *cursor, - const char *last_char, - int skip_first_n_matches, - int max_matches, - StringList &matches, void *baton) { +int IOHandlerEditline::AutoCompleteCallback( + const char *current_line, const char *cursor, const char *last_char, + int skip_first_n_matches, int max_matches, StringList &matches, + StringList &descriptions, void *baton) { IOHandlerEditline *editline_reader = (IOHandlerEditline *)baton; if (editline_reader) return editline_reader->m_delegate.IOHandlerComplete( *editline_reader, current_line, cursor, last_char, skip_first_n_matches, - max_matches, matches); + max_matches, matches, descriptions); return 0; } #endif @@ -1060,7 +1052,7 @@ public: Windows::iterator pos, end = m_subwindows.end(); size_t i = 0; for (pos = m_subwindows.begin(); pos != end; ++pos, ++i) { - if ((*pos)->m_name.compare(name) == 0) + if ((*pos)->m_name == name) return *pos; } return WindowSP(); @@ -1752,11 +1744,7 @@ public: void Initialize() { ::setlocale(LC_ALL, ""); ::setlocale(LC_CTYPE, ""); -#if 0 - ::initscr(); -#else m_screen = ::newterm(nullptr, m_out, m_in); -#endif ::start_color(); ::curs_set(0); ::noecho(); @@ -4340,6 +4328,7 @@ public: m_file_sp->GetFileSpec(), // Source file m_selected_line + 1, // Source line number (m_selected_line is zero based) + 0, // Unspecified column. 0, // No offset eLazyBoolCalculate, // Check inlines using global setting eLazyBoolCalculate, // Skip prologue using global setting, @@ -4379,6 +4368,7 @@ public: m_file_sp->GetFileSpec(), // Source file m_selected_line + 1, // Source line number (m_selected_line is zero based) + 0, // No column specified. 0, // No offset eLazyBoolCalculate, // Check inlines using global setting eLazyBoolCalculate, // Skip prologue using global setting, diff --git a/source/Core/Listener.cpp b/source/Core/Listener.cpp deleted file mode 100644 index a39ce6121b32..000000000000 --- a/source/Core/Listener.cpp +++ /dev/null @@ -1,470 +0,0 @@ -//===-- Listener.cpp --------------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "lldb/Core/Listener.h" - -#include "lldb/Core/Broadcaster.h" -#include "lldb/Core/Event.h" -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAllCategoriesSet, LIBL... - -#include "llvm/ADT/Optional.h" // for Optional - -#include <algorithm> -#include <memory> // for make_shared -#include <utility> // for pair, make_pair - -using namespace lldb; -using namespace lldb_private; - -namespace { -class BroadcasterManagerWPMatcher { -public: - BroadcasterManagerWPMatcher(BroadcasterManagerSP manager_sp) - : m_manager_sp(manager_sp) {} - bool operator()(const BroadcasterManagerWP input_wp) const { - BroadcasterManagerSP input_sp = input_wp.lock(); - return (input_sp && input_sp == m_manager_sp); - } - - BroadcasterManagerSP m_manager_sp; -}; -} // anonymous namespace - -Listener::Listener(const char *name) - : m_name(name), m_broadcasters(), m_broadcasters_mutex(), m_events(), - m_events_mutex() { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT)); - if (log != nullptr) - log->Printf("%p Listener::Listener('%s')", static_cast<void *>(this), - m_name.c_str()); -} - -Listener::~Listener() { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT)); - - Clear(); - - if (log) - log->Printf("%p Listener::%s('%s')", static_cast<void *>(this), - __FUNCTION__, m_name.c_str()); -} - -void Listener::Clear() { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT)); - std::lock_guard<std::recursive_mutex> broadcasters_guard( - m_broadcasters_mutex); - broadcaster_collection::iterator pos, end = m_broadcasters.end(); - for (pos = m_broadcasters.begin(); pos != end; ++pos) { - Broadcaster::BroadcasterImplSP broadcaster_sp(pos->first.lock()); - if (broadcaster_sp) - broadcaster_sp->RemoveListener(this, pos->second.event_mask); - } - m_broadcasters.clear(); - - std::lock_guard<std::mutex> events_guard(m_events_mutex); - m_events.clear(); - size_t num_managers = m_broadcaster_managers.size(); - - for (size_t i = 0; i < num_managers; i++) { - BroadcasterManagerSP manager_sp(m_broadcaster_managers[i].lock()); - if (manager_sp) - manager_sp->RemoveListener(this); - } - - if (log) - log->Printf("%p Listener::%s('%s')", static_cast<void *>(this), - __FUNCTION__, m_name.c_str()); -} - -uint32_t Listener::StartListeningForEvents(Broadcaster *broadcaster, - uint32_t event_mask) { - if (broadcaster) { - // Scope for "locker" - // Tell the broadcaster to add this object as a listener - { - std::lock_guard<std::recursive_mutex> broadcasters_guard( - m_broadcasters_mutex); - Broadcaster::BroadcasterImplWP impl_wp(broadcaster->GetBroadcasterImpl()); - m_broadcasters.insert( - std::make_pair(impl_wp, BroadcasterInfo(event_mask))); - } - - uint32_t acquired_mask = - broadcaster->AddListener(this->shared_from_this(), event_mask); - - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS)); - if (log != nullptr) - log->Printf("%p Listener::StartListeningForEvents (broadcaster = %p, " - "mask = 0x%8.8x) acquired_mask = 0x%8.8x for %s", - static_cast<void *>(this), static_cast<void *>(broadcaster), - event_mask, acquired_mask, m_name.c_str()); - - return acquired_mask; - } - return 0; -} - -uint32_t Listener::StartListeningForEvents(Broadcaster *broadcaster, - uint32_t event_mask, - HandleBroadcastCallback callback, - void *callback_user_data) { - if (broadcaster) { - // Scope for "locker" - // Tell the broadcaster to add this object as a listener - { - std::lock_guard<std::recursive_mutex> broadcasters_guard( - m_broadcasters_mutex); - Broadcaster::BroadcasterImplWP impl_wp(broadcaster->GetBroadcasterImpl()); - m_broadcasters.insert(std::make_pair( - impl_wp, BroadcasterInfo(event_mask, callback, callback_user_data))); - } - - uint32_t acquired_mask = - broadcaster->AddListener(this->shared_from_this(), event_mask); - - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS)); - if (log != nullptr) { - void **pointer = reinterpret_cast<void **>(&callback); - log->Printf("%p Listener::StartListeningForEvents (broadcaster = %p, " - "mask = 0x%8.8x, callback = %p, user_data = %p) " - "acquired_mask = 0x%8.8x for %s", - static_cast<void *>(this), static_cast<void *>(broadcaster), - event_mask, *pointer, static_cast<void *>(callback_user_data), - acquired_mask, m_name.c_str()); - } - - return acquired_mask; - } - return 0; -} - -bool Listener::StopListeningForEvents(Broadcaster *broadcaster, - uint32_t event_mask) { - if (broadcaster) { - // Scope for "locker" - { - std::lock_guard<std::recursive_mutex> broadcasters_guard( - m_broadcasters_mutex); - m_broadcasters.erase(broadcaster->GetBroadcasterImpl()); - } - // Remove the broadcaster from our set of broadcasters - return broadcaster->RemoveListener(this->shared_from_this(), event_mask); - } - - return false; -} - -// Called when a Broadcaster is in its destructor. We need to remove all -// knowledge of this broadcaster and any events that it may have queued up -void Listener::BroadcasterWillDestruct(Broadcaster *broadcaster) { - // Scope for "broadcasters_locker" - { - std::lock_guard<std::recursive_mutex> broadcasters_guard( - m_broadcasters_mutex); - m_broadcasters.erase(broadcaster->GetBroadcasterImpl()); - } - - // Scope for "event_locker" - { - std::lock_guard<std::mutex> events_guard(m_events_mutex); - // Remove all events for this broadcaster object. - event_collection::iterator pos = m_events.begin(); - while (pos != m_events.end()) { - if ((*pos)->GetBroadcaster() == broadcaster) - pos = m_events.erase(pos); - else - ++pos; - } - } -} - -void Listener::BroadcasterManagerWillDestruct(BroadcasterManagerSP manager_sp) { - // Just need to remove this broadcast manager from the list of managers: - broadcaster_manager_collection::iterator iter, - end_iter = m_broadcaster_managers.end(); - BroadcasterManagerWP manager_wp; - - BroadcasterManagerWPMatcher matcher(manager_sp); - iter = std::find_if<broadcaster_manager_collection::iterator, - BroadcasterManagerWPMatcher>( - m_broadcaster_managers.begin(), end_iter, matcher); - if (iter != end_iter) - m_broadcaster_managers.erase(iter); -} - -void Listener::AddEvent(EventSP &event_sp) { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS)); - if (log != nullptr) - log->Printf("%p Listener('%s')::AddEvent (event_sp = {%p})", - static_cast<void *>(this), m_name.c_str(), - static_cast<void *>(event_sp.get())); - - std::lock_guard<std::mutex> guard(m_events_mutex); - m_events.push_back(event_sp); - m_events_condition.notify_all(); -} - -class EventBroadcasterMatches { -public: - EventBroadcasterMatches(Broadcaster *broadcaster) - : m_broadcaster(broadcaster) {} - - bool operator()(const EventSP &event_sp) const { - return event_sp->BroadcasterIs(m_broadcaster); - } - -private: - Broadcaster *m_broadcaster; -}; - -class EventMatcher { -public: - EventMatcher(Broadcaster *broadcaster, const ConstString *broadcaster_names, - uint32_t num_broadcaster_names, uint32_t event_type_mask) - : m_broadcaster(broadcaster), m_broadcaster_names(broadcaster_names), - m_num_broadcaster_names(num_broadcaster_names), - m_event_type_mask(event_type_mask) {} - - bool operator()(const EventSP &event_sp) const { - if (m_broadcaster && !event_sp->BroadcasterIs(m_broadcaster)) - return false; - - if (m_broadcaster_names) { - bool found_source = false; - const ConstString &event_broadcaster_name = - event_sp->GetBroadcaster()->GetBroadcasterName(); - for (uint32_t i = 0; i < m_num_broadcaster_names; ++i) { - if (m_broadcaster_names[i] == event_broadcaster_name) { - found_source = true; - break; - } - } - if (!found_source) - return false; - } - - if (m_event_type_mask == 0 || m_event_type_mask & event_sp->GetType()) - return true; - return false; - } - -private: - Broadcaster *m_broadcaster; - const ConstString *m_broadcaster_names; - const uint32_t m_num_broadcaster_names; - const uint32_t m_event_type_mask; -}; - -bool Listener::FindNextEventInternal( - std::unique_lock<std::mutex> &lock, - Broadcaster *broadcaster, // nullptr for any broadcaster - const ConstString *broadcaster_names, // nullptr for any event - uint32_t num_broadcaster_names, uint32_t event_type_mask, EventSP &event_sp, - bool remove) { - // NOTE: callers of this function must lock m_events_mutex using a - // Mutex::Locker - // and pass the locker as the first argument. m_events_mutex is no longer - // recursive. - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS)); - - if (m_events.empty()) - return false; - - Listener::event_collection::iterator pos = m_events.end(); - - if (broadcaster == nullptr && broadcaster_names == nullptr && - event_type_mask == 0) { - pos = m_events.begin(); - } else { - pos = std::find_if(m_events.begin(), m_events.end(), - EventMatcher(broadcaster, broadcaster_names, - num_broadcaster_names, event_type_mask)); - } - - if (pos != m_events.end()) { - event_sp = *pos; - - if (log != nullptr) - log->Printf("%p '%s' Listener::FindNextEventInternal(broadcaster=%p, " - "broadcaster_names=%p[%u], event_type_mask=0x%8.8x, " - "remove=%i) event %p", - static_cast<void *>(this), GetName(), - static_cast<void *>(broadcaster), - static_cast<const void *>(broadcaster_names), - num_broadcaster_names, event_type_mask, remove, - static_cast<void *>(event_sp.get())); - - if (remove) { - m_events.erase(pos); - // Unlock the event queue here. We've removed this event and are about - // to return it so it should be okay to get the next event off the queue - // here - and it might be useful to do that in the "DoOnRemoval". - lock.unlock(); - event_sp->DoOnRemoval(); - } - return true; - } - - event_sp.reset(); - return false; -} - -Event *Listener::PeekAtNextEvent() { - std::unique_lock<std::mutex> guard(m_events_mutex); - EventSP event_sp; - if (FindNextEventInternal(guard, nullptr, nullptr, 0, 0, event_sp, false)) - return event_sp.get(); - return nullptr; -} - -Event *Listener::PeekAtNextEventForBroadcaster(Broadcaster *broadcaster) { - std::unique_lock<std::mutex> guard(m_events_mutex); - EventSP event_sp; - if (FindNextEventInternal(guard, broadcaster, nullptr, 0, 0, event_sp, false)) - return event_sp.get(); - return nullptr; -} - -Event * -Listener::PeekAtNextEventForBroadcasterWithType(Broadcaster *broadcaster, - uint32_t event_type_mask) { - std::unique_lock<std::mutex> guard(m_events_mutex); - EventSP event_sp; - if (FindNextEventInternal(guard, broadcaster, nullptr, 0, event_type_mask, - event_sp, false)) - return event_sp.get(); - return nullptr; -} - -bool Listener::GetEventInternal( - const Timeout<std::micro> &timeout, - Broadcaster *broadcaster, // nullptr for any broadcaster - const ConstString *broadcaster_names, // nullptr for any event - uint32_t num_broadcaster_names, uint32_t event_type_mask, - EventSP &event_sp) { - Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS)); - LLDB_LOG(log, "this = {0}, timeout = {1} for {2}", this, timeout, m_name); - - std::unique_lock<std::mutex> lock(m_events_mutex); - - while (true) { - if (FindNextEventInternal(lock, broadcaster, broadcaster_names, - num_broadcaster_names, event_type_mask, event_sp, - true)) { - return true; - } else { - std::cv_status result = std::cv_status::no_timeout; - if (!timeout) - m_events_condition.wait(lock); - else - result = m_events_condition.wait_for(lock, *timeout); - - if (result == std::cv_status::timeout) { - log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS); - if (log) - log->Printf("%p Listener::GetEventInternal() timed out for %s", - static_cast<void *>(this), m_name.c_str()); - return false; - } else if (result != std::cv_status::no_timeout) { - log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EVENTS); - if (log) - log->Printf("%p Listener::GetEventInternal() unknown error for %s", - static_cast<void *>(this), m_name.c_str()); - return false; - } - } - } - - return false; -} - -bool Listener::GetEventForBroadcasterWithType( - Broadcaster *broadcaster, uint32_t event_type_mask, EventSP &event_sp, - const Timeout<std::micro> &timeout) { - return GetEventInternal(timeout, broadcaster, nullptr, 0, event_type_mask, - event_sp); -} - -bool Listener::GetEventForBroadcaster(Broadcaster *broadcaster, - EventSP &event_sp, - const Timeout<std::micro> &timeout) { - return GetEventInternal(timeout, broadcaster, nullptr, 0, 0, event_sp); -} - -bool Listener::GetEvent(EventSP &event_sp, const Timeout<std::micro> &timeout) { - return GetEventInternal(timeout, nullptr, nullptr, 0, 0, event_sp); -} - -size_t Listener::HandleBroadcastEvent(EventSP &event_sp) { - size_t num_handled = 0; - std::lock_guard<std::recursive_mutex> guard(m_broadcasters_mutex); - Broadcaster *broadcaster = event_sp->GetBroadcaster(); - if (!broadcaster) - return 0; - broadcaster_collection::iterator pos; - broadcaster_collection::iterator end = m_broadcasters.end(); - Broadcaster::BroadcasterImplSP broadcaster_impl_sp( - broadcaster->GetBroadcasterImpl()); - for (pos = m_broadcasters.find(broadcaster_impl_sp); - pos != end && pos->first.lock() == broadcaster_impl_sp; ++pos) { - BroadcasterInfo info = pos->second; - if (event_sp->GetType() & info.event_mask) { - if (info.callback != nullptr) { - info.callback(event_sp, info.callback_user_data); - ++num_handled; - } - } - } - return num_handled; -} - -uint32_t -Listener::StartListeningForEventSpec(BroadcasterManagerSP manager_sp, - const BroadcastEventSpec &event_spec) { - if (!manager_sp) - return 0; - - // The BroadcasterManager mutex must be locked before m_broadcasters_mutex to - // avoid violating the lock hierarchy (manager before broadcasters). - std::lock_guard<std::recursive_mutex> manager_guard( - manager_sp->m_manager_mutex); - std::lock_guard<std::recursive_mutex> guard(m_broadcasters_mutex); - - uint32_t bits_acquired = manager_sp->RegisterListenerForEvents( - this->shared_from_this(), event_spec); - if (bits_acquired) { - broadcaster_manager_collection::iterator iter, - end_iter = m_broadcaster_managers.end(); - BroadcasterManagerWP manager_wp(manager_sp); - BroadcasterManagerWPMatcher matcher(manager_sp); - iter = std::find_if<broadcaster_manager_collection::iterator, - BroadcasterManagerWPMatcher>( - m_broadcaster_managers.begin(), end_iter, matcher); - if (iter == end_iter) - m_broadcaster_managers.push_back(manager_wp); - } - - return bits_acquired; -} - -bool Listener::StopListeningForEventSpec(BroadcasterManagerSP manager_sp, - const BroadcastEventSpec &event_spec) { - if (!manager_sp) - return false; - - std::lock_guard<std::recursive_mutex> guard(m_broadcasters_mutex); - return manager_sp->UnregisterListenerForEvents(this->shared_from_this(), - event_spec); -} - -ListenerSP Listener::MakeListener(const char *name) { - return ListenerSP(new Listener(name)); -} diff --git a/source/Core/Mangled.cpp b/source/Core/Mangled.cpp index 545ac51c870f..943df008edad 100644 --- a/source/Core/Mangled.cpp +++ b/source/Core/Mangled.cpp @@ -16,6 +16,7 @@ #pragma comment(lib, "dbghelp.lib") #endif +#include "lldb/Core/RichManglingContext.h" #include "lldb/Utility/ConstString.h" #include "lldb/Utility/Log.h" #include "lldb/Utility/Logging.h" @@ -195,7 +196,7 @@ void Mangled::Clear() { int Mangled::Compare(const Mangled &a, const Mangled &b) { return ConstString::Compare( a.GetName(lldb::eLanguageTypeUnknown, ePreferMangled), - a.GetName(lldb::eLanguageTypeUnknown, ePreferMangled)); + b.GetName(lldb::eLanguageTypeUnknown, ePreferMangled)); } //---------------------------------------------------------------------- @@ -233,6 +234,130 @@ void Mangled::SetValue(const ConstString &name) { } //---------------------------------------------------------------------- +// Local helpers for different demangling implementations. +//---------------------------------------------------------------------- +static char *GetMSVCDemangledStr(const char *M) { +#if defined(_MSC_VER) + const size_t demangled_length = 2048; + char *demangled_cstr = static_cast<char *>(::malloc(demangled_length)); + ::ZeroMemory(demangled_cstr, demangled_length); + DWORD result = safeUndecorateName(M, demangled_cstr, demangled_length); + + if (Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE)) { + if (demangled_cstr && demangled_cstr[0]) + log->Printf("demangled msvc: %s -> \"%s\"", M, demangled_cstr); + else + log->Printf("demangled msvc: %s -> error: 0x%lu", M, result); + } + + if (result != 0) { + return demangled_cstr; + } else { + ::free(demangled_cstr); + return nullptr; + } +#else + return nullptr; +#endif +} + +static char *GetItaniumDemangledStr(const char *M) { + char *demangled_cstr = nullptr; + + llvm::ItaniumPartialDemangler ipd; + bool err = ipd.partialDemangle(M); + if (!err) { + // Default buffer and size (will realloc in case it's too small). + size_t demangled_size = 80; + demangled_cstr = static_cast<char *>(std::malloc(demangled_size)); + demangled_cstr = ipd.finishDemangle(demangled_cstr, &demangled_size); + + assert(demangled_cstr && + "finishDemangle must always succeed if partialDemangle did"); + assert(demangled_cstr[demangled_size - 1] == '\0' && + "Expected demangled_size to return length including trailing null"); + } + + if (Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE)) { + if (demangled_cstr) + log->Printf("demangled itanium: %s -> \"%s\"", M, demangled_cstr); + else + log->Printf("demangled itanium: %s -> error: failed to demangle", M); + } + + return demangled_cstr; +} + +//---------------------------------------------------------------------- +// Explicit demangling for scheduled requests during batch processing. This +// makes use of ItaniumPartialDemangler's rich demangle info +//---------------------------------------------------------------------- +bool Mangled::DemangleWithRichManglingInfo( + RichManglingContext &context, SkipMangledNameFn *skip_mangled_name) { + // We need to generate and cache the demangled name. + static Timer::Category func_cat(LLVM_PRETTY_FUNCTION); + Timer scoped_timer(func_cat, + "Mangled::DemangleWithRichNameIndexInfo (m_mangled = %s)", + m_mangled.GetCString()); + + // Others are not meant to arrive here. ObjC names or C's main() for example + // have their names stored in m_demangled, while m_mangled is empty. + assert(m_mangled); + + // Check whether or not we are interested in this name at all. + ManglingScheme scheme = cstring_mangling_scheme(m_mangled.GetCString()); + if (skip_mangled_name && skip_mangled_name(m_mangled.GetStringRef(), scheme)) + return false; + + switch (scheme) { + case eManglingSchemeNone: + // The current mangled_name_filter would allow llvm_unreachable here. + return false; + + case eManglingSchemeItanium: + // We want the rich mangling info here, so we don't care whether or not + // there is a demangled string in the pool already. + if (context.FromItaniumName(m_mangled)) { + // If we got an info, we have a name. Copy to string pool and connect the + // counterparts to accelerate later access in GetDemangledName(). + context.ParseFullName(); + m_demangled.SetStringWithMangledCounterpart(context.GetBufferRef(), + m_mangled); + return true; + } else { + m_demangled.SetCString(""); + return false; + } + + case eManglingSchemeMSVC: { + // We have no rich mangling for MSVC-mangled names yet, so first try to + // demangle it if necessary. + if (!m_demangled && !m_mangled.GetMangledCounterpart(m_demangled)) { + if (char *d = GetMSVCDemangledStr(m_mangled.GetCString())) { + // If we got an info, we have a name. Copy to string pool and connect + // the counterparts to accelerate later access in GetDemangledName(). + m_demangled.SetStringWithMangledCounterpart(llvm::StringRef(d), + m_mangled); + ::free(d); + } else { + m_demangled.SetCString(""); + } + } + + if (m_demangled.IsEmpty()) { + // Cannot demangle it, so don't try parsing. + return false; + } else { + // Demangled successfully, we can try and parse it with + // CPlusPlusLanguage::MethodName. + return context.FromCxxMethodName(m_demangled); + } + } + } + llvm_unreachable("Fully covered switch above!"); +} + +//---------------------------------------------------------------------- // Generate the demangled name on demand using this accessor. Code in this // class will need to use this accessor if it wishes to decode the demangled // name. The result is cached and will be kept until a new string value is @@ -242,14 +367,12 @@ const ConstString & Mangled::GetDemangledName(lldb::LanguageType language) const { // Check to make sure we have a valid mangled name and that we haven't // already decoded our mangled name. - if (m_mangled && !m_demangled) { + if (m_mangled && m_demangled.IsNull()) { // We need to generate and cache the demangled name. static Timer::Category func_cat(LLVM_PRETTY_FUNCTION); Timer scoped_timer(func_cat, "Mangled::GetDemangledName (m_mangled = %s)", m_mangled.GetCString()); - Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE); - // Don't bother running anything that isn't mangled const char *mangled_name = m_mangled.GetCString(); ManglingScheme mangling_scheme{cstring_mangling_scheme(mangled_name)}; @@ -259,60 +382,23 @@ Mangled::GetDemangledName(lldb::LanguageType language) const { // add it to our map. char *demangled_name = nullptr; switch (mangling_scheme) { - case eManglingSchemeMSVC: { -#if defined(_MSC_VER) - if (log) - log->Printf("demangle msvc: %s", mangled_name); - const size_t demangled_length = 2048; - demangled_name = static_cast<char *>(::malloc(demangled_length)); - ::ZeroMemory(demangled_name, demangled_length); - DWORD result = - safeUndecorateName(mangled_name, demangled_name, demangled_length); - if (log) { - if (demangled_name && demangled_name[0]) - log->Printf("demangled msvc: %s -> \"%s\"", mangled_name, - demangled_name); - else - log->Printf("demangled msvc: %s -> error: 0x%lu", mangled_name, - result); - } - - if (result == 0) { - free(demangled_name); - demangled_name = nullptr; - } -#endif + case eManglingSchemeMSVC: + demangled_name = GetMSVCDemangledStr(mangled_name); break; - } case eManglingSchemeItanium: { - llvm::ItaniumPartialDemangler IPD; - bool demangle_err = IPD.partialDemangle(mangled_name); - if (!demangle_err) { - // Default buffer and size (realloc is used in case it's too small). - size_t demangled_size = 80; - demangled_name = static_cast<char *>(::malloc(demangled_size)); - demangled_name = IPD.finishDemangle(demangled_name, &demangled_size); - } - - if (log) { - if (demangled_name) - log->Printf("demangled itanium: %s -> \"%s\"", mangled_name, - demangled_name); - else - log->Printf("demangled itanium: %s -> error: failed to demangle", - mangled_name); - } + demangled_name = GetItaniumDemangledStr(mangled_name); break; } case eManglingSchemeNone: - break; + llvm_unreachable("eManglingSchemeNone was handled already"); } if (demangled_name) { - m_demangled.SetCStringWithMangledCounterpart(demangled_name, m_mangled); + m_demangled.SetStringWithMangledCounterpart( + llvm::StringRef(demangled_name), m_mangled); free(demangled_name); } } - if (!m_demangled) { + if (m_demangled.IsNull()) { // Set the demangled string to the empty string to indicate we tried to // parse it once and failed. m_demangled.SetCString(""); @@ -333,9 +419,7 @@ bool Mangled::NameMatches(const RegularExpression ®ex, return true; ConstString demangled = GetDemangledName(language); - if (demangled && regex.Execute(demangled.AsCString())) - return true; - return false; + return demangled && regex.Execute(demangled.AsCString()); } //---------------------------------------------------------------------- diff --git a/source/Core/Module.cpp b/source/Core/Module.cpp index 3b1a4fd7be0f..b48d3cca092b 100644 --- a/source/Core/Module.cpp +++ b/source/Core/Module.cpp @@ -9,65 +9,65 @@ #include "lldb/Core/Module.h" -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/AddressRange.h" #include "lldb/Core/AddressResolverFileLine.h" -#include "lldb/Core/Debugger.h" // for Debugger -#include "lldb/Core/FileSpecList.h" // for FileSpecList -#include "lldb/Core/Mangled.h" // for Mangled +#include "lldb/Core/Debugger.h" +#include "lldb/Core/FileSpecList.h" +#include "lldb/Core/Mangled.h" #include "lldb/Core/ModuleSpec.h" -#include "lldb/Core/SearchFilter.h" // for SearchFilt... +#include "lldb/Core/SearchFilter.h" #include "lldb/Core/Section.h" #include "lldb/Host/FileSystem.h" #include "lldb/Host/Host.h" #include "lldb/Interpreter/CommandInterpreter.h" #include "lldb/Interpreter/ScriptInterpreter.h" #include "lldb/Symbol/CompileUnit.h" -#include "lldb/Symbol/Function.h" // for Function +#include "lldb/Symbol/Function.h" #include "lldb/Symbol/ObjectFile.h" -#include "lldb/Symbol/Symbol.h" // for Symbol +#include "lldb/Symbol/Symbol.h" #include "lldb/Symbol/SymbolContext.h" #include "lldb/Symbol/SymbolFile.h" #include "lldb/Symbol/SymbolVendor.h" -#include "lldb/Symbol/Symtab.h" // for Symtab -#include "lldb/Symbol/Type.h" // for Type -#include "lldb/Symbol/TypeList.h" // for TypeList +#include "lldb/Symbol/Symtab.h" +#include "lldb/Symbol/Type.h" +#include "lldb/Symbol/TypeList.h" #include "lldb/Symbol/TypeMap.h" #include "lldb/Symbol/TypeSystem.h" #include "lldb/Target/Language.h" -#include "lldb/Target/Platform.h" // for Platform +#include "lldb/Target/Platform.h" #include "lldb/Target/Process.h" #include "lldb/Target/Target.h" #include "lldb/Utility/DataBufferHeap.h" #include "lldb/Utility/LLDBAssert.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAn... +#include "lldb/Utility/Logging.h" #include "lldb/Utility/RegularExpression.h" #include "lldb/Utility/Status.h" -#include "lldb/Utility/Stream.h" // for Stream +#include "lldb/Utility/Stream.h" #include "lldb/Utility/StreamString.h" #include "lldb/Utility/Timer.h" #if defined(_WIN32) -#include "lldb/Host/windows/PosixApi.h" // for PATH_MAX +#include "lldb/Host/windows/PosixApi.h" #endif #include "Plugins/Language/CPlusPlus/CPlusPlusLanguage.h" #include "Plugins/Language/ObjC/ObjCLanguage.h" -#include "llvm/ADT/STLExtras.h" // for make_unique -#include "llvm/Support/Compiler.h" // for LLVM_PRETT... +#include "llvm/ADT/STLExtras.h" +#include "llvm/Support/Compiler.h" #include "llvm/Support/FileSystem.h" #include "llvm/Support/Signals.h" -#include "llvm/Support/raw_ostream.h" // for raw_string... +#include "llvm/Support/raw_ostream.h" -#include <assert.h> // for assert -#include <cstdint> // for uint32_t -#include <inttypes.h> // for PRIx64 -#include <map> // for map -#include <stdarg.h> // for va_end -#include <string.h> // for size_t -#include <type_traits> // for move -#include <utility> // for find, pair +#include <assert.h> +#include <cstdint> +#include <inttypes.h> +#include <map> +#include <stdarg.h> +#include <string.h> +#include <type_traits> +#include <utility> namespace lldb_private { class CompilerDeclContext; @@ -162,15 +162,19 @@ Module::Module(const ModuleSpec &module_spec) // fill any ivars in so we don't accidentally grab the wrong file later since // they don't match... ModuleSpec matching_module_spec; - if (modules_specs.FindMatchingModuleSpec(module_spec, matching_module_spec) == - 0) + if (!modules_specs.FindMatchingModuleSpec(module_spec, + matching_module_spec)) { + if (log) { + log->Printf("Found local object file but the specs didn't match"); + } return; + } if (module_spec.GetFileSpec()) - m_mod_time = FileSystem::GetModificationTime(module_spec.GetFileSpec()); + m_mod_time = FileSystem::Instance().GetModificationTime(module_spec.GetFileSpec()); else if (matching_module_spec.GetFileSpec()) m_mod_time = - FileSystem::GetModificationTime(matching_module_spec.GetFileSpec()); + FileSystem::Instance().GetModificationTime(matching_module_spec.GetFileSpec()); // Copy the architecture from the actual spec if we got one back, else use // the one that was specified @@ -215,7 +219,7 @@ Module::Module(const ModuleSpec &module_spec) Module::Module(const FileSpec &file_spec, const ArchSpec &arch, const ConstString *object_name, lldb::offset_t object_offset, const llvm::sys::TimePoint<> &object_mod_time) - : m_mod_time(FileSystem::GetModificationTime(file_spec)), m_arch(arch), + : m_mod_time(FileSystem::Instance().GetModificationTime(file_spec)), m_arch(arch), m_file(file_spec), m_object_offset(object_offset), m_object_mod_time(object_mod_time), m_file_has_changed(false), m_first_file_changed_log(false) { @@ -305,7 +309,7 @@ ObjectFile *Module::GetMemoryObjectFile(const lldb::ProcessSP &process_sp, // Once we get the object file, update our module with the object // file's architecture since it might differ in vendor/os if some // parts were unknown. - m_objfile_sp->GetArchitecture(m_arch); + m_arch = m_objfile_sp->GetArchitecture(); } else { error.SetErrorString("unable to find suitable object file plug-in"); } @@ -361,26 +365,24 @@ void Module::ParseAllDebugSymbols() { for (size_t cu_idx = 0; cu_idx < num_comp_units; cu_idx++) { sc.comp_unit = symbols->GetCompileUnitAtIndex(cu_idx).get(); - if (sc.comp_unit) { - sc.function = nullptr; - symbols->ParseVariablesForContext(sc); + if (!sc.comp_unit) + continue; - symbols->ParseCompileUnitFunctions(sc); + symbols->ParseVariablesForContext(sc); - for (size_t func_idx = 0; - (sc.function = sc.comp_unit->GetFunctionAtIndex(func_idx).get()) != - nullptr; - ++func_idx) { - symbols->ParseFunctionBlocks(sc); + symbols->ParseFunctions(*sc.comp_unit); - // Parse the variables for this function and all its blocks - symbols->ParseVariablesForContext(sc); - } + sc.comp_unit->ForeachFunction([&sc, &symbols](const FunctionSP &f) { + symbols->ParseBlocksRecursive(*f); - // Parse all types for this compile unit - sc.function = nullptr; - symbols->ParseTypes(sc); - } + // Parse the variables for this function and all its blocks + sc.function = f.get(); + symbols->ParseVariablesForContext(sc); + return false; + }); + + // Parse all types for this compile unit + symbols->ParseTypes(*sc.comp_unit); } } @@ -431,8 +433,8 @@ bool Module::ResolveFileAddress(lldb::addr_t vm_addr, Address &so_addr) { } uint32_t Module::ResolveSymbolContextForAddress( - const Address &so_addr, uint32_t resolve_scope, SymbolContext &sc, - bool resolve_tail_call_address) { + const Address &so_addr, lldb::SymbolContextItem resolve_scope, + SymbolContext &sc, bool resolve_tail_call_address) { std::lock_guard<std::recursive_mutex> guard(m_mutex); uint32_t resolved_flags = 0; @@ -564,21 +566,17 @@ uint32_t Module::ResolveSymbolContextForAddress( return resolved_flags; } -uint32_t Module::ResolveSymbolContextForFilePath(const char *file_path, - uint32_t line, - bool check_inlines, - uint32_t resolve_scope, - SymbolContextList &sc_list) { - FileSpec file_spec(file_path, false); +uint32_t Module::ResolveSymbolContextForFilePath( + const char *file_path, uint32_t line, bool check_inlines, + lldb::SymbolContextItem resolve_scope, SymbolContextList &sc_list) { + FileSpec file_spec(file_path); return ResolveSymbolContextsForFileSpec(file_spec, line, check_inlines, resolve_scope, sc_list); } -uint32_t Module::ResolveSymbolContextsForFileSpec(const FileSpec &file_spec, - uint32_t line, - bool check_inlines, - uint32_t resolve_scope, - SymbolContextList &sc_list) { +uint32_t Module::ResolveSymbolContextsForFileSpec( + const FileSpec &file_spec, uint32_t line, bool check_inlines, + lldb::SymbolContextItem resolve_scope, SymbolContextList &sc_list) { std::lock_guard<std::recursive_mutex> guard(m_mutex); static Timer::Category func_cat(LLVM_PRETTY_FUNCTION); Timer scoped_timer(func_cat, @@ -637,9 +635,11 @@ size_t Module::FindCompileUnits(const FileSpec &path, bool append, return sc_list.GetSize() - start_size; } -Module::LookupInfo::LookupInfo(const ConstString &name, uint32_t name_type_mask, - lldb::LanguageType language) - : m_name(name), m_lookup_name(), m_language(language), m_name_type_mask(0), +Module::LookupInfo::LookupInfo(const ConstString &name, + FunctionNameType name_type_mask, + LanguageType language) + : m_name(name), m_lookup_name(), m_language(language), + m_name_type_mask(eFunctionNameTypeNone), m_match_name_after_lookup(false) { const char *name_cstr = name.GetCString(); llvm::StringRef basename; @@ -783,7 +783,7 @@ void Module::LookupInfo::Prune(SymbolContextList &sc_list, qualified_name = cpp_method.GetBasename().str(); else qualified_name = cpp_method.GetScopeQualifiedName(); - if (qualified_name.compare(m_name.GetCString()) != 0) { + if (qualified_name != m_name.GetCString()) { sc_list.RemoveContextAtIndex(i); continue; } @@ -797,9 +797,9 @@ void Module::LookupInfo::Prune(SymbolContextList &sc_list, size_t Module::FindFunctions(const ConstString &name, const CompilerDeclContext *parent_decl_ctx, - uint32_t name_type_mask, bool include_symbols, - bool include_inlines, bool append, - SymbolContextList &sc_list) { + FunctionNameType name_type_mask, + bool include_symbols, bool include_inlines, + bool append, SymbolContextList &sc_list) { if (!append) sc_list.Clear(); @@ -943,33 +943,33 @@ void Module::FindAddressesForLine(const lldb::TargetSP target_sp, } size_t Module::FindTypes_Impl( - const SymbolContext &sc, const ConstString &name, - const CompilerDeclContext *parent_decl_ctx, bool append, size_t max_matches, + const ConstString &name, const CompilerDeclContext *parent_decl_ctx, + bool append, size_t max_matches, llvm::DenseSet<lldb_private::SymbolFile *> &searched_symbol_files, TypeMap &types) { static Timer::Category func_cat(LLVM_PRETTY_FUNCTION); Timer scoped_timer(func_cat, LLVM_PRETTY_FUNCTION); - if (!sc.module_sp || sc.module_sp.get() == this) { - SymbolVendor *symbols = GetSymbolVendor(); - if (symbols) - return symbols->FindTypes(sc, name, parent_decl_ctx, append, max_matches, - searched_symbol_files, types); - } + SymbolVendor *symbols = GetSymbolVendor(); + if (symbols) + return symbols->FindTypes(name, parent_decl_ctx, append, max_matches, + searched_symbol_files, types); return 0; } -size_t Module::FindTypesInNamespace(const SymbolContext &sc, - const ConstString &type_name, +size_t Module::FindTypesInNamespace(const ConstString &type_name, const CompilerDeclContext *parent_decl_ctx, size_t max_matches, TypeList &type_list) { const bool append = true; TypeMap types_map; llvm::DenseSet<lldb_private::SymbolFile *> searched_symbol_files; size_t num_types = - FindTypes_Impl(sc, type_name, parent_decl_ctx, append, max_matches, + FindTypes_Impl(type_name, parent_decl_ctx, append, max_matches, searched_symbol_files, types_map); - if (num_types > 0) + if (num_types > 0) { + SymbolContext sc; + sc.module_sp = shared_from_this(); sc.SortTypeList(types_map, type_list); + } return num_types; } @@ -978,15 +978,14 @@ lldb::TypeSP Module::FindFirstType(const SymbolContext &sc, TypeList type_list; llvm::DenseSet<lldb_private::SymbolFile *> searched_symbol_files; const size_t num_matches = - FindTypes(sc, name, exact_match, 1, searched_symbol_files, type_list); + FindTypes(name, exact_match, 1, searched_symbol_files, type_list); if (num_matches) return type_list.GetTypeAtIndex(0); return TypeSP(); } size_t Module::FindTypes( - const SymbolContext &sc, const ConstString &name, bool exact_match, - size_t max_matches, + const ConstString &name, bool exact_match, size_t max_matches, llvm::DenseSet<lldb_private::SymbolFile *> &searched_symbol_files, TypeList &types) { size_t num_matches = 0; @@ -1006,8 +1005,8 @@ size_t Module::FindTypes( exact_match = type_scope.consume_front("::"); ConstString type_basename_const_str(type_basename); - if (FindTypes_Impl(sc, type_basename_const_str, nullptr, append, - max_matches, searched_symbol_files, typesmap)) { + if (FindTypes_Impl(type_basename_const_str, nullptr, append, max_matches, + searched_symbol_files, typesmap)) { typesmap.RemoveMismatchedTypes(type_scope, type_basename, type_class, exact_match); num_matches = typesmap.GetSize(); @@ -1018,13 +1017,13 @@ size_t Module::FindTypes( if (type_class != eTypeClassAny && !type_basename.empty()) { // The "type_name_cstr" will have been modified if we have a valid type // class prefix (like "struct", "class", "union", "typedef" etc). - FindTypes_Impl(sc, ConstString(type_basename), nullptr, append, - UINT_MAX, searched_symbol_files, typesmap); + FindTypes_Impl(ConstString(type_basename), nullptr, append, UINT_MAX, + searched_symbol_files, typesmap); typesmap.RemoveMismatchedTypes(type_scope, type_basename, type_class, exact_match); num_matches = typesmap.GetSize(); } else { - num_matches = FindTypes_Impl(sc, name, nullptr, append, UINT_MAX, + num_matches = FindTypes_Impl(name, nullptr, append, UINT_MAX, searched_symbol_files, typesmap); if (exact_match) { std::string name_str(name.AsCString("")); @@ -1034,8 +1033,11 @@ size_t Module::FindTypes( } } } - if (num_matches > 0) + if (num_matches > 0) { + SymbolContext sc; + sc.module_sp = shared_from_this(); sc.SortTypeList(typesmap, types); + } return num_matches; } @@ -1062,7 +1064,7 @@ void Module::SetFileSpecAndObjectName(const FileSpec &file, // Container objects whose paths do not specify a file directly can call this // function to correct the file and object names. m_file = file; - m_mod_time = FileSystem::GetModificationTime(file); + m_mod_time = FileSystem::Instance().GetModificationTime(file); m_object_name = object_name; } @@ -1125,7 +1127,7 @@ void Module::ReportError(const char *format, ...) { bool Module::FileHasChanged() const { if (!m_file_has_changed) m_file_has_changed = - (FileSystem::GetModificationTime(m_file) != m_mod_time); + (FileSystem::Instance().GetModificationTime(m_file) != m_mod_time); return m_file_has_changed; } @@ -1252,7 +1254,8 @@ ObjectFile *Module::GetObjectFile() { GetFileSpec().GetFilename().AsCString("")); DataBufferSP data_sp; lldb::offset_t data_offset = 0; - const lldb::offset_t file_size = m_file.GetByteSize(); + const lldb::offset_t file_size = + FileSystem::Instance().GetByteSize(m_file); if (file_size > m_object_offset) { m_did_load_objfile = true; m_objfile_sp = ObjectFile::FindPlugin( @@ -1264,9 +1267,7 @@ ObjectFile *Module::GetObjectFile() { // parts were unknown. But since the matching arch might already be // more specific than the generic COFF architecture, only merge in // those values that overwrite unspecified unknown values. - ArchSpec new_arch; - m_objfile_sp->GetArchitecture(new_arch); - m_arch.MergeFrom(new_arch); + m_arch.MergeFrom(m_objfile_sp->GetArchitecture()); } else { ReportError("failed to load objfile for %s", GetFileSpec().GetPath().c_str()); @@ -1417,7 +1418,7 @@ void Module::PreloadSymbols() { } void Module::SetSymbolFileFileSpec(const FileSpec &file) { - if (!file.Exists()) + if (!FileSystem::Instance().Exists(file)) return; if (m_symfile_ap) { // Remove any sections in the unified section list that come from the @@ -1447,7 +1448,7 @@ void Module::SetSymbolFileFileSpec(const FileSpec &file) { // ("/tmp/a.out.dSYM/Contents/Resources/DWARF/a.out"). So we need to // check this - if (llvm::sys::fs::is_directory(file.GetPath())) { + if (FileSystem::Instance().IsDirectory(file)) { std::string new_path(file.GetPath()); std::string old_path(obj_file->GetFileSpec().GetPath()); if (old_path.find(new_path) == 0) { @@ -1536,7 +1537,8 @@ bool Module::LoadScriptingResourceInTarget(Target *target, Status &error, if (script_interpreter) { for (uint32_t i = 0; i < num_specs; ++i) { FileSpec scripting_fspec(file_specs.GetFileSpecAtIndex(i)); - if (scripting_fspec && scripting_fspec.Exists()) { + if (scripting_fspec && + FileSystem::Instance().Exists(scripting_fspec)) { if (should_load == eLoadScriptFromSymFileWarn) { if (feedback_stream) feedback_stream->Printf( diff --git a/source/Core/ModuleList.cpp b/source/Core/ModuleList.cpp index d2896da1adca..b8de86f4eadc 100644 --- a/source/Core/ModuleList.cpp +++ b/source/Core/ModuleList.cpp @@ -8,39 +8,39 @@ //===----------------------------------------------------------------------===// #include "lldb/Core/ModuleList.h" -#include "lldb/Core/FileSpecList.h" // for FileSpecList +#include "lldb/Core/FileSpecList.h" #include "lldb/Core/Module.h" #include "lldb/Core/ModuleSpec.h" #include "lldb/Host/FileSystem.h" #include "lldb/Host/Symbols.h" -#include "lldb/Interpreter/OptionValueProperties.h" #include "lldb/Interpreter/OptionValueFileSpec.h" +#include "lldb/Interpreter/OptionValueProperties.h" #include "lldb/Interpreter/Property.h" #include "lldb/Symbol/ObjectFile.h" -#include "lldb/Symbol/SymbolContext.h" // for SymbolContextList, SymbolCon... +#include "lldb/Symbol/SymbolContext.h" #include "lldb/Symbol/VariableList.h" -#include "lldb/Utility/ArchSpec.h" // for ArchSpec -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ArchSpec.h" +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAnyCategoriesSet -#include "lldb/Utility/UUID.h" // for UUID, operator!=, operator== -#include "lldb/lldb-defines.h" // for LLDB_INVALID_INDEX32 +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/UUID.h" +#include "lldb/lldb-defines.h" #if defined(_WIN32) -#include "lldb/Host/windows/PosixApi.h" // for PATH_MAX +#include "lldb/Host/windows/PosixApi.h" #endif -#include "llvm/ADT/StringRef.h" // for StringRef +#include "clang/Driver/Driver.h" +#include "llvm/ADT/StringRef.h" #include "llvm/Support/FileSystem.h" #include "llvm/Support/Threading.h" -#include "llvm/Support/raw_ostream.h" // for fs -#include "clang/Driver/Driver.h" +#include "llvm/Support/raw_ostream.h" -#include <chrono> // for operator!=, time_point -#include <memory> // for shared_ptr +#include <chrono> +#include <memory> #include <mutex> -#include <string> // for string -#include <utility> // for distance +#include <string> +#include <utility> namespace lldb_private { class Function; @@ -66,16 +66,22 @@ using namespace lldb_private; namespace { -PropertyDefinition g_properties[] = { +static constexpr PropertyDefinition g_properties[] = { {"enable-external-lookup", OptionValue::eTypeBoolean, true, true, nullptr, - nullptr, - "Control the use of external tools or libraries to locate symbol files. " - "On macOS, Spotlight is used to locate a matching .dSYM bundle based on " - "the UUID of the executable."}, + {}, + "Control the use of external tools and repositories to locate symbol " + "files. Directories listed in target.debug-file-search-paths and " + "directory of the executable are always checked first for separate debug " + "info files. Then depending on this setting: " + "On macOS, Spotlight would be also used to locate a matching .dSYM " + "bundle based on the UUID of the executable. " + "On NetBSD, directory /usr/libdata/debug would be also searched. " + "On platforms other than NetBSD directory /usr/lib/debug would be " + "also searched." + }, {"clang-modules-cache-path", OptionValue::eTypeFileSpec, true, 0, nullptr, - nullptr, - "The path to the clang modules cache directory (-fmodules-cache-path)."}, - {nullptr, OptionValue::eTypeInvalid, false, 0, nullptr, nullptr, nullptr}}; + {}, + "The path to the clang modules cache directory (-fmodules-cache-path)."}}; enum { ePropertyEnableExternalLookup, ePropertyClangModulesCachePath }; @@ -339,8 +345,9 @@ ModuleSP ModuleList::GetModuleAtIndexUnlocked(size_t idx) const { } size_t ModuleList::FindFunctions(const ConstString &name, - uint32_t name_type_mask, bool include_symbols, - bool include_inlines, bool append, + FunctionNameType name_type_mask, + bool include_symbols, bool include_inlines, + bool append, SymbolContextList &sc_list) const { if (!append) sc_list.Clear(); @@ -374,7 +381,7 @@ size_t ModuleList::FindFunctions(const ConstString &name, } size_t ModuleList::FindFunctionSymbols(const ConstString &name, - uint32_t name_type_mask, + lldb::FunctionNameType name_type_mask, SymbolContextList &sc_list) { const size_t old_size = sc_list.GetSize(); @@ -535,7 +542,7 @@ ModuleSP ModuleList::FindModule(const UUID &uuid) const { } size_t -ModuleList::FindTypes(const SymbolContext &sc, const ConstString &name, +ModuleList::FindTypes(Module *search_first, const ConstString &name, bool name_is_fully_qualified, size_t max_matches, llvm::DenseSet<SymbolFile *> &searched_symbol_files, TypeList &types) const { @@ -543,14 +550,12 @@ ModuleList::FindTypes(const SymbolContext &sc, const ConstString &name, size_t total_matches = 0; collection::const_iterator pos, end = m_modules.end(); - if (sc.module_sp) { - // The symbol context "sc" contains a module so we want to search that one - // first if it is in our list... + if (search_first) { for (pos = m_modules.begin(); pos != end; ++pos) { - if (sc.module_sp.get() == (*pos).get()) { + if (search_first == pos->get()) { total_matches += - (*pos)->FindTypes(sc, name, name_is_fully_qualified, max_matches, - searched_symbol_files, types); + search_first->FindTypes(name, name_is_fully_qualified, max_matches, + searched_symbol_files, types); if (total_matches >= max_matches) break; @@ -559,15 +564,14 @@ ModuleList::FindTypes(const SymbolContext &sc, const ConstString &name, } if (total_matches < max_matches) { - SymbolContext world_sc; for (pos = m_modules.begin(); pos != end; ++pos) { // Search the module if the module is not equal to the one in the symbol // context "sc". If "sc" contains a empty module shared pointer, then the // comparison will always be true (valid_module_ptr != nullptr). - if (sc.module_sp.get() != (*pos).get()) + if (search_first != pos->get()) total_matches += - (*pos)->FindTypes(world_sc, name, name_is_fully_qualified, - max_matches, searched_symbol_files, types); + (*pos)->FindTypes(name, name_is_fully_qualified, max_matches, + searched_symbol_files, types); if (total_matches >= max_matches) break; @@ -663,9 +667,10 @@ bool ModuleList::ResolveFileAddress(lldb::addr_t vm_addr, return false; } -uint32_t ModuleList::ResolveSymbolContextForAddress(const Address &so_addr, - uint32_t resolve_scope, - SymbolContext &sc) const { +uint32_t +ModuleList::ResolveSymbolContextForAddress(const Address &so_addr, + SymbolContextItem resolve_scope, + SymbolContext &sc) const { // The address is already section offset so it has a module uint32_t resolved_flags = 0; ModuleSP module_sp(so_addr.GetModule()); @@ -688,15 +693,15 @@ uint32_t ModuleList::ResolveSymbolContextForAddress(const Address &so_addr, uint32_t ModuleList::ResolveSymbolContextForFilePath( const char *file_path, uint32_t line, bool check_inlines, - uint32_t resolve_scope, SymbolContextList &sc_list) const { - FileSpec file_spec(file_path, false); + SymbolContextItem resolve_scope, SymbolContextList &sc_list) const { + FileSpec file_spec(file_path); return ResolveSymbolContextsForFileSpec(file_spec, line, check_inlines, resolve_scope, sc_list); } uint32_t ModuleList::ResolveSymbolContextsForFileSpec( const FileSpec &file_spec, uint32_t line, bool check_inlines, - uint32_t resolve_scope, SymbolContextList &sc_list) const { + SymbolContextItem resolve_scope, SymbolContextList &sc_list) const { std::lock_guard<std::recursive_mutex> guard(m_modules_mutex); collection::const_iterator pos, end = m_modules.end(); for (pos = m_modules.begin(); pos != end; ++pos) { @@ -856,14 +861,13 @@ Status ModuleList::GetSharedModule(const ModuleSpec &module_spec, const auto num_directories = module_search_paths_ptr->GetSize(); for (size_t idx = 0; idx < num_directories; ++idx) { auto search_path_spec = module_search_paths_ptr->GetFileSpecAtIndex(idx); - if (!search_path_spec.ResolvePath()) - continue; + FileSystem::Instance().Resolve(search_path_spec); namespace fs = llvm::sys::fs; - if (!fs::is_directory(search_path_spec.GetPath())) + if (!FileSystem::Instance().IsDirectory(search_path_spec)) continue; search_path_spec.AppendPathComponent( module_spec.GetFileSpec().GetFilename().AsCString()); - if (!search_path_spec.Exists()) + if (!FileSystem::Instance().Exists(search_path_spec)) continue; auto resolved_module_spec(module_spec); @@ -904,13 +908,15 @@ Status ModuleList::GetSharedModule(const ModuleSpec &module_spec, // Don't look for the file if it appears to be the same one we already // checked for above... if (located_binary_modulespec.GetFileSpec() != module_file_spec) { - if (!located_binary_modulespec.GetFileSpec().Exists()) { + if (!FileSystem::Instance().Exists( + located_binary_modulespec.GetFileSpec())) { located_binary_modulespec.GetFileSpec().GetPath(path, sizeof(path)); if (path[0] == '\0') module_file_spec.GetPath(path, sizeof(path)); // How can this check ever be true? This branch it is false, and we // haven't modified file_spec. - if (located_binary_modulespec.GetFileSpec().Exists()) { + if (FileSystem::Instance().Exists( + located_binary_modulespec.GetFileSpec())) { std::string uuid_str; if (uuid_ptr && uuid_ptr->IsValid()) uuid_str = uuid_ptr->GetAsString(); @@ -951,7 +957,7 @@ Status ModuleList::GetSharedModule(const ModuleSpec &module_spec, // If we didn't have a UUID in mind when looking for the object file, // then we should make sure the modification time hasn't changed! if (platform_module_spec.GetUUIDPtr() == nullptr) { - auto file_spec_mod_time = FileSystem::GetModificationTime( + auto file_spec_mod_time = FileSystem::Instance().GetModificationTime( located_binary_modulespec.GetFileSpec()); if (file_spec_mod_time != llvm::sys::TimePoint<>()) { if (file_spec_mod_time != module_sp->GetModificationTime()) { diff --git a/source/Core/Opcode.cpp b/source/Core/Opcode.cpp index d15fdb3b17be..ed8be78a6d67 100644 --- a/source/Core/Opcode.cpp +++ b/source/Core/Opcode.cpp @@ -13,50 +13,51 @@ #include "lldb/Utility/DataExtractor.h" #include "lldb/Utility/Endian.h" #include "lldb/Utility/Stream.h" -#include "lldb/lldb-forward.h" // for DataBufferSP +#include "lldb/lldb-forward.h" -#include <memory> // for make_shared +#include <memory> -#include <inttypes.h> // for PRIx64 +#include <inttypes.h> using namespace lldb; using namespace lldb_private; int Opcode::Dump(Stream *s, uint32_t min_byte_width) { - int bytes_written = 0; + const uint32_t previous_bytes = s->GetWrittenBytes(); switch (m_type) { case Opcode::eTypeInvalid: - bytes_written = s->PutCString("<invalid>"); + s->PutCString("<invalid>"); break; case Opcode::eType8: - bytes_written = s->Printf("0x%2.2x", m_data.inst8); + s->Printf("0x%2.2x", m_data.inst8); break; case Opcode::eType16: - bytes_written = s->Printf("0x%4.4x", m_data.inst16); + s->Printf("0x%4.4x", m_data.inst16); break; case Opcode::eType16_2: case Opcode::eType32: - bytes_written = s->Printf("0x%8.8x", m_data.inst32); + s->Printf("0x%8.8x", m_data.inst32); break; case Opcode::eType64: - bytes_written = s->Printf("0x%16.16" PRIx64, m_data.inst64); + s->Printf("0x%16.16" PRIx64, m_data.inst64); break; case Opcode::eTypeBytes: for (uint32_t i = 0; i < m_data.inst.length; ++i) { if (i > 0) - bytes_written += s->PutChar(' '); - bytes_written += s->Printf("%2.2x", m_data.inst.bytes[i]); + s->PutChar(' '); + s->Printf("%2.2x", m_data.inst.bytes[i]); } break; } - // Add spaces to make sure bytes dispay comes out even in case opcodes aren't - // all the same size - if (static_cast<uint32_t>(bytes_written) < min_byte_width) - bytes_written = s->Printf("%*s", min_byte_width - bytes_written, ""); - return bytes_written; + uint32_t bytes_written_so_far = s->GetWrittenBytes() - previous_bytes; + // Add spaces to make sure bytes display comes out even in case opcodes aren't + // all the same size. + if (bytes_written_so_far < min_byte_width) + s->Printf("%*s", min_byte_width - bytes_written_so_far, ""); + return s->GetWrittenBytes() - previous_bytes; } lldb::ByteOrder Opcode::GetDataByteOrder() const { diff --git a/source/Core/PluginManager.cpp b/source/Core/PluginManager.cpp index 55affb6a1030..fbb258039882 100644 --- a/source/Core/PluginManager.cpp +++ b/source/Core/PluginManager.cpp @@ -10,30 +10,31 @@ #include "lldb/Core/PluginManager.h" #include "lldb/Core/Debugger.h" +#include "lldb/Host/FileSystem.h" #include "lldb/Host/HostInfo.h" #include "lldb/Interpreter/OptionValueProperties.h" -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/FileSpec.h" #include "lldb/Utility/Status.h" -#include "lldb/Utility/StringList.h" // for StringList +#include "lldb/Utility/StringList.h" #if defined(_WIN32) -#include "lldb/Host/windows/PosixApi.h" // for PATH_MAX +#include "lldb/Host/windows/PosixApi.h" #endif #include "llvm/ADT/StringRef.h" #include "llvm/Support/DynamicLibrary.h" -#include "llvm/Support/FileSystem.h" // for file_type, file_... -#include "llvm/Support/raw_ostream.h" // for fs +#include "llvm/Support/FileSystem.h" +#include "llvm/Support/raw_ostream.h" -#include <map> // for map<>::const_ite... -#include <memory> // for shared_ptr +#include <map> +#include <memory> #include <mutex> #include <string> -#include <utility> // for pair +#include <utility> #include <vector> -#include <assert.h> // for assert +#include <assert.h> namespace lldb_private { class CommandInterpreter; @@ -89,9 +90,9 @@ template <typename FPtrTy> static FPtrTy CastToFPtr(void *VPtr) { return reinterpret_cast<FPtrTy>(reinterpret_cast<intptr_t>(VPtr)); } -static FileSpec::EnumerateDirectoryResult +static FileSystem::EnumerateDirectoryResult LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, - const FileSpec &file_spec) { + llvm::StringRef path) { // PluginManager *plugin_manager = (PluginManager *)baton; Status error; @@ -102,11 +103,11 @@ LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, // file type information. if (ft == fs::file_type::regular_file || ft == fs::file_type::symlink_file || ft == fs::file_type::type_unknown) { - FileSpec plugin_file_spec(file_spec); - plugin_file_spec.ResolvePath(); + FileSpec plugin_file_spec(path); + FileSystem::Instance().Resolve(plugin_file_spec); if (PluginIsLoaded(plugin_file_spec)) - return FileSpec::eEnumerateDirectoryResultNext; + return FileSystem::eEnumerateDirectoryResultNext; else { PluginInfo plugin_info; @@ -138,7 +139,7 @@ LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, // plug-in info so we don't try to load it again and again. SetPluginInfo(plugin_file_spec, plugin_info); - return FileSpec::eEnumerateDirectoryResultNext; + return FileSystem::eEnumerateDirectoryResultNext; } } } @@ -149,10 +150,10 @@ LoadPluginCallback(void *baton, llvm::sys::fs::file_type ft, // also do this for unknown as sometimes the directory enumeration might be // enumerating a file system that doesn't have correct file type // information. - return FileSpec::eEnumerateDirectoryResultEnter; + return FileSystem::eEnumerateDirectoryResultEnter; } - return FileSpec::eEnumerateDirectoryResultNext; + return FileSystem::eEnumerateDirectoryResultNext; } void PluginManager::Initialize() { @@ -162,16 +163,20 @@ void PluginManager::Initialize() { const bool find_other = true; char dir_path[PATH_MAX]; if (FileSpec dir_spec = HostInfo::GetSystemPluginDir()) { - if (dir_spec.Exists() && dir_spec.GetPath(dir_path, sizeof(dir_path))) { - FileSpec::EnumerateDirectory(dir_path, find_directories, find_files, - find_other, LoadPluginCallback, nullptr); + if (FileSystem::Instance().Exists(dir_spec) && + dir_spec.GetPath(dir_path, sizeof(dir_path))) { + FileSystem::Instance().EnumerateDirectory(dir_path, find_directories, + find_files, find_other, + LoadPluginCallback, nullptr); } } if (FileSpec dir_spec = HostInfo::GetUserPluginDir()) { - if (dir_spec.Exists() && dir_spec.GetPath(dir_path, sizeof(dir_path))) { - FileSpec::EnumerateDirectory(dir_path, find_directories, find_files, - find_other, LoadPluginCallback, nullptr); + if (FileSystem::Instance().Exists(dir_spec) && + dir_spec.GetPath(dir_path, sizeof(dir_path))) { + FileSystem::Instance().EnumerateDirectory(dir_path, find_directories, + find_files, find_other, + LoadPluginCallback, nullptr); } } #endif @@ -281,7 +286,10 @@ struct ArchitectureInstance { typedef std::vector<ArchitectureInstance> ArchitectureInstances; -static std::mutex g_architecture_mutex; +static std::mutex &GetArchitectureMutex() { + static std::mutex g_architecture_mutex; + return g_architecture_mutex; +} static ArchitectureInstances &GetArchitectureInstances() { static ArchitectureInstances g_instances; @@ -291,13 +299,13 @@ static ArchitectureInstances &GetArchitectureInstances() { void PluginManager::RegisterPlugin(const ConstString &name, llvm::StringRef description, ArchitectureCreateInstance create_callback) { - std::lock_guard<std::mutex> guard(g_architecture_mutex); + std::lock_guard<std::mutex> guard(GetArchitectureMutex()); GetArchitectureInstances().push_back({name, description, create_callback}); } void PluginManager::UnregisterPlugin( ArchitectureCreateInstance create_callback) { - std::lock_guard<std::mutex> guard(g_architecture_mutex); + std::lock_guard<std::mutex> guard(GetArchitectureMutex()); auto &instances = GetArchitectureInstances(); for (auto pos = instances.begin(), end = instances.end(); pos != end; ++pos) { @@ -311,7 +319,7 @@ void PluginManager::UnregisterPlugin( std::unique_ptr<Architecture> PluginManager::CreateArchitectureInstance(const ArchSpec &arch) { - std::lock_guard<std::mutex> guard(g_architecture_mutex); + std::lock_guard<std::mutex> guard(GetArchitectureMutex()); for (const auto &instances : GetArchitectureInstances()) { if (auto plugin_up = instances.create_callback(arch)) return plugin_up; diff --git a/source/Core/RegisterValue.cpp b/source/Core/RegisterValue.cpp deleted file mode 100644 index 4f908609dde9..000000000000 --- a/source/Core/RegisterValue.cpp +++ /dev/null @@ -1,905 +0,0 @@ -//===-- RegisterValue.cpp ---------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "lldb/Core/RegisterValue.h" - -#include "lldb/Core/Scalar.h" -#include "lldb/Utility/Args.h" -#include "lldb/Utility/DataExtractor.h" -#include "lldb/Utility/Status.h" -#include "lldb/Utility/Stream.h" -#include "lldb/Utility/StreamString.h" -#include "lldb/lldb-defines.h" // for LLDB_INVALID_ADDRESS -#include "lldb/lldb-private-types.h" // for RegisterInfo, type128 - -#include "llvm/ADT/ArrayRef.h" -#include "llvm/ADT/StringRef.h" - -#include <cstdint> // for uint8_t, uint32_t, uint64_t -#include <string> // for string -#include <tuple> // for tie, tuple -#include <vector> - -#include <assert.h> // for assert -#include <inttypes.h> // for PRIx64 -#include <stdio.h> // for sscanf - -using namespace lldb; -using namespace lldb_private; - -bool RegisterValue::GetData(DataExtractor &data) const { - return data.SetData(GetBytes(), GetByteSize(), GetByteOrder()) > 0; -} - -uint32_t RegisterValue::GetAsMemoryData(const RegisterInfo *reg_info, void *dst, - uint32_t dst_len, - lldb::ByteOrder dst_byte_order, - Status &error) const { - if (reg_info == nullptr) { - error.SetErrorString("invalid register info argument."); - return 0; - } - - // ReadRegister should have already been called on this object prior to - // calling this. - if (GetType() == eTypeInvalid) { - // No value has been read into this object... - error.SetErrorStringWithFormat( - "invalid register value type for register %s", reg_info->name); - return 0; - } - - if (dst_len > kMaxRegisterByteSize) { - error.SetErrorString("destination is too big"); - return 0; - } - - const uint32_t src_len = reg_info->byte_size; - - // Extract the register data into a data extractor - DataExtractor reg_data; - if (!GetData(reg_data)) { - error.SetErrorString("invalid register value to copy into"); - return 0; - } - - // Prepare a memory buffer that contains some or all of the register value - const uint32_t bytes_copied = - reg_data.CopyByteOrderedData(0, // src offset - src_len, // src length - dst, // dst buffer - dst_len, // dst length - dst_byte_order); // dst byte order - if (bytes_copied == 0) - error.SetErrorStringWithFormat( - "failed to copy data for register write of %s", reg_info->name); - - return bytes_copied; -} - -uint32_t RegisterValue::SetFromMemoryData(const RegisterInfo *reg_info, - const void *src, uint32_t src_len, - lldb::ByteOrder src_byte_order, - Status &error) { - if (reg_info == nullptr) { - error.SetErrorString("invalid register info argument."); - return 0; - } - - // Moving from addr into a register - // - // Case 1: src_len == dst_len - // - // |AABBCCDD| Address contents - // |AABBCCDD| Register contents - // - // Case 2: src_len > dst_len - // - // Status! (The register should always be big enough to hold the data) - // - // Case 3: src_len < dst_len - // - // |AABB| Address contents - // |AABB0000| Register contents [on little-endian hardware] - // |0000AABB| Register contents [on big-endian hardware] - if (src_len > kMaxRegisterByteSize) { - error.SetErrorStringWithFormat( - "register buffer is too small to receive %u bytes of data.", src_len); - return 0; - } - - const uint32_t dst_len = reg_info->byte_size; - - if (src_len > dst_len) { - error.SetErrorStringWithFormat( - "%u bytes is too big to store in register %s (%u bytes)", src_len, - reg_info->name, dst_len); - return 0; - } - - // Use a data extractor to correctly copy and pad the bytes read into the - // register value - DataExtractor src_data(src, src_len, src_byte_order, 4); - - error = SetValueFromData(reg_info, src_data, 0, true); - if (error.Fail()) - return 0; - - // If SetValueFromData succeeded, we must have copied all of src_len - return src_len; -} - -bool RegisterValue::GetScalarValue(Scalar &scalar) const { - switch (m_type) { - case eTypeInvalid: - break; - case eTypeBytes: { - switch (buffer.length) { - default: - break; - case 1: - scalar = *(const uint8_t *)buffer.bytes; - return true; - case 2: - scalar = *(const uint16_t *)buffer.bytes; - return true; - case 4: - scalar = *(const uint32_t *)buffer.bytes; - return true; - case 8: - scalar = *(const uint64_t *)buffer.bytes; - return true; - case 16: - case 32: - if (buffer.length % sizeof(uint64_t) == 0) { - const auto length_in_bits = buffer.length * 8; - const auto length_in_uint64 = buffer.length / sizeof(uint64_t); - scalar = - llvm::APInt(length_in_bits, - llvm::ArrayRef<uint64_t>((const uint64_t *)buffer.bytes, - length_in_uint64)); - return true; - } - break; - } - } break; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - scalar = m_scalar; - return true; - } - return false; -} - -void RegisterValue::Clear() { m_type = eTypeInvalid; } - -RegisterValue::Type RegisterValue::SetType(const RegisterInfo *reg_info) { - // To change the type, we simply copy the data in again, using the new format - RegisterValue copy; - DataExtractor copy_data; - if (copy.CopyValue(*this) && copy.GetData(copy_data)) - SetValueFromData(reg_info, copy_data, 0, true); - - return m_type; -} - -Status RegisterValue::SetValueFromData(const RegisterInfo *reg_info, - DataExtractor &src, - lldb::offset_t src_offset, - bool partial_data_ok) { - Status error; - - if (src.GetByteSize() == 0) { - error.SetErrorString("empty data."); - return error; - } - - if (reg_info->byte_size == 0) { - error.SetErrorString("invalid register info."); - return error; - } - - uint32_t src_len = src.GetByteSize() - src_offset; - - if (!partial_data_ok && (src_len < reg_info->byte_size)) { - error.SetErrorString("not enough data."); - return error; - } - - // Cap the data length if there is more than enough bytes for this register - // value - if (src_len > reg_info->byte_size) - src_len = reg_info->byte_size; - - // Zero out the value in case we get partial data... - memset(buffer.bytes, 0, sizeof(buffer.bytes)); - - type128 int128; - - m_type = eTypeInvalid; - switch (reg_info->encoding) { - case eEncodingInvalid: - break; - case eEncodingUint: - case eEncodingSint: - if (reg_info->byte_size == 1) - SetUInt8(src.GetMaxU32(&src_offset, src_len)); - else if (reg_info->byte_size <= 2) - SetUInt16(src.GetMaxU32(&src_offset, src_len)); - else if (reg_info->byte_size <= 4) - SetUInt32(src.GetMaxU32(&src_offset, src_len)); - else if (reg_info->byte_size <= 8) - SetUInt64(src.GetMaxU64(&src_offset, src_len)); - else if (reg_info->byte_size <= 16) { - uint64_t data1 = src.GetU64(&src_offset); - uint64_t data2 = src.GetU64(&src_offset); - if (src.GetByteSize() == eByteOrderBig) { - int128.x[0] = data1; - int128.x[1] = data2; - } else { - int128.x[0] = data2; - int128.x[1] = data1; - } - SetUInt128(llvm::APInt(128, 2, int128.x)); - } - break; - case eEncodingIEEE754: - if (reg_info->byte_size == sizeof(float)) - SetFloat(src.GetFloat(&src_offset)); - else if (reg_info->byte_size == sizeof(double)) - SetDouble(src.GetDouble(&src_offset)); - else if (reg_info->byte_size == sizeof(long double)) - SetLongDouble(src.GetLongDouble(&src_offset)); - break; - case eEncodingVector: { - m_type = eTypeBytes; - buffer.length = reg_info->byte_size; - buffer.byte_order = src.GetByteOrder(); - assert(buffer.length <= kMaxRegisterByteSize); - if (buffer.length > kMaxRegisterByteSize) - buffer.length = kMaxRegisterByteSize; - if (src.CopyByteOrderedData( - src_offset, // offset within "src" to start extracting data - src_len, // src length - buffer.bytes, // dst buffer - buffer.length, // dst length - buffer.byte_order) == 0) // dst byte order - { - error.SetErrorStringWithFormat( - "failed to copy data for register write of %s", reg_info->name); - return error; - } - } - } - - if (m_type == eTypeInvalid) - error.SetErrorStringWithFormat( - "invalid register value type for register %s", reg_info->name); - return error; -} - -// Helper function for RegisterValue::SetValueFromString() -static bool ParseVectorEncoding(const RegisterInfo *reg_info, - llvm::StringRef vector_str, - const uint32_t byte_size, - RegisterValue *reg_value) { - // Example: vector_str = "{0x2c 0x4b 0x2a 0x3e 0xd0 0x4f 0x2a 0x3e 0xac 0x4a - // 0x2a 0x3e 0x84 0x4f 0x2a 0x3e}". - vector_str = vector_str.trim(); - vector_str.consume_front("{"); - vector_str.consume_back("}"); - vector_str = vector_str.trim(); - - char Sep = ' '; - - // The first split should give us: - // ('0x2c', '0x4b 0x2a 0x3e 0xd0 0x4f 0x2a 0x3e 0xac 0x4a 0x2a 0x3e 0x84 0x4f - // 0x2a 0x3e'). - llvm::StringRef car; - llvm::StringRef cdr = vector_str; - std::tie(car, cdr) = vector_str.split(Sep); - std::vector<uint8_t> bytes; - unsigned byte = 0; - - // Using radix auto-sensing by passing 0 as the radix. Keep on processing the - // vector elements as long as the parsing succeeds and the vector size is < - // byte_size. - while (!car.getAsInteger(0, byte) && bytes.size() < byte_size) { - bytes.push_back(byte); - std::tie(car, cdr) = cdr.split(Sep); - } - - // Check for vector of exact byte_size elements. - if (bytes.size() != byte_size) - return false; - - reg_value->SetBytes(&(bytes.front()), byte_size, eByteOrderLittle); - return true; -} - -Status RegisterValue::SetValueFromString(const RegisterInfo *reg_info, - llvm::StringRef value_str) { - Status error; - if (reg_info == nullptr) { - error.SetErrorString("Invalid register info argument."); - return error; - } - - m_type = eTypeInvalid; - if (value_str.empty()) { - error.SetErrorString("Invalid c-string value string."); - return error; - } - const uint32_t byte_size = reg_info->byte_size; - - uint64_t uval64; - int64_t ival64; - float flt_val; - double dbl_val; - long double ldbl_val; - switch (reg_info->encoding) { - case eEncodingInvalid: - error.SetErrorString("Invalid encoding."); - break; - - case eEncodingUint: - if (byte_size > sizeof(uint64_t)) { - error.SetErrorStringWithFormat( - "unsupported unsigned integer byte size: %u", byte_size); - break; - } - if (value_str.getAsInteger(0, uval64)) { - error.SetErrorStringWithFormat( - "'%s' is not a valid unsigned integer string value", - value_str.str().c_str()); - break; - } - - if (!Args::UInt64ValueIsValidForByteSize(uval64, byte_size)) { - error.SetErrorStringWithFormat( - "value 0x%" PRIx64 - " is too large to fit in a %u byte unsigned integer value", - uval64, byte_size); - break; - } - - if (!SetUInt(uval64, reg_info->byte_size)) { - error.SetErrorStringWithFormat( - "unsupported unsigned integer byte size: %u", byte_size); - break; - } - // TODO: Shouldn't we be setting m_type here? - break; - - case eEncodingSint: - if (byte_size > sizeof(long long)) { - error.SetErrorStringWithFormat("unsupported signed integer byte size: %u", - byte_size); - break; - } - - if (value_str.getAsInteger(0, ival64)) { - error.SetErrorStringWithFormat( - "'%s' is not a valid signed integer string value", - value_str.str().c_str()); - break; - } - - if (!Args::SInt64ValueIsValidForByteSize(ival64, byte_size)) { - error.SetErrorStringWithFormat( - "value 0x%" PRIx64 - " is too large to fit in a %u byte signed integer value", - ival64, byte_size); - break; - } - - if (!SetUInt(ival64, reg_info->byte_size)) { - error.SetErrorStringWithFormat("unsupported signed integer byte size: %u", - byte_size); - break; - } - - // TODO: Shouldn't we be setting m_type here? - break; - - case eEncodingIEEE754: { - std::string value_string = value_str; - if (byte_size == sizeof(float)) { - if (::sscanf(value_string.c_str(), "%f", &flt_val) != 1) { - error.SetErrorStringWithFormat("'%s' is not a valid float string value", - value_string.c_str()); - break; - } - m_scalar = flt_val; - m_type = eTypeFloat; - } else if (byte_size == sizeof(double)) { - if (::sscanf(value_string.c_str(), "%lf", &dbl_val) != 1) { - error.SetErrorStringWithFormat("'%s' is not a valid float string value", - value_string.c_str()); - break; - } - m_scalar = dbl_val; - m_type = eTypeDouble; - } else if (byte_size == sizeof(long double)) { - if (::sscanf(value_string.c_str(), "%Lf", &ldbl_val) != 1) { - error.SetErrorStringWithFormat("'%s' is not a valid float string value", - value_string.c_str()); - break; - } - m_scalar = ldbl_val; - m_type = eTypeLongDouble; - } else { - error.SetErrorStringWithFormat("unsupported float byte size: %u", - byte_size); - return error; - } - break; - } - case eEncodingVector: - if (!ParseVectorEncoding(reg_info, value_str, byte_size, this)) - error.SetErrorString("unrecognized vector encoding string value."); - break; - } - - return error; -} - -bool RegisterValue::SignExtend(uint32_t sign_bitpos) { - switch (m_type) { - case eTypeInvalid: - break; - - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - return m_scalar.SignExtend(sign_bitpos); - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - case eTypeBytes: - break; - } - return false; -} - -bool RegisterValue::CopyValue(const RegisterValue &rhs) { - if (this == &rhs) - return rhs.m_type == eTypeInvalid ? false : true; - - m_type = rhs.m_type; - switch (m_type) { - case eTypeInvalid: - return false; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - m_scalar = rhs.m_scalar; - break; - case eTypeBytes: - assert(rhs.buffer.length <= kMaxRegisterByteSize); - ::memcpy(buffer.bytes, rhs.buffer.bytes, kMaxRegisterByteSize); - buffer.length = rhs.buffer.length; - buffer.byte_order = rhs.buffer.byte_order; - break; - } - return true; -} - -uint16_t RegisterValue::GetAsUInt16(uint16_t fail_value, - bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - - switch (m_type) { - default: - break; - case eTypeUInt8: - case eTypeUInt16: - return m_scalar.UShort(fail_value); - case eTypeBytes: { - switch (buffer.length) { - default: - break; - case 1: - case 2: - return *(const uint16_t *)buffer.bytes; - } - } break; - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -uint32_t RegisterValue::GetAsUInt32(uint32_t fail_value, - bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - switch (m_type) { - default: - break; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.UInt(fail_value); - case eTypeBytes: { - switch (buffer.length) { - default: - break; - case 1: - case 2: - case 4: - return *(const uint32_t *)buffer.bytes; - } - } break; - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -uint64_t RegisterValue::GetAsUInt64(uint64_t fail_value, - bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - switch (m_type) { - default: - break; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.ULongLong(fail_value); - case eTypeBytes: { - switch (buffer.length) { - default: - break; - case 1: - return *(const uint8_t *)buffer.bytes; - case 2: - return *(const uint16_t *)buffer.bytes; - case 4: - return *(const uint32_t *)buffer.bytes; - case 8: - return *(const uint64_t *)buffer.bytes; - } - } break; - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -llvm::APInt RegisterValue::GetAsUInt128(const llvm::APInt &fail_value, - bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - switch (m_type) { - default: - break; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.UInt128(fail_value); - case eTypeBytes: { - switch (buffer.length) { - default: - break; - case 1: - case 2: - case 4: - case 8: - case 16: - return llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, - ((const type128 *)buffer.bytes)->x); - } - } break; - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -float RegisterValue::GetAsFloat(float fail_value, bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - switch (m_type) { - default: - break; - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.Float(fail_value); - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -double RegisterValue::GetAsDouble(double fail_value, bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - switch (m_type) { - default: - break; - - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.Double(fail_value); - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -long double RegisterValue::GetAsLongDouble(long double fail_value, - bool *success_ptr) const { - if (success_ptr) - *success_ptr = true; - switch (m_type) { - default: - break; - - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.LongDouble(); - } - if (success_ptr) - *success_ptr = false; - return fail_value; -} - -const void *RegisterValue::GetBytes() const { - switch (m_type) { - case eTypeInvalid: - break; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.GetBytes(); - case eTypeBytes: - return buffer.bytes; - } - return nullptr; -} - -uint32_t RegisterValue::GetByteSize() const { - switch (m_type) { - case eTypeInvalid: - break; - case eTypeUInt8: - return 1; - case eTypeUInt16: - return 2; - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar.GetByteSize(); - case eTypeBytes: - return buffer.length; - } - return 0; -} - -bool RegisterValue::SetUInt(uint64_t uint, uint32_t byte_size) { - if (byte_size == 0) { - SetUInt64(uint); - } else if (byte_size == 1) { - SetUInt8(uint); - } else if (byte_size <= 2) { - SetUInt16(uint); - } else if (byte_size <= 4) { - SetUInt32(uint); - } else if (byte_size <= 8) { - SetUInt64(uint); - } else if (byte_size <= 16) { - SetUInt128(llvm::APInt(128, uint)); - } else - return false; - return true; -} - -void RegisterValue::SetBytes(const void *bytes, size_t length, - lldb::ByteOrder byte_order) { - // If this assertion fires off we need to increase the size of buffer.bytes, - // or make it something that is allocated on the heap. Since the data buffer - // is in a union, we can't make it a collection class like SmallVector... - if (bytes && length > 0) { - assert(length <= sizeof(buffer.bytes) && - "Storing too many bytes in a RegisterValue."); - m_type = eTypeBytes; - buffer.length = length; - memcpy(buffer.bytes, bytes, length); - buffer.byte_order = byte_order; - } else { - m_type = eTypeInvalid; - buffer.length = 0; - } -} - -bool RegisterValue::operator==(const RegisterValue &rhs) const { - if (m_type == rhs.m_type) { - switch (m_type) { - case eTypeInvalid: - return true; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar == rhs.m_scalar; - case eTypeBytes: - if (buffer.length != rhs.buffer.length) - return false; - else { - uint8_t length = buffer.length; - if (length > kMaxRegisterByteSize) - length = kMaxRegisterByteSize; - return memcmp(buffer.bytes, rhs.buffer.bytes, length) == 0; - } - break; - } - } - return false; -} - -bool RegisterValue::operator!=(const RegisterValue &rhs) const { - if (m_type != rhs.m_type) - return true; - switch (m_type) { - case eTypeInvalid: - return false; - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - return m_scalar != rhs.m_scalar; - case eTypeBytes: - if (buffer.length != rhs.buffer.length) { - return true; - } else { - uint8_t length = buffer.length; - if (length > kMaxRegisterByteSize) - length = kMaxRegisterByteSize; - return memcmp(buffer.bytes, rhs.buffer.bytes, length) != 0; - } - break; - } - return true; -} - -bool RegisterValue::ClearBit(uint32_t bit) { - switch (m_type) { - case eTypeInvalid: - break; - - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - if (bit < (GetByteSize() * 8)) { - return m_scalar.ClearBit(bit); - } - break; - - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - break; - - case eTypeBytes: - if (buffer.byte_order == eByteOrderBig || - buffer.byte_order == eByteOrderLittle) { - uint32_t byte_idx; - if (buffer.byte_order == eByteOrderBig) - byte_idx = buffer.length - (bit / 8) - 1; - else - byte_idx = bit / 8; - - const uint32_t byte_bit = bit % 8; - if (byte_idx < buffer.length) { - buffer.bytes[byte_idx] &= ~(1u << byte_bit); - return true; - } - } - break; - } - return false; -} - -bool RegisterValue::SetBit(uint32_t bit) { - switch (m_type) { - case eTypeInvalid: - break; - - case eTypeUInt8: - case eTypeUInt16: - case eTypeUInt32: - case eTypeUInt64: - case eTypeUInt128: - if (bit < (GetByteSize() * 8)) { - return m_scalar.SetBit(bit); - } - break; - - case eTypeFloat: - case eTypeDouble: - case eTypeLongDouble: - break; - - case eTypeBytes: - if (buffer.byte_order == eByteOrderBig || - buffer.byte_order == eByteOrderLittle) { - uint32_t byte_idx; - if (buffer.byte_order == eByteOrderBig) - byte_idx = buffer.length - (bit / 8) - 1; - else - byte_idx = bit / 8; - - const uint32_t byte_bit = bit % 8; - if (byte_idx < buffer.length) { - buffer.bytes[byte_idx] |= (1u << byte_bit); - return true; - } - } - break; - } - return false; -} diff --git a/source/Core/RichManglingContext.cpp b/source/Core/RichManglingContext.cpp new file mode 100644 index 000000000000..f5fbe38a49fb --- /dev/null +++ b/source/Core/RichManglingContext.cpp @@ -0,0 +1,175 @@ +//===-- RichManglingContext.cpp ---------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "lldb/Core/RichManglingContext.h" + +#include "lldb/Utility/Log.h" +#include "lldb/Utility/Logging.h" + +#include "Plugins/Language/CPlusPlus/CPlusPlusLanguage.h" + +#include "llvm/ADT/StringRef.h" + +using namespace lldb; +using namespace lldb_private; + +//---------------------------------------------------------------------- +// RichManglingContext +//---------------------------------------------------------------------- +void RichManglingContext::ResetProvider(InfoProvider new_provider) { + // If we want to support parsers for other languages some day, we need a + // switch here to delete the correct parser type. + if (m_cxx_method_parser.hasValue()) { + assert(m_provider == PluginCxxLanguage); + delete get<CPlusPlusLanguage::MethodName>(m_cxx_method_parser); + m_cxx_method_parser.reset(); + } + + assert(new_provider != None && "Only reset to a valid provider"); + m_provider = new_provider; +} + +bool RichManglingContext::FromItaniumName(const ConstString &mangled) { + bool err = m_ipd.partialDemangle(mangled.GetCString()); + if (!err) { + ResetProvider(ItaniumPartialDemangler); + } + + if (Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE)) { + if (!err) { + ParseFullName(); + LLDB_LOG(log, "demangled itanium: {0} -> \"{1}\"", mangled, m_ipd_buf); + } else { + LLDB_LOG(log, "demangled itanium: {0} -> error: failed to demangle", + mangled); + } + } + + return !err; // true == success +} + +bool RichManglingContext::FromCxxMethodName(const ConstString &demangled) { + ResetProvider(PluginCxxLanguage); + m_cxx_method_parser = new CPlusPlusLanguage::MethodName(demangled); + return true; +} + +bool RichManglingContext::IsCtorOrDtor() const { + assert(m_provider != None && "Initialize a provider first"); + switch (m_provider) { + case ItaniumPartialDemangler: + return m_ipd.isCtorOrDtor(); + case PluginCxxLanguage: { + // We can only check for destructors here. + auto base_name = + get<CPlusPlusLanguage::MethodName>(m_cxx_method_parser)->GetBasename(); + return base_name.startswith("~"); + } + case None: + return false; + } + llvm_unreachable("Fully covered switch above!"); +} + +bool RichManglingContext::IsFunction() const { + assert(m_provider != None && "Initialize a provider first"); + switch (m_provider) { + case ItaniumPartialDemangler: + return m_ipd.isFunction(); + case PluginCxxLanguage: + return get<CPlusPlusLanguage::MethodName>(m_cxx_method_parser)->IsValid(); + case None: + return false; + } + llvm_unreachable("Fully covered switch above!"); +} + +void RichManglingContext::processIPDStrResult(char *ipd_res, size_t res_size) { + // Error case: Clear the buffer. + if (LLVM_UNLIKELY(ipd_res == nullptr)) { + assert(res_size == m_ipd_buf_size && + "Failed IPD queries keep the original size in the N parameter"); + + m_ipd_buf[0] = '\0'; + m_buffer = llvm::StringRef(m_ipd_buf, 0); + return; + } + + // IPD's res_size includes null terminator. + assert(ipd_res[res_size - 1] == '\0' && + "IPD returns null-terminated strings and we rely on that"); + + // Update buffer/size on realloc. + if (LLVM_UNLIKELY(ipd_res != m_ipd_buf || res_size > m_ipd_buf_size)) { + m_ipd_buf = ipd_res; // std::realloc freed or reused the old buffer. + m_ipd_buf_size = res_size; // May actually be bigger, but we can't know. + + if (Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE)) + LLDB_LOG(log, "ItaniumPartialDemangler Realloc: new buffer size is {0}", + m_ipd_buf_size); + } + + // 99% case: Just remember the string length. + m_buffer = llvm::StringRef(m_ipd_buf, res_size - 1); +} + +void RichManglingContext::ParseFunctionBaseName() { + assert(m_provider != None && "Initialize a provider first"); + switch (m_provider) { + case ItaniumPartialDemangler: { + auto n = m_ipd_buf_size; + auto buf = m_ipd.getFunctionBaseName(m_ipd_buf, &n); + processIPDStrResult(buf, n); + return; + } + case PluginCxxLanguage: + m_buffer = + get<CPlusPlusLanguage::MethodName>(m_cxx_method_parser)->GetBasename(); + return; + case None: + return; + } +} + +void RichManglingContext::ParseFunctionDeclContextName() { + assert(m_provider != None && "Initialize a provider first"); + switch (m_provider) { + case ItaniumPartialDemangler: { + auto n = m_ipd_buf_size; + auto buf = m_ipd.getFunctionDeclContextName(m_ipd_buf, &n); + processIPDStrResult(buf, n); + return; + } + case PluginCxxLanguage: + m_buffer = + get<CPlusPlusLanguage::MethodName>(m_cxx_method_parser)->GetContext(); + return; + case None: + return; + } +} + +void RichManglingContext::ParseFullName() { + assert(m_provider != None && "Initialize a provider first"); + switch (m_provider) { + case ItaniumPartialDemangler: { + auto n = m_ipd_buf_size; + auto buf = m_ipd.finishDemangle(m_ipd_buf, &n); + processIPDStrResult(buf, n); + return; + } + case PluginCxxLanguage: + m_buffer = get<CPlusPlusLanguage::MethodName>(m_cxx_method_parser) + ->GetFullName() + .GetStringRef(); + return; + case None: + return; + } +} diff --git a/source/Core/Scalar.cpp b/source/Core/Scalar.cpp deleted file mode 100644 index 6a7186969ef2..000000000000 --- a/source/Core/Scalar.cpp +++ /dev/null @@ -1,2852 +0,0 @@ -//===-- Scalar.cpp ----------------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "lldb/Core/Scalar.h" - -#include "lldb/Utility/DataExtractor.h" -#include "lldb/Utility/Endian.h" -#include "lldb/Utility/Status.h" -#include "lldb/Utility/Stream.h" -#include "lldb/lldb-types.h" // for offset_t - -#include "llvm/ADT/SmallString.h" - -#include <cinttypes> -#include <cstdio> - -using namespace lldb; -using namespace lldb_private; - -//---------------------------------------------------------------------- -// Promote to max type currently follows the ANSI C rule for type promotion in -// expressions. -//---------------------------------------------------------------------- -static Scalar::Type PromoteToMaxType( - const Scalar &lhs, // The const left hand side object - const Scalar &rhs, // The const right hand side object - Scalar &temp_value, // A modifiable temp value than can be used to hold - // either the promoted lhs or rhs object - const Scalar *&promoted_lhs_ptr, // Pointer to the resulting possibly - // promoted value of lhs (at most one of - // lhs/rhs will get promoted) - const Scalar *&promoted_rhs_ptr // Pointer to the resulting possibly - // promoted value of rhs (at most one of - // lhs/rhs will get promoted) - ) { - Scalar result; - // Initialize the promoted values for both the right and left hand side - // values to be the objects themselves. If no promotion is needed (both right - // and left have the same type), then the temp_value will not get used. - promoted_lhs_ptr = &lhs; - promoted_rhs_ptr = &rhs; - // Extract the types of both the right and left hand side values - Scalar::Type lhs_type = lhs.GetType(); - Scalar::Type rhs_type = rhs.GetType(); - - if (lhs_type > rhs_type) { - // Right hand side need to be promoted - temp_value = rhs; // Copy right hand side into the temp value - if (temp_value.Promote(lhs_type)) // Promote it - promoted_rhs_ptr = - &temp_value; // Update the pointer for the promoted right hand side - } else if (lhs_type < rhs_type) { - // Left hand side need to be promoted - temp_value = lhs; // Copy left hand side value into the temp value - if (temp_value.Promote(rhs_type)) // Promote it - promoted_lhs_ptr = - &temp_value; // Update the pointer for the promoted left hand side - } - - // Make sure our type promotion worked as expected - if (promoted_lhs_ptr->GetType() == promoted_rhs_ptr->GetType()) - return promoted_lhs_ptr->GetType(); // Return the resulting max type - - // Return the void type (zero) if we fail to promote either of the values. - return Scalar::e_void; -} - -Scalar::Scalar() : m_type(e_void), m_float((float)0) {} - -Scalar::Scalar(const Scalar &rhs) - : m_type(rhs.m_type), m_integer(rhs.m_integer), m_float(rhs.m_float) {} - -// Scalar::Scalar(const RegisterValue& reg) : -// m_type(e_void), -// m_data() -//{ -// switch (reg.info.encoding) -// { -// case eEncodingUint: // unsigned integer -// switch (reg.info.byte_size) -// { -// case 1: m_type = e_uint; m_data.uint = reg.value.uint8; break; -// case 2: m_type = e_uint; m_data.uint = reg.value.uint16; break; -// case 4: m_type = e_uint; m_data.uint = reg.value.uint32; break; -// case 8: m_type = e_ulonglong; m_data.ulonglong = reg.value.uint64; -// break; -// break; -// } -// break; -// -// case eEncodingSint: // signed integer -// switch (reg.info.byte_size) -// { -// case 1: m_type = e_sint; m_data.sint = reg.value.sint8; break; -// case 2: m_type = e_sint; m_data.sint = reg.value.sint16; break; -// case 4: m_type = e_sint; m_data.sint = reg.value.sint32; break; -// case 8: m_type = e_slonglong; m_data.slonglong = reg.value.sint64; -// break; -// break; -// } -// break; -// -// case eEncodingIEEE754: // float -// switch (reg.info.byte_size) -// { -// case 4: m_type = e_float; m_data.flt = reg.value.float32; break; -// case 8: m_type = e_double; m_data.dbl = reg.value.float64; break; -// break; -// } -// break; -// case eEncodingVector: // vector registers -// break; -// } -//} - -bool Scalar::GetData(DataExtractor &data, size_t limit_byte_size) const { - size_t byte_size = GetByteSize(); - if (byte_size > 0) { - const uint8_t *bytes = reinterpret_cast<const uint8_t *>(GetBytes()); - - if (limit_byte_size < byte_size) { - if (endian::InlHostByteOrder() == eByteOrderLittle) { - // On little endian systems if we want fewer bytes from the current - // type we just specify fewer bytes since the LSByte is first... - byte_size = limit_byte_size; - } else if (endian::InlHostByteOrder() == eByteOrderBig) { - // On big endian systems if we want fewer bytes from the current type - // have to advance our initial byte pointer and trim down the number of - // bytes since the MSByte is first - bytes += byte_size - limit_byte_size; - byte_size = limit_byte_size; - } - } - - data.SetData(bytes, byte_size, endian::InlHostByteOrder()); - return true; - } - data.Clear(); - return false; -} - -const void *Scalar::GetBytes() const { - const uint64_t *apint_words; - const uint8_t *bytes; - static float_t flt_val; - static double_t dbl_val; - static uint64_t swapped_words[4]; - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - bytes = reinterpret_cast<const uint8_t *>(m_integer.getRawData()); - // getRawData always returns a pointer to an uint64_t. If we have a - // smaller type, we need to update the pointer on big-endian systems. - if (endian::InlHostByteOrder() == eByteOrderBig) { - size_t byte_size = m_integer.getBitWidth() / 8; - if (byte_size < 8) - bytes += 8 - byte_size; - } - return bytes; - case e_sint128: - case e_uint128: - apint_words = m_integer.getRawData(); - // getRawData always returns a pointer to an array of two uint64_t values, - // where the least-significant word always comes first. On big-endian - // systems we need to swap the two words. - if (endian::InlHostByteOrder() == eByteOrderBig) { - swapped_words[0] = apint_words[1]; - swapped_words[1] = apint_words[0]; - apint_words = swapped_words; - } - return reinterpret_cast<const void *>(apint_words); - case e_sint256: - case e_uint256: - apint_words = m_integer.getRawData(); - // getRawData always returns a pointer to an array of four uint64_t values, - // where the least-significant word always comes first. On big-endian - // systems we need to swap the four words. - if (endian::InlHostByteOrder() == eByteOrderBig) { - swapped_words[0] = apint_words[3]; - swapped_words[1] = apint_words[2]; - swapped_words[2] = apint_words[1]; - swapped_words[3] = apint_words[0]; - apint_words = swapped_words; - } - return reinterpret_cast<const void *>(apint_words); - case e_float: - flt_val = m_float.convertToFloat(); - return reinterpret_cast<const void *>(&flt_val); - case e_double: - dbl_val = m_float.convertToDouble(); - return reinterpret_cast<const void *>(&dbl_val); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - apint_words = ldbl_val.getRawData(); - // getRawData always returns a pointer to an array of two uint64_t values, - // where the least-significant word always comes first. On big-endian - // systems we need to swap the two words. - if (endian::InlHostByteOrder() == eByteOrderBig) { - swapped_words[0] = apint_words[1]; - swapped_words[1] = apint_words[0]; - apint_words = swapped_words; - } - return reinterpret_cast<const void *>(apint_words); - } - return nullptr; -} - -size_t Scalar::GetByteSize() const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (m_integer.getBitWidth() / 8); - case e_float: - return sizeof(float_t); - case e_double: - return sizeof(double_t); - case e_long_double: - return sizeof(long_double_t); - } - return 0; -} - -bool Scalar::IsZero() const { - llvm::APInt zero_int = llvm::APInt::getNullValue(m_integer.getBitWidth() / 8); - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return llvm::APInt::isSameValue(zero_int, m_integer); - case e_float: - case e_double: - case e_long_double: - return m_float.isZero(); - } - return false; -} - -void Scalar::GetValue(Stream *s, bool show_type) const { - if (show_type) - s->Printf("(%s) ", GetTypeAsCString()); - - switch (m_type) { - case e_void: - break; - case e_sint: - case e_slong: - case e_slonglong: - case e_sint128: - case e_sint256: - s->PutCString(m_integer.toString(10, true)); - break; - case e_uint: - case e_ulong: - case e_ulonglong: - case e_uint128: - case e_uint256: - s->PutCString(m_integer.toString(10, false)); - break; - case e_float: - case e_double: - case e_long_double: - llvm::SmallString<24> string; - m_float.toString(string); - s->Printf("%s", string.c_str()); - break; - } -} - -const char *Scalar::GetTypeAsCString() const { - switch (m_type) { - case e_void: - return "void"; - case e_sint: - return "int"; - case e_uint: - return "unsigned int"; - case e_slong: - return "long"; - case e_ulong: - return "unsigned long"; - case e_slonglong: - return "long long"; - case e_ulonglong: - return "unsigned long long"; - case e_sint128: - return "int128_t"; - case e_uint128: - return "unsigned int128_t"; - case e_sint256: - return "int256_t"; - case e_uint256: - return "unsigned int256_t"; - case e_float: - return "float"; - case e_double: - return "double"; - case e_long_double: - return "long double"; - } - return "<invalid Scalar type>"; -} - -Scalar &Scalar::operator=(const Scalar &rhs) { - if (this != &rhs) { - m_type = rhs.m_type; - m_integer = llvm::APInt(rhs.m_integer); - m_float = rhs.m_float; - } - return *this; -} - -Scalar &Scalar::operator=(const int v) { - m_type = e_sint; - m_integer = llvm::APInt(sizeof(int) * 8, v, true); - return *this; -} - -Scalar &Scalar::operator=(unsigned int v) { - m_type = e_uint; - m_integer = llvm::APInt(sizeof(int) * 8, v); - return *this; -} - -Scalar &Scalar::operator=(long v) { - m_type = e_slong; - m_integer = llvm::APInt(sizeof(long) * 8, v, true); - return *this; -} - -Scalar &Scalar::operator=(unsigned long v) { - m_type = e_ulong; - m_integer = llvm::APInt(sizeof(long) * 8, v); - return *this; -} - -Scalar &Scalar::operator=(long long v) { - m_type = e_slonglong; - m_integer = llvm::APInt(sizeof(long) * 8, v, true); - return *this; -} - -Scalar &Scalar::operator=(unsigned long long v) { - m_type = e_ulonglong; - m_integer = llvm::APInt(sizeof(long long) * 8, v); - return *this; -} - -Scalar &Scalar::operator=(float v) { - m_type = e_float; - m_float = llvm::APFloat(v); - return *this; -} - -Scalar &Scalar::operator=(double v) { - m_type = e_double; - m_float = llvm::APFloat(v); - return *this; -} - -Scalar &Scalar::operator=(long double v) { - m_type = e_long_double; - if (m_ieee_quad) - m_float = llvm::APFloat( - llvm::APFloat::IEEEquad(), - llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((type128 *)&v)->x)); - else - m_float = llvm::APFloat( - llvm::APFloat::x87DoubleExtended(), - llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((type128 *)&v)->x)); - return *this; -} - -Scalar &Scalar::operator=(llvm::APInt rhs) { - m_integer = llvm::APInt(rhs); - switch (m_integer.getBitWidth()) { - case 8: - case 16: - case 32: - if (m_integer.isSignedIntN(sizeof(sint_t) * 8)) - m_type = e_sint; - else - m_type = e_uint; - break; - case 64: - if (m_integer.isSignedIntN(sizeof(slonglong_t) * 8)) - m_type = e_slonglong; - else - m_type = e_ulonglong; - break; - case 128: - if (m_integer.isSignedIntN(BITWIDTH_INT128)) - m_type = e_sint128; - else - m_type = e_uint128; - break; - case 256: - if (m_integer.isSignedIntN(BITWIDTH_INT256)) - m_type = e_sint256; - else - m_type = e_uint256; - break; - } - return *this; -} - -Scalar::~Scalar() = default; - -bool Scalar::Promote(Scalar::Type type) { - bool success = false; - switch (m_type) { - case e_void: - break; - - case e_sint: - switch (type) { - case e_void: - break; - case e_sint: - success = true; - break; - case e_uint: - m_integer = m_integer.sextOrTrunc(sizeof(uint_t) * 8); - success = true; - break; - - case e_slong: - m_integer = m_integer.sextOrTrunc(sizeof(slong_t) * 8); - success = true; - break; - - case e_ulong: - m_integer = m_integer.sextOrTrunc(sizeof(ulong_t) * 8); - success = true; - break; - - case e_slonglong: - m_integer = m_integer.sextOrTrunc(sizeof(slonglong_t) * 8); - success = true; - break; - - case e_ulonglong: - m_integer = m_integer.sextOrTrunc(sizeof(ulonglong_t) * 8); - success = true; - break; - - case e_sint128: - case e_uint128: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_uint: - switch (type) { - case e_void: - case e_sint: - break; - case e_uint: - success = true; - break; - case e_slong: - m_integer = m_integer.zextOrTrunc(sizeof(slong_t) * 8); - success = true; - break; - - case e_ulong: - m_integer = m_integer.zextOrTrunc(sizeof(ulong_t) * 8); - success = true; - break; - - case e_slonglong: - m_integer = m_integer.zextOrTrunc(sizeof(slonglong_t) * 8); - success = true; - break; - - case e_ulonglong: - m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); - success = true; - break; - - case e_sint128: - case e_uint128: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_slong: - switch (type) { - case e_void: - case e_sint: - case e_uint: - break; - case e_slong: - success = true; - break; - case e_ulong: - m_integer = m_integer.sextOrTrunc(sizeof(ulong_t) * 8); - success = true; - break; - - case e_slonglong: - m_integer = m_integer.sextOrTrunc(sizeof(slonglong_t) * 8); - success = true; - break; - - case e_ulonglong: - m_integer = m_integer.sextOrTrunc(sizeof(ulonglong_t) * 8); - success = true; - break; - - case e_sint128: - case e_uint128: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_ulong: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - break; - case e_ulong: - success = true; - break; - case e_slonglong: - m_integer = m_integer.zextOrTrunc(sizeof(slonglong_t) * 8); - success = true; - break; - - case e_ulonglong: - m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); - success = true; - break; - - case e_sint128: - case e_uint128: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_slonglong: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - break; - case e_slonglong: - success = true; - break; - case e_ulonglong: - m_integer = m_integer.sextOrTrunc(sizeof(ulonglong_t) * 8); - success = true; - break; - - case e_sint128: - case e_uint128: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_ulonglong: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - break; - case e_ulonglong: - success = true; - break; - case e_sint128: - case e_uint128: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_sint128: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - break; - case e_sint128: - success = true; - break; - case e_uint128: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); - success = true; - break; - - case e_sint256: - case e_uint256: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_uint128: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - break; - case e_uint128: - success = true; - break; - case e_sint256: - case e_uint256: - m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_sint256: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - break; - case e_sint256: - success = true; - break; - case e_uint256: - m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); - success = true; - break; - - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, true, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_uint256: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - break; - case e_uint256: - success = true; - break; - case e_float: - m_float = llvm::APFloat(llvm::APFloat::IEEEsingle()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_double: - m_float = llvm::APFloat(llvm::APFloat::IEEEdouble()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - - case e_long_double: - m_float = llvm::APFloat(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended()); - m_float.convertFromAPInt(m_integer, false, - llvm::APFloat::rmNearestTiesToEven); - success = true; - break; - } - break; - - case e_float: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - break; - case e_float: - success = true; - break; - case e_double: - m_float = llvm::APFloat((double_t)m_float.convertToFloat()); - success = true; - break; - - case e_long_double: { - bool ignore; - m_float.convert(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended(), - llvm::APFloat::rmNearestTiesToEven, &ignore); - success = true; - break; - } - } - break; - - case e_double: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - case e_float: - break; - case e_double: - success = true; - break; - case e_long_double: { - bool ignore; - m_float.convert(m_ieee_quad ? llvm::APFloat::IEEEquad() - : llvm::APFloat::x87DoubleExtended(), - llvm::APFloat::rmNearestTiesToEven, &ignore); - success = true; - break; - } - } - break; - - case e_long_double: - switch (type) { - case e_void: - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - case e_float: - case e_double: - break; - case e_long_double: - success = true; - break; - } - break; - } - - if (success) - m_type = type; - return success; -} - -const char *Scalar::GetValueTypeAsCString(Scalar::Type type) { - switch (type) { - case e_void: - return "void"; - case e_sint: - return "int"; - case e_uint: - return "unsigned int"; - case e_slong: - return "long"; - case e_ulong: - return "unsigned long"; - case e_slonglong: - return "long long"; - case e_ulonglong: - return "unsigned long long"; - case e_float: - return "float"; - case e_double: - return "double"; - case e_long_double: - return "long double"; - case e_sint128: - return "int128_t"; - case e_uint128: - return "uint128_t"; - case e_sint256: - return "int256_t"; - case e_uint256: - return "uint256_t"; - } - return "???"; -} - -Scalar::Type -Scalar::GetValueTypeForSignedIntegerWithByteSize(size_t byte_size) { - if (byte_size <= sizeof(sint_t)) - return e_sint; - if (byte_size <= sizeof(slong_t)) - return e_slong; - if (byte_size <= sizeof(slonglong_t)) - return e_slonglong; - return e_void; -} - -Scalar::Type -Scalar::GetValueTypeForUnsignedIntegerWithByteSize(size_t byte_size) { - if (byte_size <= sizeof(uint_t)) - return e_uint; - if (byte_size <= sizeof(ulong_t)) - return e_ulong; - if (byte_size <= sizeof(ulonglong_t)) - return e_ulonglong; - return e_void; -} - -Scalar::Type Scalar::GetValueTypeForFloatWithByteSize(size_t byte_size) { - if (byte_size == sizeof(float_t)) - return e_float; - if (byte_size == sizeof(double_t)) - return e_double; - if (byte_size == sizeof(long_double_t)) - return e_long_double; - return e_void; -} - -bool Scalar::MakeSigned() { - bool success = false; - - switch (m_type) { - case e_void: - break; - case e_sint: - success = true; - break; - case e_uint: - m_type = e_sint; - success = true; - break; - case e_slong: - success = true; - break; - case e_ulong: - m_type = e_slong; - success = true; - break; - case e_slonglong: - success = true; - break; - case e_ulonglong: - m_type = e_slonglong; - success = true; - break; - case e_sint128: - success = true; - break; - case e_uint128: - m_type = e_sint128; - success = true; - break; - case e_sint256: - success = true; - break; - case e_uint256: - m_type = e_sint256; - success = true; - break; - case e_float: - success = true; - break; - case e_double: - success = true; - break; - case e_long_double: - success = true; - break; - } - - return success; -} - -bool Scalar::MakeUnsigned() { - bool success = false; - - switch (m_type) { - case e_void: - break; - case e_sint: - m_type = e_uint; - success = true; - break; - case e_uint: - success = true; - break; - case e_slong: - m_type = e_ulong; - success = true; - break; - case e_ulong: - success = true; - break; - case e_slonglong: - m_type = e_ulonglong; - success = true; - break; - case e_ulonglong: - success = true; - break; - case e_sint128: - m_type = e_uint128; - success = true; - break; - case e_uint128: - success = true; - break; - case e_sint256: - m_type = e_uint256; - success = true; - break; - case e_uint256: - success = true; - break; - case e_float: - success = true; - break; - case e_double: - success = true; - break; - case e_long_double: - success = true; - break; - } - - return success; -} - -signed char Scalar::SChar(char fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (schar_t)(m_integer.sextOrTrunc(sizeof(schar_t) * 8)).getSExtValue(); - case e_float: - return (schar_t)m_float.convertToFloat(); - case e_double: - return (schar_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (schar_t)(ldbl_val.sextOrTrunc(sizeof(schar_t) * 8)).getSExtValue(); - } - return fail_value; -} - -unsigned char Scalar::UChar(unsigned char fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (uchar_t)(m_integer.zextOrTrunc(sizeof(uchar_t) * 8)).getZExtValue(); - case e_float: - return (uchar_t)m_float.convertToFloat(); - case e_double: - return (uchar_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (uchar_t)(ldbl_val.zextOrTrunc(sizeof(uchar_t) * 8)).getZExtValue(); - } - return fail_value; -} - -short Scalar::SShort(short fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (sshort_t)(m_integer.sextOrTrunc(sizeof(sshort_t) * 8)) - .getSExtValue(); - case e_float: - return (sshort_t)m_float.convertToFloat(); - case e_double: - return (sshort_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (sshort_t)(ldbl_val.sextOrTrunc(sizeof(sshort_t) * 8)) - .getSExtValue(); - } - return fail_value; -} - -unsigned short Scalar::UShort(unsigned short fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (ushort_t)(m_integer.zextOrTrunc(sizeof(ushort_t) * 8)) - .getZExtValue(); - case e_float: - return (ushort_t)m_float.convertToFloat(); - case e_double: - return (ushort_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (ushort_t)(ldbl_val.zextOrTrunc(sizeof(ushort_t) * 8)) - .getZExtValue(); - } - return fail_value; -} - -int Scalar::SInt(int fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (sint_t)(m_integer.sextOrTrunc(sizeof(sint_t) * 8)).getSExtValue(); - case e_float: - return (sint_t)m_float.convertToFloat(); - case e_double: - return (sint_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (sint_t)(ldbl_val.sextOrTrunc(sizeof(sint_t) * 8)).getSExtValue(); - } - return fail_value; -} - -unsigned int Scalar::UInt(unsigned int fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (uint_t)(m_integer.zextOrTrunc(sizeof(uint_t) * 8)).getZExtValue(); - case e_float: - return (uint_t)m_float.convertToFloat(); - case e_double: - return (uint_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (uint_t)(ldbl_val.zextOrTrunc(sizeof(uint_t) * 8)).getZExtValue(); - } - return fail_value; -} - -long Scalar::SLong(long fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (slong_t)(m_integer.sextOrTrunc(sizeof(slong_t) * 8)).getSExtValue(); - case e_float: - return (slong_t)m_float.convertToFloat(); - case e_double: - return (slong_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (slong_t)(ldbl_val.sextOrTrunc(sizeof(slong_t) * 8)).getSExtValue(); - } - return fail_value; -} - -unsigned long Scalar::ULong(unsigned long fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (ulong_t)(m_integer.zextOrTrunc(sizeof(ulong_t) * 8)).getZExtValue(); - case e_float: - return (ulong_t)m_float.convertToFloat(); - case e_double: - return (ulong_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (ulong_t)(ldbl_val.zextOrTrunc(sizeof(ulong_t) * 8)).getZExtValue(); - } - return fail_value; -} - -long long Scalar::SLongLong(long long fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (slonglong_t)(m_integer.sextOrTrunc(sizeof(slonglong_t) * 8)) - .getSExtValue(); - case e_float: - return (slonglong_t)m_float.convertToFloat(); - case e_double: - return (slonglong_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (slonglong_t)(ldbl_val.sextOrTrunc(sizeof(slonglong_t) * 8)) - .getSExtValue(); - } - return fail_value; -} - -unsigned long long Scalar::ULongLong(unsigned long long fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (ulonglong_t)(m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8)) - .getZExtValue(); - case e_float: - return (ulonglong_t)m_float.convertToFloat(); - case e_double: - return (ulonglong_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (ulonglong_t)(ldbl_val.zextOrTrunc(sizeof(ulonglong_t) * 8)) - .getZExtValue(); - } - return fail_value; -} - -llvm::APInt Scalar::SInt128(llvm::APInt &fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return m_integer; - case e_float: - case e_double: - case e_long_double: - return m_float.bitcastToAPInt(); - } - return fail_value; -} - -llvm::APInt Scalar::UInt128(const llvm::APInt &fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return m_integer; - case e_float: - case e_double: - case e_long_double: - return m_float.bitcastToAPInt(); - } - return fail_value; -} - -llvm::APInt Scalar::SInt256(llvm::APInt &fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return m_integer; - case e_float: - case e_double: - case e_long_double: - return m_float.bitcastToAPInt(); - } - return fail_value; -} - -llvm::APInt Scalar::UInt256(const llvm::APInt &fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return m_integer; - case e_float: - case e_double: - case e_long_double: - return m_float.bitcastToAPInt(); - } - return fail_value; -} - -float Scalar::Float(float fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return llvm::APIntOps::RoundAPIntToFloat(m_integer); - case e_float: - return m_float.convertToFloat(); - case e_double: - return (float_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return ldbl_val.bitsToFloat(); - } - return fail_value; -} - -double Scalar::Double(double fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return llvm::APIntOps::RoundAPIntToDouble(m_integer); - case e_float: - return (double_t)m_float.convertToFloat(); - case e_double: - return m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return ldbl_val.bitsToFloat(); - } - return fail_value; -} - -long double Scalar::LongDouble(long double fail_value) const { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return (long_double_t)llvm::APIntOps::RoundAPIntToDouble(m_integer); - case e_float: - return (long_double_t)m_float.convertToFloat(); - case e_double: - return (long_double_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (long_double_t)ldbl_val.bitsToDouble(); - } - return fail_value; -} - -Scalar &Scalar::operator+=(const Scalar &rhs) { - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((m_type = PromoteToMaxType(*this, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer = a->m_integer + b->m_integer; - break; - - case e_float: - case e_double: - case e_long_double: - m_float = a->m_float + b->m_float; - break; - } - } - return *this; -} - -Scalar &Scalar::operator<<=(const Scalar &rhs) { - switch (m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - switch (rhs.m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer = m_integer << rhs.m_integer; - break; - } - break; - } - return *this; -} - -bool Scalar::ShiftRightLogical(const Scalar &rhs) { - switch (m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - switch (rhs.m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer = m_integer.lshr(rhs.m_integer); - break; - } - break; - } - return m_type != e_void; -} - -Scalar &Scalar::operator>>=(const Scalar &rhs) { - switch (m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - switch (rhs.m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer = m_integer.ashr(rhs.m_integer); - break; - } - break; - } - return *this; -} - -Scalar &Scalar::operator&=(const Scalar &rhs) { - switch (m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - switch (rhs.m_type) { - case e_void: - case e_float: - case e_double: - case e_long_double: - m_type = e_void; - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer &= rhs.m_integer; - break; - } - break; - } - return *this; -} - -bool Scalar::AbsoluteValue() { - switch (m_type) { - case e_void: - break; - - case e_sint: - case e_slong: - case e_slonglong: - case e_sint128: - case e_sint256: - if (m_integer.isNegative()) - m_integer = -m_integer; - return true; - - case e_uint: - case e_ulong: - case e_ulonglong: - return true; - case e_uint128: - case e_uint256: - case e_float: - case e_double: - case e_long_double: - m_float.clearSign(); - return true; - } - return false; -} - -bool Scalar::UnaryNegate() { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer = -m_integer; - return true; - case e_float: - case e_double: - case e_long_double: - m_float.changeSign(); - return true; - } - return false; -} - -bool Scalar::OnesComplement() { - switch (m_type) { - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer = ~m_integer; - return true; - - case e_void: - case e_float: - case e_double: - case e_long_double: - break; - } - return false; -} - -const Scalar lldb_private::operator+(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - result.m_integer = a->m_integer + b->m_integer; - break; - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result.m_float = a->m_float + b->m_float; - break; - } - } - return result; -} - -const Scalar lldb_private::operator-(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - result.m_integer = a->m_integer - b->m_integer; - break; - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result.m_float = a->m_float - b->m_float; - break; - } - } - return result; -} - -const Scalar lldb_private::operator/(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - if (b->m_integer != 0) { - result.m_integer = a->m_integer.sdiv(b->m_integer); - return result; - } - break; - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - if (b->m_integer != 0) { - result.m_integer = a->m_integer.udiv(b->m_integer); - return result; - } - break; - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - if (!b->m_float.isZero()) { - result.m_float = a->m_float / b->m_float; - return result; - } - break; - } - } - // For division only, the only way it should make it here is if a promotion - // failed, or if we are trying to do a divide by zero. - result.m_type = Scalar::e_void; - return result; -} - -const Scalar lldb_private::operator*(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - result.m_integer = a->m_integer * b->m_integer; - break; - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result.m_float = a->m_float * b->m_float; - break; - } - } - return result; -} - -const Scalar lldb_private::operator&(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - result.m_integer = a->m_integer & b->m_integer; - break; - case Scalar::e_void: - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - // No bitwise AND on floats, doubles of long doubles - result.m_type = Scalar::e_void; - break; - } - } - return result; -} - -const Scalar lldb_private::operator|(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - result.m_integer = a->m_integer | b->m_integer; - break; - - case Scalar::e_void: - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - // No bitwise AND on floats, doubles of long doubles - result.m_type = Scalar::e_void; - break; - } - } - return result; -} - -const Scalar lldb_private::operator%(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - default: - break; - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - if (b->m_integer != 0) { - result.m_integer = a->m_integer.srem(b->m_integer); - return result; - } - break; - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - if (b->m_integer != 0) { - result.m_integer = a->m_integer.urem(b->m_integer); - return result; - } - break; - } - } - result.m_type = Scalar::e_void; - return result; -} - -const Scalar lldb_private::operator^(const Scalar &lhs, const Scalar &rhs) { - Scalar result; - Scalar temp_value; - const Scalar *a; - const Scalar *b; - if ((result.m_type = PromoteToMaxType(lhs, rhs, temp_value, a, b)) != - Scalar::e_void) { - switch (result.m_type) { - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - result.m_integer = a->m_integer ^ b->m_integer; - break; - - case Scalar::e_void: - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - // No bitwise AND on floats, doubles of long doubles - result.m_type = Scalar::e_void; - break; - } - } - return result; -} - -const Scalar lldb_private::operator<<(const Scalar &lhs, const Scalar &rhs) { - Scalar result = lhs; - result <<= rhs; - return result; -} - -const Scalar lldb_private::operator>>(const Scalar &lhs, const Scalar &rhs) { - Scalar result = lhs; - result >>= rhs; - return result; -} - -Status Scalar::SetValueFromCString(const char *value_str, Encoding encoding, - size_t byte_size) { - Status error; - if (value_str == nullptr || value_str[0] == '\0') { - error.SetErrorString("Invalid c-string value string."); - return error; - } - switch (encoding) { - case eEncodingInvalid: - error.SetErrorString("Invalid encoding."); - break; - - case eEncodingUint: - if (byte_size <= sizeof(uint64_t)) { - uint64_t uval64; - if (!llvm::to_integer(value_str, uval64)) - error.SetErrorStringWithFormat( - "'%s' is not a valid unsigned integer string value", value_str); - else if (!UIntValueIsValidForSize(uval64, byte_size)) - error.SetErrorStringWithFormat("value 0x%" PRIx64 - " is too large to fit in a %" PRIu64 - " byte unsigned integer value", - uval64, (uint64_t)byte_size); - else { - m_type = Scalar::GetValueTypeForUnsignedIntegerWithByteSize(byte_size); - switch (m_type) { - case e_uint: - m_integer = llvm::APInt(sizeof(uint_t) * 8, uval64, false); - break; - case e_ulong: - m_integer = llvm::APInt(sizeof(ulong_t) * 8, uval64, false); - break; - case e_ulonglong: - m_integer = llvm::APInt(sizeof(ulonglong_t) * 8, uval64, false); - break; - default: - error.SetErrorStringWithFormat( - "unsupported unsigned integer byte size: %" PRIu64 "", - (uint64_t)byte_size); - break; - } - } - } else { - error.SetErrorStringWithFormat( - "unsupported unsigned integer byte size: %" PRIu64 "", - (uint64_t)byte_size); - return error; - } - break; - - case eEncodingSint: - if (byte_size <= sizeof(int64_t)) { - int64_t sval64; - if (!llvm::to_integer(value_str, sval64)) - error.SetErrorStringWithFormat( - "'%s' is not a valid signed integer string value", value_str); - else if (!SIntValueIsValidForSize(sval64, byte_size)) - error.SetErrorStringWithFormat("value 0x%" PRIx64 - " is too large to fit in a %" PRIu64 - " byte signed integer value", - sval64, (uint64_t)byte_size); - else { - m_type = Scalar::GetValueTypeForSignedIntegerWithByteSize(byte_size); - switch (m_type) { - case e_sint: - m_integer = llvm::APInt(sizeof(sint_t) * 8, sval64, true); - break; - case e_slong: - m_integer = llvm::APInt(sizeof(slong_t) * 8, sval64, true); - break; - case e_slonglong: - m_integer = llvm::APInt(sizeof(slonglong_t) * 8, sval64, true); - break; - default: - error.SetErrorStringWithFormat( - "unsupported signed integer byte size: %" PRIu64 "", - (uint64_t)byte_size); - break; - } - } - } else { - error.SetErrorStringWithFormat( - "unsupported signed integer byte size: %" PRIu64 "", - (uint64_t)byte_size); - return error; - } - break; - - case eEncodingIEEE754: - static float f_val; - static double d_val; - static long double l_val; - if (byte_size == sizeof(float)) { - if (::sscanf(value_str, "%f", &f_val) == 1) { - m_float = llvm::APFloat(f_val); - m_type = e_float; - } else - error.SetErrorStringWithFormat("'%s' is not a valid float string value", - value_str); - } else if (byte_size == sizeof(double)) { - if (::sscanf(value_str, "%lf", &d_val) == 1) { - m_float = llvm::APFloat(d_val); - m_type = e_double; - } else - error.SetErrorStringWithFormat("'%s' is not a valid float string value", - value_str); - } else if (byte_size == sizeof(long double)) { - if (::sscanf(value_str, "%Lf", &l_val) == 1) { - m_float = - llvm::APFloat(llvm::APFloat::x87DoubleExtended(), - llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, - ((type128 *)&l_val)->x)); - m_type = e_long_double; - } else - error.SetErrorStringWithFormat("'%s' is not a valid float string value", - value_str); - } else { - error.SetErrorStringWithFormat("unsupported float byte size: %" PRIu64 "", - (uint64_t)byte_size); - return error; - } - break; - - case eEncodingVector: - error.SetErrorString("vector encoding unsupported."); - break; - } - if (error.Fail()) - m_type = e_void; - - return error; -} - -Status Scalar::SetValueFromData(DataExtractor &data, lldb::Encoding encoding, - size_t byte_size) { - Status error; - - type128 int128; - type256 int256; - switch (encoding) { - case lldb::eEncodingInvalid: - error.SetErrorString("invalid encoding"); - break; - case lldb::eEncodingVector: - error.SetErrorString("vector encoding unsupported"); - break; - case lldb::eEncodingUint: { - lldb::offset_t offset = 0; - - switch (byte_size) { - case 1: - operator=((uint8_t)data.GetU8(&offset)); - break; - case 2: - operator=((uint16_t)data.GetU16(&offset)); - break; - case 4: - operator=((uint32_t)data.GetU32(&offset)); - break; - case 8: - operator=((uint64_t)data.GetU64(&offset)); - break; - case 16: - if (data.GetByteOrder() == eByteOrderBig) { - int128.x[1] = (uint64_t)data.GetU64(&offset); - int128.x[0] = (uint64_t)data.GetU64(&offset); - } else { - int128.x[0] = (uint64_t)data.GetU64(&offset); - int128.x[1] = (uint64_t)data.GetU64(&offset); - } - operator=(llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, int128.x)); - break; - case 32: - if (data.GetByteOrder() == eByteOrderBig) { - int256.x[3] = (uint64_t)data.GetU64(&offset); - int256.x[2] = (uint64_t)data.GetU64(&offset); - int256.x[1] = (uint64_t)data.GetU64(&offset); - int256.x[0] = (uint64_t)data.GetU64(&offset); - } else { - int256.x[0] = (uint64_t)data.GetU64(&offset); - int256.x[1] = (uint64_t)data.GetU64(&offset); - int256.x[2] = (uint64_t)data.GetU64(&offset); - int256.x[3] = (uint64_t)data.GetU64(&offset); - } - operator=(llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, int256.x)); - break; - default: - error.SetErrorStringWithFormat( - "unsupported unsigned integer byte size: %" PRIu64 "", - (uint64_t)byte_size); - break; - } - } break; - case lldb::eEncodingSint: { - lldb::offset_t offset = 0; - - switch (byte_size) { - case 1: - operator=((int8_t)data.GetU8(&offset)); - break; - case 2: - operator=((int16_t)data.GetU16(&offset)); - break; - case 4: - operator=((int32_t)data.GetU32(&offset)); - break; - case 8: - operator=((int64_t)data.GetU64(&offset)); - break; - case 16: - if (data.GetByteOrder() == eByteOrderBig) { - int128.x[1] = (uint64_t)data.GetU64(&offset); - int128.x[0] = (uint64_t)data.GetU64(&offset); - } else { - int128.x[0] = (uint64_t)data.GetU64(&offset); - int128.x[1] = (uint64_t)data.GetU64(&offset); - } - operator=(llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, int128.x)); - break; - case 32: - if (data.GetByteOrder() == eByteOrderBig) { - int256.x[3] = (uint64_t)data.GetU64(&offset); - int256.x[2] = (uint64_t)data.GetU64(&offset); - int256.x[1] = (uint64_t)data.GetU64(&offset); - int256.x[0] = (uint64_t)data.GetU64(&offset); - } else { - int256.x[0] = (uint64_t)data.GetU64(&offset); - int256.x[1] = (uint64_t)data.GetU64(&offset); - int256.x[2] = (uint64_t)data.GetU64(&offset); - int256.x[3] = (uint64_t)data.GetU64(&offset); - } - operator=(llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, int256.x)); - break; - default: - error.SetErrorStringWithFormat( - "unsupported signed integer byte size: %" PRIu64 "", - (uint64_t)byte_size); - break; - } - } break; - case lldb::eEncodingIEEE754: { - lldb::offset_t offset = 0; - - if (byte_size == sizeof(float)) - operator=((float)data.GetFloat(&offset)); - else if (byte_size == sizeof(double)) - operator=((double)data.GetDouble(&offset)); - else if (byte_size == sizeof(long double)) - operator=((long double)data.GetLongDouble(&offset)); - else - error.SetErrorStringWithFormat("unsupported float byte size: %" PRIu64 "", - (uint64_t)byte_size); - } break; - } - - return error; -} - -bool Scalar::SignExtend(uint32_t sign_bit_pos) { - const uint32_t max_bit_pos = GetByteSize() * 8; - - if (sign_bit_pos < max_bit_pos) { - switch (m_type) { - case Scalar::e_void: - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - return false; - - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - if (max_bit_pos == sign_bit_pos) - return true; - else if (sign_bit_pos < (max_bit_pos - 1)) { - llvm::APInt sign_bit = llvm::APInt::getSignMask(sign_bit_pos + 1); - llvm::APInt bitwize_and = m_integer & sign_bit; - if (bitwize_and.getBoolValue()) { - const llvm::APInt mask = - ~(sign_bit) + llvm::APInt(m_integer.getBitWidth(), 1); - m_integer |= mask; - } - return true; - } - break; - } - } - return false; -} - -size_t Scalar::GetAsMemoryData(void *dst, size_t dst_len, - lldb::ByteOrder dst_byte_order, - Status &error) const { - // Get a data extractor that points to the native scalar data - DataExtractor data; - if (!GetData(data)) { - error.SetErrorString("invalid scalar value"); - return 0; - } - - const size_t src_len = data.GetByteSize(); - - // Prepare a memory buffer that contains some or all of the register value - const size_t bytes_copied = - data.CopyByteOrderedData(0, // src offset - src_len, // src length - dst, // dst buffer - dst_len, // dst length - dst_byte_order); // dst byte order - if (bytes_copied == 0) - error.SetErrorString("failed to copy data"); - - return bytes_copied; -} - -bool Scalar::ExtractBitfield(uint32_t bit_size, uint32_t bit_offset) { - if (bit_size == 0) - return true; - - switch (m_type) { - case Scalar::e_void: - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - break; - - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - m_integer = m_integer.ashr(bit_offset) - .sextOrTrunc(bit_size) - .sextOrSelf(8 * GetByteSize()); - return true; - - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - m_integer = m_integer.lshr(bit_offset) - .zextOrTrunc(bit_size) - .zextOrSelf(8 * GetByteSize()); - return true; - } - return false; -} - -bool lldb_private::operator==(const Scalar &lhs, const Scalar &rhs) { - // If either entry is void then we can just compare the types - if (lhs.m_type == Scalar::e_void || rhs.m_type == Scalar::e_void) - return lhs.m_type == rhs.m_type; - - Scalar temp_value; - const Scalar *a; - const Scalar *b; - llvm::APFloat::cmpResult result; - switch (PromoteToMaxType(lhs, rhs, temp_value, a, b)) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - return a->m_integer == b->m_integer; - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result = a->m_float.compare(b->m_float); - if (result == llvm::APFloat::cmpEqual) - return true; - } - return false; -} - -bool lldb_private::operator!=(const Scalar &lhs, const Scalar &rhs) { - // If either entry is void then we can just compare the types - if (lhs.m_type == Scalar::e_void || rhs.m_type == Scalar::e_void) - return lhs.m_type != rhs.m_type; - - Scalar - temp_value; // A temp value that might get a copy of either promoted value - const Scalar *a; - const Scalar *b; - llvm::APFloat::cmpResult result; - switch (PromoteToMaxType(lhs, rhs, temp_value, a, b)) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_uint: - case Scalar::e_slong: - case Scalar::e_ulong: - case Scalar::e_slonglong: - case Scalar::e_ulonglong: - case Scalar::e_sint128: - case Scalar::e_uint128: - case Scalar::e_sint256: - case Scalar::e_uint256: - return a->m_integer != b->m_integer; - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result = a->m_float.compare(b->m_float); - if (result != llvm::APFloat::cmpEqual) - return true; - } - return true; -} - -bool lldb_private::operator<(const Scalar &lhs, const Scalar &rhs) { - if (lhs.m_type == Scalar::e_void || rhs.m_type == Scalar::e_void) - return false; - - Scalar temp_value; - const Scalar *a; - const Scalar *b; - llvm::APFloat::cmpResult result; - switch (PromoteToMaxType(lhs, rhs, temp_value, a, b)) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - return a->m_integer.slt(b->m_integer); - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - return a->m_integer.ult(b->m_integer); - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result = a->m_float.compare(b->m_float); - if (result == llvm::APFloat::cmpLessThan) - return true; - } - return false; -} - -bool lldb_private::operator<=(const Scalar &lhs, const Scalar &rhs) { - if (lhs.m_type == Scalar::e_void || rhs.m_type == Scalar::e_void) - return false; - - Scalar temp_value; - const Scalar *a; - const Scalar *b; - llvm::APFloat::cmpResult result; - switch (PromoteToMaxType(lhs, rhs, temp_value, a, b)) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - return a->m_integer.sle(b->m_integer); - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - return a->m_integer.ule(b->m_integer); - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result = a->m_float.compare(b->m_float); - if (result == llvm::APFloat::cmpLessThan || - result == llvm::APFloat::cmpEqual) - return true; - } - return false; -} - -bool lldb_private::operator>(const Scalar &lhs, const Scalar &rhs) { - if (lhs.m_type == Scalar::e_void || rhs.m_type == Scalar::e_void) - return false; - - Scalar temp_value; - const Scalar *a; - const Scalar *b; - llvm::APFloat::cmpResult result; - switch (PromoteToMaxType(lhs, rhs, temp_value, a, b)) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - return a->m_integer.sgt(b->m_integer); - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - return a->m_integer.ugt(b->m_integer); - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result = a->m_float.compare(b->m_float); - if (result == llvm::APFloat::cmpGreaterThan) - return true; - } - return false; -} - -bool lldb_private::operator>=(const Scalar &lhs, const Scalar &rhs) { - if (lhs.m_type == Scalar::e_void || rhs.m_type == Scalar::e_void) - return false; - - Scalar temp_value; - const Scalar *a; - const Scalar *b; - llvm::APFloat::cmpResult result; - switch (PromoteToMaxType(lhs, rhs, temp_value, a, b)) { - case Scalar::e_void: - break; - case Scalar::e_sint: - case Scalar::e_slong: - case Scalar::e_slonglong: - case Scalar::e_sint128: - case Scalar::e_sint256: - return a->m_integer.sge(b->m_integer); - case Scalar::e_uint: - case Scalar::e_ulong: - case Scalar::e_ulonglong: - case Scalar::e_uint128: - case Scalar::e_uint256: - return a->m_integer.uge(b->m_integer); - case Scalar::e_float: - case Scalar::e_double: - case Scalar::e_long_double: - result = a->m_float.compare(b->m_float); - if (result == llvm::APFloat::cmpGreaterThan || - result == llvm::APFloat::cmpEqual) - return true; - } - return false; -} - -bool Scalar::ClearBit(uint32_t bit) { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer.clearBit(bit); - return true; - case e_float: - case e_double: - case e_long_double: - break; - } - return false; -} - -bool Scalar::SetBit(uint32_t bit) { - switch (m_type) { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - m_integer.setBit(bit); - return true; - case e_float: - case e_double: - case e_long_double: - break; - } - return false; -} diff --git a/source/Core/SearchFilter.cpp b/source/Core/SearchFilter.cpp index 0701955233a1..5d26c715bec6 100644 --- a/source/Core/SearchFilter.cpp +++ b/source/Core/SearchFilter.cpp @@ -9,26 +9,27 @@ #include "lldb/Core/SearchFilter.h" -#include "lldb/Breakpoint/Breakpoint.h" // for Breakpoint +#include "lldb/Breakpoint/Breakpoint.h" #include "lldb/Core/Module.h" -#include "lldb/Core/ModuleList.h" // for ModuleList +#include "lldb/Core/ModuleList.h" #include "lldb/Symbol/CompileUnit.h" -#include "lldb/Symbol/SymbolContext.h" // for SymbolContext +#include "lldb/Symbol/SymbolContext.h" +#include "lldb/Symbol/SymbolVendor.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/Utility/Status.h" // for Status -#include "lldb/Utility/Stream.h" // for Stream -#include "lldb/lldb-enumerations.h" // for SymbolContextItem::eSymbolCo... +#include "lldb/Utility/ConstString.h" +#include "lldb/Utility/Status.h" +#include "lldb/Utility/Stream.h" +#include "lldb/lldb-enumerations.h" -#include "llvm/ADT/StringRef.h" // for StringRef -#include "llvm/Support/ErrorHandling.h" // for llvm_unreachable +#include "llvm/ADT/StringRef.h" +#include "llvm/Support/ErrorHandling.h" -#include <memory> // for shared_ptr -#include <mutex> // for recursive_mutex, lock_guard -#include <string> // for string +#include <memory> +#include <mutex> +#include <string> -#include <inttypes.h> // for PRIu64 -#include <string.h> // for size_t, strcmp +#include <inttypes.h> +#include <string.h> namespace lldb_private { class Address; @@ -147,6 +148,15 @@ bool SearchFilter::CompUnitPasses(FileSpec &fileSpec) { return true; } bool SearchFilter::CompUnitPasses(CompileUnit &compUnit) { return true; } +bool SearchFilter::FunctionPasses(Function &function) { + // This is a slightly cheesy job, but since we don't have finer grained + // filters yet, just checking that the start address passes is probably + // good enough for the base class behavior. + Address addr = function.GetAddressRange().GetBaseAddress(); + return AddressPasses(addr); +} + + uint32_t SearchFilter::GetFilterRequiredItems() { return (lldb::SymbolContextItem)0; } @@ -207,7 +217,7 @@ void SearchFilter::Search(Searcher &searcher) { return; empty_sc.target_sp = m_target_sp; - if (searcher.GetDepth() == Searcher::eDepthTarget) + if (searcher.GetDepth() == lldb::eSearchDepthTarget) searcher.SearchCallback(*this, empty_sc, nullptr, false); else DoModuleIteration(empty_sc, searcher); @@ -220,7 +230,7 @@ void SearchFilter::SearchInModuleList(Searcher &searcher, ModuleList &modules) { return; empty_sc.target_sp = m_target_sp; - if (searcher.GetDepth() == Searcher::eDepthTarget) + if (searcher.GetDepth() == lldb::eSearchDepthTarget) searcher.SearchCallback(*this, empty_sc, nullptr, false); else { std::lock_guard<std::recursive_mutex> guard(modules.GetMutex()); @@ -247,9 +257,9 @@ SearchFilter::DoModuleIteration(const lldb::ModuleSP &module_sp, Searcher::CallbackReturn SearchFilter::DoModuleIteration(const SymbolContext &context, Searcher &searcher) { - if (searcher.GetDepth() >= Searcher::eDepthModule) { + if (searcher.GetDepth() >= lldb::eSearchDepthModule) { if (context.module_sp) { - if (searcher.GetDepth() == Searcher::eDepthModule) { + if (searcher.GetDepth() == lldb::eSearchDepthModule) { SymbolContext matchingContext(context.module_sp.get()); searcher.SearchCallback(*this, matchingContext, nullptr, false); } else { @@ -267,7 +277,7 @@ SearchFilter::DoModuleIteration(const SymbolContext &context, if (!ModulePasses(module_sp)) continue; - if (searcher.GetDepth() == Searcher::eDepthModule) { + if (searcher.GetDepth() == lldb::eSearchDepthModule) { SymbolContext matchingContext(m_target_sp, module_sp); Searcher::CallbackReturn shouldContinue = @@ -301,7 +311,7 @@ SearchFilter::DoCUIteration(const ModuleSP &module_sp, if (!CompUnitPasses(*(cu_sp.get()))) continue; - if (searcher.GetDepth() == Searcher::eDepthCompUnit) { + if (searcher.GetDepth() == lldb::eSearchDepthCompUnit) { SymbolContext matchingContext(m_target_sp, module_sp, cu_sp.get()); shouldContinue = @@ -312,7 +322,30 @@ SearchFilter::DoCUIteration(const ModuleSP &module_sp, else if (shouldContinue == Searcher::eCallbackReturnStop) return shouldContinue; } else { - // FIXME Descend to block. + // First make sure this compile unit's functions are parsed + // since CompUnit::ForeachFunction only iterates over already + // parsed functions. + SymbolVendor *sym_vendor = module_sp->GetSymbolVendor(); + if (!sym_vendor) + continue; + if (!sym_vendor->ParseFunctions(*cu_sp)) + continue; + // If we got any functions, use ForeachFunction to do the iteration. + cu_sp->ForeachFunction([&](const FunctionSP &func_sp) { + if (!FunctionPasses(*func_sp.get())) + return false; // Didn't pass the filter, just keep going. + if (searcher.GetDepth() == lldb::eSearchDepthFunction) { + SymbolContext matchingContext(m_target_sp, module_sp, + cu_sp.get(), func_sp.get()); + shouldContinue = searcher.SearchCallback(*this, + matchingContext, + nullptr, false); + } else { + shouldContinue = DoFunctionIteration(func_sp.get(), context, + searcher); + } + return shouldContinue != Searcher::eCallbackReturnContinue; + }); } } } @@ -353,10 +386,7 @@ SearchFilterForUnconstrainedSearches::SerializeToStructuredData() { bool SearchFilterForUnconstrainedSearches::ModulePasses( const FileSpec &module_spec) { - if (m_target_sp->ModuleIsExcludedForUnconstrainedSearches(module_spec)) - return false; - else - return true; + return !m_target_sp->ModuleIsExcludedForUnconstrainedSearches(module_spec); } bool SearchFilterForUnconstrainedSearches::ModulePasses( @@ -421,7 +451,7 @@ void SearchFilterByModule::Search(Searcher &searcher) { if (!m_target_sp) return; - if (searcher.GetDepth() == Searcher::eDepthTarget) { + if (searcher.GetDepth() == lldb::eSearchDepthTarget) { SymbolContext empty_sc; empty_sc.target_sp = m_target_sp; searcher.SearchCallback(*this, empty_sc, nullptr, false); @@ -489,7 +519,7 @@ SearchFilterSP SearchFilterByModule::CreateFromStructuredData( error.SetErrorString("SFBM::CFSD: filter module item not a string."); return nullptr; } - FileSpec module_spec(module, false); + FileSpec module_spec(module); return std::make_shared<SearchFilterByModule>(target.shared_from_this(), module_spec); @@ -535,22 +565,15 @@ bool SearchFilterByModuleList::ModulePasses(const ModuleSP &module_sp) { if (m_module_spec_list.GetSize() == 0) return true; - if (module_sp && - m_module_spec_list.FindFileIndex(0, module_sp->GetFileSpec(), false) != - UINT32_MAX) - return true; - else - return false; + return module_sp && m_module_spec_list.FindFileIndex( + 0, module_sp->GetFileSpec(), false) != UINT32_MAX; } bool SearchFilterByModuleList::ModulePasses(const FileSpec &spec) { if (m_module_spec_list.GetSize() == 0) return true; - if (m_module_spec_list.FindFileIndex(0, spec, true) != UINT32_MAX) - return true; - else - return false; + return m_module_spec_list.FindFileIndex(0, spec, true) != UINT32_MAX; } bool SearchFilterByModuleList::AddressPasses(Address &address) { @@ -570,7 +593,7 @@ void SearchFilterByModuleList::Search(Searcher &searcher) { if (!m_target_sp) return; - if (searcher.GetDepth() == Searcher::eDepthTarget) { + if (searcher.GetDepth() == lldb::eSearchDepthTarget) { SymbolContext empty_sc; empty_sc.target_sp = m_target_sp; searcher.SearchCallback(*this, empty_sc, nullptr, false); @@ -645,7 +668,7 @@ SearchFilterSP SearchFilterByModuleList::CreateFromStructuredData( "SFBM::CFSD: filter module item %zu not a string.", i); return nullptr; } - modules.Append(FileSpec(module, false)); + modules.Append(FileSpec(module)); } } @@ -710,7 +733,7 @@ lldb::SearchFilterSP SearchFilterByModuleListAndCU::CreateFromStructuredData( "SFBM::CFSD: filter module item %zu not a string.", i); return result_sp; } - modules.Append(FileSpec(module, false)); + modules.Append(FileSpec(module)); } } @@ -732,7 +755,7 @@ lldb::SearchFilterSP SearchFilterByModuleListAndCU::CreateFromStructuredData( "SFBM::CFSD: filter cu item %zu not a string.", i); return nullptr; } - cus.Append(FileSpec(cu, false)); + cus.Append(FileSpec(cu)); } return std::make_shared<SearchFilterByModuleListAndCU>( @@ -748,7 +771,15 @@ SearchFilterByModuleListAndCU::SerializeToStructuredData() { } bool SearchFilterByModuleListAndCU::AddressPasses(Address &address) { - return true; + SymbolContext sym_ctx; + address.CalculateSymbolContext(&sym_ctx, eSymbolContextEverything); + if (!sym_ctx.comp_unit) { + if (m_cu_spec_list.GetSize() != 0) + return false; // Has no comp_unit so can't pass the file check. + } + if (m_cu_spec_list.FindFileIndex(0, sym_ctx.comp_unit, false) == UINT32_MAX) + return false; // Fails the file check + return SearchFilterByModuleList::ModulePasses(sym_ctx.module_sp); } bool SearchFilterByModuleListAndCU::CompUnitPasses(FileSpec &fileSpec) { @@ -773,7 +804,7 @@ void SearchFilterByModuleListAndCU::Search(Searcher &searcher) { if (!m_target_sp) return; - if (searcher.GetDepth() == Searcher::eDepthTarget) { + if (searcher.GetDepth() == lldb::eSearchDepthTarget) { SymbolContext empty_sc; empty_sc.target_sp = m_target_sp; searcher.SearchCallback(*this, empty_sc, nullptr, false); @@ -797,7 +828,7 @@ void SearchFilterByModuleListAndCU::Search(Searcher &searcher) { SymbolContext matchingContext(m_target_sp, module_sp); Searcher::CallbackReturn shouldContinue; - if (searcher.GetDepth() == Searcher::eDepthModule) { + if (searcher.GetDepth() == lldb::eSearchDepthModule) { shouldContinue = DoModuleIteration(matchingContext, searcher); if (shouldContinue == Searcher::eCallbackReturnStop) return; diff --git a/source/Core/Section.cpp b/source/Core/Section.cpp index d9c5d32ee13c..87f75e1f50ac 100644 --- a/source/Core/Section.cpp +++ b/source/Core/Section.cpp @@ -8,18 +8,18 @@ //===----------------------------------------------------------------------===// #include "lldb/Core/Section.h" -#include "lldb/Core/Address.h" // for Address +#include "lldb/Core/Address.h" #include "lldb/Core/Module.h" #include "lldb/Symbol/ObjectFile.h" #include "lldb/Target/SectionLoadList.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/FileSpec.h" // for FileSpec -#include "lldb/Utility/Stream.h" // for Stream -#include "lldb/Utility/VMRange.h" // for VMRange +#include "lldb/Utility/FileSpec.h" +#include "lldb/Utility/Stream.h" +#include "lldb/Utility/VMRange.h" -#include <inttypes.h> // for PRIx64 -#include <limits> // for numeric_limits -#include <utility> // for distance +#include <inttypes.h> +#include <limits> +#include <utility> namespace lldb_private { class DataExtractor; @@ -61,6 +61,8 @@ const char *Section::GetTypeAsCString() const { return "objc-cfstrings"; case eSectionTypeDWARFDebugAbbrev: return "dwarf-abbrev"; + case eSectionTypeDWARFDebugAbbrevDwo: + return "dwarf-abbrev-dwo"; case eSectionTypeDWARFDebugAddr: return "dwarf-addr"; case eSectionTypeDWARFDebugAranges: @@ -71,10 +73,16 @@ const char *Section::GetTypeAsCString() const { return "dwarf-frame"; case eSectionTypeDWARFDebugInfo: return "dwarf-info"; + case eSectionTypeDWARFDebugInfoDwo: + return "dwarf-info-dwo"; case eSectionTypeDWARFDebugLine: return "dwarf-line"; + case eSectionTypeDWARFDebugLineStr: + return "dwarf-line-str"; case eSectionTypeDWARFDebugLoc: return "dwarf-loc"; + case eSectionTypeDWARFDebugLocLists: + return "dwarf-loclists"; case eSectionTypeDWARFDebugMacInfo: return "dwarf-macinfo"; case eSectionTypeDWARFDebugMacro: @@ -85,10 +93,16 @@ const char *Section::GetTypeAsCString() const { return "dwarf-pubtypes"; case eSectionTypeDWARFDebugRanges: return "dwarf-ranges"; + case eSectionTypeDWARFDebugRngLists: + return "dwarf-rnglists"; case eSectionTypeDWARFDebugStr: return "dwarf-str"; + case eSectionTypeDWARFDebugStrDwo: + return "dwarf-str-dwo"; case eSectionTypeDWARFDebugStrOffsets: return "dwarf-str-offsets"; + case eSectionTypeDWARFDebugStrOffsetsDwo: + return "dwarf-str-offsets-dwo"; case eSectionTypeDWARFDebugTypes: return "dwarf-types"; case eSectionTypeDWARFDebugNames: diff --git a/source/Core/SourceManager.cpp b/source/Core/SourceManager.cpp index a6afd64f3054..fe603c5a44e6 100644 --- a/source/Core/SourceManager.cpp +++ b/source/Core/SourceManager.cpp @@ -9,33 +9,34 @@ #include "lldb/Core/SourceManager.h" -#include "lldb/Core/Address.h" // for Address -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/Address.h" +#include "lldb/Core/AddressRange.h" #include "lldb/Core/Debugger.h" -#include "lldb/Core/FormatEntity.h" // for FormatEntity +#include "lldb/Core/FormatEntity.h" +#include "lldb/Core/Highlighter.h" #include "lldb/Core/Module.h" -#include "lldb/Core/ModuleList.h" // for ModuleList +#include "lldb/Core/ModuleList.h" #include "lldb/Host/FileSystem.h" #include "lldb/Symbol/CompileUnit.h" #include "lldb/Symbol/Function.h" -#include "lldb/Symbol/LineEntry.h" // for LineEntry +#include "lldb/Symbol/LineEntry.h" #include "lldb/Symbol/SymbolContext.h" -#include "lldb/Target/PathMappingList.h" // for PathMappingList +#include "lldb/Target/PathMappingList.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/DataBuffer.h" #include "lldb/Utility/DataBufferLLVM.h" #include "lldb/Utility/RegularExpression.h" #include "lldb/Utility/Stream.h" -#include "lldb/lldb-enumerations.h" // for StopShowColumn::eStopSho... +#include "lldb/lldb-enumerations.h" -#include "llvm/ADT/Twine.h" // for Twine +#include "llvm/ADT/Twine.h" #include <memory> -#include <utility> // for pair +#include <utility> -#include <assert.h> // for assert -#include <stdio.h> // for size_t, NULL, snprintf +#include <assert.h> +#include <stdio.h> namespace lldb_private { class ExecutionContext; @@ -91,7 +92,7 @@ SourceManager::FileSP SourceManager::GetFile(const FileSpec &file_spec) { file_sp->UpdateIfNeeded(); // If file_sp is no good or it points to a non-existent file, reset it. - if (!file_sp || !file_sp->GetFileSpec().Exists()) { + if (!file_sp || !FileSystem::Instance().Exists(file_sp->GetFileSpec())) { if (target_sp) file_sp = std::make_shared<File>(file_spec, target_sp.get()); else @@ -103,6 +104,18 @@ SourceManager::FileSP SourceManager::GetFile(const FileSpec &file_spec) { return file_sp; } +static bool should_highlight_source(DebuggerSP debugger_sp) { + if (!debugger_sp) + return false; + + // We don't use ANSI stop column formatting if the debugger doesn't think it + // should be using color. + if (!debugger_sp->GetUseColor()) + return false; + + return debugger_sp->GetHighlightSource(); +} + static bool should_show_stop_column_with_ansi(DebuggerSP debugger_sp) { // We don't use ANSI stop column formatting if we can't lookup values from // the debugger. @@ -145,7 +158,9 @@ size_t SourceManager::DisplaySourceLinesWithLineNumbersUsingLastFile( const SymbolContextList *bp_locs) { if (count == 0) return 0; - size_t return_value = 0; + + Stream::ByteDelta delta(*s); + if (start_line == 0) { if (m_last_line != 0 && m_last_line != UINT32_MAX) start_line = m_last_line + m_last_count; @@ -180,31 +195,37 @@ size_t SourceManager::DisplaySourceLinesWithLineNumbersUsingLastFile( ::snprintf(prefix, sizeof(prefix), " "); } - return_value += - s->Printf("%s%2.2s %-4u\t", prefix, - line == curr_line ? current_line_cstr : "", line); - size_t this_line_size = m_last_file_sp->DisplaySourceLines( - line, line == curr_line ? column : 0, 0, 0, s); + s->Printf("%s%2.2s %-4u\t", prefix, + line == curr_line ? current_line_cstr : "", line); + + // So far we treated column 0 as a special 'no column value', but + // DisplaySourceLines starts counting columns from 0 (and no column is + // expressed by passing an empty optional). + llvm::Optional<size_t> columnToHighlight; + if (line == curr_line && column) + columnToHighlight = column - 1; + + size_t this_line_size = + m_last_file_sp->DisplaySourceLines(line, columnToHighlight, 0, 0, s); if (column != 0 && line == curr_line && should_show_stop_column_with_caret(m_debugger_wp.lock())) { // Display caret cursor. std::string src_line; m_last_file_sp->GetLine(line, src_line); - return_value += s->Printf(" \t"); + s->Printf(" \t"); // Insert a space for every non-tab character in the source line. for (size_t i = 0; i + 1 < column && i < src_line.length(); ++i) - return_value += s->PutChar(src_line[i] == '\t' ? '\t' : ' '); + s->PutChar(src_line[i] == '\t' ? '\t' : ' '); // Now add the caret. - return_value += s->Printf("^\n"); + s->Printf("^\n"); } if (this_line_size == 0) { m_last_line = UINT32_MAX; break; - } else - return_value += this_line_size; + } } } - return return_value; + return *delta; } size_t SourceManager::DisplaySourceLinesWithLineNumbers( @@ -349,14 +370,14 @@ void SourceManager::FindLinesMatchingRegex(FileSpec &file_spec, SourceManager::File::File(const FileSpec &file_spec, lldb::DebuggerSP debugger_sp) : m_file_spec_orig(file_spec), m_file_spec(file_spec), - m_mod_time(FileSystem::GetModificationTime(file_spec)), + m_mod_time(FileSystem::Instance().GetModificationTime(file_spec)), m_debugger_wp(debugger_sp) { CommonInitializer(file_spec, nullptr); } SourceManager::File::File(const FileSpec &file_spec, Target *target) : m_file_spec_orig(file_spec), m_file_spec(file_spec), - m_mod_time(FileSystem::GetModificationTime(file_spec)), + m_mod_time(FileSystem::Instance().GetModificationTime(file_spec)), m_debugger_wp(target ? target->GetDebugger().shared_from_this() : DebuggerSP()) { CommonInitializer(file_spec, target); @@ -376,7 +397,8 @@ void SourceManager::File::CommonInitializer(const FileSpec &file_spec, size_t num_matches = target->GetImages().ResolveSymbolContextForFilePath( file_spec.GetFilename().AsCString(), 0, check_inlines, - lldb::eSymbolContextModule | lldb::eSymbolContextCompUnit, + SymbolContextItem(eSymbolContextModule | + eSymbolContextCompUnit), sc_list); bool got_multiple = false; if (num_matches != 0) { @@ -400,12 +422,12 @@ void SourceManager::File::CommonInitializer(const FileSpec &file_spec, SymbolContext sc; sc_list.GetContextAtIndex(0, sc); m_file_spec = sc.comp_unit; - m_mod_time = FileSystem::GetModificationTime(m_file_spec); + m_mod_time = FileSystem::Instance().GetModificationTime(m_file_spec); } } } // Try remapping if m_file_spec does not correspond to an existing file. - if (!m_file_spec.Exists()) { + if (!FileSystem::Instance().Exists(m_file_spec)) { FileSpec new_file_spec; // Check target specific source remappings first, then fall back to // modules objects can have individual path remappings that were @@ -413,14 +435,14 @@ void SourceManager::File::CommonInitializer(const FileSpec &file_spec, if (target->GetSourcePathMap().FindFile(m_file_spec, new_file_spec) || target->GetImages().FindSourceFile(m_file_spec, new_file_spec)) { m_file_spec = new_file_spec; - m_mod_time = FileSystem::GetModificationTime(m_file_spec); + m_mod_time = FileSystem::Instance().GetModificationTime(m_file_spec); } } } } if (m_mod_time != llvm::sys::TimePoint<>()) - m_data_sp = DataBufferLLVM::CreateFromPath(m_file_spec.GetPath()); + m_data_sp = FileSystem::Instance().CreateDataBuffer(m_file_spec); } uint32_t SourceManager::File::GetLineOffset(uint32_t line) { @@ -464,7 +486,7 @@ uint32_t SourceManager::File::GetLineLength(uint32_t line, if (end_offset > start_offset) { uint32_t length = end_offset - start_offset; - if (include_newline_chars == false) { + if (!include_newline_chars) { const char *line_start = (const char *)m_data_sp->GetBytes() + start_offset; while (length > 0) { @@ -493,17 +515,18 @@ void SourceManager::File::UpdateIfNeeded() { // TODO: use host API to sign up for file modifications to anything in our // source cache and only update when we determine a file has been updated. // For now we check each time we want to display info for the file. - auto curr_mod_time = FileSystem::GetModificationTime(m_file_spec); + auto curr_mod_time = FileSystem::Instance().GetModificationTime(m_file_spec); if (curr_mod_time != llvm::sys::TimePoint<>() && m_mod_time != curr_mod_time) { m_mod_time = curr_mod_time; - m_data_sp = DataBufferLLVM::CreateFromPath(m_file_spec.GetPath()); + m_data_sp = FileSystem::Instance().CreateDataBuffer(m_file_spec); m_offsets.clear(); } } -size_t SourceManager::File::DisplaySourceLines(uint32_t line, uint32_t column, +size_t SourceManager::File::DisplaySourceLines(uint32_t line, + llvm::Optional<size_t> column, uint32_t context_before, uint32_t context_after, Stream *s) { @@ -515,6 +538,27 @@ size_t SourceManager::File::DisplaySourceLines(uint32_t line, uint32_t column, if (!m_data_sp) return 0; + size_t bytes_written = s->GetWrittenBytes(); + + auto debugger_sp = m_debugger_wp.lock(); + + HighlightStyle style; + // Use the default Vim style if source highlighting is enabled. + if (should_highlight_source(debugger_sp)) + style = HighlightStyle::MakeVimStyle(); + + // If we should mark the stop column with color codes, then copy the prefix + // and suffix to our color style. + if (should_show_stop_column_with_ansi(debugger_sp)) + style.selected.Set(debugger_sp->GetStopShowColumnAnsiPrefix(), + debugger_sp->GetStopShowColumnAnsiSuffix()); + + HighlighterManager mgr; + std::string path = GetFileSpec().GetPath(/*denormalize*/ false); + // FIXME: Find a way to get the definitive language this file was written in + // and pass it to the highlighter. + const auto &h = mgr.getHighlighterFor(lldb::eLanguageTypeUnknown, path); + const uint32_t start_line = line <= context_before ? 1 : line - context_before; const uint32_t start_line_offset = GetLineOffset(start_line); @@ -525,71 +569,20 @@ size_t SourceManager::File::DisplaySourceLines(uint32_t line, uint32_t column, end_line_offset = m_data_sp->GetByteSize(); assert(start_line_offset <= end_line_offset); - size_t bytes_written = 0; if (start_line_offset < end_line_offset) { size_t count = end_line_offset - start_line_offset; const uint8_t *cstr = m_data_sp->GetBytes() + start_line_offset; - bool displayed_line = false; - - if (column && (column < count)) { - auto debugger_sp = m_debugger_wp.lock(); - if (should_show_stop_column_with_ansi(debugger_sp) && debugger_sp) { - // Check if we have any ANSI codes with which to mark this column. If - // not, no need to do this work. - auto ansi_prefix_entry = debugger_sp->GetStopShowColumnAnsiPrefix(); - auto ansi_suffix_entry = debugger_sp->GetStopShowColumnAnsiSuffix(); - - // We only bother breaking up the line to format the marked column if - // there is any marking specified on both sides of the marked column. - // In ANSI-terminal-sequence land, there must be a post if there is a - // pre format, and vice versa. - if (ansi_prefix_entry && ansi_suffix_entry) { - // Mark the current column with the desired escape sequence for - // formatting the column (e.g. underline, inverse, etc.) - - // First print the part before the column to mark. - bytes_written = s->Write(cstr, column - 1); - - // Write the pre escape sequence. - const SymbolContext *sc = nullptr; - const ExecutionContext *exe_ctx = nullptr; - const Address addr = LLDB_INVALID_ADDRESS; - ValueObject *valobj = nullptr; - const bool function_changed = false; - const bool initial_function = false; - - FormatEntity::Format(*ansi_prefix_entry, *s, sc, exe_ctx, &addr, - valobj, function_changed, initial_function); - - // Write the marked column. - bytes_written += s->Write(cstr + column - 1, 1); - - // Write the post escape sequence. - FormatEntity::Format(*ansi_suffix_entry, *s, sc, exe_ctx, &addr, - valobj, function_changed, initial_function); - - // And finish up with the rest of the line. - bytes_written += s->Write(cstr + column, count - column); - - // Keep track of the fact that we just wrote the line. - displayed_line = true; - } - } - } + auto ref = llvm::StringRef(reinterpret_cast<const char *>(cstr), count); - // If we didn't end up displaying the line with ANSI codes for whatever - // reason, display it now sans codes. - if (!displayed_line) - bytes_written = s->Write(cstr, count); + h.Highlight(style, ref, column, "", *s); // Ensure we get an end of line character one way or another. - if (!is_newline_char(cstr[count - 1])) - bytes_written += s->EOL(); + if (!is_newline_char(ref.back())) + s->EOL(); } - return bytes_written; } - return 0; + return s->GetWrittenBytes() - bytes_written; } void SourceManager::File::FindLinesMatchingRegex( diff --git a/source/Core/State.cpp b/source/Core/State.cpp deleted file mode 100644 index 4697ca4b5f17..000000000000 --- a/source/Core/State.cpp +++ /dev/null @@ -1,115 +0,0 @@ -//===-- State.cpp -----------------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -// C Includes -// C++ Includes -// Other libraries and framework includes -// Project includes -#include "lldb/Core/State.h" - -using namespace lldb; -using namespace lldb_private; - -const char *lldb_private::StateAsCString(StateType state) { - switch (state) { - case eStateInvalid: - return "invalid"; - case eStateUnloaded: - return "unloaded"; - case eStateConnected: - return "connected"; - case eStateAttaching: - return "attaching"; - case eStateLaunching: - return "launching"; - case eStateStopped: - return "stopped"; - case eStateRunning: - return "running"; - case eStateStepping: - return "stepping"; - case eStateCrashed: - return "crashed"; - case eStateDetached: - return "detached"; - case eStateExited: - return "exited"; - case eStateSuspended: - return "suspended"; - } - return "unknown"; -} - -const char *lldb_private::GetPermissionsAsCString(uint32_t permissions) { - switch (permissions) { - case 0: - return "---"; - case ePermissionsWritable: - return "-w-"; - case ePermissionsReadable: - return "r--"; - case ePermissionsExecutable: - return "--x"; - case ePermissionsReadable | ePermissionsWritable: - return "rw-"; - case ePermissionsReadable | ePermissionsExecutable: - return "r-x"; - case ePermissionsWritable | ePermissionsExecutable: - return "-wx"; - case ePermissionsReadable | ePermissionsWritable | ePermissionsExecutable: - return "rwx"; - default: - break; - } - return "???"; -} - -bool lldb_private::StateIsRunningState(StateType state) { - switch (state) { - case eStateAttaching: - case eStateLaunching: - case eStateRunning: - case eStateStepping: - return true; - - case eStateConnected: - case eStateDetached: - case eStateInvalid: - case eStateUnloaded: - case eStateStopped: - case eStateCrashed: - case eStateExited: - case eStateSuspended: - break; - } - return false; -} - -bool lldb_private::StateIsStoppedState(StateType state, bool must_exist) { - switch (state) { - case eStateInvalid: - case eStateConnected: - case eStateAttaching: - case eStateLaunching: - case eStateRunning: - case eStateStepping: - case eStateDetached: - break; - - case eStateUnloaded: - case eStateExited: - return !must_exist; - - case eStateStopped: - case eStateCrashed: - case eStateSuspended: - return true; - } - return false; -} diff --git a/source/Core/StreamAsynchronousIO.cpp b/source/Core/StreamAsynchronousIO.cpp index aae8636bff09..b8938bd3fc4e 100644 --- a/source/Core/StreamAsynchronousIO.cpp +++ b/source/Core/StreamAsynchronousIO.cpp @@ -10,7 +10,7 @@ #include "lldb/Core/StreamAsynchronousIO.h" #include "lldb/Core/Debugger.h" -#include "lldb/lldb-enumerations.h" // for ByteOrder::eByteOrderBig +#include "lldb/lldb-enumerations.h" using namespace lldb; using namespace lldb_private; @@ -31,7 +31,7 @@ void StreamAsynchronousIO::Flush() { } } -size_t StreamAsynchronousIO::Write(const void *s, size_t length) { +size_t StreamAsynchronousIO::WriteImpl(const void *s, size_t length) { m_data.append((const char *)s, length); return length; } diff --git a/source/Core/StreamFile.cpp b/source/Core/StreamFile.cpp index f59415485021..d24634598c36 100644 --- a/source/Core/StreamFile.cpp +++ b/source/Core/StreamFile.cpp @@ -8,6 +8,7 @@ //===----------------------------------------------------------------------===// #include "lldb/Core/StreamFile.h" +#include "lldb/Host/FileSystem.h" #include <stdio.h> @@ -28,20 +29,24 @@ StreamFile::StreamFile(int fd, bool transfer_ownership) StreamFile::StreamFile(FILE *fh, bool transfer_ownership) : Stream(), m_file(fh, transfer_ownership) {} -StreamFile::StreamFile(const char *path) - : Stream(), - m_file(path, File::eOpenOptionWrite | File::eOpenOptionCanCreate | - File::eOpenOptionCloseOnExec, - lldb::eFilePermissionsFileDefault) {} +StreamFile::StreamFile(const char *path) : Stream(), m_file() { + FileSystem::Instance().Open(m_file, FileSpec(path), + File::eOpenOptionWrite | + File::eOpenOptionCanCreate | + File::eOpenOptionCloseOnExec); +} StreamFile::StreamFile(const char *path, uint32_t options, uint32_t permissions) - : Stream(), m_file(path, options, permissions) {} + : Stream(), m_file() { + + FileSystem::Instance().Open(m_file, FileSpec(path), options, permissions); +} StreamFile::~StreamFile() {} void StreamFile::Flush() { m_file.Flush(); } -size_t StreamFile::Write(const void *s, size_t length) { +size_t StreamFile::WriteImpl(const void *s, size_t length) { m_file.Write(s, length); return length; } diff --git a/source/Core/UserSettingsController.cpp b/source/Core/UserSettingsController.cpp index a4661a6c9e8c..4406057ca6b9 100644 --- a/source/Core/UserSettingsController.cpp +++ b/source/Core/UserSettingsController.cpp @@ -13,7 +13,7 @@ #include "lldb/Utility/Status.h" #include "lldb/Utility/Stream.h" -#include <memory> // for shared_ptr +#include <memory> namespace lldb_private { class CommandInterpreter; diff --git a/source/Core/Value.cpp b/source/Core/Value.cpp index 254c9008babb..8e18458b90c2 100644 --- a/source/Core/Value.cpp +++ b/source/Core/Value.cpp @@ -9,9 +9,8 @@ #include "lldb/Core/Value.h" -#include "lldb/Core/Address.h" // for Address +#include "lldb/Core/Address.h" #include "lldb/Core/Module.h" -#include "lldb/Core/State.h" #include "lldb/Symbol/CompilerType.h" #include "lldb/Symbol/ObjectFile.h" #include "lldb/Symbol/SymbolContext.h" @@ -21,20 +20,21 @@ #include "lldb/Target/Process.h" #include "lldb/Target/SectionLoadList.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/ConstString.h" // for ConstString +#include "lldb/Utility/ConstString.h" #include "lldb/Utility/DataBufferHeap.h" #include "lldb/Utility/DataExtractor.h" -#include "lldb/Utility/Endian.h" // for InlHostByteOrder -#include "lldb/Utility/FileSpec.h" // for FileSpec +#include "lldb/Utility/Endian.h" +#include "lldb/Utility/FileSpec.h" +#include "lldb/Utility/State.h" #include "lldb/Utility/Stream.h" -#include "lldb/lldb-defines.h" // for LLDB_INVALID_ADDRESS -#include "lldb/lldb-forward.h" // for DataBufferSP, ModuleSP -#include "lldb/lldb-types.h" // for addr_t +#include "lldb/lldb-defines.h" +#include "lldb/lldb-forward.h" +#include "lldb/lldb-types.h" -#include <memory> // for make_shared -#include <string> // for string +#include <memory> +#include <string> -#include <inttypes.h> // for PRIx64 +#include <inttypes.h> using namespace lldb; using namespace lldb_private; @@ -210,34 +210,31 @@ bool Value::ValueOf(ExecutionContext *exe_ctx) { } uint64_t Value::GetValueByteSize(Status *error_ptr, ExecutionContext *exe_ctx) { - uint64_t byte_size = 0; - switch (m_context_type) { case eContextTypeRegisterInfo: // RegisterInfo * - if (GetRegisterInfo()) - byte_size = GetRegisterInfo()->byte_size; + if (GetRegisterInfo()) { + if (error_ptr) + error_ptr->Clear(); + return GetRegisterInfo()->byte_size; + } break; case eContextTypeInvalid: case eContextTypeLLDBType: // Type * case eContextTypeVariable: // Variable * { - const CompilerType &ast_type = GetCompilerType(); - if (ast_type.IsValid()) - byte_size = ast_type.GetByteSize( - exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr); - } break; - } - - if (error_ptr) { - if (byte_size == 0) { - if (error_ptr->Success()) - error_ptr->SetErrorString("Unable to determine byte size."); - } else { - error_ptr->Clear(); + auto *scope = exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr; + if (llvm::Optional<uint64_t> size = GetCompilerType().GetByteSize(scope)) { + if (error_ptr) + error_ptr->Clear(); + return *size; } + break; } - return byte_size; + } + if (error_ptr && error_ptr->Success()) + error_ptr->SetErrorString("Unable to determine byte size."); + return 0; } const CompilerType &Value::GetCompilerType() { @@ -344,10 +341,9 @@ Status Value::GetValueAsData(ExecutionContext *exe_ctx, DataExtractor &data, uint32_t limit_byte_size = UINT32_MAX; - if (ast_type.IsValid()) { - limit_byte_size = ast_type.GetByteSize( - exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr); - } + if (llvm::Optional<uint64_t> size = ast_type.GetByteSize( + exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr)) + limit_byte_size = *size; if (limit_byte_size <= m_value.GetByteSize()) { if (m_value.GetData(data, limit_byte_size)) diff --git a/source/Core/ValueObject.cpp b/source/Core/ValueObject.cpp index 244ea2936fb4..95e944b22b87 100644 --- a/source/Core/ValueObject.cpp +++ b/source/Core/ValueObject.cpp @@ -9,9 +9,8 @@ #include "lldb/Core/ValueObject.h" -#include "lldb/Core/Address.h" // for Address +#include "lldb/Core/Address.h" #include "lldb/Core/Module.h" -#include "lldb/Core/Scalar.h" // for Scalar #include "lldb/Core/ValueObjectCast.h" #include "lldb/Core/ValueObjectChild.h" #include "lldb/Core/ValueObjectConstResult.h" @@ -19,51 +18,52 @@ #include "lldb/Core/ValueObjectMemory.h" #include "lldb/Core/ValueObjectSyntheticFilter.h" #include "lldb/DataFormatters/DataVisualization.h" -#include "lldb/DataFormatters/DumpValueObjectOptions.h" // for DumpValueObj... -#include "lldb/DataFormatters/FormatManager.h" // for FormatManager +#include "lldb/DataFormatters/DumpValueObjectOptions.h" +#include "lldb/DataFormatters/FormatManager.h" #include "lldb/DataFormatters/StringPrinter.h" -#include "lldb/DataFormatters/TypeFormat.h" // for TypeFormatImpl_F... -#include "lldb/DataFormatters/TypeSummary.h" // for TypeSummaryOptions -#include "lldb/DataFormatters/TypeValidator.h" // for TypeValidatorImp... +#include "lldb/DataFormatters/TypeFormat.h" +#include "lldb/DataFormatters/TypeSummary.h" +#include "lldb/DataFormatters/TypeValidator.h" #include "lldb/DataFormatters/ValueObjectPrinter.h" -#include "lldb/Expression/ExpressionVariable.h" // for ExpressionVariable +#include "lldb/Expression/ExpressionVariable.h" #include "lldb/Symbol/ClangASTContext.h" #include "lldb/Symbol/CompileUnit.h" #include "lldb/Symbol/CompilerType.h" -#include "lldb/Symbol/Declaration.h" // for Declaration -#include "lldb/Symbol/SymbolContext.h" // for SymbolContext +#include "lldb/Symbol/Declaration.h" +#include "lldb/Symbol/SymbolContext.h" #include "lldb/Symbol/Type.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/Language.h" #include "lldb/Target/LanguageRuntime.h" #include "lldb/Target/ObjCLanguageRuntime.h" #include "lldb/Target/Process.h" -#include "lldb/Target/StackFrame.h" // for StackFrame +#include "lldb/Target/StackFrame.h" #include "lldb/Target/Target.h" #include "lldb/Target/Thread.h" -#include "lldb/Target/ThreadList.h" // for ThreadList -#include "lldb/Utility/DataBuffer.h" // for DataBuffer +#include "lldb/Target/ThreadList.h" +#include "lldb/Utility/DataBuffer.h" #include "lldb/Utility/DataBufferHeap.h" -#include "lldb/Utility/Flags.h" // for Flags +#include "lldb/Utility/Flags.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAllCateg... -#include "lldb/Utility/SharingPtr.h" // for SharingPtr -#include "lldb/Utility/Stream.h" // for Stream +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/SharingPtr.h" +#include "lldb/Utility/Stream.h" #include "lldb/Utility/StreamString.h" -#include "lldb/lldb-private-types.h" // for RegisterInfo +#include "lldb/lldb-private-types.h" -#include "llvm/Support/Compiler.h" // for LLVM_FALLTHROUGH +#include "llvm/Support/Compiler.h" -#include <algorithm> // for min -#include <cstdint> // for uint32_t, uint64_t -#include <cstdlib> // for size_t, NULL -#include <memory> // for shared_ptr, oper... -#include <tuple> // for tie, tuple +#include <algorithm> +#include <cstdint> +#include <cstdlib> +#include <memory> +#include <tuple> -#include <assert.h> // for assert -#include <inttypes.h> // for PRIu64, PRIx64 -#include <stdio.h> // for snprintf -#include <string.h> // for memcpy, memcmp +#include <assert.h> +#include <inttypes.h> +#include <stdio.h> +#include <string.h> namespace lldb_private { class ExecutionContextScope; @@ -214,7 +214,7 @@ bool ValueObject::UpdateValueIfNeeded(bool update_format) { if (first_update) SetValueDidChange(false); - else if (!m_value_did_change && success == false) { + else if (!m_value_did_change && !success) { // The value wasn't gotten successfully, so we mark this as changed if // the value used to be valid and now isn't SetValueDidChange(value_was_valid); @@ -442,10 +442,7 @@ bool ValueObject::IsLogicalTrue(Status &error) { } bool ret; - if (scalar_value.ULongLong(1) == 0) - ret = false; - else - ret = true; + ret = scalar_value.ULongLong(1) != 0; error.Clear(); return ret; } @@ -639,7 +636,7 @@ ValueObject *ValueObject::CreateChildAtIndex(size_t idx, bool child_is_deref_of_parent = false; uint64_t language_flags = 0; - const bool transparent_pointers = synthetic_array_member == false; + const bool transparent_pointers = !synthetic_array_member; CompilerType child_compiler_type; ExecutionContext exe_ctx(GetExecutionContextRef()); @@ -662,8 +659,6 @@ ValueObject *ValueObject::CreateChildAtIndex(size_t idx, child_byte_offset, child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class, child_is_deref_of_parent, eAddressTypeInvalid, language_flags); - // if (valobj) - // valobj->SetAddressTypeOfChildren(eAddressTypeInvalid); } return valobj; @@ -761,10 +756,13 @@ size_t ValueObject::GetPointeeData(DataExtractor &data, uint32_t item_idx, ExecutionContext exe_ctx(GetExecutionContextRef()); - const uint64_t item_type_size = pointee_or_element_compiler_type.GetByteSize( - exe_ctx.GetBestExecutionContextScope()); - const uint64_t bytes = item_count * item_type_size; - const uint64_t offset = item_idx * item_type_size; + llvm::Optional<uint64_t> item_type_size = + pointee_or_element_compiler_type.GetByteSize( + exe_ctx.GetBestExecutionContextScope()); + if (!item_type_size) + return 0; + const uint64_t bytes = item_count * *item_type_size; + const uint64_t offset = item_idx * *item_type_size; if (item_idx == 0 && item_count == 1) // simply a deref { @@ -827,10 +825,10 @@ size_t ValueObject::GetPointeeData(DataExtractor &data, uint32_t item_idx, } } break; case eAddressTypeHost: { - const uint64_t max_bytes = + auto max_bytes = GetCompilerType().GetByteSize(exe_ctx.GetBestExecutionContextScope()); - if (max_bytes > offset) { - size_t bytes_read = std::min<uint64_t>(max_bytes - offset, bytes); + if (max_bytes && *max_bytes > offset) { + size_t bytes_read = std::min<uint64_t>(*max_bytes - offset, bytes); addr = m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS); if (addr == 0 || addr == LLDB_INVALID_ADDRESS) break; @@ -1823,14 +1821,16 @@ ValueObjectSP ValueObject::GetSyntheticChildAtOffset( return synthetic_child_sp; if (!can_create) - return ValueObjectSP(); + return {}; ExecutionContext exe_ctx(GetExecutionContextRef()); - - ValueObjectChild *synthetic_child = new ValueObjectChild( - *this, type, name_const_str, - type.GetByteSize(exe_ctx.GetBestExecutionContextScope()), offset, 0, 0, - false, false, eAddressTypeInvalid, 0); + llvm::Optional<uint64_t> size = + type.GetByteSize(exe_ctx.GetBestExecutionContextScope()); + if (!size) + return {}; + ValueObjectChild *synthetic_child = + new ValueObjectChild(*this, type, name_const_str, *size, offset, 0, 0, + false, false, eAddressTypeInvalid, 0); if (synthetic_child) { AddSyntheticChild(name_const_str, synthetic_child); synthetic_child_sp = synthetic_child->GetSP(); @@ -1861,16 +1861,18 @@ ValueObjectSP ValueObject::GetSyntheticBase(uint32_t offset, return synthetic_child_sp; if (!can_create) - return ValueObjectSP(); + return {}; const bool is_base_class = true; ExecutionContext exe_ctx(GetExecutionContextRef()); - - ValueObjectChild *synthetic_child = new ValueObjectChild( - *this, type, name_const_str, - type.GetByteSize(exe_ctx.GetBestExecutionContextScope()), offset, 0, 0, - is_base_class, false, eAddressTypeInvalid, 0); + llvm::Optional<uint64_t> size = + type.GetByteSize(exe_ctx.GetBestExecutionContextScope()); + if (!size) + return {}; + ValueObjectChild *synthetic_child = + new ValueObjectChild(*this, type, name_const_str, *size, offset, 0, 0, + is_base_class, false, eAddressTypeInvalid, 0); if (synthetic_child) { AddSyntheticChild(name_const_str, synthetic_child); synthetic_child_sp = synthetic_child->GetSP(); @@ -1923,11 +1925,11 @@ ValueObject::GetSyntheticExpressionPathChild(const char *expression, } void ValueObject::CalculateSyntheticValue(bool use_synthetic) { - if (use_synthetic == false) + if (!use_synthetic) return; TargetSP target_sp(GetTargetSP()); - if (target_sp && target_sp->GetEnableSyntheticValue() == false) { + if (target_sp && !target_sp->GetEnableSyntheticValue()) { m_synthetic_value = NULL; return; } @@ -1978,7 +1980,7 @@ ValueObjectSP ValueObject::GetStaticValue() { return GetSP(); } lldb::ValueObjectSP ValueObject::GetNonSyntheticValue() { return GetSP(); } ValueObjectSP ValueObject::GetSyntheticValue(bool use_synthetic) { - if (use_synthetic == false) + if (!use_synthetic) return ValueObjectSP(); CalculateSyntheticValue(use_synthetic); @@ -1997,10 +1999,7 @@ bool ValueObject::HasSyntheticValue() { CalculateSyntheticValue(true); - if (m_synthetic_value) - return true; - else - return false; + return m_synthetic_value != nullptr; } bool ValueObject::GetBaseClassPath(Stream &s) { @@ -2806,31 +2805,6 @@ ValueObjectSP ValueObject::GetQualifiedRepresentationIfAvailable( return result_sp; } -lldb::addr_t ValueObject::GetCPPVTableAddress(AddressType &address_type) { - CompilerType pointee_type; - CompilerType this_type(GetCompilerType()); - uint32_t type_info = this_type.GetTypeInfo(&pointee_type); - if (type_info) { - bool ptr_or_ref = false; - if (type_info & (eTypeIsPointer | eTypeIsReference)) { - ptr_or_ref = true; - type_info = pointee_type.GetTypeInfo(); - } - - const uint32_t cpp_class = eTypeIsClass | eTypeIsCPlusPlus; - if ((type_info & cpp_class) == cpp_class) { - if (ptr_or_ref) { - address_type = GetAddressTypeOfChildren(); - return GetValueAsUnsigned(LLDB_INVALID_ADDRESS); - } else - return GetAddressOf(false, &address_type); - } - } - - address_type = eAddressTypeInvalid; - return LLDB_INVALID_ADDRESS; -} - ValueObjectSP ValueObject::Dereference(Status &error) { if (m_deref_valobj) return m_deref_valobj->GetSP(); @@ -3222,7 +3196,7 @@ ValueObject * ValueObject::FollowParentChain(std::function<bool(ValueObject *)> f) { ValueObject *vo = this; while (vo) { - if (f(vo) == false) + if (!f(vo)) break; vo = vo->m_parent; } @@ -3291,8 +3265,7 @@ bool ValueObject::CanProvideValue() { // board debugging scenarios have no notion of types, but still manage to // have raw numeric values for things like registers. sigh. const CompilerType &type(GetCompilerType()); - return (false == type.IsValid()) || - (0 != (type.GetTypeInfo() & eTypeHasValue)); + return (!type.IsValid()) || (0 != (type.GetTypeInfo() & eTypeHasValue)); } bool ValueObject::IsChecksumEmpty() { return m_value_checksum.empty(); } diff --git a/source/Core/ValueObjectCast.cpp b/source/Core/ValueObjectCast.cpp index e0978f692bc5..fb0b55b6efdf 100644 --- a/source/Core/ValueObjectCast.cpp +++ b/source/Core/ValueObjectCast.cpp @@ -9,12 +9,12 @@ #include "lldb/Core/ValueObjectCast.h" -#include "lldb/Core/Scalar.h" // for operator!=, Scalar #include "lldb/Core/Value.h" #include "lldb/Core/ValueObject.h" #include "lldb/Symbol/CompilerType.h" #include "lldb/Target/ExecutionContext.h" -#include "lldb/Utility/Status.h" // for Status +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/Status.h" namespace lldb_private { class ConstString; @@ -44,7 +44,9 @@ ValueObjectCast::~ValueObjectCast() {} CompilerType ValueObjectCast::GetCompilerTypeImpl() { return m_cast_type; } size_t ValueObjectCast::CalculateNumChildren(uint32_t max) { - auto children_count = GetCompilerType().GetNumChildren(true); + ExecutionContext exe_ctx(GetExecutionContextRef()); + auto children_count = GetCompilerType().GetNumChildren( + true, &exe_ctx); return children_count <= max ? children_count : max; } diff --git a/source/Core/ValueObjectChild.cpp b/source/Core/ValueObjectChild.cpp index 019daa2fd3d2..0f7be8317dec 100644 --- a/source/Core/ValueObjectChild.cpp +++ b/source/Core/ValueObjectChild.cpp @@ -9,21 +9,21 @@ #include "lldb/Core/ValueObjectChild.h" -#include "lldb/Core/Scalar.h" // for Scalar -#include "lldb/Core/Value.h" // for Value, Value::ValueType::e... +#include "lldb/Core/Value.h" #include "lldb/Symbol/CompilerType.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/Process.h" -#include "lldb/Utility/Flags.h" // for Flags -#include "lldb/Utility/Status.h" // for Status -#include "lldb/lldb-forward.h" // for ProcessSP, ModuleSP +#include "lldb/Utility/Flags.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/Status.h" +#include "lldb/lldb-forward.h" -#include <functional> // for _Func_impl<>::_Mybase -#include <memory> // for shared_ptr -#include <vector> // for vector +#include <functional> +#include <memory> +#include <vector> -#include <stdio.h> // for snprintf, size_t -#include <string.h> // for strlen +#include <stdio.h> +#include <string.h> using namespace lldb_private; @@ -51,7 +51,8 @@ lldb::ValueType ValueObjectChild::GetValueType() const { } size_t ValueObjectChild::CalculateNumChildren(uint32_t max) { - auto children_count = GetCompilerType().GetNumChildren(true); + ExecutionContext exe_ctx(GetExecutionContextRef()); + auto children_count = GetCompilerType().GetNumChildren(true, &exe_ctx); return children_count <= max ? children_count : max; } @@ -123,7 +124,7 @@ bool ValueObjectChild::UpdateValue() { Flags parent_type_flags(parent_type.GetTypeInfo()); const bool is_instance_ptr_base = - ((m_is_base_class == true) && + ((m_is_base_class) && (parent_type_flags.AnySet(lldb::eTypeInstanceIsPointer))); if (parent->GetCompilerType().ShouldTreatScalarValueAsAddress()) { @@ -141,7 +142,7 @@ bool ValueObjectChild::UpdateValue() { switch (addr_type) { case eAddressTypeFile: { lldb::ProcessSP process_sp(GetProcessSP()); - if (process_sp && process_sp->IsAlive() == true) + if (process_sp && process_sp->IsAlive()) m_value.SetValueType(Value::eValueTypeLoadAddress); else m_value.SetValueType(Value::eValueTypeFileAddress); @@ -201,12 +202,9 @@ bool ValueObjectChild::UpdateValue() { ExecutionContext exe_ctx( GetExecutionContextRef().Lock(thread_and_frame_only_if_stopped)); if (GetCompilerType().GetTypeInfo() & lldb::eTypeHasValue) { - if (!is_instance_ptr_base) - m_error = - m_value.GetValueAsData(&exe_ctx, m_data, 0, GetModule().get()); - else - m_error = m_parent->GetValue().GetValueAsData(&exe_ctx, m_data, 0, - GetModule().get()); + Value &value = is_instance_ptr_base ? m_parent->GetValue() : m_value; + m_error = + value.GetValueAsData(&exe_ctx, m_data, 0, GetModule().get()); } else { m_error.Clear(); // No value so nothing to read... } diff --git a/source/Core/ValueObjectConstResult.cpp b/source/Core/ValueObjectConstResult.cpp index 1023696c35a7..f6e32c03b0eb 100644 --- a/source/Core/ValueObjectConstResult.cpp +++ b/source/Core/ValueObjectConstResult.cpp @@ -9,15 +9,15 @@ #include "lldb/Core/ValueObjectConstResult.h" -#include "lldb/Core/Scalar.h" // for Scalar #include "lldb/Core/ValueObjectDynamicValue.h" #include "lldb/Symbol/CompilerType.h" #include "lldb/Target/ExecutionContext.h" -#include "lldb/Target/ExecutionContextScope.h" // for ExecutionContextScope +#include "lldb/Target/ExecutionContextScope.h" #include "lldb/Target/Process.h" -#include "lldb/Utility/DataBuffer.h" // for DataBuffer -#include "lldb/Utility/DataBufferHeap.h" // for DataBufferHeap +#include "lldb/Utility/DataBuffer.h" +#include "lldb/Utility/DataBufferHeap.h" #include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/Scalar.h" namespace lldb_private { class Module; @@ -198,17 +198,19 @@ lldb::ValueType ValueObjectConstResult::GetValueType() const { uint64_t ValueObjectConstResult::GetByteSize() { ExecutionContext exe_ctx(GetExecutionContextRef()); - - if (m_byte_size == 0) - SetByteSize( - GetCompilerType().GetByteSize(exe_ctx.GetBestExecutionContextScope())); + if (m_byte_size == 0) { + if (auto size = + GetCompilerType().GetByteSize(exe_ctx.GetBestExecutionContextScope())) + SetByteSize(*size); + } return m_byte_size; } void ValueObjectConstResult::SetByteSize(size_t size) { m_byte_size = size; } size_t ValueObjectConstResult::CalculateNumChildren(uint32_t max) { - auto children_count = GetCompilerType().GetNumChildren(true); + ExecutionContext exe_ctx(GetExecutionContextRef()); + auto children_count = GetCompilerType().GetNumChildren(true, &exe_ctx); return children_count <= max ? children_count : max; } diff --git a/source/Core/ValueObjectConstResultChild.cpp b/source/Core/ValueObjectConstResultChild.cpp index 3e9f87684162..441c16479f2c 100644 --- a/source/Core/ValueObjectConstResultChild.cpp +++ b/source/Core/ValueObjectConstResultChild.cpp @@ -9,7 +9,7 @@ #include "lldb/Core/ValueObjectConstResultChild.h" -#include "lldb/lldb-private-enumerations.h" // for AddressType::eAddressType +#include "lldb/lldb-private-enumerations.h" namespace lldb_private { class DataExtractor; } @@ -52,6 +52,11 @@ lldb::ValueObjectSP ValueObjectConstResultChild::AddressOf(Status &error) { return m_impl.AddressOf(error); } +lldb::addr_t ValueObjectConstResultChild::GetAddressOf( + bool scalar_is_load_address, AddressType* address_type) { + return m_impl.GetAddressOf(scalar_is_load_address, address_type); +} + ValueObject *ValueObjectConstResultChild::CreateChildAtIndex( size_t idx, bool synthetic_array_member, int32_t synthetic_index) { return m_impl.CreateChildAtIndex(idx, synthetic_array_member, diff --git a/source/Core/ValueObjectConstResultImpl.cpp b/source/Core/ValueObjectConstResultImpl.cpp index 714634ed56e3..6bf8e62db067 100644 --- a/source/Core/ValueObjectConstResultImpl.cpp +++ b/source/Core/ValueObjectConstResultImpl.cpp @@ -9,19 +9,19 @@ #include "lldb/Core/ValueObjectConstResultImpl.h" -#include "lldb/Core/Scalar.h" // for Scalar -#include "lldb/Core/Value.h" // for Value, Value::Val... -#include "lldb/Core/ValueObject.h" // for ValueObject +#include "lldb/Core/Value.h" +#include "lldb/Core/ValueObject.h" #include "lldb/Core/ValueObjectConstResult.h" #include "lldb/Core/ValueObjectConstResultCast.h" #include "lldb/Core/ValueObjectConstResultChild.h" #include "lldb/Symbol/CompilerType.h" #include "lldb/Target/ExecutionContext.h" -#include "lldb/Utility/DataBufferHeap.h" // for DataBufferHeap -#include "lldb/Utility/Endian.h" // for InlHostByteOrder -#include "lldb/Utility/SharingPtr.h" // for SharingPtr +#include "lldb/Utility/DataBufferHeap.h" +#include "lldb/Utility/Endian.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/SharingPtr.h" -#include <string> // for string +#include <string> namespace lldb_private { class DataExtractor; @@ -66,7 +66,7 @@ ValueObject *ValueObjectConstResultImpl::CreateChildAtIndex( bool child_is_deref_of_parent = false; uint64_t language_flags; - const bool transparent_pointers = synthetic_array_member == false; + const bool transparent_pointers = !synthetic_array_member; CompilerType compiler_type = m_impl_backend->GetCompilerType(); CompilerType child_compiler_type; @@ -77,7 +77,13 @@ ValueObject *ValueObjectConstResultImpl::CreateChildAtIndex( ignore_array_bounds, child_name_str, child_byte_size, child_byte_offset, child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class, child_is_deref_of_parent, m_impl_backend, language_flags); - if (child_compiler_type && child_byte_size) { + + // One might think we should check that the size of the children + // is always strictly positive, hence we could avoid creating a + // ValueObject if that's not the case, but it turns out there + // are languages out there which allow zero-size types with + // children (e.g. Swift). + if (child_compiler_type) { if (synthetic_index) child_byte_offset += child_byte_size * synthetic_index; diff --git a/source/Core/ValueObjectDynamicValue.cpp b/source/Core/ValueObjectDynamicValue.cpp index e9b48310b0c6..161b6e49e0dd 100644 --- a/source/Core/ValueObjectDynamicValue.cpp +++ b/source/Core/ValueObjectDynamicValue.cpp @@ -8,7 +8,6 @@ //===----------------------------------------------------------------------===// #include "lldb/Core/ValueObjectDynamicValue.h" -#include "lldb/Core/Scalar.h" // for Scalar, operator!= #include "lldb/Core/Value.h" #include "lldb/Core/ValueObject.h" #include "lldb/Symbol/CompilerType.h" @@ -17,13 +16,14 @@ #include "lldb/Target/LanguageRuntime.h" #include "lldb/Target/Process.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/DataExtractor.h" // for DataExtractor +#include "lldb/Utility/DataExtractor.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAllCategoriesSet -#include "lldb/Utility/Status.h" // for Status -#include "lldb/lldb-types.h" // for addr_t, offset_t +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/Status.h" +#include "lldb/lldb-types.h" -#include <string.h> // for strcmp, size_t +#include <string.h> namespace lldb_private { class Declaration; } @@ -92,7 +92,8 @@ ConstString ValueObjectDynamicValue::GetDisplayTypeName() { size_t ValueObjectDynamicValue::CalculateNumChildren(uint32_t max) { const bool success = UpdateValueIfNeeded(false); if (success && m_dynamic_type_info.HasType()) { - auto children_count = GetCompilerType().GetNumChildren(true); + ExecutionContext exe_ctx(GetExecutionContextRef()); + auto children_count = GetCompilerType().GetNumChildren(true, &exe_ctx); return children_count <= max ? children_count : max; } else return m_parent->GetNumChildren(max); diff --git a/source/Core/ValueObjectList.cpp b/source/Core/ValueObjectList.cpp index 0dd07252888f..7a7e0d8417b7 100644 --- a/source/Core/ValueObjectList.cpp +++ b/source/Core/ValueObjectList.cpp @@ -9,11 +9,11 @@ #include "lldb/Core/ValueObjectList.h" -#include "lldb/Core/ValueObject.h" // for ValueObject -#include "lldb/Utility/ConstString.h" // for ConstString -#include "lldb/Utility/SharingPtr.h" // for SharingPtr +#include "lldb/Core/ValueObject.h" +#include "lldb/Utility/ConstString.h" +#include "lldb/Utility/SharingPtr.h" -#include <utility> // for back_insert_iterator, back_ins... +#include <utility> using namespace lldb; using namespace lldb_private; diff --git a/source/Core/ValueObjectMemory.cpp b/source/Core/ValueObjectMemory.cpp index 3e71fea6bb35..24103204ee47 100644 --- a/source/Core/ValueObjectMemory.cpp +++ b/source/Core/ValueObjectMemory.cpp @@ -8,19 +8,19 @@ //===----------------------------------------------------------------------===// #include "lldb/Core/ValueObjectMemory.h" -#include "lldb/Core/Scalar.h" // for Scalar, operator!= #include "lldb/Core/Value.h" #include "lldb/Core/ValueObject.h" #include "lldb/Symbol/Type.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/DataExtractor.h" // for DataExtractor -#include "lldb/Utility/Status.h" // for Status -#include "lldb/lldb-types.h" // for addr_t -#include "llvm/Support/ErrorHandling.h" // for llvm_unreachable +#include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/Status.h" +#include "lldb/lldb-types.h" +#include "llvm/Support/ErrorHandling.h" -#include <assert.h> // for assert -#include <memory> // for shared_ptr +#include <assert.h> +#include <memory> namespace lldb_private { class ExecutionContextScope; @@ -128,15 +128,19 @@ size_t ValueObjectMemory::CalculateNumChildren(uint32_t max) { return child_count <= max ? child_count : max; } + ExecutionContext exe_ctx(GetExecutionContextRef()); const bool omit_empty_base_classes = true; - auto child_count = m_compiler_type.GetNumChildren(omit_empty_base_classes); + auto child_count = + m_compiler_type.GetNumChildren(omit_empty_base_classes, &exe_ctx); return child_count <= max ? child_count : max; } uint64_t ValueObjectMemory::GetByteSize() { if (m_type_sp) return m_type_sp->GetByteSize(); - return m_compiler_type.GetByteSize(nullptr); + if (llvm::Optional<uint64_t> size = m_compiler_type.GetByteSize(nullptr)) + return *size; + return 0; } lldb::ValueType ValueObjectMemory::GetValueType() const { diff --git a/source/Core/ValueObjectRegister.cpp b/source/Core/ValueObjectRegister.cpp index 05022d3ed10a..41d1c27f7361 100644 --- a/source/Core/ValueObjectRegister.cpp +++ b/source/Core/ValueObjectRegister.cpp @@ -10,23 +10,23 @@ #include "lldb/Core/ValueObjectRegister.h" #include "lldb/Core/Module.h" -#include "lldb/Core/Scalar.h" // for Scalar -#include "lldb/Core/Value.h" // for Value, Value::ContextType:... +#include "lldb/Core/Value.h" #include "lldb/Symbol/CompilerType.h" -#include "lldb/Symbol/TypeSystem.h" // for TypeSystem +#include "lldb/Symbol/TypeSystem.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/Process.h" #include "lldb/Target/RegisterContext.h" -#include "lldb/Target/StackFrame.h" // for StackFrame +#include "lldb/Target/StackFrame.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/DataExtractor.h" // for DataExtractor -#include "lldb/Utility/Status.h" // for Status -#include "lldb/Utility/Stream.h" // for Stream +#include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/Status.h" +#include "lldb/Utility/Stream.h" -#include "llvm/ADT/StringRef.h" // for StringRef +#include "llvm/ADT/StringRef.h" -#include <assert.h> // for assert -#include <memory> // for shared_ptr +#include <assert.h> +#include <memory> namespace lldb_private { class ExecutionContextScope; @@ -279,7 +279,8 @@ ConstString ValueObjectRegister::GetTypeName() { } size_t ValueObjectRegister::CalculateNumChildren(uint32_t max) { - auto children_count = GetCompilerType().GetNumChildren(true); + ExecutionContext exe_ctx(GetExecutionContextRef()); + auto children_count = GetCompilerType().GetNumChildren(true, &exe_ctx); return children_count <= max ? children_count : max; } diff --git a/source/Core/ValueObjectSyntheticFilter.cpp b/source/Core/ValueObjectSyntheticFilter.cpp index 044387a4ae12..d22b1dc1c57d 100644 --- a/source/Core/ValueObjectSyntheticFilter.cpp +++ b/source/Core/ValueObjectSyntheticFilter.cpp @@ -9,14 +9,14 @@ #include "lldb/Core/ValueObjectSyntheticFilter.h" -#include "lldb/Core/Value.h" // for Value +#include "lldb/Core/Value.h" #include "lldb/Core/ValueObject.h" #include "lldb/DataFormatters/TypeSynthetic.h" -#include "lldb/Target/ExecutionContext.h" // for ExecutionContext +#include "lldb/Target/ExecutionContext.h" #include "lldb/Utility/Log.h" -#include "lldb/Utility/Logging.h" // for GetLogIfAllCategoriesSet -#include "lldb/Utility/SharingPtr.h" // for SharingPtr -#include "lldb/Utility/Status.h" // for Status +#include "lldb/Utility/Logging.h" +#include "lldb/Utility/SharingPtr.h" +#include "lldb/Utility/Status.h" #include "llvm/ADT/STLExtras.h" @@ -119,7 +119,7 @@ bool ValueObjectSynthetic::MightHaveChildren() { if (m_might_have_children == eLazyBoolCalculate) m_might_have_children = (m_synth_filter_ap->MightHaveChildren() ? eLazyBoolYes : eLazyBoolNo); - return (m_might_have_children == eLazyBoolNo ? false : true); + return (m_might_have_children != eLazyBoolNo); } uint64_t ValueObjectSynthetic::GetByteSize() { return m_parent->GetByteSize(); } @@ -174,7 +174,7 @@ bool ValueObjectSynthetic::UpdateValue() { } // let our backend do its update - if (m_synth_filter_ap->Update() == false) { + if (!m_synth_filter_ap->Update()) { if (log) log->Printf("[ValueObjectSynthetic::UpdateValue] name=%s, synthetic " "filter said caches are stale - clearing", @@ -235,7 +235,7 @@ lldb::ValueObjectSP ValueObjectSynthetic::GetChildAtIndex(size_t idx, UpdateValueIfNeeded(); ValueObject *valobj; - if (m_children_byindex.GetValueForKey(idx, valobj) == false) { + if (!m_children_byindex.GetValueForKey(idx, valobj)) { if (can_create && m_synth_filter_ap.get() != nullptr) { if (log) log->Printf("[ValueObjectSynthetic::GetChildAtIndex] name=%s, child at " diff --git a/source/Core/ValueObjectVariable.cpp b/source/Core/ValueObjectVariable.cpp index bfe5c3de7fbf..4d401c56249c 100644 --- a/source/Core/ValueObjectVariable.cpp +++ b/source/Core/ValueObjectVariable.cpp @@ -9,14 +9,12 @@ #include "lldb/Core/ValueObjectVariable.h" -#include "lldb/Core/Address.h" // for Address -#include "lldb/Core/AddressRange.h" // for AddressRange +#include "lldb/Core/Address.h" +#include "lldb/Core/AddressRange.h" #include "lldb/Core/Module.h" -#include "lldb/Core/RegisterValue.h" -#include "lldb/Core/Scalar.h" // for Scalar, operator!= #include "lldb/Core/Value.h" -#include "lldb/Expression/DWARFExpression.h" // for DWARFExpression -#include "lldb/Symbol/Declaration.h" // for Declaration +#include "lldb/Expression/DWARFExpression.h" +#include "lldb/Symbol/Declaration.h" #include "lldb/Symbol/Function.h" #include "lldb/Symbol/ObjectFile.h" #include "lldb/Symbol/SymbolContext.h" @@ -27,15 +25,17 @@ #include "lldb/Target/Process.h" #include "lldb/Target/RegisterContext.h" #include "lldb/Target/Target.h" -#include "lldb/Utility/DataExtractor.h" // for DataExtractor -#include "lldb/Utility/Status.h" // for Status -#include "lldb/lldb-private-enumerations.h" // for AddressType::eAddressTy... -#include "lldb/lldb-types.h" // for addr_t +#include "lldb/Utility/DataExtractor.h" +#include "lldb/Utility/RegisterValue.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/Utility/Status.h" +#include "lldb/lldb-private-enumerations.h" +#include "lldb/lldb-types.h" -#include "llvm/ADT/StringRef.h" // for StringRef +#include "llvm/ADT/StringRef.h" -#include <assert.h> // for assert -#include <memory> // for shared_ptr +#include <assert.h> +#include <memory> namespace lldb_private { class ExecutionContextScope; @@ -98,8 +98,9 @@ size_t ValueObjectVariable::CalculateNumChildren(uint32_t max) { if (!type.IsValid()) return 0; + ExecutionContext exe_ctx(GetExecutionContextRef()); const bool omit_empty_base_classes = true; - auto child_count = type.GetNumChildren(omit_empty_base_classes); + auto child_count = type.GetNumChildren(omit_empty_base_classes, &exe_ctx); return child_count <= max ? child_count : max; } @@ -111,7 +112,7 @@ uint64_t ValueObjectVariable::GetByteSize() { if (!type.IsValid()) return 0; - return type.GetByteSize(exe_ctx.GetBestExecutionContextScope()); + return type.GetByteSize(exe_ctx.GetBestExecutionContextScope()).getValueOr(0); } lldb::ValueType ValueObjectVariable::GetValueType() const { |
