diff options
author | emaste <emaste@FreeBSD.org> | 2014-11-26 16:48:12 +0000 |
---|---|---|
committer | emaste <emaste@FreeBSD.org> | 2014-11-26 16:48:12 +0000 |
commit | 0147dda7de9580d13778ecb4c9e92b83b7a63911 (patch) | |
tree | b16dc95f693ed59342b6141cd3fd9f59a6cd7e7e /contrib/llvm/tools/lldb/source/Target/Target.cpp | |
parent | bfd4c39c61ae9b29542625bb12b6f7f4b1f8c727 (diff) | |
parent | 01ee1789d6aa7294e5966a97f8d29387f6f81699 (diff) | |
download | FreeBSD-src-0147dda7de9580d13778ecb4c9e92b83b7a63911.zip FreeBSD-src-0147dda7de9580d13778ecb4c9e92b83b7a63911.tar.gz |
Update LLDB snapshot to upstream r216948 (git 50f7fe44)
This is approximately "LLDB 3.5" although with a little bit of skew,
and will go along with the Clang 3.5 import.
Sponsored by: DARPA, AFRL
Diffstat (limited to 'contrib/llvm/tools/lldb/source/Target/Target.cpp')
-rw-r--r-- | contrib/llvm/tools/lldb/source/Target/Target.cpp | 127 |
1 files changed, 90 insertions, 37 deletions
diff --git a/contrib/llvm/tools/lldb/source/Target/Target.cpp b/contrib/llvm/tools/lldb/source/Target/Target.cpp index e781626..d2d0b50 100644 --- a/contrib/llvm/tools/lldb/source/Target/Target.cpp +++ b/contrib/llvm/tools/lldb/source/Target/Target.cpp @@ -94,12 +94,12 @@ Target::Target(Debugger &debugger, const ArchSpec &target_arch, const lldb::Plat SetEventName (eBroadcastBitModulesUnloaded, "modules-unloaded"); SetEventName (eBroadcastBitWatchpointChanged, "watchpoint-changed"); SetEventName (eBroadcastBitSymbolsLoaded, "symbols-loaded"); - + CheckInWithManager(); Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT)); if (log) - log->Printf ("%p Target::Target()", this); + log->Printf ("%p Target::Target()", static_cast<void*>(this)); if (m_arch.IsValid()) { LogIfAnyCategoriesSet(LIBLLDB_LOG_TARGET, "Target::Target created with architecture %s (%s)", m_arch.GetArchitectureName(), m_arch.GetTriple().getTriple().c_str()); @@ -113,7 +113,7 @@ Target::~Target() { Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT)); if (log) - log->Printf ("%p Target::~Target()", this); + log->Printf ("%p Target::~Target()", static_cast<void*>(this)); DeleteCurrentProcess (); } @@ -486,9 +486,12 @@ Target::CreateFuncRegexBreakpoint (const FileSpecList *containingModules, bool hardware) { SearchFilterSP filter_sp(GetSearchFilterForModuleAndCUList (containingModules, containingSourceFiles)); + bool skip = + (skip_prologue == eLazyBoolCalculate) ? GetSkipPrologue() + : static_cast<bool>(skip_prologue); BreakpointResolverSP resolver_sp(new BreakpointResolverName (NULL, func_regex, - skip_prologue == eLazyBoolCalculate ? GetSkipPrologue() : skip_prologue)); + skip)); return CreateBreakpoint (filter_sp, resolver_sp, internal, hardware, true); } @@ -635,7 +638,7 @@ Target::CreateWatchpoint(lldb::addr_t addr, size_t size, const ClangASTType *typ if (!CheckIfWatchpointsExhausted(this, error)) { if (!OptionGroupWatchpoint::IsWatchSizeSupported(size)) - error.SetErrorStringWithFormat("watch size of %zu is not supported", size); + error.SetErrorStringWithFormat("watch size of %" PRIu64 " is not supported", (uint64_t)size); } wp_sp.reset(); } @@ -1010,10 +1013,10 @@ LoadScriptingResourceForModule (const ModuleSP &module_sp, Target *target) target->GetDebugger().GetErrorFile()->Printf("unable to load scripting data for module %s - error reported was %s\n", module_sp->GetFileSpec().GetFileNameStrippingExtension().GetCString(), error.AsCString()); - if (feedback_stream.GetSize()) - target->GetDebugger().GetErrorFile()->Printf("%s\n", - feedback_stream.GetData()); } + if (feedback_stream.GetSize()) + target->GetDebugger().GetErrorFile()->Printf("%s\n", + feedback_stream.GetData()); } void @@ -1047,7 +1050,7 @@ Target::SetExecutableModule (ModuleSP& executable_sp, bool get_dependent_files) "Target::SetExecutableModule (executable = '%s')", executable_sp->GetFileSpec().GetPath().c_str()); - m_images.Append(executable_sp); // The first image is our exectuable file + m_images.Append(executable_sp); // The first image is our executable file // If we haven't set an architecture yet, reset our architecture based on what we found in the executable module. if (!m_arch.IsValid()) @@ -1142,41 +1145,44 @@ void Target::ModuleAdded (const ModuleList& module_list, const ModuleSP &module_sp) { // A module is being added to this target for the first time - ModuleList my_module_list; - my_module_list.Append(module_sp); - LoadScriptingResourceForModule(module_sp, this); - ModulesDidLoad (my_module_list); + if (m_valid) + { + ModuleList my_module_list; + my_module_list.Append(module_sp); + LoadScriptingResourceForModule(module_sp, this); + ModulesDidLoad (my_module_list); + } } void Target::ModuleRemoved (const ModuleList& module_list, const ModuleSP &module_sp) { // A module is being added to this target for the first time - ModuleList my_module_list; - my_module_list.Append(module_sp); - ModulesDidUnload (my_module_list, false); + if (m_valid) + { + ModuleList my_module_list; + my_module_list.Append(module_sp); + ModulesDidUnload (my_module_list, false); + } } void Target::ModuleUpdated (const ModuleList& module_list, const ModuleSP &old_module_sp, const ModuleSP &new_module_sp) { // A module is replacing an already added module - m_breakpoint_list.UpdateBreakpointsWhenModuleIsReplaced(old_module_sp, new_module_sp); + if (m_valid) + m_breakpoint_list.UpdateBreakpointsWhenModuleIsReplaced(old_module_sp, new_module_sp); } void Target::ModulesDidLoad (ModuleList &module_list) { - if (module_list.GetSize()) + if (m_valid && module_list.GetSize()) { m_breakpoint_list.UpdateBreakpoints (module_list, true, false); if (m_process_sp) { - SystemRuntime *sys_runtime = m_process_sp->GetSystemRuntime(); - if (sys_runtime) - { - sys_runtime->ModulesDidLoad (module_list); - } + m_process_sp->ModulesDidLoad (module_list); } // TODO: make event data that packages up the module_list BroadcastEvent (eBroadcastBitModulesLoaded, NULL); @@ -1186,7 +1192,7 @@ Target::ModulesDidLoad (ModuleList &module_list) void Target::SymbolsDidLoad (ModuleList &module_list) { - if (module_list.GetSize()) + if (m_valid && module_list.GetSize()) { if (m_process_sp) { @@ -1206,7 +1212,7 @@ Target::SymbolsDidLoad (ModuleList &module_list) void Target::ModulesDidUnload (ModuleList &module_list, bool delete_locations) { - if (module_list.GetSize()) + if (m_valid && module_list.GetSize()) { m_breakpoint_list.UpdateBreakpoints (module_list, false, delete_locations); // TODO: make event data that packages up the module_list @@ -1255,7 +1261,7 @@ Target::ReadMemoryFromFileCache (const Address& addr, void *dst, size_t dst_len, SectionSP section_sp (addr.GetSection()); if (section_sp) { - // If the contents of this section are encrypted, the on-disk file is unusuable. Read only from live memory. + // If the contents of this section are encrypted, the on-disk file is unusable. Read only from live memory. if (section_sp->IsEncrypted()) { error.SetErrorString("section is encrypted"); @@ -1320,7 +1326,7 @@ Target::ReadMemory (const Address& addr, } else { - // We have at least one section loaded. This can be becuase + // We have at least one section loaded. This can be because // we have manually loaded some sections with "target modules load ..." // or because we have have a live process that has sections loaded // through the dynamic loader @@ -1376,7 +1382,7 @@ Target::ReadMemory (const Address& addr, } // If the address is not section offset we have an address that // doesn't resolve to any address in any currently loaded shared - // libaries and we failed to read memory so there isn't anything + // libraries and we failed to read memory so there isn't anything // more we can do. If it is section offset, we might be able to // read cached memory from the object file. if (!resolved_addr.IsSectionOffset()) @@ -1547,7 +1553,7 @@ Target::ReadPointerFromMemory (const Address& addr, } else { - // We have at least one section loaded. This can be becuase + // We have at least one section loaded. This can be because // we have manually loaded some sections with "target modules load ..." // or because we have have a live process that has sections loaded // through the dynamic loader @@ -1698,6 +1704,8 @@ Target::GetSharedModule (const ModuleSpec &module_spec, Error *error_ptr) else m_images.Append(module_sp); } + else + module_sp.reset(); } } if (error_ptr) @@ -1765,7 +1773,7 @@ Target::GetScratchClangASTContext(bool create_on_demand) m_scratch_ast_context_ap.reset (new ClangASTContext(m_arch.GetTriple().str().c_str())); m_scratch_ast_source_ap.reset (new ClangASTSource(shared_from_this())); m_scratch_ast_source_ap->InstallASTContext(m_scratch_ast_context_ap->getASTContext()); - llvm::OwningPtr<clang::ExternalASTSource> proxy_ast_source(m_scratch_ast_source_ap->CreateProxy()); + llvm::IntrusiveRefCntPtr<clang::ExternalASTSource> proxy_ast_source(m_scratch_ast_source_ap->CreateProxy()); m_scratch_ast_context_ap->SetExternalSource(proxy_ast_source); } return m_scratch_ast_context_ap.get(); @@ -1850,7 +1858,7 @@ Target::GetTargetFromContexts (const ExecutionContext *exe_ctx_ptr, const Symbol return target; } -ExecutionResults +ExpressionResults Target::EvaluateExpression ( const char *expr_cstr, @@ -1861,7 +1869,7 @@ Target::EvaluateExpression { result_valobj_sp.reset(); - ExecutionResults execution_results = eExecutionSetupError; + ExpressionResults execution_results = eExpressionSetupError; if (expr_cstr == NULL || expr_cstr[0] == '\0') return execution_results; @@ -1896,7 +1904,7 @@ Target::EvaluateExpression if (persistent_var_sp) { result_valobj_sp = persistent_var_sp->GetValueObject (); - execution_results = eExecutionCompleted; + execution_results = eExpressionCompleted; } else { @@ -2363,7 +2371,8 @@ Target::Launch (Listener &listener, ProcessLaunchInfo &launch_info) if (!launch_info.GetArchitecture().IsValid()) launch_info.GetArchitecture() = GetArchitecture(); - + + // If we're not already connected to the process, and if we have a platform that can launch a process for debugging, go ahead and do that here. if (state != eStateConnected && platform_sp && platform_sp->CanDebugProcess ()) { m_process_sp = GetPlatform()->DebugProcess (launch_info, @@ -2380,10 +2389,12 @@ Target::Launch (Listener &listener, ProcessLaunchInfo &launch_info) } else { + // Use a Process plugin to construct the process. const char *plugin_name = launch_info.GetProcessPluginName(); CreateProcess (listener, plugin_name, NULL); } - + + // Since we didn't have a platform launch the process, launch it here. if (m_process_sp) error = m_process_sp->Launch (launch_info); } @@ -2409,9 +2420,14 @@ Target::Launch (Listener &listener, ProcessLaunchInfo &launch_info) m_process_sp->RestoreProcessEvents (); error = m_process_sp->PrivateResume(); - + if (error.Success()) { + // there is a race condition where this thread will return up the call stack to the main command + // handler and show an (lldb) prompt before HandlePrivateEvent (from PrivateStateThread) has + // a chance to call PushProcessIOHandler() + m_process_sp->SyncIOHandler(2000); + if (synchronous_execution) { state = m_process_sp->WaitForProcessToStop (NULL, NULL, true, hijack_listener_sp.get()); @@ -2429,6 +2445,27 @@ Target::Launch (Listener &listener, ProcessLaunchInfo &launch_info) error = error2; } } + else if (state == eStateExited) + { + bool with_shell = launch_info.GetShell(); + const int exit_status = m_process_sp->GetExitStatus(); + const char *exit_desc = m_process_sp->GetExitDescription(); +#define LAUNCH_SHELL_MESSAGE "\n'r' and 'run' are aliases that default to launching through a shell.\nTry launching without going through a shell by using 'process launch'." + if (exit_desc && exit_desc[0]) + { + if (with_shell) + error.SetErrorStringWithFormat ("process exited with status %i (%s)" LAUNCH_SHELL_MESSAGE, exit_status, exit_desc); + else + error.SetErrorStringWithFormat ("process exited with status %i (%s)", exit_status, exit_desc); + } + else + { + if (with_shell) + error.SetErrorStringWithFormat ("process exited with status %i" LAUNCH_SHELL_MESSAGE, exit_status); + else + error.SetErrorStringWithFormat ("process exited with status %i", exit_status); + } + } else { error.SetErrorStringWithFormat ("initial process state wasn't stopped: %s", StateAsCString(state)); @@ -2616,6 +2653,7 @@ g_properties[] = { "input-path" , OptionValue::eTypeFileSpec , false, 0 , NULL, NULL, "The file/path to be used by the executable program for reading its standard input." }, { "output-path" , OptionValue::eTypeFileSpec , false, 0 , NULL, NULL, "The file/path to be used by the executable program for writing its standard output." }, { "error-path" , OptionValue::eTypeFileSpec , false, 0 , NULL, NULL, "The file/path to be used by the executable program for writing its standard error." }, + { "detach-on-error" , OptionValue::eTypeBoolean , false, true , NULL, NULL, "debugserver will detach (rather than killing) a process if it loses connection with lldb." }, { "disable-aslr" , OptionValue::eTypeBoolean , false, true , NULL, NULL, "Disable Address Space Layout Randomization (ASLR)" }, { "disable-stdio" , OptionValue::eTypeBoolean , false, false , NULL, NULL, "Disable stdin/stdout for process (e.g. for a GUI application)" }, { "inline-breakpoint-strategy" , OptionValue::eTypeEnum , false, eInlineBreakpointsHeaders , NULL, g_inline_breakpoint_enums, "The strategy to use when settings breakpoints by file and line. " @@ -2662,6 +2700,7 @@ enum ePropertyInputPath, ePropertyOutputPath, ePropertyErrorPath, + ePropertyDetachOnError, ePropertyDisableASLR, ePropertyDisableSTDIO, ePropertyInlineStrategy, @@ -2699,7 +2738,7 @@ public: virtual const Property * GetPropertyAtIndex (const ExecutionContext *exe_ctx, bool will_modify, uint32_t idx) const { - // When gettings the value for a key from the target options, we will always + // When getting the value for a key from the target options, we will always // try and grab the setting from the current target if there is one. Else we just // use the one from this instance. if (idx == ePropertyEnvVars) @@ -2845,6 +2884,20 @@ TargetProperties::SetDisableASLR (bool b) } bool +TargetProperties::GetDetachOnError () const +{ + const uint32_t idx = ePropertyDetachOnError; + return m_collection_sp->GetPropertyAtIndexAsBoolean (NULL, idx, g_properties[idx].default_uint_value != 0); +} + +void +TargetProperties::SetDetachOnError (bool b) +{ + const uint32_t idx = ePropertyDetachOnError; + m_collection_sp->SetPropertyAtIndexAsBoolean (NULL, idx, b); +} + +bool TargetProperties::GetDisableSTDIO () const { const uint32_t idx = ePropertyDisableSTDIO; |