-
Notifications
You must be signed in to change notification settings - Fork 155
Home
GCToolKit is an API to support the generation of events that represent the data in garbage collection logs. Garbage collection logs contain a journal of all garbage collection events. The tool kit can manage GC logs from JDK 1.4.2 to JDK 17 for the serial, parallel, CMS, iCMS, G1, and Z GC collectors.
The toolkit is partitioned into 3 different modules, API, Parser, and Vertx. The API provides access to functionality of the toolkit. Parser is responsible for turning raw log lines into JVMEvent objects. The objects are then broadcasted on a message bus. The current implementation of this bus is based on Vert.x. It is the responsibility of the client to provide the implementations for Aggregator/Aggregation pairs. An Aggregation is intended to collect data to provide a unique view on it. An Aggregator listens on the bus and captures the events of interest for the Aggregation.
Below is a sample Aggregator/Aggregation pair that yields a view of total heap occupancy as a time series. The first step is to use an annotation to indicate which event sources the Aggregator is intended for. The constructor contains registrations for the individual events of interest.
`@Aggregates({EventSource.G1GC,EventSource.GENERATIONAL,EventSource.ZGC}) public class HeapOccupancyAfterCollection extends Aggregator {
public HeapOccupancyAfterCollection(HeapOccupancyAfterCollectionAggregation results) {
super(results);
/* Pair specific event with the methods that will harvest data from the event */
register(GenerationalGCPauseEvent.class, this::extractHeapOccupancy);
register(G1GCPauseEvent.class, this::extractHeapOccupancy);
register(ZGCCycle.class,this::extractHeapOccupancy);
register(ShenandoahCycle.class,this::extractHeapOccupancy);
}
/* Extract the event type, time stamp and heap occupancy at the end of the collection cycle */
private void extractHeapOccupancy(GenerationalGCPauseEvent event) {
aggregation().addDataPoint(event.getGarbageCollectionType(), event.getDateTimeStamp(), event.getHeap().getOccupancyAfterCollection());
}
private void extractHeapOccupancy(G1GCPauseEvent event) {
aggregation().addDataPoint(event.getGarbageCollectionType(), event.getDateTimeStamp(), event.getHeap().getOccupancyAfterCollection());
}
private void extractHeapOccupancy(ZGCCycle event) {
aggregation().addDataPoint(event.getGarbageCollectionType(), event.getDateTimeStamp(), event.getLive().getReclaimEnd());
}
}`
/* Annotation to tie implementation with interface. Allows for multiple implementations for each aggregation. */
@Collates(HeapOccupancyAfterCollection.class)
public class HeapOccupancyAfterCollectionSummary implements HeapOccupancyAfterCollectionAggregation {
`private HashMap<GarbageCollectionTypes,CensumXYDataSet> aggregations = new HashMap();`
`public void addDataPoint(GarbageCollectionTypes gcType, DateTimeStamp timeStamp, long heapOccupancy) {`
`CensumXYDataSet dataSet = aggregations.get(gcType);`
`if ( dataSet == null) {`
`dataSet = new CensumXYDataSet();`
`aggregations.put(gcType,dataSet);`
`}`
`dataSet.add(timeStamp.getTimeStamp(),heapOccupancy);`
`}`
`public HashMap<GarbageCollectionTypes,CensumXYDataSet> get() {`
`return aggregations;`
`}`
`@Override`
`public boolean hasWarning() {`
`return false;`
`}`
`@Override`
`public boolean isEmpty() {`
`return aggregations.isEmpty();`
`}`
}
If the Aggregator/Aggregation is packaged into a Module and exposed as a service provider, the API will pick the implementations and automatically register them. The following is a sample module-info.java implementation.
`module censum.sample {
requires censum.api;
requires censum.vertx;
requires java.logging;
exports com.microsoft.censum.sample.aggregation to censum.vertx;
provides com.microsoft.censum.aggregator.Aggregation with com.microsoft.censum.sample.aggregation.HeapOccupancyAfterCollectionSummary;
}`