228 lines
		
	
	
		
			6.3 KiB
		
	
	
	
		
			C++
		
	
	
	
			
		
		
	
	
			228 lines
		
	
	
		
			6.3 KiB
		
	
	
	
		
			C++
		
	
	
	
//===-- BreakpointList.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/Breakpoint/BreakpointList.h"
 | 
						|
 | 
						|
// C Includes
 | 
						|
// C++ Includes
 | 
						|
// Other libraries and framework includes
 | 
						|
// Project includes
 | 
						|
#include "lldb/Target/Target.h"
 | 
						|
 | 
						|
using namespace lldb;
 | 
						|
using namespace lldb_private;
 | 
						|
 | 
						|
BreakpointList::BreakpointList (bool is_internal) :
 | 
						|
    m_mutex (Mutex::eMutexTypeRecursive),
 | 
						|
    m_breakpoints(),
 | 
						|
    m_next_break_id (0),
 | 
						|
    m_is_internal (is_internal)
 | 
						|
{
 | 
						|
}
 | 
						|
 | 
						|
BreakpointList::~BreakpointList()
 | 
						|
{
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
break_id_t
 | 
						|
BreakpointList::Add (BreakpointSP &bp_sp, bool notify)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    // Internal breakpoint IDs are negative, normal ones are positive
 | 
						|
    bp_sp->SetID (m_is_internal ? --m_next_break_id : ++m_next_break_id);
 | 
						|
    
 | 
						|
    m_breakpoints.push_back(bp_sp);
 | 
						|
    if (notify)
 | 
						|
    {
 | 
						|
        if (bp_sp->GetTarget().EventTypeHasListeners(Target::eBroadcastBitBreakpointChanged))
 | 
						|
            bp_sp->GetTarget().BroadcastEvent (Target::eBroadcastBitBreakpointChanged,
 | 
						|
                                               new Breakpoint::BreakpointEventData (eBreakpointEventTypeAdded, bp_sp));
 | 
						|
    }
 | 
						|
    return bp_sp->GetID();
 | 
						|
}
 | 
						|
 | 
						|
bool
 | 
						|
BreakpointList::Remove (break_id_t break_id, bool notify)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    bp_collection::iterator pos = GetBreakpointIDIterator(break_id);    // Predicate
 | 
						|
    if (pos != m_breakpoints.end())
 | 
						|
    {
 | 
						|
        BreakpointSP bp_sp (*pos);
 | 
						|
        m_breakpoints.erase(pos);
 | 
						|
        if (notify)
 | 
						|
        {
 | 
						|
            if (bp_sp->GetTarget().EventTypeHasListeners(Target::eBroadcastBitBreakpointChanged))
 | 
						|
                bp_sp->GetTarget().BroadcastEvent (Target::eBroadcastBitBreakpointChanged,
 | 
						|
                                                   new Breakpoint::BreakpointEventData (eBreakpointEventTypeRemoved, bp_sp));
 | 
						|
        }
 | 
						|
        return true;
 | 
						|
    }
 | 
						|
    return false;
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
BreakpointList::SetEnabledAll (bool enabled)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    bp_collection::iterator pos, end = m_breakpoints.end();
 | 
						|
    for (pos = m_breakpoints.begin(); pos != end; ++pos)
 | 
						|
        (*pos)->SetEnabled (enabled);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
void
 | 
						|
BreakpointList::RemoveAll (bool notify)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    ClearAllBreakpointSites ();
 | 
						|
 | 
						|
    if (notify)
 | 
						|
    {
 | 
						|
        bp_collection::iterator pos, end = m_breakpoints.end();
 | 
						|
        for (pos = m_breakpoints.begin(); pos != end; ++pos)
 | 
						|
            if ((*pos)->GetTarget().EventTypeHasListeners(Target::eBroadcastBitBreakpointChanged))
 | 
						|
                (*pos)->GetTarget().BroadcastEvent (Target::eBroadcastBitBreakpointChanged,
 | 
						|
                                                    new Breakpoint::BreakpointEventData (eBreakpointEventTypeRemoved, *pos));
 | 
						|
    }
 | 
						|
    m_breakpoints.erase (m_breakpoints.begin(), m_breakpoints.end());
 | 
						|
}
 | 
						|
 | 
						|
class BreakpointIDMatches
 | 
						|
{
 | 
						|
public:
 | 
						|
    BreakpointIDMatches (break_id_t break_id) :
 | 
						|
        m_break_id(break_id)
 | 
						|
    {
 | 
						|
    }
 | 
						|
 | 
						|
    bool operator() (const BreakpointSP &bp) const
 | 
						|
    {
 | 
						|
        return m_break_id == bp->GetID();
 | 
						|
    }
 | 
						|
 | 
						|
private:
 | 
						|
   const break_id_t m_break_id;
 | 
						|
};
 | 
						|
 | 
						|
