0N/A/*
1879N/A * Copyright (c) 2002, 2010, Oracle and/or its affiliates. All rights reserved.
0N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0N/A *
0N/A * This code is free software; you can redistribute it and/or modify it
0N/A * under the terms of the GNU General Public License version 2 only, as
0N/A * published by the Free Software Foundation.
0N/A *
0N/A * This code is distributed in the hope that it will be useful, but WITHOUT
0N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0N/A * version 2 for more details (a copy is included in the LICENSE file that
0N/A * accompanied this code).
0N/A *
0N/A * You should have received a copy of the GNU General Public License version
0N/A * 2 along with this work; if not, write to the Free Software Foundation,
0N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0N/A *
1472N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1472N/A * or visit www.oracle.com if you need additional information or have any
1472N/A * questions.
0N/A *
0N/A */
0N/A
1879N/A#ifndef SHARE_VM_GC_IMPLEMENTATION_PARALLELSCAVENGE_PSTASKS_HPP
1879N/A#define SHARE_VM_GC_IMPLEMENTATION_PARALLELSCAVENGE_PSTASKS_HPP
1879N/A
1879N/A#include "memory/allocation.hpp"
1879N/A#include "utilities/growableArray.hpp"
1879N/A
0N/A//
0N/A// psTasks.hpp is a collection of GCTasks used by the
0N/A// parallelScavenge collector.
0N/A//
0N/A
0N/Aclass GCTask;
0N/Aclass OopClosure;
0N/Aclass OopStack;
0N/Aclass ObjectStartArray;
0N/Aclass ParallelTaskTerminator;
0N/Aclass MutableSpace;
0N/Aclass PSOldGen;
0N/Aclass Thread;
0N/Aclass VMThread;
0N/A
0N/A//
0N/A// ScavengeRootsTask
0N/A//
0N/A// This task scans all the roots of a given type.
0N/A//
0N/A//
0N/A
0N/Aclass ScavengeRootsTask : public GCTask {
0N/A public:
0N/A enum RootType {
0N/A universe = 1,
0N/A jni_handles = 2,
0N/A threads = 3,
0N/A object_synchronizer = 4,
0N/A flat_profiler = 5,
0N/A system_dictionary = 6,
0N/A management = 7,
989N/A jvmti = 8,
989N/A code_cache = 9
0N/A };
0N/A private:
0N/A RootType _root_type;
0N/A public:
0N/A ScavengeRootsTask(RootType value) : _root_type(value) {}
0N/A
0N/A char* name() { return (char *)"scavenge-roots-task"; }
0N/A
0N/A virtual void do_it(GCTaskManager* manager, uint which);
0N/A};
0N/A
0N/A//
0N/A// ThreadRootsTask
0N/A//
0N/A// This task scans the roots of a single thread. This task
0N/A// enables scanning of thread roots in parallel.
0N/A//
0N/A
0N/Aclass ThreadRootsTask : public GCTask {
0N/A private:
0N/A JavaThread* _java_thread;
0N/A VMThread* _vm_thread;
0N/A public:
0N/A ThreadRootsTask(JavaThread* root) : _java_thread(root), _vm_thread(NULL) {}
0N/A ThreadRootsTask(VMThread* root) : _java_thread(NULL), _vm_thread(root) {}
0N/A
0N/A char* name() { return (char *)"thread-roots-task"; }
0N/A
0N/A virtual void do_it(GCTaskManager* manager, uint which);
0N/A};
0N/A
0N/A//
0N/A// StealTask
0N/A//
0N/A// This task is used to distribute work to idle threads.
0N/A//
0N/A
0N/Aclass StealTask : public GCTask {
0N/A private:
0N/A ParallelTaskTerminator* const _terminator;
0N/A public:
0N/A char* name() { return (char *)"steal-task"; }
0N/A
0N/A StealTask(ParallelTaskTerminator* t);
0N/A
0N/A ParallelTaskTerminator* terminator() { return _terminator; }
0N/A
0N/A virtual void do_it(GCTaskManager* manager, uint which);
0N/A};
0N/A
0N/A//
0N/A// SerialOldToYoungRootsTask
0N/A//
0N/A// This task is used to scan for roots in the perm gen
0N/A
0N/Aclass SerialOldToYoungRootsTask : public GCTask {
0N/A private:
0N/A PSOldGen* _gen;
0N/A HeapWord* _gen_top;
0N/A
0N/A public:
0N/A SerialOldToYoungRootsTask(PSOldGen *gen, HeapWord* gen_top) :
0N/A _gen(gen), _gen_top(gen_top) { }
0N/A
0N/A char* name() { return (char *)"serial-old-to-young-roots-task"; }
0N/A
0N/A virtual void do_it(GCTaskManager* manager, uint which);
0N/A};
0N/A
0N/A//
0N/A// OldToYoungRootsTask
0N/A//
0N/A// This task is used to scan old to young roots in parallel
2941N/A//
2941N/A// A GC thread executing this tasks divides the generation (old gen)
2941N/A// into slices and takes a stripe in the slice as its part of the
2941N/A// work.
2941N/A//
2941N/A// +===============+ slice 0
2941N/A// | stripe 0 |
2941N/A// +---------------+
2941N/A// | stripe 1 |
2941N/A// +---------------+
2941N/A// | stripe 2 |
2941N/A// +---------------+
2941N/A// | stripe 3 |
2941N/A// +===============+ slice 1
2941N/A// | stripe 0 |
2941N/A// +---------------+
2941N/A// | stripe 1 |
2941N/A// +---------------+
2941N/A// | stripe 2 |
2941N/A// +---------------+
2941N/A// | stripe 3 |
2941N/A// +===============+ slice 2
2941N/A// ...
2941N/A//
2941N/A// A task is created for each stripe. In this case there are 4 tasks
2941N/A// created. A GC thread first works on its stripe within slice 0
2941N/A// and then moves to its stripe in the next slice until all stripes
2941N/A// exceed the top of the generation. Note that having fewer GC threads
2941N/A// than stripes works because all the tasks are executed so all stripes
2941N/A// will be covered. In this example if 4 tasks have been created to cover
2941N/A// all the stripes and there are only 3 threads, one of the threads will
2941N/A// get the tasks with the 4th stripe. However, there is a dependence in
2941N/A// CardTableExtension::scavenge_contents_parallel() on the number
2941N/A// of tasks created. In scavenge_contents_parallel the distance
2941N/A// to the next stripe is calculated based on the number of tasks.
2941N/A// If the stripe width is ssize, a task's next stripe is at
2941N/A// ssize * number_of_tasks (= slice_stride). In this case after
2941N/A// finishing stripe 0 in slice 0, the thread finds the stripe 0 in slice1
2941N/A// by adding slice_stride to the start of stripe 0 in slice 0 to get
2941N/A// to the start of stride 0 in slice 1.
0N/A
0N/Aclass OldToYoungRootsTask : public GCTask {
0N/A private:
0N/A PSOldGen* _gen;
0N/A HeapWord* _gen_top;
0N/A uint _stripe_number;
2941N/A uint _stripe_total;
0N/A
0N/A public:
2941N/A OldToYoungRootsTask(PSOldGen *gen,
2941N/A HeapWord* gen_top,
2941N/A uint stripe_number,
2941N/A uint stripe_total) :
2941N/A _gen(gen),
2941N/A _gen_top(gen_top),
2941N/A _stripe_number(stripe_number),
2941N/A _stripe_total(stripe_total) { }
0N/A
0N/A char* name() { return (char *)"old-to-young-roots-task"; }
0N/A
0N/A virtual void do_it(GCTaskManager* manager, uint which);
0N/A};
1879N/A
1879N/A#endif // SHARE_VM_GC_IMPLEMENTATION_PARALLELSCAVENGE_PSTASKS_HPP