Browse Source

Thread now has only one terminating event: Thread.Exited

git-svn-id: svn://svn.sharpdevelop.net/sharpdevelop/trunk@3131 1ccf3a8d-04fe-1044-b7c0-cef0b8235c61
shortcuts
David Srbecký 18 years ago
parent
commit
b30d1d7366
  1. 2
      src/AddIns/Misc/Debugger/Debugger.AddIn/Project/Src/Pads/RunningThreadsPad.cs
  2. 4
      src/AddIns/Misc/Debugger/Debugger.Core/Project/Src/Control/Process-Threads.cs
  3. 64
      src/AddIns/Misc/Debugger/Debugger.Core/Project/Src/Control/Thread.cs
  4. 2
      src/AddIns/Misc/Debugger/Debugger.Core/Project/Src/Internal/ManagedCallback.cs
  5. 26
      src/AddIns/Misc/Debugger/Debugger.Tests/Project/Src/TestPrograms/MainThreadExit.cs

2
src/AddIns/Misc/Debugger/Debugger.AddIn/Project/Src/Pads/RunningThreadsPad.cs

@ -164,7 +164,7 @@ namespace ICSharpCode.SharpDevelop.Gui.Pads
thread.NameChanged += delegate { thread.NameChanged += delegate {
RefreshThread(thread); RefreshThread(thread);
}; };
thread.Expired += delegate { thread.Exited += delegate {
RemoveThread(thread); RemoveThread(thread);
}; };
} }

4
src/AddIns/Misc/Debugger/Debugger.Core/Project/Src/Control/Process-Threads.cs

@ -39,7 +39,7 @@ namespace Debugger
get { get {
List<Thread> threads = new List<Thread>(); List<Thread> threads = new List<Thread>();
foreach(Thread thread in threadCollection) { foreach(Thread thread in threadCollection) {
if (!thread.HasExpired) { if (!thread.HasExited) {
threads.Add(thread); threads.Add(thread);
} }
} }
@ -64,7 +64,7 @@ namespace Debugger
threadCollection.Add(thread); threadCollection.Add(thread);
OnThreadStarted(thread); OnThreadStarted(thread);
thread.NativeThreadExited += delegate { thread.Exited += delegate {
threadCollection.Remove(thread); threadCollection.Remove(thread);
}; };
} }

64
src/AddIns/Misc/Debugger/Debugger.Core/Project/Src/Control/Thread.cs

@ -21,41 +21,33 @@ namespace Debugger
uint id; uint id;
ICorDebugThread corThread; ICorDebugThread corThread;
bool hasExited = false;
List<Stepper> steppers = new List<Stepper>(); List<Stepper> steppers = new List<Stepper>();
StackFrame selectedStackFrame;
Exception currentException; Exception currentException;
DebuggeeState currentException_DebuggeeState; DebuggeeState currentException_DebuggeeState;
ExceptionType currentExceptionType; ExceptionType currentExceptionType;
bool currentExceptionIsUnhandled; bool currentExceptionIsUnhandled;
bool hasExpired = false;
bool nativeThreadExited = false;
StackFrame selectedStackFrame;
public event EventHandler Expired;
public event EventHandler<ThreadEventArgs> NativeThreadExited;
public event EventHandler<ThreadEventArgs> NameChanged; public event EventHandler<ThreadEventArgs> NameChanged;
public event EventHandler<ThreadEventArgs> Exited;
public bool HasExpired {
get {
return hasExpired;
}
}
[Debugger.Tests.Ignore] [Debugger.Tests.Ignore]
public Process Process { public Process Process {
get { get { return process; }
return process;
}
} }
[Debugger.Tests.Ignore] [Debugger.Tests.Ignore]
public uint ID { public uint ID {
get{ get{ return id; }
return id; }
}
public bool HasExited {
get { return hasExited; }
private set { hasExited = value; }
} }
/// <summary> From time to time the thread may be in invalid state. </summary> /// <summary> From time to time the thread may be in invalid state. </summary>
@ -76,8 +68,8 @@ namespace Debugger
internal ICorDebugThread CorThread { internal ICorDebugThread CorThread {
get { get {
if (nativeThreadExited) { if (hasExited) {
throw new DebuggerException("Native thread has exited"); throw new DebuggerException("Thread has exited");
} }
return corThread; return corThread;
} }
@ -90,37 +82,23 @@ namespace Debugger
this.id = CorThread.ID; this.id = CorThread.ID;
} }
void Expire() internal void NotifyExited()
{ {
System.Diagnostics.Debug.Assert(!this.hasExpired); if (this.hasExited) throw new DebuggerException("Already exited");
process.TraceMessage("Thread " + this.ID + " expired"); process.TraceMessage("Thread " + this.ID + " exited");
this.hasExpired = true;
OnExpired(new ThreadEventArgs(this));
if (process.SelectedThread == this) { if (process.SelectedThread == this) {
process.SelectedThread = null; process.SelectedThread = null;
} }
}
protected virtual void OnExpired(EventArgs e)
{
if (Expired != null) {
Expired(this, e);
}
}
internal void NotifyNativeThreadExited()
{
if (!this.hasExpired) Expire();
nativeThreadExited = true; this.HasExited = true;
OnNativeThreadExited(new ThreadEventArgs(this)); OnExited(new ThreadEventArgs(this));
} }
protected virtual void OnNativeThreadExited(ThreadEventArgs e) protected virtual void OnExited(ThreadEventArgs e)
{ {
if (NativeThreadExited != null) { if (Exited != null) {
NativeThreadExited(this, e); Exited(this, e);
} }
} }

