Skip to content

Commit e98e0ec

Browse files
authored
Fix GetGenerationBounds under USE_REGIONS (#57101) (#58277)
1 parent e209402 commit e98e0ec

File tree

11 files changed

+304
-153
lines changed

11 files changed

+304
-153
lines changed

src/coreclr/gc/env/gcenv.ee.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,8 @@ class GCToEEInterface
9292
static void UpdateGCEventStatus(int publicLevel, int publicKeywords, int privateLevel, int privateKeywords);
9393
static void LogStressMsg(unsigned level, unsigned facility, const StressLogMsg &msg);
9494
static uint32_t GetCurrentProcessCpuCount();
95+
96+
static void DiagAddNewRegion(int generation, uint8_t* rangeStart, uint8_t* rangeEnd, uint8_t* rangeEndReserved);
9597
};
9698

9799
#endif // __GCENV_EE_H__

src/coreclr/gc/gc.cpp

Lines changed: 101 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5807,15 +5807,19 @@ heap_segment* gc_heap::get_segment_for_uoh (int gen_number, size_t size
58075807
gc_etw_segment_pinned_object_heap :
58085808
gc_etw_segment_large_object_heap);
58095809

5810-
GCToEEInterface::DiagUpdateGenerationBounds();
5811-
58125810
#ifndef USE_REGIONS
58135811
#ifdef MULTIPLE_HEAPS
58145812
hp->thread_uoh_segment (gen_number, res);
58155813
#else
58165814
thread_uoh_segment (gen_number, res);
58175815
#endif //MULTIPLE_HEAPS
58185816
#endif //!USE_REGIONS
5817+
GCToEEInterface::DiagAddNewRegion(
5818+
gen_number,
5819+
heap_segment_mem (res),
5820+
heap_segment_allocated (res),
5821+
heap_segment_reserved (res)
5822+
);
58195823
}
58205824

58215825
return res;
@@ -15904,18 +15908,29 @@ BOOL gc_heap::soh_try_fit (int gen_number,
1590415908
fix_youngest_allocation_area();
1590515909

1590615910
heap_segment* next_seg = heap_segment_next (ephemeral_heap_segment);
15911+
bool new_seg = false;
1590715912

1590815913
if (!next_seg)
1590915914
{
1591015915
assert (ephemeral_heap_segment == generation_tail_region (generation_of (gen_number)));
1591115916
next_seg = get_new_region (gen_number);
15917+
new_seg = true;
1591215918
}
1591315919

1591415920
if (next_seg)
1591515921
{
1591615922
dprintf (REGIONS_LOG, ("eph seg %Ix -> next %Ix",
1591715923
heap_segment_mem (ephemeral_heap_segment), heap_segment_mem (next_seg)));
1591815924
ephemeral_heap_segment = next_seg;
15925+
if (new_seg)
15926+
{
15927+
GCToEEInterface::DiagAddNewRegion(
15928+
heap_segment_gen_num (next_seg),
15929+
heap_segment_mem (next_seg),
15930+
heap_segment_allocated (next_seg),
15931+
heap_segment_reserved (next_seg)
15932+
);
15933+
}
1591915934
}
1592015935
else
1592115936
{
@@ -20996,9 +21011,22 @@ bool gc_heap::extend_soh_for_no_gc()
2099621011
}
2099721012

2099821013
region = heap_segment_next (region);
20999-
if ((region == nullptr) && !(region = get_new_region (0)))
21014+
if (region == nullptr)
2100021015
{
21001-
break;
21016+
region = get_new_region (0);
21017+
if (region == nullptr)
21018+
{
21019+
break;
21020+
}
21021+
else
21022+
{
21023+
GCToEEInterface::DiagAddNewRegion(
21024+
0,
21025+
heap_segment_mem (region),
21026+
heap_segment_allocated (region),
21027+
heap_segment_reserved (region)
21028+
);
21029+
}
2100221030
}
2100321031
}
2100421032
else
@@ -42941,6 +42969,75 @@ unsigned int GCHeap::WhichGeneration (Object* object)
4294142969
return g;
4294242970
}
4294342971

42972+
unsigned int GCHeap::GetGenerationWithRange (Object* object, uint8_t** ppStart, uint8_t** ppAllocated, uint8_t** ppReserved)
42973+
{
42974+
int generation = -1;
42975+
heap_segment * hs = gc_heap::find_segment ((uint8_t*)object, FALSE);
42976+
#ifdef USE_REGIONS
42977+
generation = heap_segment_gen_num (hs);
42978+
if (generation == max_generation)
42979+
{
42980+
if (heap_segment_loh_p (hs))
42981+
{
42982+
generation = loh_generation;
42983+
}
42984+
else if (heap_segment_poh_p (hs))
42985+
{
42986+
generation = poh_generation;
42987+
}
42988+
}
42989+
42990+
*ppStart = heap_segment_mem (hs);
42991+
*ppAllocated = heap_segment_allocated (hs);
42992+
*ppReserved = heap_segment_reserved (hs);
42993+
#else
42994+
#ifdef MULTIPLE_HEAPS
42995+
gc_heap* hp = heap_segment_heap (hs);
42996+
#else
42997+
gc_heap* hp = __this;
42998+
#endif //MULTIPLE_HEAPS
42999+
if (hs == hp->ephemeral_heap_segment)
43000+
{
43001+
uint8_t* reserved = heap_segment_reserved (hs);
43002+
uint8_t* end = heap_segment_allocated(hs);
43003+
for (int gen = 0; gen < max_generation; gen++)
43004+
{
43005+
uint8_t* start = generation_allocation_start (hp->generation_of (gen));
43006+
if ((uint8_t*)object >= start)
43007+
{
43008+
generation = gen;
43009+
*ppStart = start;
43010+
*ppAllocated = end;
43011+
*ppReserved = reserved;
43012+
break;
43013+
}
43014+
end = reserved = start;
43015+
}
43016+
if (generation == -1)
43017+
{
43018+
*ppStart = heap_segment_mem (hs);
43019+
*ppAllocated = *ppReserved = generation_allocation_start (hp->generation_of (max_generation - 1));
43020+
}
43021+
}
43022+
else
43023+
{
43024+
generation = max_generation;
43025+
if (heap_segment_loh_p (hs))
43026+
{
43027+
generation = loh_generation;
43028+
}
43029+
else if (heap_segment_poh_p (hs))
43030+
{
43031+
generation = poh_generation;
43032+
}
43033+
*ppStart = heap_segment_mem (hs);
43034+
*ppAllocated = heap_segment_allocated (hs);
43035+
*ppReserved = heap_segment_reserved (hs);
43036+
}
43037+
#endif //USE_REGIONS
43038+
return (unsigned int)generation;
43039+
}
43040+
4294443041
bool GCHeap::IsEphemeral (Object* object)
4294543042
{
4294643043
uint8_t* o = (uint8_t*)object;

src/coreclr/gc/gcenv.ee.standalone.inl

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -306,4 +306,9 @@ inline uint32_t GCToEEInterface::GetCurrentProcessCpuCount()
306306
return g_theGCToCLR->GetCurrentProcessCpuCount();
307307
}
308308

