Skip to content

Runtime crash caused by Thread internal calls called on resurrected Thread #107473

Description

@jkotas

Deterministic repro

  1. Build a private coreclr.dll with Sleep(1000) added here:
  2. Enable page heap for corerun.exe using gflags
  3. Compile and run the following test using corerun.exe:
using System;
using System.Threading;
using System.Runtime.CompilerServices;

Helper.Initialize();

new Thread(Work).Start();

GC.Collect();
GC.WaitForPendingFinalizers();

Thread.Sleep(3000);
	
static void Work()
{
   for (;;)
   {
       if (Helper.ResurectedThread != null)
       {
           Helper.ResurectedThread.DisableComObjectEagerCleanup();
       }
   }
}

class Helper
{
    public static volatile Thread ResurectedThread;

    Thread _thread;
 
    [MethodImpl(MethodImplOptions.NoInlining)]
    public static void Initialize() => GC.KeepAlive(new Helper());

    Helper()
    {
        _thread = new Thread(() => { });
        _thread.Start();
        _thread.Join();
    }

    ~Helper()
    {
        ResurectedThread = _thread;
    }
}

(It is also possible to build non-deterministic repro that reproduces the crash on shipping bits.)

Actual result

Assert failure(PID 23336 [0x00005b28], Thread: 21216 [0x52e0]): Consistency check failed: AV in clr at this callstack:
------
CORECLR! DoJoin + 0x2C3 (0x00007ffa`175c9d83)
CORECLR! ThreadNative_Join + 0x15B (0x00007ffa`175cd87b)
-----
.AV on tid=0x52e0 (21216), cxr=0000009F9477E6C0, exr=0000009F9477EBB0

The crash is caused by use-after-free of the unmanaged Thread object.

Expected result

No runtime crash. C# code that does not used unsafe blocks and that does not call any memory unsafe APIs should not lead to runtime crash.

Metadata

Metadata

Assignees

Type

No type

Projects

Status
No status

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions