/* * JaamSim Discrete Event Simulation * Copyright (C) 2009-2011 Ausenco Engineering Canada Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.jaamsim.basicsim; import java.util.ArrayList; import com.jaamsim.events.EventManager; import com.jaamsim.events.EventTraceListener; import com.jaamsim.events.ProcessTarget; import com.jaamsim.input.Input; class EventTraceRecord extends ArrayList<String> implements EventTraceListener { private String eventManagerName; private long internalTime; private String targetName; int traceLevel; public EventTraceRecord() { traceLevel = 0; } void parse() { String[] temp; // The first line of the trace is always <eventManagerName>\t<InternalSimulationTime> temp = this.get(0).split("\t"); eventManagerName = temp[0]; internalTime = Long.parseLong(temp[1]); // Try to parse a target entity and method form the second line temp = this.get(1).split("\t"); // A regular event wakeup, parse target/method if (temp[0].endsWith("Event")) { targetName = temp[3]; return; } if (temp[0].endsWith("WaitUntilEnded")) { targetName = temp[3]; return; } if (temp[0].endsWith("StartProcess")) { targetName = temp[1]; return; } if (temp[0].endsWith("SchedProcess")) { targetName = temp[3]; return; } } private void append(String record) { StringBuilder rec = new StringBuilder(); for (int i = 0; i < traceLevel; i++) { rec.append(Input.SEPARATOR); } rec.append(record); this.add(rec.toString()); } private void addHeader(String name, long internalTime) { // Don't write anything if not at level 0 if (traceLevel != 0) return; StringBuilder header = new StringBuilder(name).append("\t").append(internalTime); this.add(header.toString()); traceLevel++; } @Override public void traceWait(EventManager e, long curTick, long tick, int priority, ProcessTarget t) { this.addHeader(e.name, curTick); traceLevel--; this.append(String.format("Wait\t%d\t%d\t%s", tick, priority, EventRecorder.getWaitDescription())); } @Override public void traceEvent(EventManager e, long curTick, long tick, int priority, ProcessTarget t) { this.addHeader(e.name, curTick); this.append(String.format("Event\t%d\t%d\t%s", tick, priority, t.getDescription())); traceLevel++; } @Override public void traceInterrupt(EventManager e, long curTick, long tick, int priority, ProcessTarget t) { this.addHeader(e.name, curTick); this.append(String.format("Int\t%d\t%d\t%s", tick, priority, t.getDescription())); traceLevel++; } @Override public void traceKill(EventManager e, long curTick, long tick, int priority, ProcessTarget t) { this.addHeader(e.name, curTick); this.append(String.format("Kill\t%d\t%d\t%s", tick, priority, t.getDescription())); } @Override public void traceWaitUntil(EventManager e, long tick) { this.addHeader(e.name, tick); traceLevel--; this.append("WaitUntil"); } @Override public void traceWaitUntilEnded(EventManager e, long curTick, ProcessTarget t) { this.addHeader(e.name, curTick); this.append(String.format("WaitUntilEnded\t%s", t.getDescription())); } @Override public void traceProcessStart(EventManager e, ProcessTarget t, long tick) { this.addHeader(e.name, tick); this.append(String.format("StartProcess\t%s", t.getDescription())); traceLevel++; } @Override public void traceProcessEnd(EventManager e, long tick) { this.addHeader(e.name, tick); traceLevel--; this.append("Exit"); } @Override public void traceSchedProcess(EventManager e, long curTick, long tick, int priority, ProcessTarget t) { this.addHeader(e.name, curTick); this.append(String.format("SchedProcess\t%d\t%d\t%s", tick, priority, t.getDescription())); } boolean isDefaultEventManager() { return eventManagerName.equals("DefaultEventManager"); } long getInternalTime() { return internalTime; } /** * Does a superficial comparison of two records, check number of entries, * time/target/method and finally the basic contents of the record. */ boolean basicCompare(EventTraceRecord record) { if (record.size() != this.size()) return false; if (record.internalTime != this.internalTime) return false; if (!record.targetName.equals(this.targetName)) return false; return true; } }