When shared libraries are unloaded, they are now removed from the target
ModuleList so they don't show up in the images. Breakpoint locations that are
in shared libraries that get unloaded will persist though so that if you
have plug-ins that load/unload and you have a breakpoint set on functions
in the plug-ins, the hit counts will persist between loads/unloads.



git-svn-id: https://llvm.org/svn/llvm-project/llvdb/trunk@121069 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/include/lldb/Core/ModuleList.h b/include/lldb/Core/ModuleList.h
index 47ff65d..330f726 100644
--- a/include/lldb/Core/ModuleList.h
+++ b/include/lldb/Core/ModuleList.h
@@ -313,6 +313,9 @@
     bool
     Remove (lldb::ModuleSP &module_sp);
 
+    size_t
+    Remove (ModuleList &module_list);
+    
     bool
     ResolveFileAddress (lldb::addr_t vm_addr,
                         Address& so_addr);
diff --git a/include/lldb/lldb-enumerations.h b/include/lldb/lldb-enumerations.h
index cf52c3a..8f33201 100644
--- a/include/lldb/lldb-enumerations.h
+++ b/include/lldb/lldb-enumerations.h
@@ -56,7 +56,8 @@
 {
     eLaunchFlagNone         = 0u,
     eLaunchFlagDisableASLR  = (1u << 0),  ///< Disable Address Space Layout Randomization
-    eLaunchFlagDisableSTDIO = (1u << 1)   /// Disable stdio for inferior process (e.g. for a GUI app)
+    eLaunchFlagDisableSTDIO = (1u << 1),  ///< Disable stdio for inferior process (e.g. for a GUI app)
+    eLaunchFlagLaunchInTTY  = (1u << 2)   ///< Launch the process in a new TTY if supported by the host 
 } LaunchFlags;
     
 //----------------------------------------------------------------------
diff --git a/source/Breakpoint/Breakpoint.cpp b/source/Breakpoint/Breakpoint.cpp
index e4e0832..abe7484 100644
--- a/source/Breakpoint/Breakpoint.cpp
+++ b/source/Breakpoint/Breakpoint.cpp
@@ -291,9 +291,9 @@
             if (!m_filter_sp->ModulePasses (module_sp))
                 continue;
 
-            for (size_t j = 0; j < m_locations.GetSize(); j++)
+            for (size_t loc_idx = 0; loc_idx < m_locations.GetSize(); loc_idx++)
             {
-                BreakpointLocationSP break_loc = m_locations.GetByIndex(j);
+                BreakpointLocationSP break_loc = m_locations.GetByIndex(loc_idx);
                 if (!break_loc->IsEnabled())
                     continue;
                 const Section *section = break_loc->GetAddress().GetSection();
@@ -333,24 +333,22 @@
         for (size_t i = 0; i < module_list.GetSize(); i++)
         {
             ModuleSP module_sp (module_list.GetModuleAtIndex (i));
-            if (!m_filter_sp->ModulePasses (module_sp))
-                continue;
-
-            for (size_t j = 0; j < m_locations.GetSize(); j++)
+            if (m_filter_sp->ModulePasses (module_sp))
             {
-                BreakpointLocationSP break_loc = m_locations.GetByIndex(j);
-                const Section *section = break_loc->GetAddress().GetSection();
-                if (section)
+                const size_t num_locs = m_locations.GetSize();
+                for (size_t loc_idx = 0; loc_idx < num_locs; ++loc_idx)
                 {
-                    if (section->GetModule() == module_sp.get())
+                    BreakpointLocationSP break_loc = m_locations.GetByIndex(loc_idx);
+                    const Section *section = break_loc->GetAddress().GetSection();
+                    if (section && section->GetModule() == module_sp.get())
+                    {
+                        // Remove this breakpoint since the shared library is 
+                        // unloaded, but keep the breakpoint location around
+                        // so we always get complete hit count and breakpoint
+                        // lifetime info
                         break_loc->ClearBreakpointSite();
+                    }
                 }
-//                else
-//                {
-//                    Address temp_addr;
-//                    if (module->ResolveLoadAddress(break_loc->GetLoadAddress(), m_target->GetProcess(), temp_addr))
-//                        break_loc->ClearBreakpointSite();
-//                }
             }
         }
     }
diff --git a/source/Core/ModuleList.cpp b/source/Core/ModuleList.cpp
index d1c640e..cf40868 100644
--- a/source/Core/ModuleList.cpp
+++ b/source/Core/ModuleList.cpp
@@ -97,6 +97,20 @@
     return false;
 }
 
+size_t
+ModuleList::Remove (ModuleList &module_list)
+{
+    Mutex::Locker locker(m_modules_mutex);
+    size_t num_removed = 0;
+    collection::iterator pos, end = module_list.m_modules.end();
+    for (pos = module_list.m_modules.begin(); pos != end; ++pos)
+    {
+        if (Remove (*pos))
+            ++num_removed;
+    }
+    return num_removed;
+}
+
 
 
 void
diff --git a/source/Target/Target.cpp b/source/Target/Target.cpp
index 0dd1da3..c5dd46b 100644
--- a/source/Target/Target.cpp
+++ b/source/Target/Target.cpp
@@ -576,6 +576,10 @@
 Target::ModulesDidUnload (ModuleList &module_list)
 {
     m_breakpoint_list.UpdateBreakpoints (module_list, false);
+
+    // Remove the images from the target image list
+    m_images.Remove(module_list);
+
     // TODO: make event data that packages up the module_list
     BroadcastEvent (eBroadcastBitModulesUnloaded, NULL);
 }