BreakpointList::bp_collection::iterator
 | 
						|
BreakpointList::GetBreakpointIDIterator (break_id_t break_id)
 | 
						|
{
 | 
						|
    return std::find_if(m_breakpoints.begin(), m_breakpoints.end(), // Search full range
 | 
						|
                        BreakpointIDMatches(break_id));             // Predicate
 | 
						|
}
 | 
						|
 | 
						|
BreakpointList::bp_collection::const_iterator
 | 
						|
BreakpointList::GetBreakpointIDConstIterator (break_id_t break_id) const
 | 
						|
{
 | 
						|
    return std::find_if(m_breakpoints.begin(), m_breakpoints.end(), // Search full range
 | 
						|
                        BreakpointIDMatches(break_id));             // Predicate
 | 
						|
}
 | 
						|
 | 
						|
BreakpointSP
 | 
						|
BreakpointList::FindBreakpointByID (break_id_t break_id)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    BreakpointSP stop_sp;
 | 
						|
    bp_collection::iterator pos = GetBreakpointIDIterator(break_id);
 | 
						|
    if (pos != m_breakpoints.end())
 | 
						|
        stop_sp = *pos;
 | 
						|
 | 
						|
    return stop_sp;
 | 
						|
}
 | 
						|
 | 
						|
const BreakpointSP
 | 
						|
BreakpointList::FindBreakpointByID (break_id_t break_id) const
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    BreakpointSP stop_sp;
 | 
						|
    bp_collection::const_iterator pos = GetBreakpointIDConstIterator(break_id);
 | 
						|
    if (pos != m_breakpoints.end())
 | 
						|
        stop_sp = *pos;
 | 
						|
 | 
						|
    return stop_sp;
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
BreakpointList::Dump (Stream *s) const
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    s->Printf("%.*p: ", (int)sizeof(void*) * 2, this);
 | 
						|
    s->Indent();
 | 
						|
    s->Printf("BreakpointList with %u Breakpoints:\n", (uint32_t)m_breakpoints.size());
 | 
						|
    s->IndentMore();
 | 
						|
    bp_collection::const_iterator pos;
 | 
						|
    bp_collection::const_iterator end = m_breakpoints.end();
 | 
						|
    for (pos = m_breakpoints.begin(); pos != end; ++pos)
 | 
						|
        (*pos)->Dump(s);
 | 
						|
    s->IndentLess();
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
BreakpointSP
 | 
						|
BreakpointList::GetBreakpointAtIndex (uint32_t i)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    BreakpointSP stop_sp;
 | 
						|
    bp_collection::iterator end = m_breakpoints.end();
 | 
						|
    bp_collection::iterator pos;
 | 
						|
    uint32_t curr_i = 0;
 | 
						|
    for (pos = m_breakpoints.begin(), curr_i = 0; pos != end; ++pos, ++curr_i)
 | 
						|
    {
 | 
						|
        if (curr_i == i)
 | 
						|
            stop_sp = *pos;
 | 
						|
    }
 | 
						|
    return stop_sp;
 | 
						|
}
 | 
						|
 | 
						|
const BreakpointSP
 | 
						|
BreakpointList::GetBreakpointAtIndex (uint32_t i) const
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    BreakpointSP stop_sp;
 | 
						|
    bp_collection::const_iterator end = m_breakpoints.end();
 | 
						|
    bp_collection::const_iterator pos;
 | 
						|
    uint32_t curr_i = 0;
 | 
						|
    for (pos = m_breakpoints.begin(), curr_i = 0; pos != end; ++pos, ++curr_i)
 | 
						|
    {
 | 
						|
        if (curr_i == i)
 | 
						|
            stop_sp = *pos;
 | 
						|
    }
 | 
						|
    return stop_sp;
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
BreakpointList::UpdateBreakpoints (ModuleList& module_list, bool added)
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    bp_collection::iterator end = m_breakpoints.end();
 | 
						|
    bp_collection::iterator pos;
 | 
						|
    for (pos = m_breakpoints.begin(); pos != end; ++pos)
 | 
						|
        (*pos)->ModulesChanged (module_list, added);
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
BreakpointList::ClearAllBreakpointSites ()
 | 
						|
{
 | 
						|
    Mutex::Locker locker(m_mutex);
 | 
						|
    bp_collection::iterator end = m_breakpoints.end();
 | 
						|
    bp_collection::iterator pos;
 | 
						|
    for (pos = m_breakpoints.begin(); pos != end; ++pos)
 | 
						|
        (*pos)->ClearAllBreakpointSites ();
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
BreakpointList::GetListMutex (Mutex::Locker &locker)
 | 
						|
{
 | 
						|
    return locker.Reset (m_mutex.GetMutex());
 | 
						|
}
 |