Clinton
Clinton

Reputation: 23135

Check if any threads remain at end of test

Is there a way to check if any "user" threads are running. I'd like to put this in the [TestCleanup] method, failing the test if a test hasn't joined all the threads it started.

I figured just listing all the currently running threads wouldn't help, as there's probably for example, garbage collection threads that start at indeterminate times. So I basically want the threads that aren't just associated with the runtime.

Upvotes: 2

Views: 298

Answers (2)

Patrick
Patrick

Reputation: 697

I would recommend taking a look at the Microsoft.Diagnostics.Runtime library (Nuget). Specifically the CLR capabilities. You can get a list of all threads with stacktraces with the following code

using (DataTarget target = DataTarget.AttachToProcess(Process.GetCurrentProcess().Id, 5000, AttachFlag.Passive))
{
    ClrRuntime runtime = target.ClrVersions.First().CreateRuntime();
    return new runtime.Threads;
}

Upvotes: 1

tmaj
tmaj

Reputation: 34987

There are some really valid points in the comments section of the question but you could

  1. Try and see if thread counting works for you without worrying about
  2. Try TryStartNoGCRegion:
    GC.TryStartNoGCRegion(1024*1204*10);
    var count = System.Diagnostics.Process.GetCurrentProcess().Threads.Count;
    GC.EndNoGCRegion();
    

Here's a trivial example.

public static void Main()
{
    int GetThreadCount() {
        GC.TryStartNoGCRegion(1024*1204*10);
        var count = System.Diagnostics.Process.GetCurrentProcess().Threads.Count;
        GC.EndNoGCRegion();
        return count;
    }


    var count1 = GetThreadCount();
    Console.WriteLine($"Headcount at (in?) the beginning: {count1}");

    var t1 = new Thread(() => {       
            Thread.Sleep(1000);
        });
    t1.Start();

    var count2 = GetThreadCount();
    Console.WriteLine($"Headcount later: {count2}");

    if (count2 != count1 ) {
        Console.WriteLine("Oh no! Threads running!");
    }

    t1.Join();

    var count3 = GetThreadCount();
    Console.WriteLine($"Headcount even later: {count3}");

    if (count3 != count1 ) {
        Console.WriteLine("Oh no! Threads running!");
    } else {
            Console.WriteLine("Phew. Everybody Joined the party.");
    }

    Console.ReadLine();
}

Output

// .NETCoreApp,Version=v3.0
Headcount at (in?) the beginning: 10
Headcount later: 11
Oh no! Threads running!
The thread 9620 has exited with code 0 (0x0).
Headcount even later: 10
Phew. Everybody Joined the party.

Upvotes: 1

Related Questions