package org.eclipse.tracecompass.tmf.ui.views.callstack;
+import java.util.Optional;
+
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.GC;
import org.eclipse.swt.graphics.RGB;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model.NullTimeEvent;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.widgets.Utils;
+import com.google.common.cache.CacheBuilder;
+import com.google.common.cache.CacheLoader;
+import com.google.common.cache.LoadingCache;
+
/**
* Presentation provider for the Call Stack view, based on the generic TMF
* presentation provider.
private Integer fAverageCharWidth;
+ private final LoadingCache<CallStackEvent, Optional<String>> fTimeEventNames = CacheBuilder.newBuilder()
+ .maximumSize(1000)
+ .build(new CacheLoader<CallStackEvent, Optional<String>>() {
+ @Override
+ public Optional<String> load(CallStackEvent event) {
+ CallStackEntry entry = event.getEntry();
+ ITmfStateSystem ss = entry.getStateSystem();
+ try {
+ ITmfStateValue value = ss.querySingleState(event.getTime(), entry.getQuark()).getStateValue();
+ if (!value.isNull()) {
+ String name = fView.getFunctionName(entry.getTrace(), entry.getProcessId(), event.getTime(), value);
+ return Optional.ofNullable(name);
+ }
+ } catch (TimeRangeException e) {
+ Activator.getDefault().logError("Error querying state system", e); //$NON-NLS-1$
+ } catch (StateSystemDisposedException e) {
+ /* Ignored */
+ }
+ return Optional.empty();
+ }
+ });
+
private enum State {
MULTIPLE (new RGB(100, 100, 100)),
EXEC (new RGB(0, 200, 0));
@Override
public String getEventName(ITimeEvent event) {
if (event instanceof CallStackEvent) {
- CallStackEntry entry = (CallStackEntry) event.getEntry();
- ITmfStateSystem ss = entry.getStateSystem();
- try {
- ITmfStateValue value = ss.querySingleState(event.getTime(), entry.getQuark()).getStateValue();
- if (!value.isNull()) {
- return fView.getFunctionName(entry.getTrace(), entry.getProcessId(), event.getTime(), value);
- }
- } catch (TimeRangeException e) {
- Activator.getDefault().logError("Error querying state system", e); //$NON-NLS-1$
- } catch (StateSystemDisposedException e) {
- /* Ignored */
- }
- return null;
+ return fTimeEventNames.getUnchecked((CallStackEvent) event).orElse(null);
}
return State.MULTIPLE.toString();
}
if (!(event instanceof CallStackEvent)) {
return;
}
- CallStackEntry entry = (CallStackEntry) event.getEntry();
- ITmfStateSystem ss = entry.getStateSystem();
- try {
- ITmfStateValue value = ss.querySingleState(event.getTime(), entry.getQuark()).getStateValue();
- if (!value.isNull()) {
- String name = fView.getFunctionName(entry.getTrace(), entry.getProcessId(), event.getTime(), value);
- gc.setForeground(gc.getDevice().getSystemColor(SWT.COLOR_WHITE));
- Utils.drawText(gc, name, bounds.x, bounds.y, bounds.width, bounds.height, true, true);
- }
- } catch (TimeRangeException e) {
- Activator.getDefault().logError("Error querying state system", e); //$NON-NLS-1$
- } catch (StateSystemDisposedException e) {
- /* Ignored */
- }
+ String name = fTimeEventNames.getUnchecked((CallStackEvent) event).orElse(null);
+ gc.setForeground(gc.getDevice().getSystemColor(SWT.COLOR_WHITE));
+ Utils.drawText(gc, name, bounds.x, bounds.y, bounds.width, bounds.height, true, true);
+ }
+
+ /**
+ * Indicate that the provider of function names has changed, so any cached
+ * values must be reset.
+ */
+ void resetFunctionNames() {
+ fTimeEventNames.invalidateAll();
}
}
*/
public CallStackView() {
super(ID, new CallStackPresentationProvider());
- ((CallStackPresentationProvider) getPresentationProvider()).setCallStackView(this);
+ getPresentationProvider().setCallStackView(this);
setTreeColumns(COLUMN_NAMES);
setTreeLabelProvider(new CallStackTreeLabelProvider());
setEntryComparator(new CallStackComparator());
// Internal
// ------------------------------------------------------------------------
+ /**
+ * @since 2.1
+ */
+ @Override
+ protected CallStackPresentationProvider getPresentationProvider() {
+ /* Set to this type by the constructor */
+ return (CallStackPresentationProvider) super.getPresentationProvider();
+ }
+
@Override
@TmfSignalHandler
public void traceClosed(TmfTraceClosedSignal signal) {
public void run() {
SymbolProviderConfigDialog dialog = new SymbolProviderConfigDialog(getSite().getShell(), getProviderPages());
if (dialog.open() == IDialogConstants.OK_ID) {
+ getPresentationProvider().resetFunctionNames();
refresh();
}
}
package org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model;
+import java.util.Objects;
+
/**
* Generic TimeEvent implementation
*
null);
}
+ @Override
+ public int hashCode() {
+ return Objects.hash(fEntry, fTime, fDuration, fValue);
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if (obj == null) {
+ return false;
+ }
+ if (getClass() != obj.getClass()) {
+ return false;
+ }
+ TimeEvent other = (TimeEvent) obj;
+ return Objects.equals(fEntry, other.fEntry) &&
+ Objects.equals(fTime, other.fTime) &&
+ Objects.equals(fDuration, other.fDuration) &&
+ Objects.equals(fValue, other.fValue);
+ }
+
@Override
public String toString() {
return getClass().getSimpleName() + " start=" + fTime + " end=" + (fTime + fDuration) + " duration=" + fDuration + (hasValue() ? (" value=" + fValue) : ""); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$