//===-- TargetList.cpp ------------------------------------------*- C++ -*-===//
//
//                     The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//

// C Includes
// C++ Includes
// Other libraries and framework includes
// Project includes
#include "lldb/Core/Broadcaster.h"
#include "lldb/Core/Event.h"
#include "lldb/Core/State.h"
#include "lldb/Core/Timer.h"
#include "lldb/Host/Host.h"
#include "lldb/Target/Process.h"
#include "lldb/Target/TargetList.h"

using namespace lldb;
using namespace lldb_private;


//----------------------------------------------------------------------
// TargetList constructor
//----------------------------------------------------------------------
TargetList::TargetList() :
    Broadcaster("TargetList"),
    m_target_list(),
    m_target_list_mutex (Mutex::eMutexTypeRecursive),
    m_current_target_idx (0)
{
}

//----------------------------------------------------------------------
// Destructor
//----------------------------------------------------------------------
TargetList::~TargetList()
{
    Mutex::Locker locker(m_target_list_mutex);
    m_target_list.clear();
}

Error
TargetList::CreateTarget
(
    const FileSpec& file,
    const ArchSpec& arch,
    const UUID *uuid_ptr,
    bool get_dependent_files,
    TargetSP &target_sp
)
{
    Timer scoped_timer (__PRETTY_FUNCTION__,
                        "TargetList::CreateTarget (file = '%s/%s', arch = '%s', uuid = %p)",
                        file.GetDirectory().AsCString(),
                        file.GetFilename().AsCString(),
                        arch.AsCString(),
                        uuid_ptr);
    ModuleSP exe_module_sp;
    FileSpec resolved_file(file);
    if (!Host::ResolveExecutableInBundle (&resolved_file))
        resolved_file = file;

    Error error = ModuleList::GetSharedModule(resolved_file, 
                                              arch, 
                                              uuid_ptr, 
                                              NULL, 
                                              0, 
                                              exe_module_sp, 
                                              NULL, 
                                              NULL);
    if (exe_module_sp)
    {
        target_sp.reset(new Target);
        target_sp->SetExecutableModule (exe_module_sp, get_dependent_files);

        if (target_sp.get())
        {
            Mutex::Locker locker(m_target_list_mutex);
            m_current_target_idx = m_target_list.size();
            m_target_list.push_back(target_sp);
        }

//        target_sp.reset(new Target);
//        // Let the target resolve any funky bundle paths before we try and get
//        // the object file...
//        target_sp->SetExecutableModule (exe_module_sp, get_dependent_files);
//        if (exe_module_sp->GetObjectFile() == NULL)
//        {
//            error.SetErrorStringWithFormat("%s%s%s: doesn't contain architecture %s",
//                                           file.GetDirectory().AsCString(),
//                                           file.GetDirectory() ? "/" : "",
//                                           file.GetFilename().AsCString(),
//                                           arch.AsCString());
//        }
//        else
//        {
//            if (target_sp.get())
//            {
//                error.Clear();
//                Mutex::Locker locker(m_target_list_mutex);
//                m_current_target_idx = m_target_list.size();
//                m_target_list.push_back(target_sp);
//            }
//        }
    }
    else
    {
        target_sp.reset();
    }

    return error;
}

bool
TargetList::DeleteTarget (TargetSP &target_sp)
{
    Mutex::Locker locker(m_target_list_mutex);
    collection::iterator pos, end = m_target_list.end();

    for (pos = m_target_list.begin(); pos != end; ++pos)
    {
        if (pos->get() == target_sp.get())
        {
            m_target_list.erase(pos);
            return true;
        }
    }
    return false;
}


TargetSP
TargetList::FindTargetWithExecutableAndArchitecture
(
    const FileSpec &exe_file_spec,
    const ArchSpec *exe_arch_ptr
) const
{
    Mutex::Locker locker (m_target_list_mutex);
    TargetSP target_sp;
    bool full_match = exe_file_spec.GetDirectory();

    collection::const_iterator pos, end = m_target_list.end();
    for (pos = m_target_list.begin(); pos != end; ++pos)
    {
        ModuleSP module_sp ((*pos)->GetExecutableModule());

        if (module_sp)
        {
            if (FileSpec::Equal (exe_file_spec, module_sp->GetFileSpec(), full_match))
            {
                if (exe_arch_ptr)
                {
                    if (*exe_arch_ptr != module_sp->GetArchitecture())
                        continue;
                }
                target_sp = *pos;
                break;
            }
        }
    }
    return target_sp;
}

TargetSP
TargetList::FindTargetWithProcessID (lldb::pid_t pid) const
{
    Mutex::Locker locker(m_target_list_mutex);
    TargetSP target_sp;
    collection::const_iterator pos, end = m_target_list.end();
    for (pos = m_target_list.begin(); pos != end; ++pos)
    {
        Process* process = (*pos)->GetProcessSP().get();
        if (process && process->GetID() == pid)
        {
            target_sp = *pos;
            break;
        }
    }
    return target_sp;
}


TargetSP
TargetList::FindTargetWithProcess (Process *process) const
{
    TargetSP target_sp;
    if (process)
    {
        Mutex::Locker locker(m_target_list_mutex);
        collection::const_iterator pos, end = m_target_list.end();
        for (pos = m_target_list.begin(); pos != end; ++pos)
        {
            if (process == (*pos)->GetProcessSP().get())
            {
                target_sp = *pos;
                break;
            }
        }
    }
    return target_sp;
}

TargetSP
TargetList::GetTargetSP (Target *target) const
{
    TargetSP target_sp;
    if (target)
    {
        Mutex::Locker locker(m_target_list_mutex);
        collection::const_iterator pos, end = m_target_list.end();
        for (pos = m_target_list.begin(); pos != end; ++pos)
        {
            if (target == (*pos).get())
            {
                target_sp = *pos;
                break;
            }
        }
    }
    return target_sp;
}

uint32_t
TargetList::SendAsyncInterrupt (lldb::pid_t pid)
{
    uint32_t num_async_interrupts_sent = 0;

    if (pid != LLDB_INVALID_PROCESS_ID)
    {
        TargetSP target_sp(FindTargetWithProcessID (pid));
        if (target_sp.get())
        {
            Process* process = target_sp->GetProcessSP().get();
            if (process)
            {
                process->BroadcastEvent (Process::eBroadcastBitInterrupt, NULL);
                ++num_async_interrupts_sent;
            }
        }
    }
    else
    {
        // We don't have a valid pid to broadcast to, so broadcast to the target
        // list's async broadcaster...
        BroadcastEvent (Process::eBroadcastBitInterrupt, NULL);
    }

    return num_async_interrupts_sent;
}

uint32_t
TargetList::SignalIfRunning (lldb::pid_t pid, int signo)
{
    uint32_t num_signals_sent = 0;
    Process *process = NULL;
    if (pid == LLDB_INVALID_PROCESS_ID)
    {
        // Signal all processes with signal
        Mutex::Locker locker(m_target_list_mutex);
        collection::iterator pos, end = m_target_list.end();
        for (pos = m_target_list.begin(); pos != end; ++pos)
        {
            process = (*pos)->GetProcessSP().get();
            if (process)
            {
                if (process->IsAlive())
                {
                    ++num_signals_sent;
                    process->Signal (signo);
                }
            }
        }
    }
    else
    {
        // Signal a specific process with signal
        TargetSP target_sp(FindTargetWithProcessID (pid));
        if (target_sp.get())
        {
            process = target_sp->GetProcessSP().get();
            if (process)
            {
                if (process->IsAlive())
                {
                    ++num_signals_sent;
                    process->Signal (signo);
                }
            }
        }
    }
    return num_signals_sent;
}

int
TargetList::GetNumTargets () const
{
    Mutex::Locker locker (m_target_list_mutex);
    return m_target_list.size();
}

lldb::TargetSP
TargetList::GetTargetAtIndex (uint32_t idx) const
{
    TargetSP target_sp;
    Mutex::Locker locker (m_target_list_mutex);
    if (idx < m_target_list.size())
        target_sp = m_target_list[idx];
    return target_sp;
}

uint32_t
TargetList::SetCurrentTarget (Target* target)
{
    Mutex::Locker locker (m_target_list_mutex);
    collection::const_iterator pos,
        begin = m_target_list.begin(),
        end = m_target_list.end();
    for (pos = begin; pos != end; ++pos)
    {
        if (pos->get() == target)
        {
            m_current_target_idx = std::distance (begin, pos);
            return m_current_target_idx;
        }
    }
    m_current_target_idx = 0;
    return m_current_target_idx;
}

lldb::TargetSP
TargetList::GetCurrentTarget ()
{
    Mutex::Locker locker (m_target_list_mutex);
    if (m_current_target_idx >= m_target_list.size())
        m_current_target_idx = 0;
    return GetTargetAtIndex (m_current_target_idx);
}
