Skip to content

Commit b20632e

Browse files
authored
Adding GetAppDomainData cDAC API (#117827)
* adding GetAppDomainData cDAC API
1 parent 27c8534 commit b20632e

File tree

12 files changed

+228
-29
lines changed

12 files changed

+228
-29
lines changed

docs/design/datacontracts/Loader.md

Lines changed: 38 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -66,12 +66,15 @@ ModuleFlags GetFlags(ModuleHandle handle);
6666
string GetPath(ModuleHandle handle);
6767
string GetFileName(ModuleHandle handle);
6868
TargetPointer GetLoaderAllocator(ModuleHandle handle);
69-
TargetPointer GetThunkHeap(ModuleHandle handle);
7069
TargetPointer GetILBase(ModuleHandle handle);
7170
ModuleLookupTables GetLookupTables(ModuleHandle handle);
7271
TargetPointer GetModuleLookupMapElement(TargetPointer table, uint token, out TargetNUInt flags);
7372
bool IsCollectible(ModuleHandle handle);
7473
bool IsAssemblyLoaded(ModuleHandle handle);
74+
TargetPointer GetGlobalLoaderAllocator();
75+
TargetPointer GetHighFrequencyHeap(TargetPointer loaderAllocatorPointer);
76+
TargetPointer GetLowFrequencyHeap(TargetPointer loaderAllocatorPointer);
77+
TargetPointer GetStubHeap(TargetPointer loaderAllocatorPointer);
7578
```
7679

7780
## Version 1
@@ -84,7 +87,6 @@ bool IsAssemblyLoaded(ModuleHandle handle);
8487
| `Module` | `Base` | Pointer to start of PE file in memory |
8588
| `Module` | `Flags` | Assembly of the Module |
8689
| `Module` | `LoaderAllocator` | LoaderAllocator of the Module |
87-
| `Module` | `ThunkHeap` | Pointer to the thunk heap |
8890
| `Module` | `Path` | Path of the Module (UTF-16, null-terminated) |
8991
| `Module` | `FileName` | File name of the Module (UTF-16, null-terminated) |
9092
| `Module` | `GrowableSymbolStream` | Pointer to the in memory symbol stream |
@@ -115,17 +117,22 @@ bool IsAssemblyLoaded(ModuleHandle handle);
115117
| `AppDomain` | `RootAssembly` | Pointer to the root assembly |
116118
| `AppDomain` | `DomainAssemblyList` | ArrayListBase of assemblies in the AppDomain |
117119
| `LoaderAllocator` | `ReferenceCount` | Reference count of LoaderAllocator |
120+
| `LoaderAllocator` | `HighFrequencyHeap` | High-frequency heap of LoaderAllocator |
121+
| `LoaderAllocator` | `LowFrequencyHeap` | Low-frequency heap of LoaderAllocator |
122+
| `LoaderAllocator` | `StubHeap` | Stub heap of LoaderAllocator |
118123
| `ArrayListBase` | `Count` | Total number of elements in the ArrayListBase |
119124
| `ArrayListBase` | `FirstBlock` | First ArrayListBlock |
120125
| `ArrayListBlock` | `Next` | Next ArrayListBlock in chain |
121126
| `ArrayListBlock` | `Size` | Size of data section in block |
122127
| `ArrayListBlock` | `ArrayStart` | Start of data section in block |
128+
| `SystemDomain` | `GlobalLoaderAllocator` | global LoaderAllocator |
123129

124130

125131
### Global variables used:
126132
| Global Name | Type | Purpose |
127133
| --- | --- | --- |
128134
| `AppDomain` | TargetPointer | Pointer to the global AppDomain |
135+
| `SystemDomain` | TargetPointer | Pointer to the global SystemDomain |
129136

130137

131138
### Contract Constants:
@@ -361,11 +368,6 @@ TargetPointer GetLoaderAllocator(ModuleHandle handle)
361368
return target.ReadPointer(handle.Address + /* Module::LoaderAllocator offset */);
362369
}
363370

364-
TargetPointer GetThunkHeap(ModuleHandle handle)
365-
{
366-
return target.ReadPointer(handle.Address + /* Module::ThunkHeap offset */);
367-
}
368-
369371
TargetPointer GetILBase(ModuleHandle handle)
370372
{
371373
return target.ReadPointer(handle.Address + /* Module::Base offset */);
@@ -411,20 +413,41 @@ TargetPointer GetModuleLookupMapElement(TargetPointer table, uint token, out Tar
411413
} while (table != TargetPointer.Null);
412414
return TargetPointer.Null;
413415
}
414-
```
415416

416-
```csharp
417-
bool ILoader.IsCollectible(ModuleHandle handle)
417+
bool IsCollectible(ModuleHandle handle)
418418
{
419-
TargetPointer assembly = _target.ReadPointer(handle.Address + /*Module::Assembly*/);
420-
byte isCollectible = _target.Read<byte>(assembly + /* Assembly::IsCollectible*/);
419+
TargetPointer assembly = target.ReadPointer(handle.Address + /*Module::Assembly*/);
420+
byte isCollectible = target.Read<byte>(assembly + /* Assembly::IsCollectible*/);
421421
return isCollectible != 0;
422422
}
423423

424-
bool ILoader.IsAssemblyLoaded(ModuleHandle handle)
424+
bool IsAssemblyLoaded(ModuleHandle handle)
425425
{
426-
TargetPointer assembly = _target.ReadPointer(handle.Address + /*Module::Assembly*/);
427-
uint loadLevel = _target.Read<uint>(assembly + /* Assembly::Level*/);
426+
TargetPointer assembly = target.ReadPointer(handle.Address + /*Module::Assembly*/);
427+
uint loadLevel = target.Read<uint>(assembly + /* Assembly::Level*/);
428428
return assembly.Level >= ASSEMBLY_LEVEL_LOADED;
429429
}
430+
431+
TargetPointer GetGlobalLoaderAllocator()
432+
{
433+
TargetPointer systemDomainPointer = target.ReadGlobalPointer(Constants.Globals.SystemDomain);
434+
TargetPointer systemDomain = target.ReadPointer(systemDomainPointer);
435+
return target.ReadPointer(systemDomain + /* SystemDomain::GlobalLoaderAllocator offset */);
436+
}
437+
438+
TargetPointer GetHighFrequencyHeap(TargetPointer loaderAllocatorPointer)
439+
{
440+
return target.ReadPointer(loaderAllocatorPointer + /* LoaderAllocator::HighFrequencyHeap offset */);
441+
}
442+
443+
TargetPointer GetLowFrequencyHeap(TargetPointer loaderAllocatorPointer)
444+
{
445+
return target.ReadPointer(loaderAllocatorPointer + /* LoaderAllocator::LowFrequencyHeap offset */);
446+
}
447+
448+
TargetPointer GetStubHeap(TargetPointer loaderAllocatorPointer)
449+
{
450+
return target.ReadPointer(loaderAllocatorPointer + /* LoaderAllocator::StubHeap offset */);
451+
}
452+
430453
```

src/coreclr/debug/runtimeinfo/datadescriptor.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,9 @@ CDAC_TYPE_END(Assembly)
258258
CDAC_TYPE_BEGIN(LoaderAllocator)
259259
CDAC_TYPE_INDETERMINATE(LoaderAllocator)
260260
CDAC_TYPE_FIELD(LoaderAllocator, /*uint32*/, ReferenceCount, cdac_data<LoaderAllocator>::ReferenceCount)
261+
CDAC_TYPE_FIELD(LoaderAllocator, /*pointer*/, HighFrequencyHeap, cdac_data<LoaderAllocator>::HighFrequencyHeap)
262+
CDAC_TYPE_FIELD(LoaderAllocator, /*pointer*/, LowFrequencyHeap, cdac_data<LoaderAllocator>::LowFrequencyHeap)
263+
CDAC_TYPE_FIELD(LoaderAllocator, /*pointer*/, StubHeap, cdac_data<LoaderAllocator>::StubHeap)
261264
CDAC_TYPE_END(LoaderAllocator)
262265

263266
CDAC_TYPE_BEGIN(PEAssembly)
@@ -294,6 +297,11 @@ CDAC_TYPE_FIELD(AppDomain, /*pointer*/, RootAssembly, cdac_data<AppDomain>::Root
294297
CDAC_TYPE_FIELD(AppDomain, /*DomainAssemblyList*/, DomainAssemblyList, cdac_data<AppDomain>::DomainAssemblyList)
295298
CDAC_TYPE_END(AppDomain)
296299

300+
CDAC_TYPE_BEGIN(SystemDomain)
301+
CDAC_TYPE_INDETERMINATE(SystemDomain)
302+
CDAC_TYPE_FIELD(SystemDomain, /*GlobalLoaderAllocator*/, GlobalLoaderAllocator, cdac_data<SystemDomain>::GlobalLoaderAllocator)
303+
CDAC_TYPE_END(SystemDomain)
304+
297305
CDAC_TYPE_BEGIN(ArrayListBase)
298306
CDAC_TYPE_INDETERMINATE(ArrayListBase)
299307
CDAC_TYPE_FIELD(ArrayListBase, /*uint32*/, Count, cdac_data<ArrayListBase>::Count)
@@ -963,6 +971,7 @@ CDAC_GLOBAL(MethodDescAlignment, uint64, MethodDesc::ALIGNMENT)
963971
CDAC_GLOBAL(ObjectHeaderSize, uint64, OBJHEADER_SIZE)
964972
CDAC_GLOBAL(SyncBlockValueToObjectOffset, uint16, OBJHEADER_SIZE - cdac_data<ObjHeader>::SyncBlockValue)
965973
CDAC_GLOBAL(StubCodeBlockLast, uint8, STUB_CODE_BLOCK_LAST)
974+
CDAC_GLOBAL(DefaultADID, uint32, DefaultADID)
966975
CDAC_GLOBAL(MaxClrNotificationArgs, uint32, MAX_CLR_NOTIFICATION_ARGS)
967976
CDAC_GLOBAL_POINTER(ClrNotificationArguments, &::g_clrNotificationArguments)
968977
CDAC_GLOBAL_POINTER(ArrayBoundsZero, cdac_data<ArrayBase>::ArrayBoundsZero)

src/coreclr/vm/appdomain.hpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1881,6 +1881,7 @@ template<>
18811881
struct cdac_data<SystemDomain>
18821882
{
18831883
static constexpr PTR_SystemDomain* SystemDomainPtr = &SystemDomain::m_pSystemDomain;
1884+
static constexpr size_t GlobalLoaderAllocator = offsetof(SystemDomain, m_GlobalAllocator);
18841885
};
18851886
#endif // DACCESS_COMPILE
18861887

src/coreclr/vm/loaderallocator.hpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -885,6 +885,9 @@ template<>
885885
struct cdac_data<LoaderAllocator>
886886
{
887887
static constexpr size_t ReferenceCount = offsetof(LoaderAllocator, m_cReferences);
888+
static constexpr size_t HighFrequencyHeap = offsetof(LoaderAllocator, m_pHighFrequencyHeap);
889+
static constexpr size_t LowFrequencyHeap = offsetof(LoaderAllocator, m_pLowFrequencyHeap);
890+
static constexpr size_t StubHeap = offsetof(LoaderAllocator, m_pStubHeap);
888891
};
889892

890893
typedef VPTR(LoaderAllocator) PTR_LoaderAllocator;

src/native/managed/cdac/Microsoft.Diagnostics.DataContractReader.Abstractions/Contracts/ILoader.cs

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -41,15 +41,6 @@ public enum ModuleFlags
4141
BeingUnloaded = 0x100000,
4242
}
4343

44-
public record struct ModuleLookupTables(
45-
TargetPointer FieldDefToDesc,
46-
TargetPointer ManifestModuleReferences,
47-
TargetPointer MemberRefToDesc,
48-
TargetPointer MethodDefToDesc,
49-
TargetPointer TypeDefToMethodTable,
50-
TargetPointer TypeRefToMethodTable,
51-
TargetPointer MethodDefToILCodeVersioningState);
52-
5344
[Flags]
5445
public enum AssemblyIterationFlags
5546
{
@@ -71,6 +62,15 @@ public enum AssemblyIterationFlags
7162
IncludeCollected = 0x00000080, // Include all collectible assemblies that have been collected
7263
}
7364

65+
public record struct ModuleLookupTables(
66+
TargetPointer FieldDefToDesc,
67+
TargetPointer ManifestModuleReferences,
68+
TargetPointer MemberRefToDesc,
69+
TargetPointer MethodDefToDesc,
70+
TargetPointer TypeDefToMethodTable,
71+
TargetPointer TypeRefToMethodTable,
72+
TargetPointer MethodDefToILCodeVersioningState);
73+
7474
public interface ILoader : IContract
7575
{
7676
static string IContract.Name => nameof(Loader);
@@ -88,14 +88,17 @@ public interface ILoader : IContract
8888
ModuleFlags GetFlags(ModuleHandle handle) => throw new NotImplementedException();
8989
string GetPath(ModuleHandle handle) => throw new NotImplementedException();
9090
string GetFileName(ModuleHandle handle) => throw new NotImplementedException();
91-
9291
TargetPointer GetLoaderAllocator(ModuleHandle handle) => throw new NotImplementedException();
9392
TargetPointer GetILBase(ModuleHandle handle) => throw new NotImplementedException();
9493
ModuleLookupTables GetLookupTables(ModuleHandle handle) => throw new NotImplementedException();
95-
9694
TargetPointer GetModuleLookupMapElement(TargetPointer table, uint token, out TargetNUInt flags) => throw new NotImplementedException();
9795
bool IsCollectible(ModuleHandle handle) => throw new NotImplementedException();
9896
bool IsAssemblyLoaded(ModuleHandle handle) => throw new NotImplementedException();
97+
98+
TargetPointer GetGlobalLoaderAllocator() => throw new NotImplementedException();
99+
TargetPointer GetHighFrequencyHeap(TargetPointer loaderAllocatorPointer) => throw new NotImplementedException();
100+
TargetPointer GetLowFrequencyHeap(TargetPointer loaderAllocatorPointer) => throw new NotImplementedException();
101+
TargetPointer GetStubHeap(TargetPointer loaderAllocatorPointer) => throw new NotImplementedException();
99102
}
100103

101104
public readonly struct Loader : ILoader

src/native/managed/cdac/Microsoft.Diagnostics.DataContractReader.Abstractions/DataType.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ public enum DataType
3131
Module,
3232
ModuleLookupMap,
3333
AppDomain,
34+
SystemDomain,
3435
Assembly,
3536
LoaderAllocator,
3637
PEAssembly,

src/native/managed/cdac/Microsoft.Diagnostics.DataContractReader.Contracts/Constants.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ public static class Globals
5454

5555
public const string ExecutionManagerCodeRangeMapAddress = nameof(ExecutionManagerCodeRangeMapAddress);
5656
public const string StubCodeBlockLast = nameof(StubCodeBlockLast);
57+
public const string DefaultADID = nameof(DefaultADID);
5758
public const string MaxClrNotificationArgs = nameof(MaxClrNotificationArgs);
5859
public const string ClrNotificationArguments = nameof(ClrNotificationArguments);
5960
public const string PlatformMetadata = nameof(PlatformMetadata);

src/native/managed/cdac/Microsoft.Diagnostics.DataContractReader.Contracts/Contracts/Loader_1.cs

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,7 @@ TargetPointer ILoader.GetModule(ModuleHandle handle)
143143
{
144144
return handle.Address;
145145
}
146+
146147
TargetPointer ILoader.GetAssembly(ModuleHandle handle)
147148
{
148149
Data.Module module = _target.ProcessedData.GetOrAdd<Data.Module>(handle.Address);
@@ -353,4 +354,29 @@ bool ILoader.IsAssemblyLoaded(ModuleHandle handle)
353354
Data.Assembly assembly = _target.ProcessedData.GetOrAdd<Data.Assembly>(module.Assembly);
354355
return assembly.Level >= ASSEMBLY_LEVEL_LOADED /* IsLoaded */;
355356
}
357+
358+
TargetPointer ILoader.GetGlobalLoaderAllocator()
359+
{
360+
TargetPointer systemDomainPointer = _target.ReadGlobalPointer(Constants.Globals.SystemDomain);
361+
Data.SystemDomain systemDomain = _target.ProcessedData.GetOrAdd<Data.SystemDomain>(_target.ReadPointer(systemDomainPointer));
362+
return systemDomain.GlobalLoaderAllocator;
363+
}
364+
365+
TargetPointer ILoader.GetHighFrequencyHeap(TargetPointer loaderAllocatorPointer)
366+
{
367+
Data.LoaderAllocator loaderAllocator = _target.ProcessedData.GetOrAdd<Data.LoaderAllocator>(loaderAllocatorPointer);
368+
return loaderAllocator.HighFrequencyHeap;
369+
}
370+
371+
TargetPointer ILoader.GetLowFrequencyHeap(TargetPointer loaderAllocatorPointer)
372+
{
373+
Data.LoaderAllocator loaderAllocator = _target.ProcessedData.GetOrAdd<Data.LoaderAllocator>(loaderAllocatorPointer);
374+
return loaderAllocator.LowFrequencyHeap;
375+
}
376+
377+
TargetPointer ILoader.GetStubHeap(TargetPointer loaderAllocatorPointer)
378+
{
379+
Data.LoaderAllocator loaderAllocator = _target.ProcessedData.GetOrAdd<Data.LoaderAllocator>(loaderAllocatorPointer);
380+
return loaderAllocator.StubHeap;
381+
}
356382
}

src/native/managed/cdac/Microsoft.Diagnostics.DataContractReader.Contracts/Data/LoaderAllocator.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,16 @@ public LoaderAllocator(Target target, TargetPointer address)
1313
Target.TypeInfo type = target.GetTypeInfo(DataType.LoaderAllocator);
1414

1515
ReferenceCount = target.Read<uint>(address + (ulong)type.Fields[nameof(ReferenceCount)].Offset);
16+
HighFrequencyHeap = target.ReadPointer(address + (ulong)type.Fields[nameof(HighFrequencyHeap)].Offset);
17+
LowFrequencyHeap = target.ReadPointer(address + (ulong)type.Fields[nameof(LowFrequencyHeap)].Offset);
18+
StubHeap = target.ReadPointer(address + (ulong)type.Fields[nameof(StubHeap)].Offset);
1619

1720
}
1821

1922
public uint ReferenceCount { get; init; }
23+
public TargetPointer HighFrequencyHeap { get; init; }
24+
public TargetPointer LowFrequencyHeap { get; init; }
25+
public TargetPointer StubHeap { get; init; }
2026

2127
public bool IsAlive => ReferenceCount != 0;
2228
}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// Licensed to the .NET Foundation under one or more agreements.
2+
// The .NET Foundation licenses this file to you under the MIT license.
3+
4+
using System;
5+
6+
namespace Microsoft.Diagnostics.DataContractReader.Data;
7+
8+
internal sealed class SystemDomain : IData<SystemDomain>
9+
{
10+
static SystemDomain IData<SystemDomain>.Create(Target target, TargetPointer address) => new SystemDomain(target, address);
11+
public SystemDomain(Target target, TargetPointer address)
12+
{
13+
Target.TypeInfo type = target.GetTypeInfo(DataType.SystemDomain);
14+
GlobalLoaderAllocator = address + (ulong)type.Fields[nameof(GlobalLoaderAllocator)].Offset;
15+
}
16+
17+
public TargetPointer GlobalLoaderAllocator { get; init; }
18+
}

0 commit comments

Comments
 (0)