All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.graalvm.visualvm.lib.profiler.ResultsManager Maven / Gradle / Ivy

/*
 * Copyright (c) 1997, 2021, Oracle and/or its affiliates. All rights reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.  Oracle designates this
 * particular file as subject to the "Classpath" exception as provided
 * by Oracle in the LICENSE file that accompanied this code.
 *
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 * or visit www.oracle.com if you need additional information or have any
 * questions.
 */

package org.graalvm.visualvm.lib.profiler;

import java.awt.Cursor;
import java.awt.Window;
import java.io.*;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;
import java.util.*;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JFileChooser;
import org.netbeans.api.progress.ProgressHandle;
import org.graalvm.visualvm.lib.jfluid.ProfilerClient;
import org.graalvm.visualvm.lib.jfluid.ProfilerLogger;
import org.graalvm.visualvm.lib.jfluid.TargetAppRunner;
import org.graalvm.visualvm.lib.jfluid.client.ClientUtils;
import org.graalvm.visualvm.lib.common.CommonUtils;
import org.graalvm.visualvm.lib.common.Profiler;
import org.graalvm.visualvm.lib.common.ProfilingSettings;
import org.graalvm.visualvm.lib.jfluid.global.CommonConstants;
import org.graalvm.visualvm.lib.jfluid.results.ProfilingResultsDispatcher;
import org.graalvm.visualvm.lib.jfluid.results.ResultsSnapshot;
import org.graalvm.visualvm.lib.jfluid.results.RuntimeCCTNode;
import org.graalvm.visualvm.lib.jfluid.results.cpu.CPUCCTProvider;
import org.graalvm.visualvm.lib.jfluid.results.cpu.CPUResultsDiff;
import org.graalvm.visualvm.lib.jfluid.results.cpu.CPUResultsSnapshot;
import org.graalvm.visualvm.lib.jfluid.results.jdbc.JdbcResultsDiff;
import org.graalvm.visualvm.lib.jfluid.results.jdbc.JdbcResultsSnapshot;
import org.graalvm.visualvm.lib.jfluid.results.memory.AllocMemoryResultsDiff;
import org.graalvm.visualvm.lib.jfluid.results.memory.AllocMemoryResultsSnapshot;
import org.graalvm.visualvm.lib.jfluid.results.memory.LivenessMemoryResultsDiff;
import org.graalvm.visualvm.lib.jfluid.results.memory.LivenessMemoryResultsSnapshot;
import org.graalvm.visualvm.lib.jfluid.results.memory.MemoryCCTProvider;
import org.graalvm.visualvm.lib.jfluid.results.memory.SampledMemoryResultsDiff;
import org.graalvm.visualvm.lib.jfluid.results.memory.SampledMemoryResultsSnapshot;
import org.graalvm.visualvm.lib.ui.swing.ExportUtils;
import org.graalvm.visualvm.lib.jfluid.utils.StringUtils;
import org.graalvm.visualvm.lib.profiler.api.ProfilerDialogs;
import org.graalvm.visualvm.lib.profiler.api.ProfilerStorage;
import org.graalvm.visualvm.lib.profiler.utilities.ProfilerUtils;
import org.openide.cookies.OpenCookie;
import org.openide.filesystems.FileLock;
import org.openide.filesystems.FileObject;
import org.openide.filesystems.FileUtil;
import org.openide.loaders.DataObject;
import org.openide.loaders.DataObjectNotFoundException;
import org.openide.util.Exceptions;
import org.openide.util.Lookup;
import org.openide.util.NbBundle;
import org.openide.util.lookup.ServiceProvider;
import org.openide.util.lookup.ServiceProviders;
import org.openide.windows.WindowManager;


/** An manager for management/notifications about obtainer profiling results.
 *
 * @author Tomas Hurka
 * @author Ian Formanek
 */