309+
inline void GCToEEInterface::DiagAddNewRegion(int generation, uint8_t* rangeStart, uint8_t* rangeEnd, uint8_t* rangeEndReserved)
310+
{
311+
g_theGCToCLR->DiagAddNewRegion(generation, rangeStart, rangeEnd, rangeEndReserved);
312+
}
313+
309314
#endif // __GCTOENV_EE_STANDALONE_INL__

src/coreclr/gc/gcimpl.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -309,6 +309,7 @@ class GCHeap : public IGCHeapInternal
309309

310310
virtual void DiagGetGCSettings(EtwGCSettingsInfo* etw_settings);
311311

312+
virtual unsigned int GetGenerationWithRange(Object* object, uint8_t** ppStart, uint8_t** ppAllocated, uint8_t** ppReserved);
312313
public:
313314
Object * NextObj (Object * object);
314315

src/coreclr/gc/gcinterface.ee.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -443,6 +443,9 @@ class IGCToCLR {
443443

444444
virtual
445445
uint32_t GetCurrentProcessCpuCount() = 0;
446+
447+
virtual
448+
void DiagAddNewRegion(int generation, uint8_t* rangeStart, uint8_t* rangeEnd, uint8_t* rangeEndReserved) = 0;
446449
};
447450

448451
#endif // _GCINTERFACE_EE_H_

src/coreclr/gc/gcinterface.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
// The major version of the GC/EE interface. Breaking changes to this interface
88
// require bumps in the major version number.
9-
#define GC_INTERFACE_MAJOR_VERSION 4
9+
#define GC_INTERFACE_MAJOR_VERSION 5
1010

1111
// The minor version of the GC/EE interface. Non-breaking changes are required
1212
// to bump the minor version number. GCs and EEs with minor version number
@@ -921,6 +921,8 @@ class IGCHeap {
921921
// Enables or disables the given keyword or level on the private event provider.
922922
virtual void ControlPrivateEvents(GCEventKeyword keyword, GCEventLevel level) = 0;
923923

924+
virtual unsigned int GetGenerationWithRange(Object* object, uint8_t** ppStart, uint8_t** ppAllocated, uint8_t** ppReserved) = 0;
925+
924926
IGCHeap() {}
925927
virtual ~IGCHeap() {}
926928
};

src/coreclr/gc/sample/gcenv.ee.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -354,3 +354,7 @@ uint32_t GCToEEInterface::GetCurrentProcessCpuCount()
354354
{
355355
return GCToOSInterface::GetTotalProcessorCount();
356356
}
357+
358+
void GCToEEInterface::DiagAddNewRegion(int generation, uint8_t* rangeStart, uint8_t* rangeEnd, uint8_t* rangeEndReserved)
359+
{
360+
}

src/coreclr/vm/eeprofinterfaces.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,8 @@ void __stdcall GarbageCollectionStartedCallback(int generation, BOOL induced);
4747
void __stdcall GarbageCollectionFinishedCallback();
4848

4949
void __stdcall UpdateGenerationBounds();
50+
51+
void __stdcall ProfilerAddNewRegion(int generation, uint8_t* rangeStart, uint8_t* rangeEnd, uint8_t* rangeEndReserved);
5052
#include "eetoprofinterfaceimpl.h"
5153

5254

src/coreclr/vm/gcenv.ee.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1732,3 +1732,8 @@ uint32_t GCToEEInterface::GetCurrentProcessCpuCount()
17321732
{
17331733
return ::GetCurrentProcessCpuCount();
17341734
}
1735+
1736+
void GCToEEInterface::DiagAddNewRegion(int generation, uint8_t* rangeStart, uint8_t* rangeEnd, uint8_t* rangeEndReserved)
1737+
{
1738+
ProfilerAddNewRegion(generation, rangeStart, rangeEnd, rangeEndReserved);
1739+
}

src/coreclr/vm/gcenv.ee.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,8 @@ class GCToEEInterface : public IGCToCLR {
8585

8686
void LogStressMsg(unsigned level, unsigned facility, const StressLogMsg& msg);
8787
uint32_t GetCurrentProcessCpuCount();
88+
89+
void DiagAddNewRegion(int generation, BYTE * rangeStart, BYTE * rangeEnd, BYTE * rangeEndReserved);
8890
};
8991

9092
} // namespace standalone

0 commit comments

Comments
 (0)