Skip to content

Commit

Permalink
1145: editor can have two reconcilers running
Browse files Browse the repository at this point in the history
  • Loading branch information
vladdu committed Feb 14, 2013
1 parent 089fcfc commit fdd6008
Show file tree
Hide file tree
Showing 3 changed files with 67 additions and 15 deletions.
Expand Up @@ -127,7 +127,7 @@ public IReconciler getReconciler(final ISourceViewer sourceViewer) {
final String path = module != null ? module.getFilePath() : null; final String path = module != null ? module.getFilePath() : null;
final boolean logging = module != null ? module.getLogging() : true; final boolean logging = module != null ? module.getLogging() : true;
reconciler = new ErlReconciler(strategy, true, true, path, module, reconciler = new ErlReconciler(strategy, true, true, path, module,
logging); logging, getEditor());
reconciler.setProgressMonitor(new NullProgressMonitor()); reconciler.setProgressMonitor(new NullProgressMonitor());
reconciler.setIsAllowedToModifyDocument(false); reconciler.setIsAllowedToModifyDocument(false);
reconciler.setDelay(500); reconciler.setDelay(500);
Expand Down
26 changes: 26 additions & 0 deletions org.erlide.ui/src/org/erlide/ui/editors/erl/ErlangEditor.java
Expand Up @@ -1927,4 +1927,30 @@ public IErlScanner getScanner() {
return scanner; return scanner;
} }


/**
* Mutex for the reconciler. See
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=63898 for a description of
* the problem.
* <p>
* XXX remove once the underlying problem
* (https://bugs.eclipse.org/bugs/show_bug.cgi?id=66176) is solved.
* </p>
*/
private final Object fReconcilerLock = new Object();

/**
* Returns the mutex for the reconciler. See
* https://bugs.eclipse.org/bugs/show_bug.cgi?id=63898 for a description of
* the problem.
* <p>
* XXX remove once the underlying problem
* (https://bugs.eclipse.org/bugs/show_bug.cgi?id=66176) is solved.
* </p>
*
* @return the lock reconcilers may use to synchronize on
*/
public Object getReconcilerLock() {
return fReconcilerLock;
}

} }
Expand Up @@ -20,8 +20,10 @@
import org.eclipse.jface.text.reconciler.IReconciler; import org.eclipse.jface.text.reconciler.IReconciler;
import org.eclipse.jface.text.reconciler.IReconcilingStrategy; import org.eclipse.jface.text.reconciler.IReconcilingStrategy;
import org.eclipse.jface.text.reconciler.IReconcilingStrategyExtension; import org.eclipse.jface.text.reconciler.IReconcilingStrategyExtension;
import org.eclipse.ui.texteditor.ITextEditor;
import org.erlide.model.erlang.IErlModule; import org.erlide.model.erlang.IErlModule;
import org.erlide.model.root.ErlModelManager; import org.erlide.model.root.ErlModelManager;
import org.erlide.ui.editors.erl.ErlangEditor;
import org.erlide.utils.ErlLogger; import org.erlide.utils.ErlLogger;


import com.google.common.collect.Lists; import com.google.common.collect.Lists;
Expand Down Expand Up @@ -55,10 +57,12 @@ public class ErlReconciler implements IReconciler {


List<ErlDirtyRegion> log = Lists.newLinkedList(); List<ErlDirtyRegion> log = Lists.newLinkedList();
boolean logging; boolean logging;
private Object fMutex;


public ErlReconciler(final IErlReconcilingStrategy strategy, public ErlReconciler(final IErlReconcilingStrategy strategy,
final boolean isIncremental, final boolean chunkReconciler, final boolean isIncremental, final boolean chunkReconciler,
final String path, final IErlModule module, final boolean logging) { final String path, final IErlModule module, final boolean logging,
final ITextEditor editor) {


super(); super();
this.logging = logging; this.logging = logging;
Expand All @@ -71,6 +75,26 @@ public ErlReconciler(final IErlReconcilingStrategy strategy,
if (path != null) { if (path != null) {
ErlModelManager.getErlangModel().putEdited(path, module); ErlModelManager.getErlangModel().putEdited(path, module);
} }
// https://bugs.eclipse.org/bugs/show_bug.cgi?id=63898
// when re-using editors, a new reconciler is set up by the source
// viewer
// and the old one uninstalled. However, the old reconciler may still be
// running.
// To avoid having to reconcilers calling
// Editor.reconciled,
// we synchronized on a lock object provided by the editor.
// The critical section is really the entire run() method of the
// reconciler
// thread, but synchronizing process() only will keep
// the ReconcilingStrategy
// from running concurrently on the same editor.
// TODO remove once we have ensured that there is only one reconciler
// per editor.
if (editor instanceof ErlangEditor) {
fMutex = ((ErlangEditor) editor).getReconcilerLock();
} else {
fMutex = new Object(); // Null Object
}
} }


/** /**
Expand Down Expand Up @@ -321,7 +345,7 @@ public void inputDocumentAboutToBeChanged(final IDocument oldInput,
if (fDocument != null && fDocument.getLength() > 0) { if (fDocument != null && fDocument.getLength() > 0) {
// final DocumentEvent e = new DocumentEvent(fDocument, // final DocumentEvent e = new DocumentEvent(fDocument,
// 0, // 0,
// fDocument.getLength(), ""); //$NON-NLS-1$ // fDocument.getLength(), ""); //$NON-NLS-1$
// createDirtyRegion(e); // createDirtyRegion(e);
fThread.reset(); fThread.reset();
fThread.suspendCallerWhileDirty(); fThread.suspendCallerWhileDirty();
Expand Down Expand Up @@ -676,18 +700,20 @@ public void setProgressMonitor(final IProgressMonitor monitor) {
* only once during the life time of the reconciler. * only once during the life time of the reconciler.
*/ */
protected void initialProcess() { protected void initialProcess() {
if (fStrategy instanceof IReconcilingStrategyExtension) { synchronized (fMutex) {
final IReconcilingStrategyExtension extension = (IReconcilingStrategyExtension) fStrategy; if (fStrategy instanceof IReconcilingStrategyExtension) {
extension.initialReconcile(); final IReconcilingStrategyExtension extension = (IReconcilingStrategyExtension) fStrategy;
if (logging) { extension.initialReconcile();
log.clear(); if (logging) {
final ErlReconcilingStrategy erlReconcilerStrategy = (ErlReconcilingStrategy) fStrategy; log.clear();
final IErlModule module = erlReconcilerStrategy.getModule(); final ErlReconcilingStrategy erlReconcilerStrategy = (ErlReconcilingStrategy) fStrategy;
final String scannerName = module.getScannerName(); final IErlModule module = erlReconcilerStrategy.getModule();
final String erlFilename = module.getFilePath(); final String scannerName = module.getScannerName();
final ErlDirtyRegion erlDirtyRegion = new InitialScan( final String erlFilename = module.getFilePath();
getDocument().get(), scannerName, erlFilename); final ErlDirtyRegion erlDirtyRegion = new InitialScan(
log.add(erlDirtyRegion); getDocument().get(), scannerName, erlFilename);
log.add(erlDirtyRegion);
}
} }
} }
} }
Expand Down

0 comments on commit fdd6008

Please sign in to comment.