Skip to content

The dead thread reported in ICorProfilerInfo4::EnumThreads #60566

Closed
@ww898

Description

@ww898

Description

As described in documentation ICorProfilerInfo::ForceGC requires separate native thread for working. The thread will be finished by my profiler during detaching procedure. And I see it in lldb. However, after attaching again to the process the ICorProfilerInfo4::EnumThreads call returns me the already dead thread where ICorProfilerInfo::ForceGC was called sometime ago .

It's the important problem because the thread id can be already reused for a new native thread.

My investigation shows the CoreCLR keeps the static list of managed threads. and only alive threads will be returned in ICorProfilerInfo4::EnumThreads. On the other hand the ICorProfilerInfo::ForceGC adds current thread in this list.

Reproduction Steps

  • Create following "hello world" application:
using System;
namespace test { class Program { static void Main(string[] args) {
  Console.WriteLine("Hello World!");
  Console.ReadLine();
}}}
  • Publish it as a self contained application and run it in separate console
  • Attach and detach a profiler which use ICorProfilerInfo::ForceGC and dump somewhere the thread id after the call.
  • Attach lldb and dump the thread list. Check that the thread id is not in the list.
  • Attach a profiler which use ICorProfilerInfo4::EnumThreads and see that the dead thread id is in the list of managed threads.

Actual behavior

The native thread id which interesting us is 1BCF69.

The part of the first profiler log;

00000000001BCF69 0 0000000000000000 GCCQ::ForceGcThread
00000000001BCF69 0 0000000000000000 GCCQ::ForceGc // <-- ICorProfilerInfo::ForceGC started
00000000001BCF69 1 000000014180AA00 MProf::GarbageCollectionStarted gcNumber=0 reason=induced c=5
00000000001BCF69 1 000000014180AA00 GCCQ::OnStarted gcNumber=0 gcState=normal
00000000001BCF69 1 000000014180AA00 MDG2::FlushMetadata
00000000001BCF69 1 000000014180AA00 MDG2::FlushMetadata res=ok
00000000001BCF69 1 000000014180AA00 MProf::GarbageCollectionStarted gcNumber=0 res=ok
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122F650
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122FA50
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122FC40
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122FCC0
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122FD40
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122FDC0
00000000001BCF69 1 000000014180AA00 MProf::FinalizeableObjectQueued f=C oid=000000010122FE48
00000000001BCF69 1 000000014180AA00 MProf::SurvivingReferences2 c=1
00000000001BCF69 1 000000014180AA00 MProf::SurvivingReferences2 c=91
00000000001BCF69 1 000000014180AA00 MProf::RootReferences2 c=42
00000000001BCF69 1 000000014180AA00 BProf::RootReferences c=42
00000000001BCF69 1 000000014180AA00 MProf::ObjectReferences oid=0000000101220048 cid=0000000280E48C80 c=0
00000000001BCF69 1 000000014180AA00 MProf::GarbageCollectionFinished gcNumber=0
00000000001BCF69 1 000000014180AA00 MProf::GarbageCollectionFinished gcNumber=0 res=ok
00000000001BCF69 1 000000014180AA00 GCCQ::OnFinished gcNumber=0 gcState=normal
00000000001BCF69 0 0000000000000000 GCCQ::ForceGc res=ok  // <-- ICorProfilerInfo::ForceGC finished
00000000001BCF69 0 0000000000000000 GCCQ::ForceGcThread res=ok

lldb check:

(lldb) thread list
Process 52251 stopped
* thread #1: tid = 0x1bce01, 0x0000000194e1a538 libsystem_kernel.dylib`read + 8, queue = 'com.apple.main-thread', stop reason = signal SIGSTOP
  thread #2: tid = 0x1bce03, 0x0000000194e19954 libsystem_kernel.dylib`mach_msg_trap + 8
  thread #3: tid = 0x1bce04, 0x0000000194e1f8cc libsystem_kernel.dylib`kevent + 8
  thread #4: tid = 0x1bce05, 0x0000000194e21ad0 libsystem_kernel.dylib`poll + 8
  thread #5: tid = 0x1bce06, 0x0000000194e1a3d4 libsystem_kernel.dylib`__open + 8
  thread #6: tid = 0x1bce07, 0x0000000194e1d0c0 libsystem_kernel.dylib`__psynch_cvwait + 8
  thread #7: tid = 0x1bce08, 0x0000000194e1d0c0 libsystem_kernel.dylib`__psynch_cvwait + 8
  thread #8: tid = 0x1bce0a, 0x0000000194e1a538 libsystem_kernel.dylib`read + 8
  thread #9: tid = 0x1bcf5c, 0x0000000194e1d0c0 libsystem_kernel.dylib`__psynch_cvwait + 8
  thread #10: tid = 0x1bcf5d, 0x0000000194e1b604 libsystem_kernel.dylib`__workq_kernreturn + 8

The part of the second profiler log:

00000000001BCE05 1 0000000000000000 BProf::ProfilerAttachComplete // <--- ICorProfilerCallback3::ProfilerAttachComplete
00000000001BCE05 1 0000000000000000 BProf::ProfilerAttachComplete tid=000000015200C000
00000000001BCE05 1 0000000000000000 BPPool::DoThreadRecovered tid=000000015200C000 osTid=001BCE01
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=000000015200C000 osTid=001BCE01 (1822209)
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=000000015200C000 id=00000001
00000000001BCE05 1 0000000000000000 BProf::ProfilerAttachComplete tid=000000015200C600
00000000001BCE05 1 0000000000000000 BPPool::DoThreadRecovered tid=000000015200C600 osTid=001BCE08
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=000000015200C600 osTid=001BCE08 (1822216)
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=000000015200C600 id=00000002
00000000001BCE05 1 0000000000000000 BProf::ProfilerAttachComplete tid=0000000131808200
00000000001BCE05 1 0000000000000000 BPPool::DoThreadRecovered tid=0000000131808200 osTid=001BCE0A
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=0000000131808200 osTid=001BCE0A (1822218)
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=0000000131808200 id=00000003
00000000001BCE05 1 0000000000000000 BProf::ProfilerAttachComplete tid=000000014180AA00 // <--- The dead thread reported here!!!
00000000001BCE05 1 0000000000000000 BPPool::DoThreadRecovered tid=000000014180AA00 osTid=001BCF69
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=000000014180AA00 osTid=001BCF69 (1822569)
00000000001BCE05 1 0000000000000000 BPool::DoThreadRecovered tid=000000014180AA00 id=00000004
00000000001BCE05 1 0000000000000000 ERROR: No such thread

Configuration

I reproduced the issue on macOS:

  • Catalina x64: .NET v5.0.402 x64
  • Big Sur x64: .NET v5.0.402 x64 / v6.0-rc2 x64
  • Monterey arm64: .NET v5.0.402 x64 + Rosetta2 / v6.0-rc2 x64 + Rosetta2 / v6.0-rc2 arm64

The Linux x64/arm64 versions work properly.

Metadata

Metadata

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions