diff options
author | Greg Clayton <gclayton@apple.com> | 2011-08-22 22:23:48 +0000 |
---|---|---|
committer | Greg Clayton <gclayton@apple.com> | 2011-08-22 22:23:48 +0000 |
commit | d4bfbc9ac0e13148c9d7d2637af6184ddc782460 (patch) | |
tree | d2a81f5c73b4216508f8344b498b2a43a69480e2 /lldb/source/Plugins/OperatingSystem/Darwin-Kernel/OperatingSystemDarwinKernel.cpp | |
parent | 81ab3f5d314f7b640deef77e2b9f2ec7444107d7 (diff) | |
download | bcm5719-llvm-d4bfbc9ac0e13148c9d7d2637af6184ddc782460.tar.gz bcm5719-llvm-d4bfbc9ac0e13148c9d7d2637af6184ddc782460.zip |
Renaming "MacOSX-Kernel" to "Darwin-Kernel". The file contents and project
commit will come shortly after this commit.
llvm-svn: 138282
Diffstat (limited to 'lldb/source/Plugins/OperatingSystem/Darwin-Kernel/OperatingSystemDarwinKernel.cpp')
-rw-r--r-- | lldb/source/Plugins/OperatingSystem/Darwin-Kernel/OperatingSystemDarwinKernel.cpp | 309 |
1 files changed, 309 insertions, 0 deletions
diff --git a/lldb/source/Plugins/OperatingSystem/Darwin-Kernel/OperatingSystemDarwinKernel.cpp b/lldb/source/Plugins/OperatingSystem/Darwin-Kernel/OperatingSystemDarwinKernel.cpp new file mode 100644 index 00000000000..f95e2ca335d --- /dev/null +++ b/lldb/source/Plugins/OperatingSystem/Darwin-Kernel/OperatingSystemDarwinKernel.cpp @@ -0,0 +1,309 @@ +//===-- OperatingSystemMacOSXKernel.cpp --------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "OperatingSystemMacOSXKernel.h" +// C Includes +// C++ Includes +// Other libraries and framework includes +#include "llvm/ADT/Triple.h" + +#include "lldb/Core/ArchSpec.h" +#include "lldb/Core/DataBufferHeap.h" +#include "lldb/Core/Module.h" +#include "lldb/Core/PluginManager.h" +#include "lldb/Core/RegisterValue.h" +#include "lldb/Core/ValueObjectVariable.h" +#include "lldb/Symbol/ObjectFile.h" +#include "lldb/Symbol/VariableList.h" +#include "lldb/Target/Process.h" +#include "lldb/Target/StopInfo.h" +#include "lldb/Target/Target.h" +#include "lldb/Target/ThreadList.h" +#include "lldb/Target/Thread.h" +#include "Plugins/Process/Utility/DynamicRegisterInfo.h" +#include "Plugins/Process/Utility/RegisterContextMemory.h" +#include "Plugins/Process/Utility/ThreadMemory.h" + +using namespace lldb; +using namespace lldb_private; + +static ConstString & +GetThreadGPRMemberName () +{ + static ConstString g_gpr_member_name("gpr"); + return g_gpr_member_name; +} + +void +OperatingSystemMacOSXKernel::Initialize() +{ + PluginManager::RegisterPlugin (GetPluginNameStatic(), + GetPluginDescriptionStatic(), + CreateInstance); +} + +void +OperatingSystemMacOSXKernel::Terminate() +{ + PluginManager::UnregisterPlugin (CreateInstance); +} + +OperatingSystem * +OperatingSystemMacOSXKernel::CreateInstance (Process *process, bool force) +{ +#if 0 + bool create = force; + if (!create) + { + Module* exe_module = process->GetTarget().GetExecutableModulePointer(); + if (exe_module) + { + ObjectFile *object_file = exe_module->GetObjectFile(); + if (object_file) + { + SectionList *section_list = object_file->GetSectionList(); + if (section_list) + { + static ConstString g_kld_section_name ("__KLD"); + if (section_list->FindSectionByName (g_kld_section_name)) + { + create = true; + } + } + } + } + + // We can limit the creation of this plug-in to "*-apple-darwin" triples + // if we command out the lines below... +// if (create) +// { +// const llvm::Triple &triple_ref = process->GetTarget().GetArchitecture().GetTriple(); +// create = triple_ref.getOS() == llvm::Triple::Darwin && triple_ref.getVendor() == llvm::Triple::Apple; +// } + } + + if (create) + return new OperatingSystemMacOSXKernel (process); +#endif + return NULL; +} + + +const char * +OperatingSystemMacOSXKernel::GetPluginNameStatic() +{ + return "macosx-kernel"; +} + +const char * +OperatingSystemMacOSXKernel::GetPluginDescriptionStatic() +{ + return "Operating system plug-in that gathers OS information from darwin kernels."; +} + + +OperatingSystemMacOSXKernel::OperatingSystemMacOSXKernel (lldb_private::Process *process) : + OperatingSystem (process), + m_thread_list_valobj_sp (), + m_register_info_ap () +{ +} + +OperatingSystemMacOSXKernel::~OperatingSystemMacOSXKernel () +{ +} + +ValueObjectSP +OperatingSystemMacOSXKernel::GetThreadListValueObject () +{ + if (m_thread_list_valobj_sp.get() == NULL) + { + VariableList variable_list; + const uint32_t max_matches = 1; + const bool append = true; + static ConstString g_thread_list_name("g_thread_list"); + Module *exe_module = m_process->GetTarget().GetExecutableModulePointer(); + if (exe_module) + { + if (exe_module->FindGlobalVariables (g_thread_list_name, + append, + max_matches, + variable_list)) + { + m_thread_list_valobj_sp = ValueObjectVariable::Create (m_process, variable_list.GetVariableAtIndex(0)); + } + } + } + return m_thread_list_valobj_sp; +} + +DynamicRegisterInfo * +OperatingSystemMacOSXKernel::GetDynamicRegisterInfo () +{ + if (m_register_info_ap.get() == NULL && m_thread_list_valobj_sp) + { + m_register_info_ap.reset (new DynamicRegisterInfo()); + ConstString empty_name; + const bool can_create = true; + AddressType addr_type; + addr_t base_addr = LLDB_INVALID_ADDRESS; + ValueObjectSP gpr_valobj_sp (m_thread_list_valobj_sp->GetChildMemberWithName(GetThreadGPRMemberName (), can_create)); + + if (gpr_valobj_sp->IsPointerType ()) + base_addr = gpr_valobj_sp->GetPointerValue (addr_type, true); + else + base_addr = gpr_valobj_sp->GetAddressOf (addr_type, true); + + ValueObjectSP child_valobj_sp; + if (gpr_valobj_sp) + { + ABI *abi = m_process->GetABI().get(); + assert (abi); + uint32_t num_children = gpr_valobj_sp->GetNumChildren(); + + ConstString gpr_name (gpr_valobj_sp->GetName()); + uint32_t reg_num = 0; + for (uint32_t i=0; i<num_children; ++i) + { + child_valobj_sp = gpr_valobj_sp->GetChildAtIndex(i, can_create); + + ConstString reg_name(child_valobj_sp->GetName()); + if (reg_name) + { + const char *reg_name_cstr = reg_name.GetCString(); + while (reg_name_cstr[0] == '_') + ++reg_name_cstr; + if (reg_name_cstr != reg_name.GetCString()) + reg_name.SetCString (reg_name_cstr); + } + + RegisterInfo reg_info; + if (abi->GetRegisterInfoByName(reg_name, reg_info)) + { + // Adjust the byte size and the offset to match the layout of registers in our struct + reg_info.byte_size = child_valobj_sp->GetByteSize(); + reg_info.byte_offset = child_valobj_sp->GetAddressOf(addr_type, true) - base_addr; + reg_info.kinds[eRegisterKindLLDB] = reg_num++; + m_register_info_ap->AddRegister (reg_info, reg_name, empty_name, gpr_name); + } + else + { + printf ("not able to find register info for %s\n", reg_name.GetCString()); // REMOVE THIS printf before checkin!!! + } + } + + m_register_info_ap->Finalize(); + } + } + assert (m_register_info_ap.get()); + return m_register_info_ap.get(); +} + +//------------------------------------------------------------------ +// PluginInterface protocol +//------------------------------------------------------------------ +const char * +OperatingSystemMacOSXKernel::GetPluginName() +{ + return "OperatingSystemMacOSXKernel"; +} + +const char * +OperatingSystemMacOSXKernel::GetShortPluginName() +{ + return GetPluginNameStatic(); +} + +uint32_t +OperatingSystemMacOSXKernel::GetPluginVersion() +{ + return 1; +} + +uint32_t +OperatingSystemMacOSXKernel::UpdateThreadList (ThreadList &old_thread_list, ThreadList &new_thread_list) +{ + // Make any constant strings once and cache the uniqued C string values + // so we don't have to rehash them each time through this function call + static ConstString g_tid_member_name("tid"); + static ConstString g_next_member_name("next"); + + ValueObjectSP root_valobj_sp (GetThreadListValueObject ()); + ValueObjectSP valobj_sp = root_valobj_sp; + const bool can_create = true; + while (valobj_sp) + { + if (valobj_sp->GetValueAsUnsigned(0) == 0) + break; + + ValueObjectSP tid_valobj_sp(valobj_sp->GetChildMemberWithName(g_tid_member_name, can_create)); + if (!tid_valobj_sp) + break; + + tid_t tid = tid_valobj_sp->GetValueAsUnsigned (LLDB_INVALID_THREAD_ID); + if (tid == LLDB_INVALID_THREAD_ID) + break; + + ThreadSP thread_sp (old_thread_list.FindThreadByID (tid, false)); + if (!thread_sp) + thread_sp.reset (new ThreadMemory (*m_process, tid, valobj_sp)); + + new_thread_list.AddThread(thread_sp); + + ValueObjectSP next_valobj_sp (valobj_sp->GetChildMemberWithName(g_next_member_name, can_create)); + + if (next_valobj_sp) + { + // Watch for circular linked lists + if (next_valobj_sp.get() == root_valobj_sp.get()) + break; + } + next_valobj_sp.swap(valobj_sp); + } + return new_thread_list.GetSize(false); +} + +void +OperatingSystemMacOSXKernel::ThreadWasSelected (Thread *thread) +{ +} + +RegisterContextSP +OperatingSystemMacOSXKernel::CreateRegisterContextForThread (Thread *thread) +{ + ThreadMemory *generic_thread = (ThreadMemory *)thread; + RegisterContextSP reg_ctx_sp; + + ValueObjectSP thread_valobj_sp (generic_thread->GetValueObject()); + if (thread_valobj_sp) + { + const bool can_create = true; + AddressType addr_type; + addr_t base_addr = LLDB_INVALID_ADDRESS; + ValueObjectSP gpr_valobj_sp (thread_valobj_sp->GetChildMemberWithName(GetThreadGPRMemberName (), can_create)); + if (gpr_valobj_sp) + { + if (gpr_valobj_sp->IsPointerType ()) + base_addr = gpr_valobj_sp->GetPointerValue (addr_type, true); + else + base_addr = gpr_valobj_sp->GetAddressOf (addr_type, true); + reg_ctx_sp.reset (new RegisterContextMemory (*thread, 0, *GetDynamicRegisterInfo (), base_addr)); + } + } + return reg_ctx_sp; +} + +StopInfoSP +OperatingSystemMacOSXKernel::CreateThreadStopReason (lldb_private::Thread *thread) +{ + StopInfoSP stop_info_sp; //(StopInfo::CreateStopReasonWithSignal (*thread, SIGSTOP)); + return stop_info_sp; +} + + |