forked from OSchip/llvm-project
Fixed SBTarget attach calls to properly deal with being connected to a remotely
connected process connection. Also added support for more kinds of continue packet when multiple threads need to continue where some want to continue with signals. llvm-svn: 133785
This commit is contained in:
parent
1da39282ec
commit
0c74e78d63
|
@ -479,15 +479,15 @@ SBProcess::GetAddressByteSize () const
|
|||
SBError
|
||||
SBProcess::Continue ()
|
||||
{
|
||||
Mutex::Locker api_locker (m_opaque_sp->GetTarget().GetAPIMutex());
|
||||
|
||||
LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API));
|
||||
if (log)
|
||||
log->Printf ("SBProcess(%p)::Continue ()...", m_opaque_sp.get());
|
||||
|
||||
SBError sb_error;
|
||||
if (IsValid())
|
||||
if (m_opaque_sp)
|
||||
{
|
||||
Mutex::Locker api_locker (m_opaque_sp->GetTarget().GetAPIMutex());
|
||||
|
||||
Error error (m_opaque_sp->Resume());
|
||||
if (error.Success())
|
||||
{
|
||||
|
@ -545,7 +545,7 @@ SBError
|
|||
SBProcess::Stop ()
|
||||
{
|
||||
SBError sb_error;
|
||||
if (IsValid())
|
||||
if (m_opaque_sp)
|
||||
{
|
||||
Mutex::Locker api_locker (m_opaque_sp->GetTarget().GetAPIMutex());
|
||||
sb_error.SetError (m_opaque_sp->Halt());
|
||||
|
|
|
@ -282,11 +282,43 @@ SBTarget::AttachToProcessWithID
|
|||
if (m_opaque_sp)
|
||||
{
|
||||
Mutex::Locker api_locker (m_opaque_sp->GetAPIMutex());
|
||||
if (listener.IsValid())
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (listener.ref()));
|
||||
|
||||
StateType state = eStateInvalid;
|
||||
sb_process.SetProcess (m_opaque_sp->GetProcessSP());
|
||||
if (sb_process.IsValid())
|
||||
{
|
||||
state = sb_process->GetState();
|
||||
|
||||
if (sb_process->IsAlive() && state != eStateConnected)
|
||||
{
|
||||
if (state == eStateAttaching)
|
||||
error.SetErrorString ("process attach is in progress");
|
||||
else
|
||||
error.SetErrorString ("a process is already being debugged");
|
||||
sb_process.Clear();
|
||||
return sb_process;
|
||||
}
|
||||
}
|
||||
|
||||
if (state == eStateConnected)
|
||||
{
|
||||
// If we are already connected, then we have already specified the
|
||||
// listener, so if a valid listener is supplied, we need to error out
|
||||
// to let the client know.
|
||||
if (listener.IsValid())
|
||||
{
|
||||
error.SetErrorString ("process is connected and already has a listener, pass empty listener");
|
||||
sb_process.Clear();
|
||||
return sb_process;
|
||||
}
|
||||
}
|
||||
else
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (m_opaque_sp->GetDebugger().GetListener()));
|
||||
|
||||
{
|
||||
if (listener.IsValid())
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (listener.ref()));
|
||||
else
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (m_opaque_sp->GetDebugger().GetListener()));
|
||||
}
|
||||
|
||||
if (sb_process.IsValid())
|
||||
{
|
||||
|
@ -323,10 +355,42 @@ SBTarget::AttachToProcessWithName
|
|||
{
|
||||
Mutex::Locker api_locker (m_opaque_sp->GetAPIMutex());
|
||||
|
||||
if (listener.IsValid())
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (listener.ref()));
|
||||
StateType state = eStateInvalid;
|
||||
sb_process.SetProcess (m_opaque_sp->GetProcessSP());
|
||||
if (sb_process.IsValid())
|
||||
{
|
||||
state = sb_process->GetState();
|
||||
|
||||
if (sb_process->IsAlive() && state != eStateConnected)
|
||||
{
|
||||
if (state == eStateAttaching)
|
||||
error.SetErrorString ("process attach is in progress");
|
||||
else
|
||||
error.SetErrorString ("a process is already being debugged");
|
||||
sb_process.Clear();
|
||||
return sb_process;
|
||||
}
|
||||
}
|
||||
|
||||
if (state == eStateConnected)
|
||||
{
|
||||
// If we are already connected, then we have already specified the
|
||||
// listener, so if a valid listener is supplied, we need to error out
|
||||
// to let the client know.
|
||||
if (listener.IsValid())
|
||||
{
|
||||
error.SetErrorString ("process is connected and already has a listener, pass empty listener");
|
||||
sb_process.Clear();
|
||||
return sb_process;
|
||||
}
|
||||
}
|
||||
else
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (m_opaque_sp->GetDebugger().GetListener()));
|
||||
{
|
||||
if (listener.IsValid())
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (listener.ref()));
|
||||
else
|
||||
sb_process.SetProcess (m_opaque_sp->CreateProcess (m_opaque_sp->GetDebugger().GetListener()));
|
||||
}
|
||||
|
||||
if (sb_process.IsValid())
|
||||
{
|
||||
|
|
|
@ -901,7 +901,6 @@ ProcessGDBRemote::DoResume ()
|
|||
|
||||
if (continue_packet_error)
|
||||
{
|
||||
continue_packet_error = false;
|
||||
// Either no vCont support, or we tried to use part of the vCont
|
||||
// packet that wasn't supported by the remote GDB server.
|
||||
// We need to try and make a simple packet that can do our continue
|
||||
|
@ -916,7 +915,8 @@ ProcessGDBRemote::DoResume ()
|
|||
{
|
||||
// All threads are resuming...
|
||||
m_gdb_comm.SetCurrentThreadForRun (-1);
|
||||
continue_packet.PutChar ('c');
|
||||
continue_packet.PutChar ('c');
|
||||
continue_packet_error = false;
|
||||
}
|
||||
else if (num_continue_c_tids == 1 &&
|
||||
num_continue_C_tids == 0 &&
|
||||
|
@ -926,57 +926,60 @@ ProcessGDBRemote::DoResume ()
|
|||
// Only one thread is continuing
|
||||
m_gdb_comm.SetCurrentThreadForRun (m_continue_c_tids.front());
|
||||
continue_packet.PutChar ('c');
|
||||
}
|
||||
else
|
||||
{
|
||||
// We can't represent this continue packet....
|
||||
continue_packet_error = true;
|
||||
continue_packet_error = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (!continue_packet_error && num_continue_C_tids > 0)
|
||||
if (continue_packet_error && num_continue_C_tids > 0)
|
||||
{
|
||||
if (num_continue_C_tids == num_threads)
|
||||
if ((num_continue_C_tids + num_continue_c_tids) == num_threads &&
|
||||
num_continue_C_tids > 0 &&
|
||||
num_continue_s_tids == 0 &&
|
||||
num_continue_S_tids == 0 )
|
||||
{
|
||||
const int continue_signo = m_continue_C_tids.front().second;
|
||||
// Only one thread is continuing
|
||||
if (num_continue_C_tids > 1)
|
||||
{
|
||||
for (size_t i=1; i<num_threads; ++i)
|
||||
// More that one thread with a signal, yet we don't have
|
||||
// vCont support and we are being asked to resume each
|
||||
// thread with a signal, we need to make sure they are
|
||||
// all the same signal, or we can't issue the continue
|
||||
// accurately with the current support...
|
||||
if (num_continue_C_tids > 1)
|
||||
{
|
||||
if (m_continue_C_tids[i].second != continue_signo)
|
||||
continue_packet_error = true;
|
||||
continue_packet_error = false;
|
||||
for (size_t i=1; i<m_continue_C_tids.size(); ++i)
|
||||
{
|
||||
if (m_continue_C_tids[i].second != continue_signo)
|
||||
continue_packet_error = true;
|
||||
}
|
||||
}
|
||||
if (!continue_packet_error)
|
||||
m_gdb_comm.SetCurrentThreadForRun (-1);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Set the continue thread ID
|
||||
continue_packet_error = false;
|
||||
m_gdb_comm.SetCurrentThreadForRun (m_continue_C_tids.front().first);
|
||||
}
|
||||
if (!continue_packet_error)
|
||||
{
|
||||
// Add threads continuing with the same signo...
|
||||
m_gdb_comm.SetCurrentThreadForRun (-1);
|
||||
continue_packet.Printf("C%2.2x", continue_signo);
|
||||
}
|
||||
}
|
||||
else if (num_continue_c_tids == 0 &&
|
||||
num_continue_C_tids == 1 &&
|
||||
num_continue_s_tids == 0 &&
|
||||
num_continue_S_tids == 0 )
|
||||
{
|
||||
// Only one thread is continuing with signal
|
||||
m_gdb_comm.SetCurrentThreadForRun (m_continue_C_tids.front().first);
|
||||
continue_packet.Printf("C%2.2x", m_continue_C_tids.front().second);
|
||||
}
|
||||
else
|
||||
{
|
||||
// We can't represent this continue packet....
|
||||
continue_packet_error = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (!continue_packet_error && num_continue_s_tids > 0)
|
||||
if (continue_packet_error && num_continue_s_tids > 0)
|
||||
{
|
||||
if (num_continue_s_tids == num_threads)
|
||||
{
|
||||
// All threads are resuming...
|
||||
m_gdb_comm.SetCurrentThreadForRun (-1);
|
||||
continue_packet.PutChar ('s');
|
||||
continue_packet.PutChar ('s');
|
||||
continue_packet_error = false;
|
||||
}
|
||||
else if (num_continue_c_tids == 0 &&
|
||||
num_continue_C_tids == 0 &&
|
||||
|
@ -986,11 +989,7 @@ ProcessGDBRemote::DoResume ()
|
|||
// Only one thread is stepping
|
||||
m_gdb_comm.SetCurrentThreadForRun (m_continue_s_tids.front());
|
||||
continue_packet.PutChar ('s');
|
||||
}
|
||||
else
|
||||
{
|
||||
// We can't represent this continue packet....
|
||||
continue_packet_error = true;
|
||||
continue_packet_error = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1000,6 +999,7 @@ ProcessGDBRemote::DoResume ()
|
|||
{
|
||||
const int step_signo = m_continue_S_tids.front().second;
|
||||
// Are all threads trying to step with the same signal?
|
||||
continue_packet_error = false;
|
||||
if (num_continue_S_tids > 1)
|
||||
{
|
||||
for (size_t i=1; i<num_threads; ++i)
|
||||
|
@ -1023,11 +1023,7 @@ ProcessGDBRemote::DoResume ()
|
|||
// Only one thread is stepping with signal
|
||||
m_gdb_comm.SetCurrentThreadForRun (m_continue_S_tids.front().first);
|
||||
continue_packet.Printf("S%2.2x", m_continue_S_tids.front().second);
|
||||
}
|
||||
else
|
||||
{
|
||||
// We can't represent this continue packet....
|
||||
continue_packet_error = true;
|
||||
continue_packet_error = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue