1402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/*******************************************************************************
2402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Copyright (c) 2000, 2009 IBM Corporation and others.
3402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * All rights reserved. This program and the accompanying materials
4402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * are made available under the terms of the Eclipse Public License v1.0
5402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * which accompanies this distribution, and is available at
6402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * http://www.eclipse.org/legal/epl-v10.html
7402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *
8402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Contributors:
9402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *     IBM Corporation - initial API and implementation
10402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *******************************************************************************/
11402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollpackage org.eclipse.test.internal.performance.results.db;
12402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
13402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.BufferedInputStream;
14402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.BufferedOutputStream;
15402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.DataInputStream;
16402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.DataOutputStream;
17402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.File;
18402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.FileInputStream;
19402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.FileNotFoundException;
20402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.FileOutputStream;
21402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.io.IOException;
22402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.util.ArrayList;
23402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.util.Arrays;
24402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.util.Comparator;
25402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.util.HashSet;
26402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.util.List;
27402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport java.util.Set;
28402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
29402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport org.eclipse.core.runtime.SubMonitor;
30402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollimport org.eclipse.test.internal.performance.results.utils.Util;
31402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
32402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/**
33402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Class to handle performance results of an eclipse component
34402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * (for example 'org.eclipse.jdt.core').
35402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *
36402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * It gives access to results for each scenario run for this component.
37402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *
38402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @see ScenarioResults
39402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll */
40402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollpublic class ComponentResults extends AbstractResults {
41402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
42402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollpublic ComponentResults(AbstractResults parent, String name) {
43402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	super(parent, name);
44402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	this.printStream = parent.printStream;
45402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
46402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
47402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael MollSet getAllBuildNames() {
48402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	Set buildNames = new HashSet();
49402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int size = size();
50402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	for (int i=0; i<size; i++) {
51402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		ScenarioResults scenarioResults = (ScenarioResults) this.children.get(i);
52402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		Set builds = scenarioResults.getAllBuildNames();
53402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		buildNames.addAll(builds);
54402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
55402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return buildNames;
56402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
57402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
58402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/**
59402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Return all the build names for this component sorted by ascending order.
60402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *
61402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @return An array of names
62402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll */
63402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollpublic String[] getAllSortedBuildNames() {
64402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return getAllSortedBuildNames(false/*ascending order*/);
65402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
66402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
67402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael MollString[] getAllSortedBuildNames(final boolean reverse) {
68402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	Set allBuildNames = getAllBuildNames();
69402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String[] sortedNames = new String[allBuildNames.size()];
70402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	allBuildNames.toArray(sortedNames);
71402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	Arrays.sort(sortedNames, new Comparator() {
72402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		public int compare(Object o1, Object o2) {
73402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			String s1 = (String) (reverse ? o2 : o1);
74402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			String s2 = (String) (reverse ? o1 : o2);
75402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			return Util.getBuildDate(s1).compareTo(Util.getBuildDate(s2));
76402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	    }
77402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	});
78402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return sortedNames;
79402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
80402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
81402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael MollComponentResults getComponentResults() {
82402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return this;
83402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
84402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
85402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/**
86402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Get all results numbers for a given machine of the current component.
87402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *
88402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @param configName The name of the configuration to get numbers
89402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @param fingerprints Set whether only fingerprints scenario should be taken into account
90402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @return A list of lines. Each line represent a build and is a list of either strings or values.
91402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll  * 	Values are an array of double:
92402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 	<ul>
93402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 		<li>{@link #BUILD_VALUE_INDEX}: the build value in milliseconds</li>
94402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 		<li>{@link #BASELINE_VALUE_INDEX}: the baseline value in milliseconds</li>
95402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 		<li>{@link #DELTA_VALUE_INDEX}: the difference between the build value and its more recent baseline</li>
96402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 		<li>{@link #DELTA_ERROR_INDEX}: the error made while computing the difference</li>
97402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 		<li>{@link #BUILD_ERROR_INDEX}: the error made while measuring the build value</li>
98402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 		<li>{@link #BASELINE_ERROR_INDEX}: the error made while measuring the baseline value</li>
99402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * 	</ul>
100402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll*/
101402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollpublic List getConfigNumbers(String configName, boolean fingerprints, List differences) {
102402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
103402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Initialize lists
104402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	AbstractResults[] scenarios = getChildren();
105402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int length = scenarios.length;
106402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
107402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Print scenario names line
108402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	List firstLine = new ArrayList();
109402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	for (int i=0; i<length; i++) {
110402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		ScenarioResults scenarioResults = (ScenarioResults) scenarios[i];
111402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		if (!fingerprints || scenarioResults.hasSummary()) {
112402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			firstLine.add(scenarioResults.getName());
113402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
114402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
115402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
116402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Print each build line
117402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String[] builds = getAllSortedBuildNames(true/*descending order*/);
118402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	int milestoneIndex = 0;
119402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	String milestoneDate = Util.getMilestoneDate(milestoneIndex);
120402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String currentBuildName = null;
121402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int buildsLength= builds.length;
122402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	firstLine.add(0, new Integer(buildsLength));
123402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	differences.add(firstLine);
124402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	for (int i=0; i<buildsLength; i++) {
125402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		List line = new ArrayList();
126402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		String buildName = builds[i];
127402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		line.add(buildName);
128402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		if (!buildName.startsWith(DB_Results.getDbBaselinePrefix())) {
129402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			for (int j=0; j<length; j++) {
130402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				ScenarioResults scenarioResults = (ScenarioResults) scenarios[j];
131402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				if (!fingerprints || scenarioResults.hasSummary()) {
132402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll					ConfigResults configResults = scenarioResults.getConfigResults(configName);
133402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll					BuildResults buildResults = configResults == null ? null : configResults.getBuildResults(buildName);
134402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll					if (buildResults == null) {
135402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll						// no result for this scenario in this build
136402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll						line.add(NO_BUILD_RESULTS);
137402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll					} else {
138402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll						line.add(configResults.getNumbers(buildResults, configResults.getBaselineBuildResults(buildName)));
139402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll					}
140402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				}
141402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
142402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			differences.add(line);
143402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (currentBuildName != null && currentBuildName.charAt(0) != 'N') {
144402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll            }
145402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			currentBuildName = buildName;
146402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
147402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//		if (milestoneDate != null) { // update previous builds
148402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//			int dateComparison = milestoneDate.compareTo(Util.getBuildDate(buildName));
149402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//			if (dateComparison <= 0) {
150402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				if (dateComparison == 0) {
151402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//                }
152402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				if (++milestoneIndex == Util.MILESTONES.length) {
153402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//					milestoneDate = null;
154402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				} else {
155402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//					milestoneDate = Util.getMilestoneDate(milestoneIndex);
156402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				}
157402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//			}
158402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//		}
159402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
160402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
161402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Write differences lines
162402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int last = buildsLength-1;
163402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String lastBuildName = builds[last];
164402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	while (last > 0 && lastBuildName.startsWith(DB_Results.getDbBaselinePrefix())) {
165402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		lastBuildName = builds[--last];
166402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
167402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	appendDifferences(lastBuildName, configName, previousMilestoneName, differences, fingerprints);
168402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	appendDifferences(lastBuildName, configName, previousBuildName, differences, fingerprints);
169402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
170402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Return the computed differences
171402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return differences;
172402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
173402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
174402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/*
175402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Molldouble[] getConfigNumbers(BuildResults buildResults, BuildResults baselineResults) {
176402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (baselineResults == null) {
177402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		return INVALID_RESULTS;
178402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
179402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	double[] values = new double[NUMBERS_LENGTH];
180402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	for (int i=0 ;i<NUMBERS_LENGTH; i++) {
181402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		values[i] = Double.NaN;
182402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
183402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	double buildValue = buildResults.getValue();
184402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	values[BUILD_VALUE_INDEX] = buildValue;
185402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	double baselineValue = baselineResults.getValue();
186402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	values[BASELINE_VALUE_INDEX] = baselineValue;
187402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	double delta = (baselineValue - buildValue) / baselineValue;
188402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	values[DELTA_VALUE_INDEX] = delta;
189402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (Double.isNaN(delta)) {
190402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		return values;
191402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
192402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	long baselineCount = baselineResults.getCount();
193402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	long currentCount = buildResults.getCount();
194402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (baselineCount > 1 && currentCount > 1) {
195402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		double baselineError = baselineResults.getError();
196402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		double currentError = buildResults.getError();
197402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		values[BASELINE_ERROR_INDEX] = baselineError;
198402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		values[BUILD_ERROR_INDEX] = currentError;
199402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		values[DELTA_ERROR_INDEX] = Double.isNaN(baselineError)
200402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				? currentError / baselineValue
201402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				: Math.sqrt(baselineError*baselineError + currentError*currentError) / baselineValue;
202402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
203402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return values;
204402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
205402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll*/
206402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
207402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollprivate ScenarioResults getScenarioResults(List scenarios, int searchedId) {
208402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int size = scenarios.size();
209402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	for (int i=0; i<size; i++) {
210402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		ScenarioResults scenarioResults = (ScenarioResults) scenarios.get(i);
211402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		if (scenarioResults.id == searchedId) {
212402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			return scenarioResults;
213402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
214402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
215402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return null;
216402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
217402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
218402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/**
219402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Returns a list of scenario results which have a summary
220402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll *
221402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @param global Indicates whether the summary must be global or not.
222402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @param config Configuration name
223402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * @return A list of {@link ScenarioResults scenario results} which have a summary
224402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll */
225402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollpublic List getSummaryScenarios(boolean global, String config) {
226402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int size= size();
227402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	List scenarios = new ArrayList(size);
228402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	for (int i=0; i<size; i++) {
229402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		ScenarioResults scenarioResults = (ScenarioResults) this.children.get(i);
230402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		ConfigResults configResults = scenarioResults.getConfigResults(config);
231402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		if (configResults != null) {
232402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			BuildResults buildResults = configResults.getCurrentBuildResults();
233402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if ((global && buildResults.summaryKind == 1) || (!global && buildResults.summaryKind >= 0)) {
234402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarios.add(scenarioResults);
235402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
236402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
237402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
238402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return scenarios;
239402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
240402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
241402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollprivate String lastBuildName(int kind) {
242402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String[] builds = getAllSortedBuildNames();
243402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int idx = builds.length-1;
244402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String lastBuildName = builds[idx--];
245402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	switch (kind) {
246402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		case 1: // no ref
247402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			while (lastBuildName.startsWith(DB_Results.getDbBaselinePrefix())) {
248402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				lastBuildName = builds[idx--];
249402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
250402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			break;
251402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		case 2: // only I-build or M-build
252402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			char ch = lastBuildName.charAt(0);
253402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			while (ch != 'I' && ch != 'M') {
254402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				lastBuildName = builds[idx--];
255402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				ch = lastBuildName.charAt(0);
256402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
257402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			break;
258402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		default:
259402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			break;
260402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
261402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return lastBuildName;
262402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
263402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
264402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/*
265402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Read local file contents and populate the results model with the collected
266402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * information.
267402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll */
268402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael MollString readLocalFile(File dir, List scenarios) throws FileNotFoundException {
269402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	if (!dir.exists()) return null;
270402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	File dataFile = new File(dir, getName()+".dat");	//$NON-NLS-1$
271402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (!dataFile.exists()) throw new FileNotFoundException();
272402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	DataInputStream stream = null;
273402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	try {
274402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		// Read local file info
275402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		stream = new DataInputStream(new BufferedInputStream(new FileInputStream(dataFile)));
276402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		print(" - read local files info"); //$NON-NLS-1$
277402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		String lastBuildName = stream.readUTF(); // first string is the build name
278402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
279402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		// Next field is the number of scenarios for the component
280402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		int size = stream.readInt();
281402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
282402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		// Then follows all the scenario information
283402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		for (int i=0; i<size; i++) {
284402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			// ... which starts with the scenario id
285402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			int scenario_id = stream.readInt();
286402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			ScenarioResults scenarioResults = scenarios == null ? null : getScenarioResults(scenarios, scenario_id);
287402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (scenarioResults == null) {
288402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				// this can happen if scenario pattern does not cover all those stored in local data file
289402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				// hence, creates a fake scenario to read the numbers and skip to the next scenario
290402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarioResults = new ScenarioResults(-1, null, null);
291402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				scenarioResults.parent = this;
292402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				scenarioResults.readData(stream);
293402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				// Should no longer occur as we get all scenarios from database now
294402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//				throw new RuntimeException("Unexpected unfound scenario!"); //$NON-NLS-1$
295402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
296402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			scenarioResults.parent = this;
297402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			scenarioResults.printStream = this.printStream;
298402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			scenarioResults.readData(stream);
299402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			addChild(scenarioResults, true);
300402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (this.printStream != null) this.printStream.print('.');
301402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
302402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		println();
303402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		println("	=> "+size+" scenarios data were read from file "+dataFile); //$NON-NLS-1$ //$NON-NLS-2$
304402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
305402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		// Return last build name stored in the local files
306402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		return lastBuildName;
307402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	} catch (IOException ioe) {
308402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		println("	!!! "+dataFile+" should be deleted as it contained invalid data !!!"); //$NON-NLS-1$ //$NON-NLS-2$
309402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	} finally {
310402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		try {
311402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	        stream.close();
312402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll        } catch (IOException e) {
313402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	        // nothing else to do!
314402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll        }
315402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
316402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	return null;
317402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
318402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
319402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/*
320402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Read the database values for a build name and a list of scenarios.
321402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * The database is read only if the components does not already knows the
322402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * given build (i.e. if it has not been already read) or if the force arguments is set.
323402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll */
324402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollvoid updateBuild(String buildName, List scenarios, boolean force, File dataDir, SubMonitor subMonitor, PerformanceResults.RemainingTimeGuess timeGuess) {
325402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
326402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Read all variations
327402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	println("Component '"+this.name+"':"); //$NON-NLS-1$ //$NON-NLS-2$
328402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
329402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// manage monitor
330402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	int size = scenarios.size();
331402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	subMonitor.setWorkRemaining(size+1);
332402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	StringBuffer buffer = new StringBuffer("Component "); //$NON-NLS-1$
333402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	buffer.append(this.name);
334402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	buffer.append("..."); //$NON-NLS-1$
335402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String title = buffer.toString();
336402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	subMonitor.subTask(title+timeGuess.display());
337402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	timeGuess.count++;
338402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	subMonitor.worked(1);
339402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (subMonitor.isCanceled()) return;
340402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
341402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Read new values for the local result
342402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	boolean dirty = false;
343402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	long readTime = System.currentTimeMillis();
344402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	String log = " - read scenarios from DB:"; //$NON-NLS-1$
345402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (size > 0) {
346402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		for (int i=0; i<size; i++) {
347402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
348402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			// manage monitor
349402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			subMonitor.subTask(title+timeGuess.display());
350402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			timeGuess.count++;
351402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (log != null) {
352402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				println(log);
353402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				log = null;
354402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
355402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
356402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			// read results
357402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			ScenarioResults nextScenarioResults= (ScenarioResults) scenarios.get(i);
358402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			ScenarioResults scenarioResults = (ScenarioResults) getResults(nextScenarioResults.id);
359402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (scenarioResults == null) {
360402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				// Scenario is not known yet, force an update
361402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarioResults = nextScenarioResults;
362402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarioResults.parent = this;
363402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarioResults.printStream = this.printStream;
364402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarioResults.updateBuild(buildName, true);
365402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				dirty = true;
366402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				addChild(scenarioResults, true);
367402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			} else {
368402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				if (scenarioResults.updateBuild(buildName, force)) {
369402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll					dirty = true;
370402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				}
371402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
372402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (dataDir != null && dirty && (System.currentTimeMillis() - readTime) > 300000) { // save every 5mn
373402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				writeData(buildName, dataDir, true, true);
374402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				dirty = false;
375402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				readTime = System.currentTimeMillis();
376402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
377402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
378402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			// manage monitor
379402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			subMonitor.worked(1);
380402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (subMonitor.isCanceled()) return;
381402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
382402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
383402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
384402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Write local files
385402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (dataDir != null) {
386402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		writeData(buildName, dataDir, false, dirty);
387402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
388402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
389402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	// Print global time
390402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	printGlobalTime(readTime);
391402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
392402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
393402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
394402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll/*
395402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll * Write the component results data to the file '<component name>.dat' in the given directory.
396402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll */
397402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Mollvoid writeData(String buildName, File dir, boolean temp, boolean dirty) {
398402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	if (!dir.exists() && !dir.mkdirs()) {
399402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//		System.err.println("can't create directory "+dir); //$NON-NLS-1$
400402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll//	}
401402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	File tmpFile = new File(dir, getName()+".tmp"); //$NON-NLS-1$
402402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	File dataFile = new File(dir, getName()+".dat"); //$NON-NLS-1$
403402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (!dirty) { // only possible on final write
404402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		if (tmpFile.exists()) {
405402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			if (dataFile.exists()) dataFile.delete();
406402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			tmpFile.renameTo(dataFile);
407402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			println("	=> rename temporary file to "+dataFile); //$NON-NLS-1$
408402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
409402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		return;
410402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
411402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (tmpFile.exists()) {
412402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		tmpFile.delete();
413402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
414402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	File file;
415402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	if (temp) {
416402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		file = tmpFile;
417402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	} else {
418402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		if (dataFile.exists()) {
419402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			dataFile.delete();
420402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
421402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		file = dataFile;
422402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
423402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	try {
424402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		DataOutputStream stream = new DataOutputStream(new BufferedOutputStream(new FileOutputStream(file)));
425402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		try {
426402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			int size = this.children.size();
427402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			stream.writeUTF(lastBuildName(0));
428402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			stream.writeInt(size);
429402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			for (int i=0; i<size; i++) {
430402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				ScenarioResults scenarioResults = (ScenarioResults) this.children.get(i);
431402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll				scenarioResults.write(stream);
432402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			}
433402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
434402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		finally {
435402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			stream.close();
436402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll			println("	=> extracted data "+(temp?"temporarily ":"")+"written in file "+file); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
437402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		}
438402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	} catch (FileNotFoundException e) {
439402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		System.err.println("can't create output file"+file); //$NON-NLS-1$
440402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	} catch (IOException e) {
441402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll		e.printStackTrace();
442402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll	}
443402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
444402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll
445402794e73aed8611d62eb4b01cd155e2d76fcb87Raphael Moll}
446