예제 #1
0
파일: Driver.cpp 프로젝트: Jean-Daniel/lldb
void
Driver::ExecuteInitialCommands (bool before_file)
{
    size_t num_commands;
    std::vector<std::pair<bool, std::string> > *command_set;
    if (before_file)
        command_set = &(m_option_data.m_initial_commands);
    else
        command_set = &(m_option_data.m_after_file_commands);
    
    num_commands = command_set->size();
    SBCommandReturnObject result;
    bool old_async = GetDebugger().GetAsync();
    GetDebugger().SetAsync(false);
    for (size_t idx = 0; idx < num_commands; idx++)
    {
        bool is_file = (*command_set)[idx].first;
        const char *command = (*command_set)[idx].second.c_str();
        char command_string[PATH_MAX * 2];
        const bool dump_stream_only_if_no_immediate = true;
        const char *executed_command = command;
        if (is_file)
        {
            ::snprintf (command_string, sizeof(command_string), "command source -s %i '%s'", m_option_data.m_source_quietly, command);
            executed_command = command_string;
        }
        
        m_debugger.GetCommandInterpreter().HandleCommand (executed_command, result, false);
        if (!m_option_data.m_source_quietly || result.Succeeded() == false)
        {
            const size_t output_size = result.GetOutputSize();
            if (output_size > 0)
            {
                const char *cstr = result.GetOutput(dump_stream_only_if_no_immediate);
                if (cstr)
                    printf ("%s", cstr);
            }
            const size_t error_size = result.GetErrorSize();
            if (error_size > 0)
            {
                const char *cstr = result.GetError(dump_stream_only_if_no_immediate);
                if (cstr)
                    printf ("%s", cstr);
            }
        }
        
        if (result.Succeeded() == false)
        {
            const char *type = before_file ? "before file" : "after_file";
            if (is_file)
                ::fprintf(stderr, "Aborting %s command execution, command file: '%s' failed.\n", type, command);
            else
                ::fprintf(stderr, "Aborting %s command execution, command: '%s' failed.\n", type, command);
            break;
        }
        result.Clear();
    }
    GetDebugger().SetAsync(old_async);
}
예제 #2
0
bool
Driver::HandleIOEvent (const SBEvent &event)
{
    bool quit = false;

    const uint32_t event_type = event.GetType();

    if (event_type & IOChannel::eBroadcastBitHasUserInput)
    {
        // We got some input (i.e. a command string) from the user; pass it off to the command interpreter for
        // handling.

        const char *command_string = SBEvent::GetCStringFromEvent(event);
        if (command_string == NULL)
            command_string = "";
        SBCommandReturnObject result;
        
        // We don't want the result to bypass the OutWrite function in IOChannel, as this can result in odd
        // output orderings and problems with the prompt.
        m_debugger.GetCommandInterpreter().HandleCommand (command_string, result, true);

        if (result.GetOutputSize() > 0)
            m_io_channel_ap->OutWrite (result.GetOutput(), result.GetOutputSize(), NO_ASYNC);
            
        if (result.GetErrorSize() > 0)
            m_io_channel_ap->OutWrite (result.GetError(), result.GetErrorSize(), NO_ASYNC);

        // We are done getting and running our command, we can now clear the
        // m_waiting_for_command so we can get another one.
        m_waiting_for_command = false;

        // If our editline input reader is active, it means another input reader
        // got pushed onto the input reader and caused us to become deactivated.
        // When the input reader above us gets popped, we will get re-activated
        // and our prompt will refresh in our callback
        if (m_editline_reader.IsActive())
        {
            ReadyForCommand ();
        }
    }
    else if (event_type & IOChannel::eBroadcastBitUserInterrupt)
    {
        // This is here to handle control-c interrupts from the user.  It has not yet really been implemented.
        // TO BE DONE:  PROPERLY HANDLE CONTROL-C FROM USER
        //m_io_channel_ap->CancelInput();
        // Anything else?  Send Interrupt to process?
    }
    else if ((event_type & IOChannel::eBroadcastBitThreadShouldExit) ||
             (event_type & IOChannel::eBroadcastBitThreadDidExit))
    {
        // If the IOChannel thread is trying to go away, then it is definitely
        // time to end the debugging session.
        quit = true;
    }

    return quit;
}
예제 #3
0
// This function handles events that were broadcast by the process.
void
Driver::HandleProcessEvent (const SBEvent &event)
{
    using namespace lldb;
    const uint32_t event_type = event.GetType();

    if (event_type & SBProcess::eBroadcastBitSTDOUT)
    {
        // The process has stdout available, get it and write it out to the
        // appropriate place.
        GetProcessSTDOUT ();
    }
    else if (event_type & SBProcess::eBroadcastBitSTDERR)
    {
        // The process has stderr available, get it and write it out to the
        // appropriate place.
        GetProcessSTDERR ();
    }
    else if (event_type & SBProcess::eBroadcastBitStateChanged)
    {
        // Drain all stout and stderr so we don't see any output come after
        // we print our prompts
        GetProcessSTDOUT ();
        GetProcessSTDERR ();
        // Something changed in the process;  get the event and report the process's current status and location to
        // the user.
        StateType event_state = SBProcess::GetStateFromEvent (event);
        if (event_state == eStateInvalid)
            return;

        SBProcess process (SBProcess::GetProcessFromEvent (event));
        assert (process.IsValid());

        switch (event_state)
        {
        case eStateInvalid:
        case eStateUnloaded:
        case eStateConnected:
        case eStateAttaching:
        case eStateLaunching:
        case eStateStepping:
        case eStateDetached:
            {
                char message[1024];
                int message_len = ::snprintf (message, sizeof(message), "Process %llu %s\n", process.GetProcessID(),
                                              m_debugger.StateAsCString (event_state));
                m_io_channel_ap->OutWrite(message, message_len, ASYNC);
            }
            break;

        case eStateRunning:
            // Don't be chatty when we run...
            break;

        case eStateExited:
            {
                SBCommandReturnObject result;
                m_debugger.GetCommandInterpreter().HandleCommand("process status", result, false);
                m_io_channel_ap->ErrWrite (result.GetError(), result.GetErrorSize(), ASYNC);
                m_io_channel_ap->OutWrite (result.GetOutput(), result.GetOutputSize(), ASYNC);
            }
            break;

        case eStateStopped:
        case eStateCrashed:
        case eStateSuspended:
            // Make sure the program hasn't been auto-restarted:
            if (SBProcess::GetRestartedFromEvent (event))
            {
                // FIXME: Do we want to report this, or would that just be annoyingly chatty?
                char message[1024];
                int message_len = ::snprintf (message, sizeof(message), "Process %llu stopped and was programmatically restarted.\n",
                                              process.GetProcessID());
                m_io_channel_ap->OutWrite(message, message_len, ASYNC);
            }
            else
            {
                if (GetDebugger().GetSelectedTarget() == process.GetTarget())
                {
                    SBCommandReturnObject result;
                    UpdateSelectedThread ();
                    m_debugger.GetCommandInterpreter().HandleCommand("process status", result, false);
                    m_io_channel_ap->ErrWrite (result.GetError(), result.GetErrorSize(), ASYNC);
                    m_io_channel_ap->OutWrite (result.GetOutput(), result.GetOutputSize(), ASYNC);
                }
                else
                {
                    SBStream out_stream;
                    uint32_t target_idx = GetDebugger().GetIndexOfTarget(process.GetTarget());
                    if (target_idx != UINT32_MAX)
                        out_stream.Printf ("Target %d: (", target_idx);
                    else
                        out_stream.Printf ("Target <unknown index>: (");
                    process.GetTarget().GetDescription (out_stream, eDescriptionLevelBrief);
                    out_stream.Printf (") stopped.\n");
                    m_io_channel_ap->OutWrite (out_stream.GetData(), out_stream.GetSize(), ASYNC);
                }
            }
            break;
        }
    }
}