package com.tagtraum.perf.gcviewer;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

/**
 * Collection of GCEvents.
 *
 * Date: Jan 30, 2002
 * Time: 5:01:45 PM
 * @author <a href="mailto:hs@tagtraum.com">Hendrik Schreiber</a>
 * @version $Id: $
 */
public class GCModel implements Serializable {
    private List gcEvents;
    private long footprint;
    private double runningTime;
    private double maxPause;
    private double minPause;
    private double avgPause;
    private double pauseTime;
    private long freedMemory;
    private Format format;

    public GCModel() {
        gcEvents = new ArrayList();
    }

    public Iterator getGCEvents() {
        return gcEvents.iterator();
    }

    public void add(GCEvent gcEvent) {
        gcEvents.add(gcEvent);
        footprint = Math.max(footprint, gcEvent.getTotal());
        runningTime = Math.max(runningTime, gcEvent.getTimestamp());
        maxPause = Math.max(maxPause, gcEvent.getPause());
        if (minPause != 0)
            minPause = Math.min(minPause, gcEvent.getPause());
        else
            minPause = gcEvent.getPause();
        pauseTime += gcEvent.getPause();
        freedMemory += gcEvent.getPreUsed()-gcEvent.getPostUsed();
    }

    public int size() {
        return gcEvents.size();
    }

    public GCEvent get(int index) {
        return (GCEvent) gcEvents.get(index);
    }

    /**
     * Pause in sec.
     */
    public double getAvgPause() {
        return pauseTime / (double) gcEvents.size();
    }

    /**
     * Pause in sec.
     */
    public double getPauseTime() {
        return pauseTime;
    }

    /**
     * Throughput in percent.
     */
    public double getThroughput() {
        return 100 * (runningTime - pauseTime) / runningTime;
    }

    /**
     * Footprint in KB.
     */
    public long getFootprint() {
        return footprint;
    }

    /**
     * Running time in sec.
     */
    public double getRunningTime() {
        return runningTime;
    }

    /**
     * Max pause in sec.
     */
    public double getMaxPause() {
        return maxPause;
    }

    /**
     * Min pause in sec.
     */
    public double getMinPause() {
        return minPause;
    }

    /**
     * Freed memory in KB.
     */
    public long getFreedMemory() {
        return freedMemory;
    }

    public Format getFormat() {
        return format;
    }

    public void setFormat(Format format) {
        this.format = format;
    }

    public boolean hasCorrectTimestamp() {
        return format == Format.IBM_VERBOSE_GC || format == Format.SUN_X_LOG_GC || format == Format.SUN_1_2_2VERBOSE_GC;
    }

    public String toString() {
        return gcEvents.toString();
    }

    public static class Format implements Serializable {
        private String format;

        private Format(String format) {
            this.format = format;
        }

        public String toString() {
            return format;
        }

        public static final Format SUN_VERBOSE_GC = new Format("Sun -verbose:gc");
        public static final Format SUN_X_LOG_GC = new Format("Sun -Xloggc:<file>");
        public static final Format IBM_VERBOSE_GC = new Format("IBM -verbose:gc");
        public static final Format SUN_1_2_2VERBOSE_GC = new Format("Sun 1.2.2 -verbose:gc");
    }
}
