Full core file support has been added for mach-o core files.

Tracking modules down when you have a UUID and a path has been improved.

DynamicLoaderDarwinKernel no longer parses mach-o load commands and it
now uses the memory based modules now that we can load modules from memory.

Added a target setting named "target.exec-search-paths" which can be used
to supply a list of directories to use when trying to look for executables.
This allows one or more directories to be used when searching for modules
that may not exist in the SDK/PDK. The target automatically adds the directory
for the main executable to this list so this should help us in tracking down
shared libraries and other binaries. 



git-svn-id: https://llvm.org/svn/llvm-project/lldb/trunk@150426 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/source/Target/Target.cpp b/source/Target/Target.cpp
index 20b8e93..6a6cb0e 100644
--- a/source/Target/Target.cpp
+++ b/source/Target/Target.cpp
@@ -869,6 +869,7 @@
                                                       NULL, 
                                                       0, 
                                                       executable_sp, 
+                                                      &GetExecutableSearchPaths(),
                                                       NULL, 
                                                       NULL);
                                           
@@ -1227,7 +1228,15 @@
         if (m_image_search_paths.RemapPath (file_spec.GetDirectory(), transformed_spec.GetDirectory()))
         {
             transformed_spec.GetFilename() = file_spec.GetFilename();
-            error = ModuleList::GetSharedModule (transformed_spec, arch, uuid_ptr, object_name, object_offset, module_sp, &old_module_sp, &did_create_module);
+            error = ModuleList::GetSharedModule (transformed_spec, 
+                                                 arch, 
+                                                 uuid_ptr, 
+                                                 object_name, 
+                                                 object_offset, 
+                                                 module_sp, 
+                                                 &GetExecutableSearchPaths(),
+                                                 &old_module_sp, 
+                                                 &did_create_module);
         }
     }
 
@@ -1242,6 +1251,7 @@
                                                 object_name, 
                                                 object_offset, 
                                                 module_sp, 
+                                                &GetExecutableSearchPaths(),
                                                 &old_module_sp, 
                                                 &did_create_module);
     }
@@ -1395,6 +1405,20 @@
     return g_settings_controller_sp;
 }
 
+FileSpecList
+Target::GetDefaultExecutableSearchPaths ()
+{
+    lldb::UserSettingsControllerSP settings_controller_sp (GetSettingsController());
+    if (settings_controller_sp)
+    {
+        lldb::InstanceSettingsSP instance_settings_sp (settings_controller_sp->GetDefaultInstanceSettings ());
+        if (instance_settings_sp)
+            return static_cast<TargetInstanceSettings *>(instance_settings_sp.get())->GetExecutableSearchPaths ();
+    }
+    return FileSpecList();
+}
+
+
 ArchSpec
 Target::GetDefaultArchitecture ()
 {
@@ -2016,6 +2040,7 @@
 #define TSC_PREFER_DYNAMIC      "prefer-dynamic-value"
 #define TSC_SKIP_PROLOGUE       "skip-prologue"
 #define TSC_SOURCE_MAP          "source-map"
+#define TSC_EXE_SEARCH_PATHS    "exec-search-paths"
 #define TSC_MAX_CHILDREN        "max-children-count"
 #define TSC_MAX_STRLENSUMMARY   "max-string-summary-length"
 #define TSC_PLATFORM_AVOID      "breakpoints-use-platform-avoid-list"
@@ -2058,6 +2083,13 @@
 }
 
 static const ConstString &
+GetSettingNameForExecutableSearchPaths ()
+{
+    static ConstString g_const_string (TSC_EXE_SEARCH_PATHS);
+    return g_const_string;
+}
+
+static const ConstString &
 GetSettingNameForSkipPrologue ()
 {
     static ConstString g_const_string (TSC_SKIP_PROLOGUE);
@@ -2193,6 +2225,7 @@
     m_prefer_dynamic_value (2),
     m_skip_prologue (true, true),
     m_source_map (NULL, NULL),
+    m_exe_search_paths (),
     m_max_children_display(256),
     m_max_strlen_length(1024),
     m_breakpoints_use_platform_avoid (true, true),
@@ -2231,6 +2264,7 @@
     m_prefer_dynamic_value (rhs.m_prefer_dynamic_value),
     m_skip_prologue (rhs.m_skip_prologue),
     m_source_map (rhs.m_source_map),
+    m_exe_search_paths (rhs.m_exe_search_paths),
     m_max_children_display (rhs.m_max_children_display),
     m_max_strlen_length (rhs.m_max_strlen_length),
     m_breakpoints_use_platform_avoid (rhs.m_breakpoints_use_platform_avoid),
@@ -2265,6 +2299,7 @@
         m_prefer_dynamic_value = rhs.m_prefer_dynamic_value;
         m_skip_prologue = rhs.m_skip_prologue;
         m_source_map = rhs.m_source_map;
+        m_exe_search_paths = rhs.m_exe_search_paths;
         m_max_children_display = rhs.m_max_children_display;
         m_max_strlen_length = rhs.m_max_strlen_length;
         m_breakpoints_use_platform_avoid = rhs.m_breakpoints_use_platform_avoid;
@@ -2357,6 +2392,49 @@
         if (ok)
             m_max_strlen_length = new_value;
     }