2
src/AddIns/Misc/Debugger/Debugger.Core/Project/Src/Internal/ManagedCallback.cs

@ -408,7 +408,7 @@ namespace Debugger
// It seems that ICorDebugThread is still not dead and can be used // It seems that ICorDebugThread is still not dead and can be used
EnterCallback(PausedReason.Other, "ExitThread " + pThread.ID, pThread); EnterCallback(PausedReason.Other, "ExitThread " + pThread.ID, pThread);
process.GetThread(pThread).NotifyNativeThreadExited(); process.GetThread(pThread).NotifyExited();
try { try {
ExitCallback(); ExitCallback();

26
src/AddIns/Misc/Debugger/Debugger.Tests/Project/Src/TestPrograms/MainThreadExit.cs

@ -63,7 +63,7 @@ namespace Debugger.Tests {
<CurrentException>null</CurrentException> <CurrentException>null</CurrentException>
<CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled> <CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled>
<CurrentExceptionType>0</CurrentExceptionType> <CurrentExceptionType>0</CurrentExceptionType>
<HasExpired>False</HasExpired> <HasExited>False</HasExited>
<IsAtSafePoint>True</IsAtSafePoint> <IsAtSafePoint>True</IsAtSafePoint>
<IsInValidState>True</IsInValidState> <IsInValidState>True</IsInValidState>
<IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative> <IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative>
@ -73,25 +73,24 @@ namespace Debugger.Tests {
</Name> </Name>
<OldestStackFrame>Debugger.Tests.TestPrograms.MainThreadExit.Main</OldestStackFrame> <OldestStackFrame>Debugger.Tests.TestPrograms.MainThreadExit.Main</OldestStackFrame>
<Priority>Normal</Priority> <Priority>Normal</Priority>
<RuntimeValue exception="Thread has not started jet" /> <RuntimeValue>? = {System.Threading.Thread}</RuntimeValue>
<SelectedStackFrame>Debugger.Tests.TestPrograms.MainThreadExit.Main</SelectedStackFrame> <SelectedStackFrame>Debugger.Tests.TestPrograms.MainThreadExit.Main</SelectedStackFrame>
<Suspended>False</Suspended> <Suspended>False</Suspended>
</Item> </Item>
<Item Type="Thread" ToString="Thread Name = Suspended = False"> <Item Type="Thread" ToString="Thread Name = Worker thread Suspended = False">
<CurrentException>null</CurrentException> <CurrentException>null</CurrentException>
<CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled> <CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled>
<CurrentExceptionType>0</CurrentExceptionType> <CurrentExceptionType>0</CurrentExceptionType>
<HasExpired>False</HasExpired> <HasExited>False</HasExited>
<IsAtSafePoint>False</IsAtSafePoint> <IsAtSafePoint>False</IsAtSafePoint>
<IsInValidState>True</IsInValidState> <IsInValidState>True</IsInValidState>
<IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative> <IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative>
<MostRecentStackFrame>System.Threading.ThreadHelper.ThreadStart</MostRecentStackFrame> <MostRecentStackFrame>System.Threading.ThreadHelper.ThreadStart</MostRecentStackFrame>
<MostRecentStackFrameWithLoadedSymbols>null</MostRecentStackFrameWithLoadedSymbols> <MostRecentStackFrameWithLoadedSymbols>null</MostRecentStackFrameWithLoadedSymbols>
<Name> <Name>Worker thread</Name>
</Name>
<OldestStackFrame>System.Threading.ThreadHelper.ThreadStart</OldestStackFrame> <OldestStackFrame>System.Threading.ThreadHelper.ThreadStart</OldestStackFrame>
<Priority>Normal</Priority> <Priority>Normal</Priority>
<RuntimeValue exception="Thread has not started jet" /> <RuntimeValue>? = {System.Threading.Thread}</RuntimeValue>
<SelectedStackFrame>null</SelectedStackFrame> <SelectedStackFrame>null</SelectedStackFrame>
<Suspended>False</Suspended> <Suspended>False</Suspended>
</Item> </Item>
@ -103,7 +102,7 @@ namespace Debugger.Tests {
<CurrentException>null</CurrentException> <CurrentException>null</CurrentException>
<CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled> <CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled>
<CurrentExceptionType>0</CurrentExceptionType> <CurrentExceptionType>0</CurrentExceptionType>
<HasExpired>False</HasExpired> <HasExited>False</HasExited>
<IsAtSafePoint>False</IsAtSafePoint> <IsAtSafePoint>False</IsAtSafePoint>
<IsInValidState>False</IsInValidState> <IsInValidState>False</IsInValidState>
<IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative> <IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative>
@ -113,25 +112,24 @@ namespace Debugger.Tests {
</Name> </Name>
<OldestStackFrame>null</OldestStackFrame> <OldestStackFrame>null</OldestStackFrame>
<Priority>Normal</Priority> <Priority>Normal</Priority>
<RuntimeValue exception="Thread has not started jet" /> <RuntimeValue exception="The state of the thread is invalid. (Exception from HRESULT: 0x8013132D)" />
<SelectedStackFrame>null</SelectedStackFrame> <SelectedStackFrame>null</SelectedStackFrame>
<Suspended>False</Suspended> <Suspended>False</Suspended>
</Item> </Item>
<Item Type="Thread" ToString="Thread Name = Suspended = False"> <Item Type="Thread" ToString="Thread Name = Worker thread Suspended = False">
<CurrentException>null</CurrentException> <CurrentException>null</CurrentException>
<CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled> <CurrentExceptionIsUnhandled>False</CurrentExceptionIsUnhandled>
<CurrentExceptionType>0</CurrentExceptionType> <CurrentExceptionType>0</CurrentExceptionType>
<HasExpired>False</HasExpired> <HasExited>False</HasExited>
<IsAtSafePoint>True</IsAtSafePoint> <IsAtSafePoint>True</IsAtSafePoint>
<IsInValidState>True</IsInValidState> <IsInValidState>True</IsInValidState>
<IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative> <IsMostRecentStackFrameNative>False</IsMostRecentStackFrameNative>
<MostRecentStackFrame>System.Threading.WaitHandle.WaitOne</MostRecentStackFrame> <MostRecentStackFrame>System.Threading.WaitHandle.WaitOne</MostRecentStackFrame>
<MostRecentStackFrameWithLoadedSymbols>Debugger.Tests.TestPrograms.MainThreadExit.WaitForALongTime</MostRecentStackFrameWithLoadedSymbols> <MostRecentStackFrameWithLoadedSymbols>Debugger.Tests.TestPrograms.MainThreadExit.WaitForALongTime</MostRecentStackFrameWithLoadedSymbols>
<Name> <Name>Worker thread</Name>
</Name>
<OldestStackFrame>System.Threading.ThreadHelper.ThreadStart</OldestStackFrame> <OldestStackFrame>System.Threading.ThreadHelper.ThreadStart</OldestStackFrame>
<Priority>Normal</Priority> <Priority>Normal</Priority>
<RuntimeValue exception="Thread has not started jet" /> <RuntimeValue>? = {System.Threading.Thread}</RuntimeValue>
<SelectedStackFrame>Debugger.Tests.TestPrograms.MainThreadExit.WaitForALongTime</SelectedStackFrame> <SelectedStackFrame>Debugger.Tests.TestPrograms.MainThreadExit.WaitForALongTime</SelectedStackFrame>
<Suspended>False</Suspended> <Suspended>False</Suspended>
</Item> </Item>

Loading…
Cancel
Save