1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-04-23 06:32:10 +02:00

Fix for 188282, potential use of unlocked index.

This commit is contained in:
Markus Schorn 2007-05-23 10:38:34 +00:00
parent dc82b160c3
commit d1db017310
7 changed files with 247 additions and 206 deletions

View file

@ -7,6 +7,7 @@
*
* Contributors:
* Anton Leherbauer (Wind River Systems) - initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/
package org.eclipse.cdt.core.model.tests;
@ -24,12 +25,15 @@ import org.eclipse.cdt.core.testplugin.CProjectHelper;
import org.eclipse.cdt.core.testplugin.util.BaseTestCase;
import org.eclipse.cdt.core.testplugin.util.TestSourceReader;
import org.eclipse.cdt.internal.core.model.ASTCache;
import org.eclipse.cdt.internal.core.model.ASTCache.ASTRunnable;
import org.eclipse.core.resources.IContainer;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.core.runtime.Path;
import org.eclipse.core.runtime.Status;
/**
* Tests for the {@link ASTCache}.
@ -149,24 +153,44 @@ public class ASTCacheTests extends BaseTestCase {
}
private void checkSingleThreadAccess() throws Exception {
ASTCache cache= new ASTCache();
final ASTCache cache= new ASTCache();
final int[] counter= {0};
cache.setActiveElement(fTU1);
IASTTranslationUnit ast;
ast= cache.getAST(fTU1, fIndex, false, null);
assertNull(ast);
IStatus status= cache.runOnAST(fTU1, false, null, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) throws CoreException {
assertNull(ast);
counter[0]++;
return Status.OK_STATUS;
}
});
assertEquals(1, counter[0]);
IProgressMonitor npm= new NullProgressMonitor();
npm.setCanceled(true);
ast= cache.getAST(fTU1, fIndex, true, npm);
assertNull(ast);
status= cache.runOnAST(fTU1, true, npm, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) throws CoreException {
assertNull(ast);
counter[0]++;
return Status.OK_STATUS;
}
});
assertEquals(2, counter[0]);
npm.setCanceled(false);
ast= cache.getAST(fTU1, fIndex, true, npm);
assertNotNull(ast);
status= cache.runOnAST(fTU1, true, npm, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) throws CoreException {
assertNotNull(ast);
counter[0]++;
return Status.OK_STATUS;
}
});
assertEquals(3, counter[0]);
}
private void checkAccessWithSequentialReconciler() throws Exception {
ASTCache cache= new ASTCache();
MockReconciler reconciler1= new MockReconciler(fTU1, cache);
MockReconciler reconciler2= new MockReconciler(fTU2, cache);
final ASTCache cache= new ASTCache();
final MockReconciler reconciler1= new MockReconciler(fTU1, cache);
final MockReconciler reconciler2= new MockReconciler(fTU2, cache);
try {
cache.setActiveElement(fTU1);
assertFalse(cache.isReconciling(fTU1));
@ -178,12 +202,15 @@ public class ASTCacheTests extends BaseTestCase {
assertTrue(cache.isReconciling(fTU1));
}
reconciler1.fStopped= true;
IASTTranslationUnit ast;
ast= cache.getAST(fTU1, fIndex, true, null);
assertNotNull(ast);
assertTrue(cache.isActiveElement(fTU1));
assertFalse(cache.isReconciling(fTU1));
assertSame(ast, reconciler1.fAST);
IStatus status= cache.runOnAST(fTU1, true, null, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) throws CoreException {
assertNotNull(ast);
assertTrue(cache.isActiveElement(fTU1));
assertFalse(cache.isReconciling(fTU1));
assertSame(ast, reconciler1.fAST);
return Status.OK_STATUS;
}
});
// change active element
cache.setActiveElement(fTU2);
@ -196,11 +223,16 @@ public class ASTCacheTests extends BaseTestCase {
assertTrue(cache.isReconciling(fTU2));
}
reconciler2.fStopped= true;
ast= cache.getAST(fTU2, fIndex, true, null);
assertNotNull(ast);
assertTrue(cache.isActiveElement(fTU2));
assertFalse(cache.isReconciling(fTU2));
assertSame(ast, reconciler2.fAST);
status= cache.runOnAST(fTU2, true, null, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) throws CoreException {
assertNotNull(ast);
assertTrue(cache.isActiveElement(fTU2));
assertFalse(cache.isReconciling(fTU2));
assertSame(ast, reconciler2.fAST);
return Status.OK_STATUS;
}
});
} finally {
reconciler1.fStopped= true;
reconciler1.join(1000);
@ -221,27 +253,42 @@ public class ASTCacheTests extends BaseTestCase {
while (iterations < 10) {
++iterations;
if (DEBUG) System.out.println("iteration="+iterations);
IASTTranslationUnit ast;
cache.setActiveElement(fTU1);
Thread.sleep(50);
ast = waitForAST(cache, fTU1);
assertNotNull(ast);
assertEquals("void foo1() {}", ast.getDeclarations()[0].getRawSignature());
waitForAST(cache, fTU1, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) {
assertNotNull(ast);
assertEquals("void foo1() {}", ast.getDeclarations()[0].getRawSignature());
return Status.OK_STATUS;
}
});
ast = waitForAST(cache, fTU2);
assertNotNull(ast);
assertEquals("void foo2() {}", ast.getDeclarations()[0].getRawSignature());
waitForAST(cache, fTU2, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) {
assertNotNull(ast);
assertEquals("void foo2() {}", ast.getDeclarations()[0].getRawSignature());
return Status.OK_STATUS;
}
});
// change active element
cache.setActiveElement(fTU2);
Thread.sleep(50);
ast = waitForAST(cache, fTU2);
assertNotNull(ast);
assertEquals("void foo2() {}", ast.getDeclarations()[0].getRawSignature());
waitForAST(cache, fTU2, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) {
assertNotNull(ast);
assertEquals("void foo2() {}", ast.getDeclarations()[0].getRawSignature());
return Status.OK_STATUS;
}
});
ast = waitForAST(cache, fTU1);
assertNotNull(ast);
assertEquals("void foo1() {}", ast.getDeclarations()[0].getRawSignature());
waitForAST(cache, fTU1, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) {
assertNotNull(ast);
assertEquals("void foo1() {}", ast.getDeclarations()[0].getRawSignature());
return Status.OK_STATUS;
}
});
}
} finally {
reconciler1.fStopped= true;
@ -251,13 +298,14 @@ public class ASTCacheTests extends BaseTestCase {
}
}
private IASTTranslationUnit waitForAST(ASTCache cache, ITranslationUnit tUnit) {
private void waitForAST(ASTCache cache, ITranslationUnit tUnit, ASTRunnable runnable) {
if (DEBUG) System.out.println("waiting for "+tUnit.getElementName());
long start= System.currentTimeMillis();
IASTTranslationUnit ast;
ast= cache.getAST(tUnit, fIndex, true, null);
if (DEBUG) System.out.println("wait time= " + (System.currentTimeMillis() - start));
return ast;
try {
cache.runOnAST(tUnit, true, null, runnable);
}
finally {
if (DEBUG) System.out.println("wait time= " + (System.currentTimeMillis() - start));
}
}
}

View file

@ -4,14 +4,16 @@
* terms of the Eclipse Public License v1.0 which accompanies this distribution,
* and is available at http://www.eclipse.org/legal/epl-v10.html
*
* Contributors: Anton Leherbauer (Wind River Systems) - initial API and
* implementation
* Contributors:
* Anton Leherbauer (Wind River Systems) - initial API and implementation
* Markus Schorn (Wind River Systems)
******************************************************************************/
package org.eclipse.cdt.internal.core.model;
import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.index.IIndex;
import org.eclipse.cdt.core.index.IIndexManager;
import org.eclipse.cdt.core.model.ITranslationUnit;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
@ -51,7 +53,7 @@ public class ASTCache {
* @param ast the translation unit AST, may be <code>null</code>
* @return a status object
*/
IStatus runOnAST(IASTTranslationUnit ast);
IStatus runOnAST(IASTTranslationUnit ast) throws CoreException;
}
private final int fParseMode;
@ -92,7 +94,7 @@ public class ASTCache {
* @param progressMonitor the progress monitor or <code>null</code>
* @return the AST or <code>null</code> if the AST is not available
*/
public IASTTranslationUnit getAST(ITranslationUnit tUnit, IIndex index, boolean wait, IProgressMonitor progressMonitor) {
private IASTTranslationUnit getAST(ITranslationUnit tUnit, IIndex index, boolean wait, IProgressMonitor progressMonitor) {
if (tUnit == null)
return null;
@ -193,7 +195,7 @@ public class ASTCache {
ASTRunnable astRunnable) {
IIndex index;
try {
index = CCorePlugin.getIndexManager().getIndex(tUnit.getCProject());
index = CCorePlugin.getIndexManager().getIndex(tUnit.getCProject(), IIndexManager.ADD_DEPENDENCIES);
index.acquireReadLock();
} catch (CoreException e) {
return e.getStatus();
@ -205,6 +207,9 @@ public class ASTCache {
IASTTranslationUnit ast= getAST(tUnit, index, wait, monitor);
return astRunnable.runOnAST(ast);
}
catch (CoreException e) {
return e.getStatus();
}
finally {
index.releaseReadLock();
}

View file

@ -154,7 +154,7 @@ public class CallHierarchyUI {
index.acquireReadLock();
try {
IASTName name= IndexUI.getSelectedName(index, editorInput, sel);
IASTName name= IndexUI.getSelectedName(editorInput, sel);
if (name != null) {
IBinding binding= name.resolveBinding();
if (CallHierarchyUI.isRelevantForCallHierarchy(binding)) {

View file

@ -25,7 +25,6 @@ import org.eclipse.ui.IWorkbenchWindow;
import org.eclipse.ui.PlatformUI;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.index.IIndex;
import org.eclipse.cdt.core.model.ICElement;
import org.eclipse.cdt.core.model.ITranslationUnit;
import org.eclipse.cdt.ui.CUIPlugin;
@ -280,30 +279,6 @@ public final class ASTProvider {
fCache.aboutToBeReconciled((ITranslationUnit)cElement);
}
/**
* Returns a shared translation unit AST for the given
* C element.
* <p>
* Clients are not allowed to modify the AST and must
* synchronize all access to its nodes.
* </p>
*
* @param cElement the C element
* @param index the index used to create the AST, needs to be read-locked.
* @param waitFlag {@link #WAIT_YES}, {@link #WAIT_NO} or {@link #WAIT_ACTIVE_ONLY}
* @param progressMonitor the progress monitor or <code>null</code>
* @return the AST or <code>null</code> if the AST is not available
*/
public IASTTranslationUnit getAST(ICElement cElement, IIndex index, WAIT_FLAG waitFlag, IProgressMonitor progressMonitor) {
if (cElement == null)
return null;
Assert.isTrue(cElement instanceof ITranslationUnit);
if (waitFlag == WAIT_ACTIVE_ONLY && !isActive((ITranslationUnit)cElement)) {
return null;
}
return fCache.getAST((ITranslationUnit)cElement, index, waitFlag != WAIT_NO, progressMonitor);
}
/**
* Disposes this AST provider.
*/
@ -334,16 +309,5 @@ public final class ASTProvider {
}
return fCache.runOnAST((ITranslationUnit)cElement, waitFlag != WAIT_NO, monitor, astRunnable);
}
/**
* @param cElement
* @param index
* @param monitor
* @return an AST or <code>null</code>, if no AST could be computed
*/
public IASTTranslationUnit createAST(ICElement cElement, IIndex index, IProgressMonitor monitor) {
Assert.isTrue(cElement instanceof ITranslationUnit);
return fCache.createAST((ITranslationUnit)cElement, index, monitor);
}
}

View file

@ -8,11 +8,14 @@
* Contributors:
* QNX Software Systems - Initial API and implementation
* IBM Corporation
* Markus Schorn (Wind River Systems)
*******************************************************************************/
package org.eclipse.cdt.internal.ui.editor;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.jface.action.IAction;
import org.eclipse.jface.text.IRegion;
import org.eclipse.jface.text.ITextSelection;
@ -33,6 +36,8 @@ import org.eclipse.cdt.core.index.IIndexManager;
import org.eclipse.cdt.core.model.IWorkingCopy;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.internal.core.model.ASTCache.ASTRunnable;
import org.eclipse.cdt.internal.ui.search.actions.OpenDeclarationsAction;
public class CElementHyperlinkDetector implements IHyperlinkDetector {
@ -51,16 +56,16 @@ public class CElementHyperlinkDetector implements IHyperlinkDetector {
CEditor editor = (CEditor) fTextEditor;
int offset = region.getOffset();
IAction openAction= editor.getAction("OpenDeclarations"); //$NON-NLS-1$
final IAction openAction= editor.getAction("OpenDeclarations"); //$NON-NLS-1$
if (openAction == null)
return null;
// reuse the logic from Open Decl that recognizes a word in the editor
ITextSelection selection = OpenDeclarationsAction.selectWord(offset, editor);
final ITextSelection selection = OpenDeclarationsAction.selectWord(offset, editor);
if(selection == null)
return null;
IWorkingCopy workingCopy = CUIPlugin.getDefault().getWorkingCopyManager().getWorkingCopy(editor.getEditorInput());
final IWorkingCopy workingCopy = CUIPlugin.getDefault().getWorkingCopyManager().getWorkingCopy(editor.getEditorInput());
if (workingCopy == null) {
return null;
}
@ -79,29 +84,36 @@ public class CElementHyperlinkDetector implements IHyperlinkDetector {
return null;
}
final IHyperlink[] result= {null};
try {
IASTTranslationUnit ast =
ASTProvider.getASTProvider().getAST(workingCopy, index, ASTProvider.WAIT_YES, null);
IASTName[] selectedNames =
workingCopy.getLanguage().getSelectedNames(ast, selection.getOffset(), selection.getLength());
IRegion linkRegion;
if(selectedNames.length > 0 && selectedNames[0] != null) { // found a name
linkRegion = new Region(selection.getOffset(), selection.getLength());
}
else { // check if we are in an include statement
linkRegion = matchIncludeStatement(ast, selection);
}
if(linkRegion != null)
return new IHyperlink[] { new CElementHyperlink(linkRegion, openAction) };
} catch(CoreException e) {
ASTProvider.getASTProvider().runOnAST(workingCopy, ASTProvider.WAIT_YES, null, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) {
try {
IASTName[] selectedNames =
workingCopy.getLanguage().getSelectedNames(ast, selection.getOffset(), selection.getLength());
IRegion linkRegion;
if(selectedNames.length > 0 && selectedNames[0] != null) { // found a name
linkRegion = new Region(selection.getOffset(), selection.getLength());
}
else { // check if we are in an include statement
linkRegion = matchIncludeStatement(ast, selection);
}
if(linkRegion != null)
result[0]= new CElementHyperlink(linkRegion, openAction);
}
catch (CoreException e) {
return e.getStatus();
}
return Status.OK_STATUS;
}
});
} finally {
index.releaseReadLock();
}
return null;
return result[0] == null ? null : result;
}

View file

@ -49,6 +49,8 @@ import org.eclipse.cdt.core.model.util.CElementBaseLabels;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.internal.core.model.ASTCache.ASTRunnable;
import org.eclipse.cdt.internal.ui.actions.OpenActionUtil;
import org.eclipse.cdt.internal.ui.editor.ASTProvider;
import org.eclipse.cdt.internal.ui.editor.CEditor;
@ -70,7 +72,10 @@ public class OpenDeclarationsAction extends SelectionParseAction {
setDescription(CEditorMessages.getString("OpenDeclarations.description")); //$NON-NLS-1$
}
private class Runner extends Job {
private class Runner extends Job implements ASTRunnable {
private IWorkingCopy fWorkingCopy;
private IIndex fIndex;
Runner() {
super(CEditorMessages.getString("OpenDeclarations.dialog.title")); //$NON-NLS-1$
}
@ -79,116 +84,115 @@ public class OpenDeclarationsAction extends SelectionParseAction {
try {
clearStatusLine();
int selectionStart = selNode.getOffset();
int selectionLength = selNode.getLength();
IWorkingCopy workingCopy = CUIPlugin.getDefault().getWorkingCopyManager().getWorkingCopy(fEditor.getEditorInput());
if (workingCopy == null)
fWorkingCopy = CUIPlugin.getDefault().getWorkingCopyManager().getWorkingCopy(fEditor.getEditorInput());
if (fWorkingCopy == null)
return Status.CANCEL_STATUS;
IIndex index = CCorePlugin.getIndexManager().getIndex(workingCopy.getCProject(),
fIndex= CCorePlugin.getIndexManager().getIndex(fWorkingCopy.getCProject(),
IIndexManager.ADD_DEPENDENCIES | IIndexManager.ADD_DEPENDENT);
try {
index.acquireReadLock();
fIndex.acquireReadLock();
} catch (InterruptedException e) {
return Status.CANCEL_STATUS;
}
try {
IASTTranslationUnit ast=
ASTProvider.getASTProvider().getAST(
workingCopy, index, ASTProvider.WAIT_YES, monitor);
IASTName[] selectedNames = workingCopy.getLanguage().getSelectedNames(ast, selectionStart, selectionLength);
if (selectedNames.length > 0 && selectedNames[0] != null) { // just right, only one name selected
boolean found = false;
IASTName searchName = selectedNames[0];
boolean isDefinition= searchName.isDefinition();
IBinding binding = searchName.resolveBinding();
if (binding != null && !(binding instanceof IProblemBinding)) {
IName[] declNames = findNames(index, ast, isDefinition, binding);
if (declNames.length == 0) {
// bug 86829, handle implicit methods.
if (binding instanceof ICPPMethod) {
ICPPMethod method= (ICPPMethod) binding;
if (method.isImplicit()) {
try {
IBinding clsBinding= method.getClassOwner();
if (clsBinding != null && !(clsBinding instanceof IProblemBinding)) {
declNames= findNames(index, ast, false, clsBinding);
}
} catch (DOMException e) {
CCorePlugin.log(e);
}
}
}
}
if (navigateViaCElements(workingCopy.getCProject(), index, declNames)) {
found= true;
}
else {
// leave old method as fallback for local variables, parameters and
// everything else not covered by ICElementHandle.
found = navigateOneLocation(declNames);
}
}
if (!found) {
reportSymbolLookupFailure(new String(searchName.toCharArray()));
}
} else {
// Check if we're in an include statement
IASTPreprocessorStatement[] preprocs = ast.getAllPreprocessorStatements();
boolean foundInInclude = false;
for (int i = 0; i < preprocs.length; ++i) {
if (!(preprocs[i] instanceof IASTPreprocessorIncludeStatement))
continue;
IASTPreprocessorIncludeStatement incStmt = (IASTPreprocessorIncludeStatement)preprocs[i];
IASTFileLocation loc = preprocs[i].getFileLocation();
if (loc != null
&& loc.getFileName().equals(ast.getFilePath())
&& loc.getNodeOffset() < selectionStart
&& loc.getNodeOffset() + loc.getNodeLength() > selectionStart) {
// Got it
foundInInclude = true;
String name = null;
if (incStmt.isResolved())
name = incStmt.getPath();
if (name != null) {
final IPath path = new Path(name);
runInUIThread(new Runnable() {
public void run() {
try {
open(path, 0, 0);
} catch (CoreException e) {
CUIPlugin.getDefault().log(e);
}
}
});
} else {
reportIncludeLookupFailure(new String(incStmt.getName().toCharArray()));
}
break;
}
if (!foundInInclude) {
reportSelectionMatchFailure();
}
}
}
return ASTProvider.getASTProvider().runOnAST(fWorkingCopy, ASTProvider.WAIT_YES, monitor, this);
} finally {
index.releaseReadLock();
fIndex.releaseReadLock();
}
return Status.OK_STATUS;
} catch (CoreException e) {
return e.getStatus();
}
}
public IStatus runOnAST(IASTTranslationUnit ast) throws CoreException {
int selectionStart = selNode.getOffset();
int selectionLength = selNode.getLength();
IASTName[] selectedNames = fWorkingCopy.getLanguage().getSelectedNames(ast, selectionStart, selectionLength);
if (selectedNames.length > 0 && selectedNames[0] != null) { // just right, only one name selected
boolean found = false;
IASTName searchName = selectedNames[0];
boolean isDefinition= searchName.isDefinition();
IBinding binding = searchName.resolveBinding();
if (binding != null && !(binding instanceof IProblemBinding)) {
IName[] declNames = findNames(fIndex, ast, isDefinition, binding);
if (declNames.length == 0) {
// bug 86829, handle implicit methods.
if (binding instanceof ICPPMethod) {
ICPPMethod method= (ICPPMethod) binding;
if (method.isImplicit()) {
try {
IBinding clsBinding= method.getClassOwner();
if (clsBinding != null && !(clsBinding instanceof IProblemBinding)) {
declNames= findNames(fIndex, ast, false, clsBinding);
}
} catch (DOMException e) {
CCorePlugin.log(e);
}
}
}
}
if (navigateViaCElements(fWorkingCopy.getCProject(), fIndex, declNames)) {
found= true;
}
else {
// leave old method as fallback for local variables, parameters and
// everything else not covered by ICElementHandle.
found = navigateOneLocation(declNames);
}
}
if (!found) {
reportSymbolLookupFailure(new String(searchName.toCharArray()));
}
} else {
// Check if we're in an include statement
IASTPreprocessorStatement[] preprocs = ast.getAllPreprocessorStatements();
boolean foundInInclude = false;
for (int i = 0; i < preprocs.length; ++i) {
if (!(preprocs[i] instanceof IASTPreprocessorIncludeStatement))
continue;
IASTPreprocessorIncludeStatement incStmt = (IASTPreprocessorIncludeStatement)preprocs[i];
IASTFileLocation loc = preprocs[i].getFileLocation();
if (loc != null
&& loc.getFileName().equals(ast.getFilePath())
&& loc.getNodeOffset() < selectionStart
&& loc.getNodeOffset() + loc.getNodeLength() > selectionStart) {
// Got it
foundInInclude = true;
String name = null;
if (incStmt.isResolved())
name = incStmt.getPath();
if (name != null) {
final IPath path = new Path(name);
runInUIThread(new Runnable() {
public void run() {
try {
open(path, 0, 0);
} catch (CoreException e) {
CUIPlugin.getDefault().log(e);
}
}
});
} else {
reportIncludeLookupFailure(new String(incStmt.getName().toCharArray()));
}
break;
}
if (!foundInInclude) {
reportSelectionMatchFailure();
}
}
}
return Status.OK_STATUS;
}
private boolean navigateOneLocation(IName[] declNames) {
for (int i = 0; i < declNames.length; i++) {
IASTFileLocation fileloc = declNames[i].getFileLocation();

View file

@ -17,8 +17,10 @@ import java.util.ArrayList;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.core.runtime.Path;
import org.eclipse.core.runtime.Status;
import org.eclipse.jface.text.IRegion;
import org.eclipse.jface.text.ITextSelection;
import org.eclipse.jface.text.Region;
@ -54,6 +56,7 @@ import org.eclipse.cdt.core.model.ITranslationUnit;
import org.eclipse.cdt.core.model.IWorkingCopy;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.internal.core.model.ASTCache.ASTRunnable;
import org.eclipse.cdt.internal.core.model.ext.CElementHandleFactory;
import org.eclipse.cdt.internal.core.model.ext.ICElementHandle;
@ -238,18 +241,23 @@ public class IndexUI {
return null;
}
public static IASTName getSelectedName(IIndex index, IEditorInput editorInput, ITextSelection selection) throws CoreException {
int selectionStart = selection.getOffset();
int selectionLength = selection.getLength();
public static IASTName getSelectedName(IEditorInput editorInput, ITextSelection selection) throws CoreException {
final int selectionStart = selection.getOffset();
final int selectionLength = selection.getLength();
IWorkingCopy workingCopy = CUIPlugin.getDefault().getWorkingCopyManager().getWorkingCopy(editorInput);
if (workingCopy == null)
return null;
IASTTranslationUnit ast= ASTProvider.getASTProvider().getAST(
workingCopy, index, ASTProvider.WAIT_YES, new NullProgressMonitor());
FindNameForSelectionVisitor finder= new FindNameForSelectionVisitor(ast.getFilePath(), selectionStart, selectionLength);
ast.accept(finder);
return finder.getSelectedName();
final IASTName[] result= {null};
ASTProvider.getASTProvider().runOnAST(workingCopy, ASTProvider.WAIT_YES, null, new ASTRunnable() {
public IStatus runOnAST(IASTTranslationUnit ast) {
FindNameForSelectionVisitor finder= new FindNameForSelectionVisitor(ast.getFilePath(), selectionStart, selectionLength);
ast.accept(finder);
result[0]= finder.getSelectedName();
return Status.OK_STATUS;
}
});
return result[0];
}
}