From 69c3e2780c44c6ad2ef0f296e8cfba7796f2213e Mon Sep 17 00:00:00 2001 From: Thomas Schatzl Date: Tue, 3 Feb 2026 12:37:33 +0000 Subject: [PATCH] 8376410: G1: Task queue statistics not reset properly on mark abort Reviewed-by: shade, iwalulya --- src/hotspot/share/gc/g1/g1ConcurrentMark.cpp | 14 ++++++++------ src/hotspot/share/gc/g1/g1ConcurrentMark.hpp | 4 +++- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/src/hotspot/share/gc/g1/g1ConcurrentMark.cpp b/src/hotspot/share/gc/g1/g1ConcurrentMark.cpp index 5f096c2b9d7..8f3cafe1f5b 100644 --- a/src/hotspot/share/gc/g1/g1ConcurrentMark.cpp +++ b/src/hotspot/share/gc/g1/g1ConcurrentMark.cpp @@ -639,8 +639,7 @@ void G1ConcurrentMark::reset_marking_for_restart() { _finger = _heap.start(); for (uint i = 0; i < _max_num_tasks; ++i) { - G1CMTaskQueue* queue = _task_queues->queue(i); - queue->set_empty(); + _tasks[i]->reset_for_restart(); } } @@ -1943,11 +1942,7 @@ bool G1ConcurrentMark::concurrent_cycle_abort() { return false; } - // Empty mark stack reset_marking_for_restart(); - for (uint i = 0; i < _max_num_tasks; ++i) { - _tasks[i]->clear_region_fields(); - } abort_marking_threads(); @@ -2118,6 +2113,13 @@ void G1CMTask::reset(G1CMBitMap* mark_bitmap) { _mark_stats_cache.reset(); } +void G1CMTask::reset_for_restart() { + clear_region_fields(); + _task_queue->set_empty(); + TASKQUEUE_STATS_ONLY(_partial_array_splitter.stats()->reset()); + TASKQUEUE_STATS_ONLY(_task_queue->stats.reset()); +} + void G1CMTask::register_partial_array_splitter() { ::new (&_partial_array_splitter) PartialArraySplitter(_cm->partial_array_state_manager(), diff --git a/src/hotspot/share/gc/g1/g1ConcurrentMark.hpp b/src/hotspot/share/gc/g1/g1ConcurrentMark.hpp index 3a4cbf1b83e..0271e6a4208 100644 --- a/src/hotspot/share/gc/g1/g1ConcurrentMark.hpp +++ b/src/hotspot/share/gc/g1/g1ConcurrentMark.hpp @@ -844,8 +844,10 @@ private: // Apply the closure to the given range of elements in the objArray. inline void process_array_chunk(objArrayOop obj, size_t start, size_t end); public: - // Resets the task; should be called right at the beginning of a marking phase. + // Resets the task completely for a new marking; should be called right at the beginning of a marking phase. void reset(G1CMBitMap* mark_bitmap); + // Minimal reset of the task, making it ready for continuing to mark. + void reset_for_restart(); // Register/unregister Partial Array Splitter Allocator with the PartialArrayStateManager. // This allows us to discard memory arenas used for partial object array states at the end // of a concurrent mark cycle.