Ejemplo n.º 1
0
bool CodeLiteLLDBApp::InitializeLLDB(const LLDBCommand& command)
{
    if(IsDebugSessionInProgress()) {
        wxPrintf("codelite-lldb: another session is already in progress\n");
        return false;
    }

    if(!command.GetWorkingDirectory().IsEmpty()) {
        ::wxSetWorkingDirectory(command.GetWorkingDirectory());
    }

    wxPrintf("codelite-lldb: working directory is set to %s\n", ::wxGetCwd());
#ifdef __WXMAC__
    // On OSX, debugserver executable must exists otherwise lldb will not work properly
    // we ensure that it exists by checking the environment variable LLDB_DEBUGSERVER_PATH
    wxString lldbDebugServer;
    if(!::wxGetEnv("LLDB_DEBUGSERVER_PATH", &lldbDebugServer) || !wxFileName::Exists(lldbDebugServer)) {
        wxPrintf("codelite-lldb: LLDB_DEBUGSERVER_PATH environment does not exist or contains a path to a non existent "
                 "file\n");
        NotifyExited();
        return false;
    }
#endif

    m_debuggeePid = wxNOT_FOUND;
    wxPrintf("codelite-lldb: creating target for file '%s'\n", command.GetExecutable());
    m_debugger = lldb::SBDebugger::Create();
    lldb::SBError lldbError;
    m_target = m_debugger.CreateTarget(command.GetExecutable().mb_str().data(), NULL, NULL, true, lldbError);
    if(!m_target.IsValid()) {
        wxPrintf("codelite-lldb: could not create target for file %s. %s\n",
                 command.GetExecutable(),
                 lldbError.GetCString());
        NotifyExited();
        return false;
    }
    // Print the content of the summaries (for debugging purposes)
    wxPrintf("codelite-lldb: created target for %s\n", command.GetExecutable());
    m_debugger.SetAsync(true);

    // Keep the settings
    m_settings = command.GetSettings();

    // First, source the .lldbinit file
    wxString source_command;
    source_command << "command source '" << ::wxGetHomeDir() << "/.lldbinit"
                   << "'";
    DoExecutueShellCommand(source_command);

    // Apply the types
    lldb::SBCommandReturnObject ret;
    wxArrayString commands = ::wxStringTokenize(m_settings.GetTypes(), "\n", wxTOKEN_STRTOK);
    for(size_t i = 0; i < commands.GetCount(); ++i) {
        DoExecutueShellCommand(commands.Item(i));
    }
    // DoExecutueShellCommand("type summary list");
    return true;
}
Ejemplo n.º 2
0
void CodeLiteLLDBApp::AttachProcess(const LLDBCommand& command)
{
    wxPrintf("codeite-lldb: attaching to process with PID %d\n", command.GetProcessID());
    if(!InitializeLLDB(command)) {
        return;
    }

    lldb::SBError errorCode;
    lldb::SBListener listener;
    lldb::SBProcess process = m_target.AttachToProcessWithID(listener, (lldb::pid_t)command.GetProcessID(), errorCode);
    if(!errorCode.Success()) {
        wxPrintf("codeite-lldb: error attaching process %d. '%s'\n", command.GetProcessID(), errorCode.GetCString());
        NotifyExited();
        return;
    }
    wxPrintf("codeite-lldb: process attached successfully\n");

    // Launch the thread that will handle the LLDB process events
    m_lldbProcessEventThread =
        new LLDBProcessEventHandlerThread(this, m_debugger, m_target.GetProcess(), kDebugSessionTypeAttach);
    m_lldbProcessEventThread->Start();

    // In any case, reset the interrupt reason
    m_interruptReason = kInterruptReasonNone;

    // Notify codelite that the debugger started successfully
    NotifyStarted(kDebugSessionTypeAttach);
}
Ejemplo n.º 3
0
void CodeLiteLLDBApp::OpenCoreFile(const LLDBCommand& command)
{
    wxPrintf("codeite-lldb: debugging core file '%s'\n", command.GetCorefile());
    wxPrintf("codeite-lldb: executable file '%s'\n", command.GetExecutable());

    if(!InitializeLLDB(command)) {
        return;
    }

    lldb::SBProcess process = m_target.LoadCore(command.GetCorefile().mb_str(wxConvUTF8).data());
    if(!process.IsValid()) {
        wxPrintf("codeite-lldb: error loading core file '%s'\n", command.GetCorefile());
        NotifyExited();
        return;
    }

    // Launch the thread that will handle the LLDB process events
    m_lldbProcessEventThread =
        new LLDBProcessEventHandlerThread(this, m_debugger, m_target.GetProcess(), kDebugSessionTypeCore);
    m_lldbProcessEventThread->Start();

    // Notify codelite that the debugger started successfully
    NotifyStarted(kDebugSessionTypeCore);

    // In any case, reset the interrupt reason
    m_interruptReason = kInterruptReasonNone;

    // Since we are in 'core' session
    // immediately notify about 'stop'
    NotifyStopped();
}
Ejemplo n.º 4
0
bool LLDBDebugger::Run( const wxString &in, const wxString& out, const wxString &err, 
                        const wxArrayString& argvArr,
                        const wxArrayString& envArr,
                        const wxString &workingDirectory)
{
    if ( m_debugger.IsValid() ) {
        // Construct char** arrays
        const char** argv = (const char**)_wxArrayStringToCharPtrPtr(argvArr);
        const char** envp = (const char**)_wxArrayStringToCharPtrPtr(envArr);
        const char* pin  = in.mb_str(wxConvUTF8).data();
        const char* pout = out.mb_str(wxConvUTF8).data();
        const char* perr = err.mb_str(wxConvUTF8).data();

        const char* wd = workingDirectory.mb_str(wxConvUTF8).data();

        lldb::SBError error;
        lldb::SBListener listener = m_debugger.GetListener();
        bool isOk = m_target.Launch(listener, argv, envp, pin, pout, perr, wd, 0, false, error).IsValid();
        _deleteCharPtrPtr( const_cast<char**>(argv) );
        _deleteCharPtrPtr( const_cast<char**>(envp) );
        if ( !isOk ) {
            Cleanup();
            NotifyExited();
        }
        return isOk;
    }
    return false;
}
Ejemplo n.º 5
0
void LLDBDebugger::OnTimer(wxTimerEvent& e)
{
    if ( m_debugger.IsValid() ) {
        lldb::SBEvent lldbEvent;
        if ( m_debugger.GetListener().WaitForEvent(0, lldbEvent) ) {
            if ( lldbEvent.IsValid() ) {
                lldb::StateType state = m_target.GetProcess().GetStateFromEvent( lldbEvent );
                switch ( state ) {
                case lldb::eStateStopped:
                    NotifyBacktrace();
                    NotifyStopped();
                    break;

                case lldb::eStateConnected:
                    break;

                case lldb::eStateLaunching:
                    break;

                case lldb::eStateRunning:
                    break;

                case lldb::eStateExited:
                    Cleanup();
                    NotifyExited();
                    break;
                default:
                    break;
                }
            }
        }
    }
}
Ejemplo n.º 6
0
void LLDBDebugger::Stop(bool notifyExit)
{
    wxDELETE(m_thread);
    m_target.GetProcess().Kill();
    Cleanup();
    if ( notifyExit ) {
        NotifyExited();
    }
}
Ejemplo n.º 7
0
void CodeLiteLLDBApp::DetachDebugger(const LLDBCommand& command)
{
    // detach from the process
    wxPrintf("codelite-lldb: detaching from process\n");

    m_target.DeleteAllBreakpoints();
    m_target.DeleteAllWatchpoints();
    if(m_target.GetProcess().IsValid()) {
        // detch and 'continue'
        m_target.GetProcess().Detach(false);
    }
    NotifyExited();
}
Ejemplo n.º 8
0
bool LLDBDebugger::Run( const wxString &in, const wxString& out, const wxString &err, 
                        const wxArrayString& argvArr,
                        const wxArrayString& envArr,
                        const wxString &workingDirectory)
{
    if ( m_thread ) {
        return false;
    }
    
    if ( m_debugger.IsValid() ) {
        // Construct char** arrays
        const char** argv = (const char**)_wxArrayStringToCharPtrPtr(argvArr);
        const char** envp = (const char**)_wxArrayStringToCharPtrPtr(envArr);
        const char* pin  = in.mb_str(wxConvUTF8).data();
        const char* pout = out.mb_str(wxConvUTF8).data();
        const char* perr = err.mb_str(wxConvUTF8).data();
        const char* wd = workingDirectory.mb_str(wxConvUTF8).data();
        
        wxUnusedVar(pin);
        wxUnusedVar(pout);
        wxUnusedVar(perr);
        
        lldb::SBLaunchInfo launchInfo(argv);
        lldb::SBError error;
        
        // Set the launch flags
        launchInfo.SetLaunchFlags(lldb::eLaunchFlagStopAtEntry | lldb::eLaunchFlagLaunchInSeparateProcessGroup);
        launchInfo.SetEnvironmentEntries(envp, false);
        launchInfo.SetWorkingDirectory(wd);
        launchInfo.AddOpenFileAction(STDIN_FILENO,  pin,  true, false);
        launchInfo.AddOpenFileAction(STDERR_FILENO, perr, false, true);
        launchInfo.AddOpenFileAction(STDOUT_FILENO, pout, false, true);
        bool isOk = m_target.Launch(launchInfo, error).IsValid();
        
        //bool isOk = m_target.LaunchSimple(argv, envp, wd).IsValid();
        _deleteCharPtrPtr( const_cast<char**>(argv) );
        _deleteCharPtrPtr( const_cast<char**>(envp) );
        if ( !isOk ) {
            Cleanup();
            NotifyExited();
        }
        
        m_debugeePid = m_target.GetProcess().GetProcessID();
        m_thread = new LLDBDebuggerThread(this, m_debugger.GetListener(), m_target.GetProcess());
        m_thread->Start();
        return isOk;
    }
    return false;
}
Ejemplo n.º 9
0
void CodeLiteLLDBApp::StopDebugger(const LLDBCommand& command)
{
    CHECK_DEBUG_SESSION_RUNNING();
    NotifyExited();
}
Ejemplo n.º 10
0
void CodeLiteLLDBApp::RunDebugger(const LLDBCommand& command)
{
    if(m_debuggeePid != wxNOT_FOUND) {
        wxPrintf("codelite-lldb: another session is already in progress\n");
        return;
    }

    if(m_debugger.IsValid()) {
        m_variables.clear();
        m_watches.clear();

        // Construct char** arrays
        clCommandLineParser parser(command.GetCommandArguments());
        const char** argv = (const char**)_wxArrayStringToCharPtrPtr(parser.ToArray());
        char** penv = command.GetEnvArray();

        std::string tty_c;
        std::string workingDirectory;
        if(!command.GetRedirectTTY().IsEmpty()) {
            tty_c = command.GetRedirectTTY().mb_str(wxConvUTF8).data();
        }

        if(!command.GetWorkingDirectory().IsEmpty()) {
            workingDirectory = command.GetWorkingDirectory().mb_str(wxConvUTF8).data();
        }

        const char* ptty = tty_c.empty() ? NULL : tty_c.c_str();
        wxPrintf("codelite-lldb: running debugger. tty=%s\n", ptty);

        const char* pwd = workingDirectory.empty() ? NULL : workingDirectory.c_str();
        wxPrintf("codelite-lldb: target working directory is set to: %s\n", pwd ? pwd : "NULL");

        // wxPrintf("codelite-lldb: Environment is set to:\n");
        // print_c_array( (const char**)penv );

        wxPrintf("codelite-lldb: Arguments are set to:\n");
        print_c_array(argv);

        // Execute startup commands
        wxArrayString startupCommands = ::wxStringTokenize(command.GetStartupCommands(), "\n", wxTOKEN_STRTOK);
        for(size_t i = 0; i < startupCommands.GetCount(); ++i) {
            lldb::SBCommandReturnObject ret;
            std::string c_command = startupCommands.Item(i).Trim().mb_str(wxConvUTF8).data();
            wxPrintf("codelite-lldb: executing: '%s'\n", c_command.c_str());
            m_debugger.GetCommandInterpreter().HandleCommand(c_command.c_str(), ret);
        }

        lldb::SBError lldbError;
        lldb::SBListener listener = m_debugger.GetListener();
        lldb::SBProcess process =
            m_target.Launch(listener,
                            argv,
                            (const char**)penv,
                            ptty,
                            ptty,
                            ptty,
                            pwd,
                            lldb::eLaunchFlagLaunchInSeparateProcessGroup | lldb::eLaunchFlagStopAtEntry,
                            true,
                            lldbError);

        // bool isOk = m_target.LaunchSimple(argv, envp, wd).IsValid();
        DELETE_CHAR_PTR_PTR(const_cast<char**>(argv));
        DELETE_CHAR_PTR_PTR(penv);

        if(!process.IsValid() || !lldbError.Success()) {
            wxPrintf("codelite-lldb: error while launching process. %s\n", lldbError.GetCString());
            NotifyExited();

        } else {
            m_debuggeePid = process.GetProcessID();
            NotifyRunning();
        }
    }
}
Ejemplo n.º 11
0
void LLDBDebugger::Stop()
{
    m_target.GetProcess().Kill();
    Cleanup();
    NotifyExited();
}