+    else if (var_name == GetSettingNameForExecutableSearchPaths())
+    {
+        switch (op)
+        {
+            case eVarSetOperationReplace:
+            case eVarSetOperationInsertBefore:
+            case eVarSetOperationInsertAfter:
+            case eVarSetOperationRemove:
+            default:
+                break;
+            case eVarSetOperationAssign:
+                m_exe_search_paths.Clear();
+                // Fall through to append....
+            case eVarSetOperationAppend:
+            {   
+                Args args(value);
+                const uint32_t argc = args.GetArgumentCount();
+                if (argc > 0)
+                {
+                    const char *exe_search_path_dir;
+                    for (uint32_t idx = 0; (exe_search_path_dir = args.GetArgumentAtIndex(idx)) != NULL; ++idx)
+                    {
+                        FileSpec file_spec;
+                        file_spec.GetDirectory().SetCString(exe_search_path_dir);
+                        FileSpec::FileType file_type = file_spec.GetFileType();
+                        if (file_type == FileSpec::eFileTypeDirectory || file_type == FileSpec::eFileTypeInvalid)
+                        {
+                            m_exe_search_paths.Append(file_spec);
+                        }
+                        else
+                        {
+                            err.SetErrorStringWithFormat("executable search path '%s' exists, but it does not resolve to a directory", exe_search_path_dir);
+                        }
+                    }
+                }
+            }
+                break;
+                
+            case eVarSetOperationClear:
+                m_exe_search_paths.Clear();
+                break;
+        }
+    }
     else if (var_name == GetSettingNameForSourcePathMap ())
     {
         switch (op)
@@ -2487,6 +2565,16 @@
         else
             value.AppendString ("false");
     }
+    else if (var_name == GetSettingNameForExecutableSearchPaths())
+    {
+        if (m_exe_search_paths.GetSize())
+        {
+            for (size_t i = 0, n = m_exe_search_paths.GetSize(); i < n; ++i) 
+            {
+                value.AppendString(m_exe_search_paths.GetFileSpecAtIndex (i).GetDirectory().AsCString());
+            }
+        }
+    }
     else if (var_name == GetSettingNameForSourcePathMap ())
     {
         if (m_source_map.GetSize())
@@ -2670,6 +2758,7 @@
     { TSC_PREFER_DYNAMIC    , eSetVarTypeEnum   , NULL          , g_dynamic_value_types, false, false, "Should printed values be shown as their dynamic value." },
     { TSC_SKIP_PROLOGUE     , eSetVarTypeBoolean, "true"        , NULL,                  false, false, "Skip function prologues when setting breakpoints by name." },
     { TSC_SOURCE_MAP        , eSetVarTypeArray  , NULL          , NULL,                  false, false, "Source path remappings to use when locating source files from debug information." },
+    { TSC_EXE_SEARCH_PATHS  , eSetVarTypeArray  , NULL          , NULL,                  false, false, "Executable search paths to use when locating executable files whose paths don't match the local file system." },
     { TSC_MAX_CHILDREN      , eSetVarTypeInt    , "256"         , NULL,                  true,  false, "Maximum number of children to expand in any level of depth." },
     { TSC_MAX_STRLENSUMMARY , eSetVarTypeInt    , "1024"        , NULL,                  true,  false, "Maximum number of characters to show when using %s in summary strings." },
     { TSC_PLATFORM_AVOID    , eSetVarTypeBoolean, "true"        , NULL,                  false, false, "Consult the platform module avoid list when setting non-module specific breakpoints." },