@NbBundle.Messages({
    "ResultsManager_SnapshotSaveFailedMsg=Failed to save snapshot: {0}",
    "ResultsManager_SnapshotCreateFailedMsg=Failed to create snapshot file: {0}",
    "ResultsManager_ProfiledAppTerminatedMsg=Failed to obtain results snapshot. The profiled application terminated.",
    "ResultsManager_DataNotAvailableMsg=Failed to obtain results snapshot. Data is not available yet.",
    "ResultsManager_OutOfMemoryMsg=Too much data collected - the profiler ran out of memory.\n\nCollected profiling data has been deleted and profiling resumed.\nTo avoid this error please increase the -Xmx value\nin the etc/visualvm.conf file in VisualVM directory\nor decrease the amount of detail in profiling settings.",
    "ResultsManager_SnapshotDeleteFailedMsg=Failed to delete the snapshot file: {0}",
    "ResultsManager_CantFindSnapshotLocationMsg=Cannot find default location for snapshot in project: {0}",
    "ResultsManager_SnapshotCreateInProjectFailedMsg=Failed to create snapshot file in project: {0}",
    "ResultsManager_SnapshotLoadFailed=Error while loading snapshot: {0}",
    "ResultsManager_SnapshotsLoadFailedMsg=Loading snapshots failed.",
    "ResultsManager_ObtainSavedSnapshotsFailedMsg=Failed to obtain list of saved snaphshots for project: {0}",
    "ResultsManager_SelectDirDialogCaption=Select Target Directory",
    "ResultsManager_SaveButtonName=Save",
    "ResultsManager_OverwriteFileDialogCaption=Overwrite Existing File?",
    "ResultsManager_OverwriteFileDialogMsg=The target folder already contains file {0}\n Do you want to overwrite this file?",
    "ResultsManager_FileDeleteFailedMsg=Cannot delete the existing file: {0}",
    "ResultsManager_SnapshotExportFailedMsg=Failed to export snapshot:

{0}", "ResultsManager_ExportSnapshotData=Export Snapshot Data", "ResultsManager_SelectFileOrDirDialogCaption=Select File or Directory", "ResultsManager_ProfilerSnapshotFileFilter=Profiler Snapshot File (*.{0})", "ResultsManager_ProfilerHeapdumpFileFilter=Heap Dump File (*.{0})", "ResultsManager_OutOfMemorySavingMsg=Not enough memory to save the snapshot.

To avoid this error please increase the -Xmx value
in the etc/visualvm.conf file in VisualVM directory.", "ResultsManager_CannotCompareSnapshotsMsg=Cannot compare snapshots:

{0}
{1}

Make sure that both snaphots are the same type.", "ResultsManager_DirectoryDoesntExistCaption=Selected Directory Does Not Exist", "ResultsManager_DirectoryDoesntExistMsg=The directory you have selected does not exist.\nDo you want to create the directory?", "ResultsManager_SnapshotLoadFailedMsg=Snapshot {0} failed to load.

{1}", "ResultsManager_CannotOpenSnapshotMsg=Cannot open profiler snapshot.

Attempting to open null snapshot.
Check the logfile for details.", "ResultsManager_CpuSnapshotDisplayName=cpu: {0}", "ResultsManager_MemorySnapshotDisplayName=mem: {0}", "ResultsManager_HeapSnapshotDisplayName=heap: {0}", "MSG_SavingSnapshots=Saving Snapshots", "MSG_SavingSnapshot=Saving Snapshot", "ResultsManager_CaptionWarning=Warning", "ResultsManager_DifferentObjectSize=Object sizes are different.

Size of the same objects differ for each snapshot and their comparison is invalid.
The snapshots have likely been taken on different architectures (32bit vs. 64bit)." }) public final class ResultsManager { final private static Logger LOGGER = Logger.getLogger(ResultsManager.class.getName()); //~ Inner Classes ------------------------------------------------------------------------------------------------------------ // /** // * Resets collected results (either memory or CPU, depending on current mode). // */ // public void resetCollectors() { // reset(); // int instr = Profiler.getDefault().getTargetAppRunner().getProfilerClient().getCurrentInstrType(); // ProfilingResultsDispatcher.getDefault().reset(); // if (instr == CommonConstants.INSTR_RECURSIVE_FULL || instr == CommonConstants.INSTR_RECURSIVE_SAMPLED) { // // TODO reset cpu profiling results collectors //// CPUCallGraphBuilder.resetCollectors(); // } else if (instr == CommonConstants.INSTR_OBJECT_ALLOCATIONS || instr == CommonConstants.INSTR_OBJECT_LIVENESS) { // MemoryCallGraphBuilder mcgb = Profiler.getDefault().getTargetAppRunner().getProfilerClient().getMemoryCallGraphBuilder(); // mcgb.resetCollectors(); // } // fireResultsReset(); // } static class SelectedFile { //~ Instance fields ------------------------------------------------------------------------------------------------------ FileObject folder; String fileExt; String fileName; //~ Constructors --------------------------------------------------------------------------------------------------------- SelectedFile(FileObject folder, String fileName, String fileExt) { this.folder = folder; this.fileName = fileName; this.fileExt = fileExt; } } //~ Static fields/initializers ----------------------------------------------------------------------------------------------- public static final String SNAPSHOT_EXTENSION = "nps"; // NOI18N public static final String HEAPDUMP_EXTENSION = "hprof"; // NOI18N /* see org.netbeans.modules.sampler.SampleOutputStream.FILE_EXT */ public static final String STACKTRACES_SNAPSHOT_EXTENSION = "npss"; // NOI18N static final String HEAPDUMP_PREFIX = "heapdump-"; // NOI18N // should differ from generated OOME heapdumps not to be detected as OOME private static final String SNAPSHOT_PREFIX = "snapshot-"; // NOI18N private static final long MINIMAL_TIMESTAMP = 946684800000L; // Sat, 01 Jan 2000 00:00:00 GMT in milliseconds since 01 Jan 1970 //~ Instance fields ---------------------------------------------------------------------------------------------------------- private ArrayList loadedSnapshots = new ArrayList(); private File exportDir; private HashMap settingsCache = new HashMap(); private HashMap typeCache = new HashMap(); private Window mainWindow; private boolean resultsAvailable = false; private Lookup.Result snapshotListeners; private Lookup.Result resultsListeners; //~ Constructors ------------------------------------------------------------------------------------------------------------- private ResultsManager() { Lookup l = Lookup.getDefault(); snapshotListeners = l.lookupResult(SnapshotsListener.class); resultsListeners = l.lookupResult(ResultsListener.class); } private static class Singleton { final private static ResultsManager INSTANCE = new ResultsManager(); } //~ Methods ------------------------------------------------------------------------------------------------------------------ public static ResultsManager getDefault() { return Singleton.INSTANCE; } public String getDefaultSnapshotFileName(LoadedSnapshot ls) { return SNAPSHOT_PREFIX + ls.getSnapshot().getTimeTaken(); } public String getSnapshotDisplayName(LoadedSnapshot ls) { String name = ls.getFile() == null ? null : ls.getFile().getName(); if (name == null) { name = getDefaultSnapshotFileName(ls); } else { int dotIndex = name.lastIndexOf('.'); // NOI18N if (dotIndex > 0 && dotIndex <= name.length() - 2) name = name.substring(0, dotIndex); } return getSnapshotDisplayName(name, ls.getType()); } public String getSnapshotDisplayName(String fileName, int snapshotType) { String displayName; if (fileName.startsWith(SNAPSHOT_PREFIX)) { String time = fileName.substring(SNAPSHOT_PREFIX.length(), fileName.length()); try { long timeStamp = Long.parseLong(time); if (timeStamp > MINIMAL_TIMESTAMP) { displayName = StringUtils.formatUserDate(new Date(timeStamp)); } else { // file name is probably customized displayName = fileName; } } catch (NumberFormatException e) { // file name is probably customized displayName = fileName; } } else { displayName = fileName; } // switch (snapshotType) { // case LoadedSnapshot.SNAPSHOT_TYPE_CPU: // return Bundle.ResultsManager_CpuSnapshotDisplayName(displayName); // case LoadedSnapshot.SNAPSHOT_TYPE_MEMORY_ALLOCATIONS: // case LoadedSnapshot.SNAPSHOT_TYPE_MEMORY_LIVENESS: // case LoadedSnapshot.SNAPSHOT_TYPE_MEMORY_SAMPLED: // return Bundle.ResultsManager_MemorySnapshotDisplayName(displayName); // default: // return displayName; // } return displayName; } public String getDefaultHeapDumpFileName(long time) { return HEAPDUMP_PREFIX + time; } public String getHeapDumpDisplayName(String fileName) { String displayName; if (fileName.startsWith(HEAPDUMP_PREFIX)) { String time = fileName.substring(HEAPDUMP_PREFIX.length(), fileName.length()); try { long timeStamp = Long.parseLong(time); if (timeStamp > MINIMAL_TIMESTAMP) { displayName = StringUtils.formatUserDate(new Date(timeStamp)); } else { // file name is probably customized displayName = fileName; } } catch (NumberFormatException e) { // file name is probably customized displayName = fileName; } } else { displayName = fileName; } return displayName; // return Bundle.ResultsManager_HeapSnapshotDisplayName(displayName); } public LoadedSnapshot[] getLoadedSnapshots() { return loadedSnapshots.toArray(new LoadedSnapshot[0]); } public LoadedSnapshot getSnapshotFromFileObject(FileObject fo) { LoadedSnapshot ls = findAlreadyLoadedSnapshot(fo); if (ls != null) { return ls; } try { return loadSnapshotFromFileObject(fo); } catch (IOException e) { LOGGER.log(Level.SEVERE, null, e); return null; } } public ProfilingSettings getSnapshotSettings(FileObject fo) { ProfilingSettings settings = settingsCache.get(fo); if ((settings == null) && !settingsCache.containsKey(fo)) { settings = readSettingsFromFile(fo); settingsCache.put(fo, settings); } return settings; } public int getSnapshotType(FileObject fo) { Integer type = typeCache.get(fo); if (type == null) { type = Integer.valueOf(readTypeFromFile(fo)); typeCache.put(fo, type); } return type.intValue(); } @ServiceProviders({@ServiceProvider(service=CPUCCTProvider.Listener.class), @ServiceProvider(service=MemoryCCTProvider.Listener.class)}) public static final class ResultsMonitor implements CPUCCTProvider.Listener, MemoryCCTProvider.Listener { //~ Methods -------------------------------------------------------------------------------------------------------------- public void cctEstablished(RuntimeCCTNode runtimeCCTNode, boolean empty) { if (!empty) { ResultsManager rm = getDefault(); if (!rm.resultsAvailable() && !isSomeResultsAvailable()) { return; } rm.resultsBecameAvailable(); } } public void cctReset() { getDefault().resultsReset(); } private boolean isSomeResultsAvailable() { // check that we have data for snapshot, CPU profiling can have non-empty // batch, but this batch can contain only marker methods Profiler profiler = Profiler.getDefault(); ProfilerClient client = profiler.getTargetAppRunner().getProfilerClient(); int profilingType = profiler.getLastProfilingSettings().getProfilingType(); if (profilingType == ProfilingSettings.PROFILE_CPU_ENTIRE || profilingType == ProfilingSettings.PROFILE_CPU_PART) { try { // construct snapshot and check that it has some data client.getCPUProfilingResultsSnapshot(false); } catch (CPUResultsSnapshot.NoDataAvailableException ex) { // we don't have data for snapshot return false; } catch (ClientUtils.TargetAppOrVMTerminated ex) { // target VM is down return false; } } return true; } } public void closeSnapshot(LoadedSnapshot ls) { if (ls != null) { loadedSnapshots.remove(ls); fireSnapshotRemoved(ls); } } public void compareSnapshots(FileObject snapshot1FO, FileObject snapshot2FO) { LoadedSnapshot s1 = null; LoadedSnapshot s2 = null; FileObject snapshotFO = snapshot1FO; try { s1 = findAlreadyLoadedSnapshot(snapshot1FO); if (s1 == null) { s1 = loadSnapshotImpl(snapshot1FO); } snapshotFO = snapshot2FO; s2 = findAlreadyLoadedSnapshot(snapshot2FO); if (s2 == null) { s2 = loadSnapshotFromFileObject(snapshot2FO); } } catch (Exception e) { LOGGER.log(Level.INFO, Bundle.ResultsManager_SnapshotLoadFailed(snapshotFO.getPath()), e); ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotLoadFailedMsg(snapshotFO.getNameExt(), e.getMessage())); return; } if ((s1 != null) && (s2 != null)) { compareSnapshots(s1, s2); } else { ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotsLoadFailedMsg()); } } public ResultsSnapshot createDiffSnapshot(LoadedSnapshot s1, LoadedSnapshot s2) { ResultsSnapshot snap1 = s1.getSnapshot(); ResultsSnapshot snap2 = s2.getSnapshot(); ResultsSnapshot diff = null; if (snap1 instanceof SampledMemoryResultsSnapshot && snap2 instanceof SampledMemoryResultsSnapshot) { SampledMemoryResultsSnapshot sn1 = (SampledMemoryResultsSnapshot)snap1; SampledMemoryResultsSnapshot sn2 = (SampledMemoryResultsSnapshot)snap2; checkObjectSizes(sn1.getClassNames(), sn1.getObjectsCounts(), sn1.getObjectsSizePerClass(), 1, sn2.getClassNames(), sn2.getObjectsCounts(), sn2.getObjectsSizePerClass(), 1); diff = new SampledMemoryResultsDiff((SampledMemoryResultsSnapshot)snap1, (SampledMemoryResultsSnapshot)snap2); } else if (snap1 instanceof AllocMemoryResultsSnapshot && snap2 instanceof AllocMemoryResultsSnapshot) { AllocMemoryResultsSnapshot sn1 = (AllocMemoryResultsSnapshot)snap1; AllocMemoryResultsSnapshot sn2 = (AllocMemoryResultsSnapshot)snap2; // Note: instrumented allocations not compared because of #236363 // ProfilingSettings sn1s = s1.getSettings(); // ProfilingSettings sn2s = s2.getSettings(); // checkObjectSizes(sn1.getClassNames(), sn1.getObjectsCounts(), sn1.getObjectsSizePerClass(), sn1s.getAllocTrackEvery(), // sn2.getClassNames(), sn2.getObjectsCounts(), sn2.getObjectsSizePerClass(), sn2s.getAllocTrackEvery()); checkObjectSizes(sn1.getClassNames(), sn1.getObjectsCounts(), sn1.getObjectsSizePerClass(), Integer.MAX_VALUE, sn2.getClassNames(), sn2.getObjectsCounts(), sn2.getObjectsSizePerClass(), Integer.MAX_VALUE); diff = new AllocMemoryResultsDiff((AllocMemoryResultsSnapshot)snap1, (AllocMemoryResultsSnapshot)snap2); } else if (snap1 instanceof LivenessMemoryResultsSnapshot && snap2 instanceof LivenessMemoryResultsSnapshot) { LivenessMemoryResultsSnapshot sn1 = (LivenessMemoryResultsSnapshot)snap1; LivenessMemoryResultsSnapshot sn2 = (LivenessMemoryResultsSnapshot)snap2; // Note: using track each 1 object to prevent unnecessary division, the data are always correct for liveness results // ProfilingSettings sn1s = s1.getSettings(); // ProfilingSettings sn2s = s2.getSettings(); // checkObjectSizes(sn1.getClassNames(), sn1.getNTrackedLiveObjects(), sn1.getTrackedLiveObjectsSize(), sn1s.getAllocTrackEvery(), // sn2.getClassNames(), sn2.getNTrackedLiveObjects(), sn2.getTrackedLiveObjectsSize(), sn2s.getAllocTrackEvery()); checkObjectSizes(sn1.getClassNames(), sn1.getNTrackedLiveObjects(), sn1.getTrackedLiveObjectsSize(), 1, sn2.getClassNames(), sn2.getNTrackedLiveObjects(), sn2.getTrackedLiveObjectsSize(), 1); diff = new LivenessMemoryResultsDiff((LivenessMemoryResultsSnapshot)snap1, (LivenessMemoryResultsSnapshot)snap2); } else if (snap1 instanceof CPUResultsSnapshot && snap2 instanceof CPUResultsSnapshot) { diff = new CPUResultsDiff((CPUResultsSnapshot)snap1, (CPUResultsSnapshot)snap2); } else if (snap1 instanceof JdbcResultsSnapshot && snap2 instanceof JdbcResultsSnapshot) { diff = new JdbcResultsDiff((JdbcResultsSnapshot)snap1, (JdbcResultsSnapshot)snap2); } return diff; } public void compareSnapshots(final LoadedSnapshot s1, final LoadedSnapshot s2) { CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { SnapshotResultsWindow srw = SnapshotResultsWindow.get(s1, 0, false); if (!srw.setRefSnapshot(s2)) { ProfilerDialogs.displayError(Bundle.ResultsManager_CannotCompareSnapshotsMsg( s1.getFile().getName(), s2.getFile().getName())); } else { srw.open(); srw.requestActive(); } } }); } static void checkObjectSizes(String[] names1, int[] counts1, long[] sizes1, int n1, String[] names2, int[] counts2, long[] sizes2, int n2) { String obj1 = "java.lang.Object"; // NOI18N // Sampled snapshots String obj2 = "java/lang/Object"; // NOI18N // Instrumented snapshots int idx1 = -1; for (int i = 0; i < names1.length; i++) if (obj1.equals(names1[i]) || obj2.equals(names1[i])) { idx1 = i; break; } if (idx1 == -1 || counts1[idx1] == 0) return; // Should not happen int idx2 = -1; for (int i = 0; i < names2.length; i++) if (obj1.equals(names2[i]) || obj2.equals(names2[i])) { idx2 = i; break; } if (idx2 == -1 || counts2[idx2] == 0) return; // Should not happen // Note: instrumented allocations not compared because of #236363 long objsize1 = n1 == 1 ? sizes1[idx1] / counts1[idx1] : 0; long objsize2 = n2 == 1 ? sizes2[idx2] / counts2[idx2] : 0; if (objsize1 != objsize2) ProfilerDialogs.displayWarningDNSA(Bundle.ResultsManager_DifferentObjectSize(), Bundle.ResultsManager_CaptionWarning(), null, "ResultsManager.checkObjectSizes", false); // NOI18N } public void deleteSnapshot(FileObject snapshotFile) { LoadedSnapshot ls = findLoadedSnapshot(FileUtil.toFile(snapshotFile)); try { snapshotFile.delete(); } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_SnapshotDeleteFailedMsg(e.getMessage()), e); return; // do not proceed with removing the snapshot from internal structures } if (ls != null) { // if the snapshot has been loaded, remove the internal structures as well loadedSnapshots.remove(ls); fireSnapshotRemoved(ls); } } public void exportSnapshots(final FileObject[] selectedSnapshots) { assert (selectedSnapshots != null); assert (selectedSnapshots.length > 0); final String[] fileName = new String[1], fileExt = new String[1]; final FileObject[] dir = new FileObject[1]; if (selectedSnapshots.length == 1) { SelectedFile sf = selectSnapshotTargetFile(selectedSnapshots[0].getName(), selectedSnapshots[0].getExt().equals(HEAPDUMP_EXTENSION)); if ((sf != null) && checkFileExists(sf)) { fileName[0] = sf.fileName; fileExt[0] = sf.fileExt; dir[0] = sf.folder; } else { // dialog cancelled by the user return; } } else { JFileChooser chooser = new JFileChooser(); if (exportDir != null) { chooser.setCurrentDirectory(exportDir); } chooser.setDialogTitle(Bundle.ResultsManager_SelectDirDialogCaption()); chooser.setApproveButtonText(Bundle.ResultsManager_SaveButtonName()); chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY); chooser.setMultiSelectionEnabled(false); if (chooser.showSaveDialog(WindowManager.getDefault().getMainWindow()) == JFileChooser.APPROVE_OPTION) { File file = chooser.getSelectedFile(); if (!file.exists()) { if (!ProfilerDialogs.displayConfirmation( Bundle.ResultsManager_DirectoryDoesntExistMsg(), Bundle.ResultsManager_DirectoryDoesntExistCaption())) { return; // cancelled by the user } file.mkdir(); } exportDir = file; dir[0] = FileUtil.toFileObject(FileUtil.normalizeFile(file)); } else { // dialog cancelled return; } } final ProgressHandle ph = ProgressHandle.createHandle(Bundle.MSG_SavingSnapshots()); ph.setInitialDelay(500); ph.start(); ProfilerUtils.runInProfilerRequestProcessor(new Runnable() { @Override public void run() { try { for (int i = 0; i < selectedSnapshots.length; i++) { exportSnapshot(selectedSnapshots[i], dir[0], fileName[0] != null ? fileName[0] : selectedSnapshots[i].getName(), fileExt[0] != null ? fileExt[0] : selectedSnapshots[i].getExt()); } } finally { ph.finish(); } } }); } public LoadedSnapshot findLoadedSnapshot(ResultsSnapshot snapshot) { Iterator it = loadedSnapshots.iterator(); while (it.hasNext()) { LoadedSnapshot ls = (LoadedSnapshot) it.next(); if (ls.getSnapshot() == snapshot) { return ls; } } return null; } public LoadedSnapshot findLoadedSnapshot(File snapshotFile) { Iterator it = loadedSnapshots.iterator(); while (it.hasNext()) { LoadedSnapshot ls = (LoadedSnapshot) it.next(); if ((ls.getFile() != null) && ls.getFile().equals(snapshotFile)) { return ls; } } return null; } private static final String HPROF_HEADER = "JAVA PROFILE 1.0"; // NOI18H private static final long MIN_HPROF_SIZE = 1024*1024L; public static boolean checkHprofFile(File file) { try { if (file.isFile() && file.canRead() && file.length()>MIN_HPROF_SIZE) { // heap dump must be 1M and bigger byte[] prefix = new byte[HPROF_HEADER.length()+4]; RandomAccessFile raf = new RandomAccessFile(file,"r"); // NOI18H raf.readFully(prefix); raf.close(); if (new String(prefix).startsWith(HPROF_HEADER)) { return true; } } } catch (FileNotFoundException ex) { return false; } catch (IOException ex) { return false; } return false; } public FileObject[] listSavedHeapdumps(Lookup.Provider project, File directory) { try { FileObject snapshotsFolder = null; if (project == null && directory != null) { snapshotsFolder = FileUtil.toFileObject(directory); } else { snapshotsFolder = ProfilerStorage.getProjectFolder(project, false); } if (snapshotsFolder == null) { return new FileObject[0]; } snapshotsFolder.refresh(); FileObject[] children = snapshotsFolder.getChildren(); ArrayList /**/ files = new ArrayList /**/(); for (int i = 0; i < children.length; i++) { FileObject child = children[i]; if (checkHprofFile(FileUtil.toFile(children[i]))) files.add(child); } Collections.sort(files, new Comparator() { public int compare(Object o1, Object o2) { FileObject f1 = (FileObject) o1; FileObject f2 = (FileObject) o2; return f1.getName().compareTo(f2.getName()); } }); return (FileObject[])files.toArray(new FileObject[0]); } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_ObtainSavedSnapshotsFailedMsg(e.getMessage()), e); return new FileObject[0]; } } public FileObject[] listSavedSnapshots(Lookup.Provider project, File directory) { try { FileObject snapshotsFolder = null; if (project == null && directory != null) { snapshotsFolder = FileUtil.toFileObject(directory); } else { snapshotsFolder = ProfilerStorage.getProjectFolder(project, false); } if (snapshotsFolder == null) { return new FileObject[0]; } snapshotsFolder.refresh(); FileObject[] children = snapshotsFolder.getChildren(); ArrayList /**/ files = new ArrayList /**/(); for (int i = 0; i < children.length; i++) { FileObject child = children[i]; if (child.getExt().equalsIgnoreCase(SNAPSHOT_EXTENSION)) { files.add(child); } } Collections.sort(files, new Comparator() { public int compare(Object o1, Object o2) { FileObject f1 = (FileObject) o1; FileObject f2 = (FileObject) o2; return f1.getName().compareTo(f2.getName()); } }); return (FileObject[])files.toArray(new FileObject[0]); } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_ObtainSavedSnapshotsFailedMsg(e.getMessage()), e); return new FileObject[0]; } } public boolean hasSnapshotsFor(Lookup.Provider project) { try { FileObject snapshotsFolder = ProfilerStorage.getProjectFolder(project, false); FileObject[] children; if (snapshotsFolder == null) { return false; } snapshotsFolder.refresh(); children = snapshotsFolder.getChildren(); for (FileObject child : children) { if (child.getExt().equalsIgnoreCase(SNAPSHOT_EXTENSION)) return true; if (checkHprofFile(FileUtil.toFile(child))) return true; } } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_ObtainSavedSnapshotsFailedMsg(e.getMessage()), e); } return false; } public int getSnapshotsCountFor(Lookup.Provider project) { int count = 0; try { FileObject snapshotsFolder = ProfilerStorage.getProjectFolder(project, false); FileObject[] children; if (snapshotsFolder == null) { return count; } snapshotsFolder.refresh(); children = snapshotsFolder.getChildren(); for (FileObject child : children) { if (child.getExt().equalsIgnoreCase(SNAPSHOT_EXTENSION) || checkHprofFile(FileUtil.toFile(child))) count++; } } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_ObtainSavedSnapshotsFailedMsg(e.getMessage()), e); } return count; } public LoadedSnapshot loadSnapshot(FileObject selectedFile) { try { return loadSnapshotImpl(selectedFile); } catch (IOException e) { LOGGER.log(Level.INFO, Bundle.ResultsManager_SnapshotLoadFailed(selectedFile.getPath()), e); ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotLoadFailedMsg(selectedFile.getNameExt(), e.getMessage())); return null; } } public LoadedSnapshot[] loadSnapshots(FileObject[] selectedFiles) { LoadedSnapshot[] ret = new LoadedSnapshot[selectedFiles.length]; for (int i = 0; i < selectedFiles.length; i++) { try { if (selectedFiles[i] != null) { ret[i] = loadSnapshotImpl(selectedFiles[i]); } } catch (IOException e) { LOGGER.log(Level.INFO, Bundle.ResultsManager_SnapshotLoadFailed(selectedFiles[i].getPath()), e); ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotLoadFailedMsg(selectedFiles[i].getNameExt(), e.getMessage())); } } return ret; } public void openSnapshot(File snapshot) { File sf = FileUtil.normalizeFile(snapshot); FileObject snapshotFo = FileUtil.toFileObject(sf); openSnapshot(snapshotFo); } public void openSnapshot(FileObject snapshotFo) { try { DataObject snapshotDo = DataObject.find(snapshotFo); OpenCookie open = snapshotDo.getCookie(OpenCookie.class); if (open != null) { open.open(); } } catch (DataObjectNotFoundException ex) { Exceptions.printStackTrace(ex); } } public void openSnapshot(LoadedSnapshot ls) { openSnapshot(ls, CommonConstants.SORTING_COLUMN_DEFAULT, false); // target component decides which column will be used for sorting } public void openSnapshot(final LoadedSnapshot ls, final int sortingColumn, final boolean sortingOrder) { if (ls == null) ProfilerDialogs.displayError(Bundle.ResultsManager_CannotOpenSnapshotMsg()); else CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { SnapshotResultsWindow srw = SnapshotResultsWindow.get(ls, sortingColumn, sortingOrder); srw.open(); srw.requestActive(); } }); } public void openSnapshots(LoadedSnapshot[] loaded) { LoadedSnapshot loadedSnapshot = null; try { SnapshotResultsWindow srw = null; for (int i = 0; i < loaded.length; i++) { loadedSnapshot = loaded[i]; if (loaded[i] != null) { srw = SnapshotResultsWindow.get(loadedSnapshot); srw.open(); } } if (srw != null) { srw.requestActive(); // activate the last one } } catch (Exception e) { LOGGER.log(Level.INFO, Bundle.ResultsManager_SnapshotLoadFailed(loadedSnapshot.getFile().getAbsoluteFile()), e); ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotLoadFailedMsg(loadedSnapshot.getFile().getName(), e.getMessage())); } } public LoadedSnapshot prepareSnapshot() { return prepareSnapshot(true); } public LoadedSnapshot prepareSnapshot(boolean reqeustData) { ResultsSnapshot snapshot = null; if (!resultsAvailable()) { return null; } try { final Profiler profiler = Profiler.getDefault(); final TargetAppRunner runner = profiler.getTargetAppRunner(); final ProfilerClient client = runner.getProfilerClient(); final int currentProfilingType = profiler.getLastProfilingSettings().getProfilingType(); try { switch (currentProfilingType) { case ProfilingSettings.PROFILE_MEMORY_ALLOCATIONS: case ProfilingSettings.PROFILE_MEMORY_LIVENESS: case ProfilingSettings.PROFILE_MEMORY_SAMPLING: snapshot = client.getMemoryProfilingResultsSnapshot(reqeustData); break; case ProfilingSettings.PROFILE_CPU_ENTIRE: case ProfilingSettings.PROFILE_CPU_PART: case ProfilingSettings.PROFILE_CPU_SAMPLING: snapshot = client.getCPUProfilingResultsSnapshot(reqeustData); break; case ProfilingSettings.PROFILE_CPU_STOPWATCH: snapshot = client.getCodeRegionProfilingResultsSnapshot(); break; case ProfilingSettings.PROFILE_CPU_JDBC: snapshot = client.getJdbcProfilingResultsSnapshot(reqeustData); break; } } catch (ClientUtils.TargetAppOrVMTerminated e1) { ProfilerDialogs.displayWarning(Bundle.ResultsManager_ProfiledAppTerminatedMsg()); ProfilerLogger.log(e1.getMessage()); } catch (CPUResultsSnapshot.NoDataAvailableException e2) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_DataNotAvailableMsg(), e2); } catch (OutOfMemoryError e) { try { reset(); // reset the client data runner.resetTimers(); // reset the server data } catch (ClientUtils.TargetAppOrVMTerminated targetAppOrVMTerminated) { // the target app has died; clean up all client data client.resetClientData(); } LOGGER.log(Level.SEVERE, Bundle.ResultsManager_OutOfMemoryMsg(), e); } } finally { if (snapshot != null) { ProfilingSettings settings = new ProfilingSettings(); Profiler.getDefault().getLastProfilingSettings().copySettingsInto(settings); settings.setSettingsName(Profiler.getDefault().getLastProfilingSettings().getSettingsName()); Lookup.Provider profiledProject = NetBeansProfiler.getDefaultNB().getProfiledProject(); return new LoadedSnapshot(snapshot, settings, null, profiledProject); } } return null; } /** * This should be called when the app is restarted or "Reset Collected Results" is invoked (because once this happened, * there are all sorts of data that's going to be deleted/changed, and an attempt to do something with old results displayed * here can cause big problems). It should also set the results panel invisible (or is it already happening?) etc. */ public void reset() { ProfilingResultsDispatcher.getDefault().reset(); resultsReset(); } public boolean resultsAvailable() { return resultsAvailable; } public static interface SnapshotHandle { public LoadedSnapshot getSnapshot(); } public ExportUtils.Exportable createSnapshotExporter(final LoadedSnapshot snapshot) { return createSnapshotExporter(new SnapshotHandle() { public LoadedSnapshot getSnapshot() { return snapshot; } }); } public ExportUtils.Exportable createSnapshotExporter(final SnapshotHandle handle) { return new ExportUtils.Exportable() { public String getName() { return Bundle.ResultsManager_ExportSnapshotData(); } public boolean isEnabled() { return true; } public ExportUtils.ExportProvider[] getProviders() { final LoadedSnapshot snapshot = handle.getSnapshot(); return new ExportUtils.ExportProvider[] { new ExportUtils.AbstractNPSExportProvider(snapshot.getFile()) { protected void doExport(File targetFile) { exportSnapshot(snapshot, targetFile); } } }; } }; } private boolean exportSnapshot(LoadedSnapshot snapshot, File targetFile) { File sourceFile = snapshot.getFile(); if (sourceFile != null) { try { Files.copy(sourceFile.toPath(), targetFile.toPath(), StandardCopyOption.REPLACE_EXISTING, StandardCopyOption.COPY_ATTRIBUTES); return true; } catch (Throwable t) { LOGGER.log(Level.INFO, t.getMessage(), t); String msg = t.getLocalizedMessage().replace("<", "<").replace(">", ">"); // NOI18N ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotExportFailedMsg(msg)); return false; } } else { FileLock lock = null; FileObject target = null; DataOutputStream dos = null; try { targetFile = FileUtil.normalizeFile(targetFile); target = targetFile.isFile() ? FileUtil.toFileObject(targetFile) : FileUtil.createData(targetFile); lock = target.lock(); OutputStream os = target.getOutputStream(lock); BufferedOutputStream bos = new BufferedOutputStream(os); dos = new DataOutputStream(bos); // System.out.println("Saving snapshot [" + snapshot.getSnapshot().getTimeTaken() + "]"); snapshot.save(dos); dos.close(); } catch (IOException e) { try { if (dos != null) dos.close(); if (lock != null) target.delete(lock); } catch (Exception e2) {} ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotSaveFailedMsg(e.getMessage())); return false; // failure => we wont continue with firing the event } catch (OutOfMemoryError e) { try { if (dos != null) dos.close(); if (lock != null) target.delete(lock); } catch (Exception e2) {} ProfilerDialogs.displayError(Bundle.ResultsManager_OutOfMemorySavingMsg()); return false; // failure => we wont continue with firing the event } finally { if (lock != null) lock.releaseLock(); } return true; } } public boolean saveSnapshot(LoadedSnapshot snapshot, FileObject profFile) { FileLock lock = null; DataOutputStream dos = null; boolean isSaved = snapshot.isSaved(); snapshot.setSaved(true); // Set the file as saved in advance to prevent saving it again try { lock = profFile.lock(); OutputStream os = profFile.getOutputStream(lock); BufferedOutputStream bos = new BufferedOutputStream(os); dos = new DataOutputStream(bos); // System.out.println("Saving snapshot [" + snapshot.getSnapshot().getTimeTaken() + "]"); snapshot.save(dos); dos.close(); snapshot.setFile(FileUtil.toFile(profFile)); snapshot.setSaved(true); fireSnapshotSaved(snapshot); } catch (IOException e) { snapshot.setSaved(isSaved); try { if (dos != null) { dos.close(); } if (lock != null) { profFile.delete(lock); } } catch (Exception e2) { } ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotSaveFailedMsg(e.getMessage())); return false; // failure => we wont continue with firing the event } catch (OutOfMemoryError e) { snapshot.setSaved(isSaved); try { if (dos != null) { dos.close(); } if (lock != null) { profFile.delete(lock); } } catch (Exception e2) { } ProfilerDialogs.displayError(Bundle.ResultsManager_OutOfMemorySavingMsg()); return false; // failure => we wont continue with firing the event } finally { if (lock != null) { lock.releaseLock(); } } return true; } public boolean saveSnapshot(LoadedSnapshot ls) { FileObject profFile = null; Lookup.Provider p = ls.getProject(); FileObject saveDir = null; try { saveDir = ProfilerStorage.getProjectFolder(p, true); } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_CantFindSnapshotLocationMsg(e.getMessage()), e); return false; } try { profFile = saveDir.createData(getDefaultSnapshotFileName(ls), SNAPSHOT_EXTENSION); } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_SnapshotCreateInProjectFailedMsg(e.getMessage()), e); return false; } return saveSnapshot(ls, profFile); } public LoadedSnapshot takeSnapshot() { CommonUtils.runInEventDispatchThreadAndWait(new Runnable() { public void run() { mainWindow = WindowManager.getDefault().getMainWindow(); } }); final Cursor cursor = mainWindow.getCursor(); mainWindow.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR)); try { LoadedSnapshot snapshot = prepareSnapshot(); if (snapshot != null) { loadedSnapshots.add(snapshot); fireSnapshotTaken(snapshot); return snapshot; } } finally { mainWindow.setCursor(cursor); } return null; } protected void fireResultsAvailable() { if (LOGGER.isLoggable(Level.FINEST)) { LOGGER.log(Level.FINEST, "fireResultsAvailable", new Exception()); } if (resultsListeners.allClasses().isEmpty()) { return; } CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { for(ResultsListener rl : resultsListeners.allInstances()) { rl.resultsAvailable(); } } }); } protected void fireResultsReset() { if (LOGGER.isLoggable(Level.FINEST)) { LOGGER.log(Level.FINEST, "fireResultsReset", new Exception()); } if (resultsListeners.allClasses().isEmpty()) { return; } CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { for(ResultsListener rl : resultsListeners.allInstances()) { rl.resultsReset(); } } }); } protected void fireSnapshotLoaded(final LoadedSnapshot snapshot) { if (snapshotListeners.allClasses().isEmpty()) { return; } CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { for(SnapshotsListener sl : snapshotListeners.allInstances()) { sl.snapshotLoaded(snapshot); } } }); } protected void fireSnapshotRemoved(final LoadedSnapshot snapshot) { if (snapshotListeners.allClasses().isEmpty()) { return; } CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { for(SnapshotsListener sl : snapshotListeners.allInstances()) { sl.snapshotRemoved(snapshot); } } }); } protected void fireSnapshotSaved(final LoadedSnapshot snapshot) { if (snapshotListeners.allClasses().isEmpty()) { return; } CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { for(SnapshotsListener sl : snapshotListeners.allInstances()) { sl.snapshotSaved(snapshot); } } }); } protected void fireSnapshotTaken(final LoadedSnapshot snapshot) { if (snapshotListeners.allClasses().isEmpty()) { return; } CommonUtils.runInEventDispatchThread(new Runnable() { public void run() { for(SnapshotsListener sl : snapshotListeners.allInstances()) { sl.snapshotTaken(snapshot); } } }); } void resultsBecameAvailable() { if (Profiler.getDefault().getProfilingState() == Profiler.PROFILING_INACTIVE) return; // Calibration, ignore resultsAvailable = true; fireResultsAvailable(); } void resultsReset() { // NOTE: originally left as true for memory profiling due to Issue 60432, now seems to work correctly resultsAvailable = false; fireResultsReset(); } // heapdump == true means selecting heapdump (*.hprof) SelectedFile selectSnapshotTargetFile(final String defaultName, final boolean heapdump) { String targetName; FileObject targetDir; // 1. let the user choose file or directory JFileChooser chooser = new JFileChooser(); if (exportDir != null) { chooser.setCurrentDirectory(exportDir); } chooser.setFileSelectionMode(JFileChooser.FILES_AND_DIRECTORIES); chooser.setMultiSelectionEnabled(false); chooser.setDialogTitle(Bundle.ResultsManager_SelectFileOrDirDialogCaption()); chooser.setApproveButtonText(Bundle.ResultsManager_SaveButtonName()); chooser.setAcceptAllFileFilterUsed(false); chooser.setFileFilter(new javax.swing.filechooser.FileFilter() { public boolean accept(File f) { return f.isDirectory() || f.getName().endsWith("." + (heapdump ? HEAPDUMP_EXTENSION : SNAPSHOT_EXTENSION)); //NOI18N } public String getDescription() { if (heapdump) { return Bundle.ResultsManager_ProfilerHeapdumpFileFilter(HEAPDUMP_EXTENSION); } return Bundle.ResultsManager_ProfilerSnapshotFileFilter(SNAPSHOT_EXTENSION); } }); if (chooser.showSaveDialog(WindowManager.getDefault().getMainWindow()) != JFileChooser.APPROVE_OPTION) { return null; // cancelled by the user } // 2. process both cases and extract file name and extension to use File file = chooser.getSelectedFile(); String targetExt = heapdump ? HEAPDUMP_EXTENSION : SNAPSHOT_EXTENSION; if (file.isDirectory()) { // save to selected directory under default name exportDir = chooser.getCurrentDirectory(); targetDir = FileUtil.toFileObject(FileUtil.normalizeFile(file)); targetName = defaultName; } else { // save to selected file exportDir = chooser.getCurrentDirectory(); targetDir = FileUtil.toFileObject(FileUtil.normalizeFile(exportDir)); String fName = file.getName(); // divide the file name into name and extension int idx = fName.lastIndexOf('.'); // NOI18N if (idx == -1) { // no extension targetName = fName; // extension will be used from source file } else { // extension exists if (heapdump || fName.endsWith("." + targetExt)) { // NOI18N targetName = fName.substring(0, idx); targetExt = fName.substring(idx + 1); } else { targetName = fName; } } } // 3. return a newly created FileObject return new SelectedFile(targetDir, targetName, targetExt); } private boolean checkFileExists(SelectedFile sf) { // check if the file already exists and if so prompt the user FileObject existingFile = sf.folder.getFileObject(sf.fileName, sf.fileExt); if (existingFile != null) { if (!ProfilerDialogs.displayConfirmation(Bundle.ResultsManager_OverwriteFileDialogMsg( sf.fileName + "." //NOI18N + sf.fileExt), Bundle.ResultsManager_OverwriteFileDialogCaption())) { return false; // cancelled by the user } try { existingFile.delete(); } catch (IOException e) { LOGGER.log(Level.SEVERE, Bundle.ResultsManager_FileDeleteFailedMsg(e.getMessage()), e); return false; } } return true; } private void exportSnapshot(FileObject selectedSnapshot, FileObject targetFolder, String fileName, String fileExt) { if (checkFileExists(new SelectedFile(targetFolder, fileName, fileExt))) { try { FileUtil.copyFile(selectedSnapshot, targetFolder, fileName, fileExt); } catch (Throwable t) { LOGGER.log(Level.INFO, t.getMessage(), t); String msg = t.getLocalizedMessage().replace("<", "<").replace(">", ">"); // NOI18N ProfilerDialogs.displayError(Bundle.ResultsManager_SnapshotExportFailedMsg(msg)); } } } private LoadedSnapshot findAlreadyLoadedSnapshot(FileObject selectedFile) { Iterator it = loadedSnapshots.iterator(); File f = FileUtil.toFile(selectedFile); if (f == null) { return null; } while (it.hasNext()) { LoadedSnapshot ls = (LoadedSnapshot) it.next(); if ((ls.getFile() != null) && (ls.getFile().equals(f))) { return ls; } } return null; } private Lookup.Provider findProjectForSnapshot(FileObject selectedFile) { return ProfilerStorage.getProjectFromFolder(selectedFile.getParent()); } private LoadedSnapshot loadSnapshotFromFileObject(FileObject selectedFile) throws IOException { DataInputStream dis = null; try { InputStream is = selectedFile.getInputStream(); BufferedInputStream bis = new BufferedInputStream(is); dis = new DataInputStream(bis); LoadedSnapshot ls = LoadedSnapshot.loadSnapshot(dis); if (ls != null) { ls.setFile(FileUtil.toFile(selectedFile)); ls.setProject(findProjectForSnapshot(selectedFile)); } return ls; } finally { if (dis != null) { dis.close(); } } } private LoadedSnapshot loadSnapshotImpl(FileObject selectedFile) throws IOException { LoadedSnapshot ls = findAlreadyLoadedSnapshot(selectedFile); if (ls != null) { return ls; } ls = loadSnapshotFromFileObject(selectedFile); if (ls != null) { loadedSnapshots.add(ls); fireSnapshotLoaded(ls); } return ls; } private ProfilingSettings readSettingsFromFile(FileObject fo) { LoadedSnapshot ls = findAlreadyLoadedSnapshot(fo); if (ls != null) { return ls.getSettings(); } DataInputStream dis = null; try { InputStream is = fo.getInputStream(); BufferedInputStream bis = new BufferedInputStream(is); dis = new DataInputStream(bis); // data before settings byte[] magicArray = new byte[LoadedSnapshot.PROFILER_FILE_MAGIC_STRING.length()]; int len = dis.read(magicArray); if ((len != LoadedSnapshot.PROFILER_FILE_MAGIC_STRING.length()) || !LoadedSnapshot.PROFILER_FILE_MAGIC_STRING.equals(new String(magicArray))) { return null; } byte majorVersion = dis.readByte(); byte minorVersion = dis.readByte(); int type = dis.readInt(); int compressedDataLen = dis.readInt(); int uncompressedDataLen = dis.readInt(); if (dis.skipBytes(compressedDataLen) != compressedDataLen) { return null; } // settings data int settingsLen = dis.readInt(); byte[] settingsBytes = new byte[settingsLen]; if (dis.read(settingsBytes) != settingsLen) { return null; } // create settings Properties props = new Properties(); ProfilingSettings settings = new ProfilingSettings(); ByteArrayInputStream bais2 = new ByteArrayInputStream(settingsBytes); BufferedInputStream bufBais2 = new BufferedInputStream(bais2); DataInputStream settingsDis = new DataInputStream(bufBais2); try { props.load(settingsDis); } catch (IOException e) { ProfilerLogger.log(e); return null; } finally { settingsDis.close(); } settings.load(props); return settings; } catch (Exception e) { ProfilerLogger.log(e); return null; } finally { try { if (dis != null) { dis.close(); } } catch (IOException e) { ProfilerLogger.log(e); } } } private int readTypeFromFile(FileObject fo) { LoadedSnapshot ls = findAlreadyLoadedSnapshot(fo); if (ls != null) { return ls.getType(); } DataInputStream dis = null; try { InputStream is = fo.getInputStream(); BufferedInputStream bis = new BufferedInputStream(is); dis = new DataInputStream(bis); byte[] magicArray = new byte[LoadedSnapshot.PROFILER_FILE_MAGIC_STRING.length()]; int len = dis.read(magicArray); if ((len != LoadedSnapshot.PROFILER_FILE_MAGIC_STRING.length()) || !LoadedSnapshot.PROFILER_FILE_MAGIC_STRING.equals(new String(magicArray))) { return LoadedSnapshot.SNAPSHOT_TYPE_UNKNOWN; } byte majorVersion = dis.readByte(); byte minorVersion = dis.readByte(); int type = dis.readInt(); return type; } catch (Exception e) { return LoadedSnapshot.SNAPSHOT_TYPE_UNKNOWN; } finally { try { if (dis != null) { dis.close(); } } catch (IOException e) { e.printStackTrace(System.err); } } } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy