Path: blob/master/runtime/gc_realtime/RealtimeMarkingSchemeRootClearer.hpp
5986 views
/*******************************************************************************1* Copyright (c) 2019, 2020 IBM Corp. and others2*3* This program and the accompanying materials are made available under4* the terms of the Eclipse Public License 2.0 which accompanies this5* distribution and is available at https://www.eclipse.org/legal/epl-2.0/6* or the Apache License, Version 2.0 which accompanies this distribution and7* is available at https://www.apache.org/licenses/LICENSE-2.0.8*9* This Source Code may also be made available under the following10* Secondary Licenses when the conditions for such availability set11* forth in the Eclipse Public License, v. 2.0 are satisfied: GNU12* General Public License, version 2 with the GNU Classpath13* Exception [1] and GNU General Public License, version 2 with the14* OpenJDK Assembly Exception [2].15*16* [1] https://www.gnu.org/software/classpath/license.html17* [2] http://openjdk.java.net/legal/assembly-exception.html18*19* SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 OR GPL-2.0 WITH Classpath-exception-2.0 OR LicenseRef-GPL-2.0 WITH Assembly-exception20*******************************************************************************/2122/**23* @file24* @ingroup GC_Metronome25*/2627#if !defined(REALTIMEROOTCLEARER_HPP_)28#define REALTIMEROOTCLEARER_HPP_2930#include "j9.h"31#include "j9cfg.h"32#include "modronopt.h"3334#include "EnvironmentRealtime.hpp"35#include "RealtimeRootScanner.hpp"36#include "RealtimeGC.hpp"37#include "RealtimeMarkingScheme.hpp"3839/**40* This scanner will mark objects that pass through its doSlot.41*/42class MM_RealtimeMarkingSchemeRootClearer : public MM_RealtimeRootScanner43{44/* Data members / types */45public:46protected:47private:4849/* Methods */50public:5152/**53* Simple chained constructor.54*/55MM_RealtimeMarkingSchemeRootClearer(MM_EnvironmentRealtime *env, MM_RealtimeGC *realtimeGC) :56MM_RealtimeRootScanner(env, realtimeGC)57{58_typeId = __FUNCTION__;59}6061/**62* This should not be called63*/64virtual void65doSlot(J9Object** slot)66{67Assert_MM_unreachable();68}6970/**71* This scanner can be instantiated so we must give it a name.72*/73virtual const char*74scannerName()75{76return "Clearable";77}7879/**80* Destroys unmarked monitors.81*/82virtual void83doMonitorReference(J9ObjectMonitor *objectMonitor, GC_HashTableIterator *monitorReferenceIterator)84{85J9ThreadAbstractMonitor * monitor = (J9ThreadAbstractMonitor*)objectMonitor->monitor;86if(!_markingScheme->isMarked((J9Object *)monitor->userData)) {87monitorReferenceIterator->removeSlot();88/* We must call objectMonitorDestroy (as opposed to omrthread_monitor_destroy) when the89* monitor is not internal to the GC */90static_cast<J9JavaVM*>(_omrVM->_language_vm)->internalVMFunctions->objectMonitorDestroy(static_cast<J9JavaVM*>(_omrVM->_language_vm), (J9VMThread *)_env->getLanguageVMThread(), (omrthread_monitor_t)monitor);91}92}9394/**95* Wraps the MM_RootScanner::scanMonitorReferences method to disable yielding during the scan.96* @see MM_RootScanner::scanMonitorReferences()97*/98virtual void99scanMonitorReferences(MM_EnvironmentBase *envBase)100{101MM_EnvironmentRealtime *env = (MM_EnvironmentRealtime *)envBase;102103/* @NOTE For SRT and MT to play together this needs to be investigated */104if(_singleThread || J9MODRON_HANDLE_NEXT_WORK_UNIT(env)) {105reportScanningStarted(RootScannerEntity_MonitorReferences);106107J9ObjectMonitor *objectMonitor = NULL;108J9MonitorTableListEntry *monitorTableList = static_cast<J9JavaVM*>(_omrVM->_language_vm)->monitorTableList;109while (NULL != monitorTableList) {110J9HashTable *table = monitorTableList->monitorTable;111if (NULL != table) {112GC_HashTableIterator iterator(table);113iterator.disableTableGrowth();114while (NULL != (objectMonitor = (J9ObjectMonitor*)iterator.nextSlot())) {115doMonitorReference(objectMonitor, &iterator);116if (shouldYieldFromMonitorScan()) {117yield();118}119}120iterator.enableTableGrowth();121}122monitorTableList = monitorTableList->next;123}124125reportScanningEnded(RootScannerEntity_MonitorReferences);126}127}128129virtual CompletePhaseCode scanMonitorReferencesComplete(MM_EnvironmentBase *envBase) {130MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);131reportScanningStarted(RootScannerEntity_MonitorReferenceObjectsComplete);132((J9JavaVM *)env->getLanguageVM())->internalVMFunctions->objectMonitorDestroyComplete((J9JavaVM *)env->getLanguageVM(), (J9VMThread *)env->getLanguageVMThread());133reportScanningEnded(RootScannerEntity_MonitorReferenceObjectsComplete);134return complete_phase_OK;135}136137virtual void scanWeakReferenceObjects(MM_EnvironmentBase *envBase) {138MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);139reportScanningStarted(RootScannerEntity_WeakReferenceObjects);140141_realtimeGC->getRealtimeDelegate()->scanWeakReferenceObjects(env);142143reportScanningEnded(RootScannerEntity_WeakReferenceObjects);144}145146virtual CompletePhaseCode scanWeakReferencesComplete(MM_EnvironmentBase *envBase) {147MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);148reportScanningStarted(RootScannerEntity_WeakReferenceObjectsComplete);149150if (env->_currentTask->synchronizeGCThreadsAndReleaseMain(env, UNIQUE_ID)) {151env->_cycleState->_referenceObjectOptions |= MM_CycleState::references_clear_weak;152env->_currentTask->releaseSynchronizedGCThreads(env);153}154155reportScanningEnded(RootScannerEntity_WeakReferenceObjectsComplete);156157return complete_phase_OK;158}159160virtual void scanSoftReferenceObjects(MM_EnvironmentBase *envBase) {161MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);162reportScanningStarted(RootScannerEntity_SoftReferenceObjects);163164_realtimeGC->getRealtimeDelegate()->scanSoftReferenceObjects(env);165166reportScanningEnded(RootScannerEntity_SoftReferenceObjects);167}168169virtual CompletePhaseCode scanSoftReferencesComplete(MM_EnvironmentBase *envBase) {170MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);171reportScanningStarted(RootScannerEntity_SoftReferenceObjectsComplete);172if (env->_currentTask->synchronizeGCThreadsAndReleaseMain(env, UNIQUE_ID)) {173env->_cycleState->_referenceObjectOptions |= MM_CycleState::references_clear_soft;174env->_currentTask->releaseSynchronizedGCThreads(env);175}176reportScanningEnded(RootScannerEntity_SoftReferenceObjectsComplete);177return complete_phase_OK;178}179180virtual void scanPhantomReferenceObjects(MM_EnvironmentBase *envBase) {181MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);182reportScanningStarted(RootScannerEntity_PhantomReferenceObjects);183184_realtimeGC->getRealtimeDelegate()->scanPhantomReferenceObjects(env);185186reportScanningEnded(RootScannerEntity_PhantomReferenceObjects);187}188189virtual CompletePhaseCode scanPhantomReferencesComplete(MM_EnvironmentBase *envBase) {190MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);191reportScanningStarted(RootScannerEntity_PhantomReferenceObjectsComplete);192if (env->_currentTask->synchronizeGCThreadsAndReleaseMain(env, UNIQUE_ID)) {193env->_cycleState->_referenceObjectOptions |= MM_CycleState::references_clear_phantom;194env->_currentTask->releaseSynchronizedGCThreads(env);195}196/* phantom reference processing may resurrect objects - scan them now */197_realtimeGC->completeMarking(MM_EnvironmentRealtime::getEnvironment(env));198reportScanningEnded(RootScannerEntity_PhantomReferenceObjectsComplete);199return complete_phase_OK;200}201202#if defined(J9VM_GC_FINALIZATION)203/**204* Wraps the MM_RootScanner::scanUnfinalizedObjects method to disable yielding during the scan205* then yield after scanning.206* @see MM_RootScanner::scanUnfinalizedObjects()207*/208virtual void209scanUnfinalizedObjects(MM_EnvironmentBase *envBase) {210MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);211212reportScanningStarted(RootScannerEntity_UnfinalizedObjects);213/* allow the marking scheme to handle this */214_realtimeGC->getRealtimeDelegate()->scanUnfinalizedObjects(env);215reportScanningEnded(RootScannerEntity_UnfinalizedObjects);216}217218virtual CompletePhaseCode scanUnfinalizedObjectsComplete(MM_EnvironmentBase *envBase) {219MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);220reportScanningStarted(RootScannerEntity_UnfinalizedObjectsComplete);221/* ensure that all unfinalized processing is complete before we start marking additional objects */222env->_currentTask->synchronizeGCThreads(env, UNIQUE_ID);223_realtimeGC->completeMarking(env);224reportScanningEnded(RootScannerEntity_UnfinalizedObjectsComplete);225return complete_phase_OK;226}227228virtual void doFinalizableObject(j9object_t object) {229Assert_MM_unreachable();230}231#endif /* J9VM_GC_FINALIZATION */232233virtual void234scanOwnableSynchronizerObjects(MM_EnvironmentBase *envBase) {235MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);236237reportScanningStarted(RootScannerEntity_OwnableSynchronizerObjects);238/* allow the marking scheme to handle this */239_realtimeGC->getRealtimeDelegate()->scanOwnableSynchronizerObjects(env);240reportScanningEnded(RootScannerEntity_OwnableSynchronizerObjects);241}242243/**244* Wraps the MM_RootScanner::scanJNIWeakGlobalReferences method to disable yielding during the scan.245* @see MM_RootScanner::scanJNIWeakGlobalReferences()246*/247virtual void248scanJNIWeakGlobalReferences(MM_EnvironmentBase *envBase)249{250MM_EnvironmentRealtime *env = MM_EnvironmentRealtime::getEnvironment(envBase);251252env->disableYield();253MM_RootScanner::scanJNIWeakGlobalReferences(env);254env->enableYield();255}256257/**258* Clears slots holding unmarked objects.259*/260virtual void261doJNIWeakGlobalReference(J9Object **slotPtr)262{263J9Object *objectPtr = *slotPtr;264if(objectPtr && !_markingScheme->isMarked(objectPtr)) {265*slotPtr = NULL;266}267}268269#if defined(J9VM_OPT_JVMTI)270/**271* Clears slots holding unmarked objects.272*/273virtual void274doJVMTIObjectTagSlot(J9Object **slotPtr, GC_JVMTIObjectTagTableIterator *objectTagTableIterator)275{276J9Object *objectPtr = *slotPtr;277if(objectPtr && !_markingScheme->isMarked(objectPtr)) {278*slotPtr = NULL;279}280}281#endif /* J9VM_OPT_JVMTI */282283protected:284private:285};286287#endif /* REALTIMEROOTCLEARER_HPP_ */288289290291