1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-04-23 22:52:11 +02:00

Bug 442754 - Refactor the test harness for semantic highlightings

Change-Id: I649b80e96f87481802c6b2f29029ed42bdb491a8
Signed-off-by: Nathan Ridge <zeratul976@hotmail.com>
Reviewed-on: https://git.eclipse.org/r/35518
Tested-by: Hudson CI
Reviewed-by: Sergey Prigogin <eclipse.sprigogin@gmail.com>
Tested-by: Sergey Prigogin <eclipse.sprigogin@gmail.com>
This commit is contained in:
Nathan Ridge 2014-10-26 02:04:14 -04:00 committed by Sergey Prigogin
parent 40cdeb4102
commit 356478286c
5 changed files with 384 additions and 785 deletions

View file

@ -1,161 +0,0 @@
#define INT int
#define FUNCTION_MACRO(arg) globalFunc(arg)
#define EMPTY_MACRO(arg)
enum Enumeration {
enumerator
};
const int globalConstant = 0;
int globalVariable = 0;
static int globalStaticVariable = 0;
void globalFunc(int a);
static void globalStaticFunc() {
EMPTY_MACRO(n);
};
class Base1 {};
class Base2 {};
class ClassContainer : Base1, Base2 {
friend void friendFunc();
friend class FriendClass;
public:
static int staticPubField;
const int constPubField;
const static int constStaticPubField;
int pubField;
static int staticPubMethod(int arg) {
FUNCTION_MACRO(arg);
globalFunc(arg);
return globalStaticVariable;
}
int pubMethod();
enum pubEnumeration {pubEnumerator};
class pubClass{};
class pubStruct{};
class pubUnion{};
typedef pubClass pubTypedef;
protected:
static const int constStaticProtField = 12;
static int staticProtField;
const int constProtField;
int protField;
static int staticProtMethod();
int protMethod();
enum protEnumeration {protEnumerator};
class protClass{};
class protStruct{};
class protUnion{};
typedef protClass protTypedef;
private:
static const int constStaticPrivField = 12;
static int staticPrivField;
const int constPrivField;
int privField;
static int staticPrivMethod();
int privMethod();
enum privEnumeration {privEnumerator};
class privClass{};
class privStruct{};
class privUnion{};
typedef privClass privTypedef;
};
template<class T1, class T2> class TemplateClass {
T1 tArg1;
T2 tArg2;
TemplateClass(T1 arg1, T2 arg2) {
tArg1 = arg1;
tArg2 = arg2;
}
};
template<class T1> class PartialInstantiatedClass : TemplateClass<T1, Base1> {};
struct CppStruct {
int structField;
};
union CppUnion {
int unionField;
CppUnion operator+(CppUnion);
CppUnion operator[](int);
};
typedef CppUnion TUnion;
namespace ns {
int namespaceVar = 0;
int namespaceFunc() {
globalStaticFunc();
return namespaceVar;
}
}
INT ClassContainer::protMethod() {
return protField;
}
INT ClassContainer::pubMethod() {
int localVar = 0;
return pubField + localVar;
}
INT ClassContainer::staticPrivMethod() {
CppStruct* st= new CppStruct();
st->structField= 1;
CppUnion un;
un.unionField= 2;
staticPubMethod(staticPrivField);
un + un[6];
label:
FUNCTION_MACRO(0);
if (un.unionField < st->structField) goto label;
problemMethod();
// external SDK
SDKClass sdkClass;
sdkClass.SDKMethod();
SDKFunction();
return 0;
}
//http://bugs.eclipse.org/209203
template <int n>
int f()
{
return n;
}
//http://bugs.eclipse.org/220392
#define EMPTY
EMPTY int f();
//http://bugs.eclipse.org/340492
template< template<class> class U > class myClass {};
//http://bugs.eclipse.org/372004
void g() {
extern int globalVariable; // declared as global near top
}
//http://bugs.eclipse.org/399149
class C final {
void finalMethod() final;
void overrideMethod() override;
int final; // ordinary field, happens to be named 'final'
};

View file

@ -1,215 +0,0 @@
/*******************************************************************************
* Copyright (c) 2000, 2012 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the 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:
* IBM Corporation - initial API and implementation
* Anton Leherbauer (Wind River Systems)
*******************************************************************************/
package org.eclipse.cdt.ui.tests.text;
import java.io.File;
import java.io.FileOutputStream;
import junit.extensions.TestSetup;
import junit.framework.Test;
import junit.framework.TestCase;
import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.Path;
import org.eclipse.jface.preference.IPreferenceStore;
import org.eclipse.jface.text.BadLocationException;
import org.eclipse.jface.text.BadPositionCategoryException;
import org.eclipse.jface.text.IDocument;
import org.eclipse.jface.text.Position;
import org.eclipse.jface.text.source.SourceViewer;
import org.eclipse.cdt.core.model.ICProject;
import org.eclipse.cdt.core.testplugin.CProjectHelper;
import org.eclipse.cdt.core.testplugin.TestScannerProvider;
import org.eclipse.cdt.core.testplugin.util.BaseTestCase;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.ui.PreferenceConstants;
import org.eclipse.cdt.ui.testplugin.Accessor;
import org.eclipse.cdt.ui.testplugin.EditorTestHelper;
import org.eclipse.cdt.ui.testplugin.ResourceTestHelper;
import org.eclipse.cdt.internal.ui.editor.CEditor;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlighting;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightingManager;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightingPresenter;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightings;
/**
* Derived from JDT.
*
* @since 4.0
*/
public class AbstractSemanticHighlightingTest extends TestCase {
protected static class SemanticHighlightingTestSetup extends TestSetup {
private ICProject fCProject;
private final String fTestFilename;
private File fExternalFile;
public SemanticHighlightingTestSetup(Test test, String testFilename) {
super(test);
fTestFilename= testFilename;
}
@Override
protected void setUp() throws Exception {
super.setUp();
String sdkCode=
"void SDKFunction();\n"+
"class SDKClass { public: void SDKMethod(); };\n\n";
fExternalFile= createExternalFile(sdkCode);
assertNotNull(fExternalFile);
// Load the file using option -include to make it part of the index.
TestScannerProvider.sIncludeFiles= new String[] {fExternalFile.getAbsolutePath()};
fCProject= EditorTestHelper.createCProject(PROJECT, LINKED_FOLDER, false, true);
BaseTestCase.waitForIndexer(fCProject);
fEditor= (CEditor) EditorTestHelper.openInEditor(ResourceTestHelper.findFile(fTestFilename), true);
fSourceViewer= EditorTestHelper.getSourceViewer(fEditor);
assertTrue(EditorTestHelper.joinReconciler(fSourceViewer, 500, 10000, 100));
EditorTestHelper.joinBackgroundActivities();
}
private static File createExternalFile(final String code) throws Exception {
File dest = File.createTempFile("external", ".h");
FileOutputStream fos = new FileOutputStream(dest);
fos.write(code.getBytes());
fos.close();
return dest;
}
protected String getTestFilename() {
return fTestFilename;
}
@Override
protected void tearDown () throws Exception {
EditorTestHelper.closeEditor(fEditor);
IPreferenceStore store= CUIPlugin.getDefault().getPreferenceStore();
store.setToDefault(PreferenceConstants.EDITOR_SEMANTIC_HIGHLIGHTING_ENABLED);
SemanticHighlighting[] semanticHighlightings= SemanticHighlightings.getSemanticHighlightings();
for (SemanticHighlighting semanticHighlighting : semanticHighlightings) {
String enabledPreferenceKey= SemanticHighlightings.getEnabledPreferenceKey(semanticHighlighting);
if (!store.isDefault(enabledPreferenceKey))
store.setToDefault(enabledPreferenceKey);
}
if (fCProject != null)
CProjectHelper.delete(fCProject);
if (fExternalFile != null) {
fExternalFile.delete();
}
TestScannerProvider.sIncludeFiles= null;
super.tearDown();
}
}
public static final String LINKED_FOLDER= "resources/semanticHighlighting";
public static final String PROJECT= "SHTest";
public static final String TESTFILE= "/SHTest/src/SHTest.cpp";
private static CEditor fEditor;
private static SourceViewer fSourceViewer;
private String fCurrentHighlighting;
private SemanticHighlightingTestSetup fProjectSetup;
@Override
protected void setUp() throws Exception {
super.setUp();
if (!ResourcesPlugin.getWorkspace().getRoot().exists(new Path(PROJECT))) {
fProjectSetup= new SemanticHighlightingTestSetup(this, TESTFILE);
fProjectSetup.setUp();
}
disableAllSemanticHighlightings();
EditorTestHelper.runEventQueue(500);
}
@Override
protected void tearDown() throws Exception {
if (fProjectSetup != null) {
fProjectSetup.tearDown();
fProjectSetup= null;
}
super.tearDown();
}
protected void assertEqualPositions(Position[] expected, Position[] actual) {
assertEquals(expected.length, actual.length);
for (int i= 0, n= expected.length; i < n; i++) {
assertEquals(expected[i].isDeleted(), actual[i].isDeleted());
assertEquals(expected[i].getOffset(), actual[i].getOffset());
assertEquals(expected[i].getLength(), actual[i].getLength());
}
}
protected Position createPosition(int line, int column, int length) throws BadLocationException {
IDocument document= fSourceViewer.getDocument();
return new Position(document.getLineOffset(line) + column, length);
}
String toString(Position[] positions) throws BadLocationException {
StringBuffer buf= new StringBuffer();
buf.append("// "+fCurrentHighlighting+'\n');
IDocument document= fSourceViewer.getDocument();
buf.append("Position[] expected= new Position[] {\n");
for (Position position : positions) {
int line= document.getLineOfOffset(position.getOffset());
int column= position.getOffset() - document.getLineOffset(line);
buf.append("\tcreatePosition(" + line + ", " + column + ", " + position.getLength() + "),\n");
}
buf.append("};\n");
return buf.toString();
}
protected Position[] getSemanticHighlightingPositions() throws BadPositionCategoryException {
SemanticHighlightingManager manager= (SemanticHighlightingManager) new Accessor(fEditor, CEditor.class).get("fSemanticManager");
SemanticHighlightingPresenter presenter= (SemanticHighlightingPresenter) new Accessor(manager, manager.getClass()).get("fPresenter");
String positionCategory= (String) new Accessor(presenter, presenter.getClass()).invoke("getPositionCategory", new Object[0]);
IDocument document= fSourceViewer.getDocument();
return document.getPositions(positionCategory);
}
protected void setUpSemanticHighlighting(String semanticHighlighting) {
fCurrentHighlighting= semanticHighlighting;
enableSemanticHighlighting(semanticHighlighting);
// give enough time to finish updating the highlighting positions
EditorTestHelper.runEventQueue(1000);
}
private void enableSemanticHighlighting(String preferenceKey) {
IPreferenceStore store= CUIPlugin.getDefault().getPreferenceStore();
store.setValue(getEnabledPreferenceKey(preferenceKey), true);
}
private String getEnabledPreferenceKey(String preferenceKey) {
return PreferenceConstants.EDITOR_SEMANTIC_HIGHLIGHTING_PREFIX + preferenceKey + PreferenceConstants.EDITOR_SEMANTIC_HIGHLIGHTING_ENABLED_SUFFIX;
}
private static void disableAllSemanticHighlightings() {
IPreferenceStore store= CUIPlugin.getDefault().getPreferenceStore();
store.setValue(PreferenceConstants.EDITOR_SEMANTIC_HIGHLIGHTING_ENABLED, true);
SemanticHighlighting[] semanticHilightings= SemanticHighlightings.getSemanticHighlightings();
for (SemanticHighlighting semanticHilighting : semanticHilightings) {
if (store.getBoolean(SemanticHighlightings.getEnabledPreferenceKey(semanticHilighting)))
store.setValue(SemanticHighlightings.getEnabledPreferenceKey(semanticHilighting), false);
}
}
}

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2000, 2013 IBM Corporation and others. * Copyright (c) 2000, 2014 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials * All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0 * are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at * which accompanies this distribution, and is available at
@ -8,16 +8,51 @@
* Contributors: * Contributors:
* IBM Corporation - initial API and implementation * IBM Corporation - initial API and implementation
* Anton Leherbauer (Wind River Systems) - Adapted for CDT * Anton Leherbauer (Wind River Systems) - Adapted for CDT
* Nathan Ridge - refactoring
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.ui.tests.text; package org.eclipse.cdt.ui.tests.text;
import java.io.File;
import java.io.FileOutputStream;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.core.runtime.Path;
import org.eclipse.jface.preference.IPreferenceStore;
import org.eclipse.jface.text.BadPositionCategoryException;
import org.eclipse.jface.text.IDocument;
import org.eclipse.jface.text.Position;
import org.eclipse.jface.text.source.SourceViewer;
import junit.framework.Test; import junit.framework.Test;
import junit.framework.TestCase;
import junit.framework.TestSuite; import junit.framework.TestSuite;
import org.eclipse.jface.text.Position; import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.dom.IPDOMManager;
import org.eclipse.cdt.ui.text.ICColorConstants; import org.eclipse.cdt.core.dom.ast.IASTComment;
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.ICProject;
import org.eclipse.cdt.core.testplugin.CProjectHelper;
import org.eclipse.cdt.core.testplugin.TestScannerProvider;
import org.eclipse.cdt.core.testplugin.util.BaseTestCase;
import org.eclipse.cdt.core.testplugin.util.TestSourceReader;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.ui.PreferenceConstants;
import org.eclipse.cdt.ui.testplugin.Accessor;
import org.eclipse.cdt.ui.testplugin.CTestPlugin;
import org.eclipse.cdt.ui.testplugin.EditorTestHelper;
import org.eclipse.cdt.ui.testplugin.ResourceTestHelper;
import org.eclipse.cdt.internal.ui.editor.CEditor;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlighting;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightingManager;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightingPresenter;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightingPresenter.TestHighlightedPosition;
import org.eclipse.cdt.internal.ui.editor.SemanticHighlightings; import org.eclipse.cdt.internal.ui.editor.SemanticHighlightings;
/** /**
@ -27,419 +62,323 @@ import org.eclipse.cdt.internal.ui.editor.SemanticHighlightings;
* *
* @since 4.0 * @since 4.0
*/ */
public class SemanticHighlightingTest extends AbstractSemanticHighlightingTest { public class SemanticHighlightingTest extends TestCase {
private static final boolean PRINT_POSITIONS= false;
private static final Class<?> THIS= SemanticHighlightingTest.class;
public static Test suite() { public static Test suite() {
return new SemanticHighlightingTestSetup(new TestSuite(THIS), TESTFILE); return new TestSuite(SemanticHighlightingTest.class);
} }
public void testStaticFieldHighlighting() throws Exception { private File fExternalFile;
setUpSemanticHighlighting(SemanticHighlightings.STATIC_FIELD); private ICProject fCProject;
Position[] actual= getSemanticHighlightingPositions(); private CEditor fEditor;
Position[] expected= new Position[] { private SourceViewer fSourceViewer;
createPosition(25, 15, 14), private IIndex fIndex;
createPosition(27, 21, 19), private IASTTranslationUnit fAST;
createPosition(44, 21, 20),
createPosition(45, 15, 15), private static File createExternalFile(final String code) throws Exception {
createPosition(59, 21, 20), File dest = File.createTempFile("external", ".h");
createPosition(60, 15, 15), FileOutputStream fos = new FileOutputStream(dest);
createPosition(122, 20, 15), fos.write(code.getBytes());
}; fos.close();
if (PRINT_POSITIONS) System.out.println(toString(actual)); return dest;
assertEqualPositions(expected, actual);
} }
public void testFieldHighlighting() throws Exception { private static void enableAllSemanticHighlightings() {
setUpSemanticHighlighting(SemanticHighlightings.FIELD); IPreferenceStore store= CUIPlugin.getDefault().getPreferenceStore();
Position[] actual= getSemanticHighlightingPositions(); store.setValue(PreferenceConstants.EDITOR_SEMANTIC_HIGHLIGHTING_ENABLED, true);
Position[] expected= new Position[] { SemanticHighlighting[] semanticHilightings= SemanticHighlightings.getSemanticHighlightings();
createPosition(25, 15, 14), for (SemanticHighlighting semanticHilighting : semanticHilightings) {
createPosition(26, 14, 13), String enabledPreferenceKey = SemanticHighlightings.getEnabledPreferenceKey(semanticHilighting);
createPosition(27, 21, 19), if (!store.getBoolean(enabledPreferenceKey))
createPosition(28, 8, 8), store.setValue(enabledPreferenceKey, true);
createPosition(44, 21, 20), }
createPosition(45, 15, 15),
createPosition(46, 15, 14),
createPosition(47, 8, 9),
createPosition(59, 21, 20),
createPosition(60, 15, 15),
createPosition(61, 15, 14),
createPosition(62, 8, 9),
createPosition(77, 7, 5),
createPosition(78, 7, 5),
createPosition(80, 8, 5),
createPosition(81, 8, 5),
createPosition(89, 8, 11),
createPosition(93, 8, 10),
createPosition(109, 11, 9),
createPosition(114, 11, 8),
createPosition(119, 8, 11),
createPosition(121, 7, 10),
createPosition(122, 20, 15),
createPosition(126, 11, 10),
createPosition(126, 28, 11),
createPosition(159, 8, 5),
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testMethodDeclarationHighlighting() throws Exception { private static void restoreAllSemanticHighlightingToDefaults() {
setUpSemanticHighlighting(SemanticHighlightings.METHOD_DECLARATION); IPreferenceStore store= CUIPlugin.getDefault().getPreferenceStore();
Position[] actual= getSemanticHighlightingPositions(); store.setToDefault(PreferenceConstants.EDITOR_SEMANTIC_HIGHLIGHTING_ENABLED);
Position[] expected= new Position[] { SemanticHighlighting[] semanticHighlightings= SemanticHighlightings.getSemanticHighlightings();
createPosition(30, 15, 15), for (SemanticHighlighting semanticHighlighting : semanticHighlightings) {
createPosition(35, 8, 9), String enabledPreferenceKey= SemanticHighlightings.getEnabledPreferenceKey(semanticHighlighting);
createPosition(49, 15, 16), if (!store.isDefault(enabledPreferenceKey))
createPosition(50, 8, 10), store.setToDefault(enabledPreferenceKey);
createPosition(64, 15, 16), }
createPosition(65, 8, 10),
createPosition(79, 4, 13),
createPosition(94, 13, 9),
createPosition(95, 13, 10),
createPosition(108, 4, 26),
createPosition(112, 4, 25),
createPosition(117, 4, 32),
createPosition(156, 9, 11),
createPosition(157, 9, 14),
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testMethodHighlighting() throws Exception { @Override
setUpSemanticHighlighting(SemanticHighlightings.METHOD); protected void setUp() throws Exception {
Position[] expected= new Position[] { super.setUp();
createPosition(30, 15, 15),
createPosition(35, 8, 9), enableAllSemanticHighlightings();
createPosition(49, 15, 16),
createPosition(50, 8, 10), SemanticHighlightingPresenter.sIsForTest = true;
createPosition(64, 15, 16),
createPosition(65, 8, 10), StringBuilder[] testData = TestSourceReader.getContentsForTest(CTestPlugin.getDefault().getBundle(), "ui", getClass(), getName(), 0);
createPosition(79, 4, 13),
createPosition(94, 13, 9), if (testData.length == 2) {
createPosition(95, 13, 10), fExternalFile= createExternalFile(testData[0].toString());
createPosition(108, 4, 26), assertNotNull(fExternalFile);
createPosition(112, 4, 25), // Load the file using option -include to make it part of the index.
createPosition(117, 4, 32), TestScannerProvider.sIncludeFiles= new String[] {fExternalFile.getAbsolutePath()};
createPosition(122, 4, 15),
createPosition(130, 13, 9),
createPosition(156, 9, 11),
createPosition(157, 9, 14),
};
Position[] actual= getSemanticHighlightingPositions();
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testStaticMethodInvocationHighlighting() throws Exception { fCProject= CProjectHelper.createCCProject("SHTest", "bin", IPDOMManager.ID_FAST_INDEXER);
setUpSemanticHighlighting(SemanticHighlightings.STATIC_METHOD_INVOCATION); IFile cppfile = TestSourceReader.createFile(fCProject.getProject(), new Path("SHTest.cpp"),
Position[] expected= new Position[] { testData.length == 2 ? testData[1].toString() : testData[0].toString());
createPosition(122, 4, 15), IIndexManager indexManager= CCorePlugin.getIndexManager();
}; indexManager.joinIndexer(5000, new NullProgressMonitor());
Position[] actual= getSemanticHighlightingPositions();
if (PRINT_POSITIONS) System.out.println(toString(actual)); BaseTestCase.waitForIndexer(fCProject);
assertEqualPositions(expected, actual); fEditor= (CEditor) EditorTestHelper.openInEditor(ResourceTestHelper.findFile("/SHTest/SHTest.cpp"), true);
fSourceViewer= EditorTestHelper.getSourceViewer(fEditor);
assertTrue(EditorTestHelper.joinReconciler(fSourceViewer, 500, 10000, 100));
EditorTestHelper.joinBackgroundActivities();
fIndex = CCorePlugin.getIndexManager().getIndex(fCProject);
fIndex.acquireReadLock();
fAST = TestSourceReader.createIndexBasedAST(fIndex, fCProject, cppfile);
} }
public void testLocalVariableDeclarationHighlighting() throws Exception { @Override
setUpSemanticHighlighting(SemanticHighlightings.LOCAL_VARIABLE_DECLARATION); protected void tearDown() throws Exception {
Position[] expected= new Position[] { fIndex.releaseReadLock();
createPosition(113, 8, 8),
createPosition(118, 15, 2), EditorTestHelper.closeEditor(fEditor);
createPosition(120, 13, 2),
createPosition(129, 13, 8), if (fCProject != null)
}; CProjectHelper.delete(fCProject);
Position[] actual= getSemanticHighlightingPositions();
if (PRINT_POSITIONS) System.out.println(toString(actual)); if (fExternalFile != null) {
assertEqualPositions(expected, actual); fExternalFile.delete();
} }
public void testLocalVariableReferencesHighlighting() throws Exception { TestScannerProvider.sIncludeFiles= null;
setUpSemanticHighlighting(SemanticHighlightings.LOCAL_VARIABLE); SemanticHighlightingPresenter.sIsForTest = false;
Position[] expected= new Position[] {
createPosition(114, 22, 8), restoreAllSemanticHighlightingToDefaults();
createPosition(119, 4, 2),
createPosition(121, 4, 2), super.tearDown();
createPosition(123, 4, 2),
createPosition(123, 9, 2),
createPosition(126, 8, 2),
createPosition(126, 24, 2),
createPosition(130, 4, 8),
};
Position[] actual= getSemanticHighlightingPositions();
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testParameterVariableHighlighting() throws Exception { private Position[] getSemanticHighlightingPositions() throws BadPositionCategoryException {
setUpSemanticHighlighting(SemanticHighlightings.PARAMETER_VARIABLE); SemanticHighlightingManager manager= (SemanticHighlightingManager) new Accessor(fEditor, CEditor.class).get("fSemanticManager");
Position[] actual= getSemanticHighlightingPositions(); SemanticHighlightingPresenter presenter= (SemanticHighlightingPresenter) new Accessor(manager, manager.getClass()).get("fPresenter");
Position[] expected= new Position[] { String positionCategory= (String) new Accessor(presenter, presenter.getClass()).invoke("getPositionCategory", new Object[0]);
createPosition(12, 20, 1), IDocument document= fSourceViewer.getDocument();
createPosition(30, 35, 3), return document.getPositions(positionCategory);
createPosition(31, 23, 3),
createPosition(32, 19, 3),
createPosition(79, 21, 4),
createPosition(79, 30, 4),
createPosition(80, 16, 4),
createPosition(81, 16, 4),
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testTemplateParameterHighlighting() throws Exception { private void makeAssertions() throws Exception {
setUpSemanticHighlighting(SemanticHighlightings.TEMPLATE_PARAMETER); IDocument document = fSourceViewer.getDocument();
Position[] actual= getSemanticHighlightingPositions(); int lines = document.getNumberOfLines();
Position[] expected= new Position[] {
createPosition(76, 15, 2), List<String>[] expected = new List[lines];
createPosition(76, 25, 2), for (int i = 0; i < lines; ++i) {
createPosition(77, 4, 2), expected[i] = new ArrayList<String>();
createPosition(78, 4, 2), }
createPosition(79, 18, 2), for (IASTComment comment : fAST.getComments()) {
createPosition(79, 27, 2), String contents = new String(comment.getComment());
createPosition(85, 15, 2), if (contents.length() > 2 && contents.substring(0, 3).equals("//$")) {
createPosition(85, 66, 2), for (String component : contents.substring(3).split(",")) {
createPosition(136, 14, 1), // subtract 1 to make it into a 0-based line number
createPosition(139, 9, 1), expected[comment.getFileLocation().getStartingLineNumber() - 1].add(component);
createPosition(147, 32, 1), }
}; }
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testEnumHighlighting() throws Exception { List<String>[] actual = new List[lines];
setUpSemanticHighlighting(SemanticHighlightings.ENUM); for (int i = 0; i < lines; ++i) {
Position[] actual= getSemanticHighlightingPositions(); actual[i] = new ArrayList<String>();
Position[] expected= new Position[] { }
createPosition(4, 5, 11), for (Position p : getSemanticHighlightingPositions()) {
createPosition(37, 9, 14), assertTrue(p instanceof TestHighlightedPosition);
createPosition(52, 9, 15), int line = document.getLineOfOffset(p.getOffset());
createPosition(67, 9, 15), actual[line].add(((TestHighlightedPosition) p).getPreferenceKey());
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testClassHighlighting() throws Exception { assertEqualMaps(actual, expected);
setUpSemanticHighlighting(SemanticHighlightings.CLASS);
Position[] actual= getSemanticHighlightingPositions();
Position[] expected= new Position[] {
createPosition(17, 6, 5),
createPosition(18, 6, 5),
createPosition(20, 6, 14),
createPosition(20, 23, 5),
createPosition(20, 30, 5),
createPosition(22, 17, 11),
createPosition(38, 10, 8),
createPosition(39, 10, 9),
createPosition(40, 10, 8),
createPosition(41, 12, 8),
createPosition(53, 10, 9),
createPosition(54, 10, 10),
createPosition(55, 10, 9),
createPosition(56, 12, 9),
createPosition(68, 10, 9),
createPosition(69, 10, 10),
createPosition(70, 10, 9),
createPosition(71, 12, 9),
createPosition(76, 35, 13),
createPosition(85, 25, 24),
createPosition(85, 52, 13),
createPosition(85, 70, 5),
createPosition(88, 7, 9),
createPosition(92, 6, 8),
createPosition(94, 4, 8),
createPosition(94, 23, 8),
createPosition(95, 4, 8),
createPosition(98, 8, 8),
createPosition(108, 4, 14),
createPosition(112, 4, 14),
createPosition(117, 4, 14),
createPosition(118, 4, 9),
createPosition(118, 23, 9),
createPosition(120, 4, 8),
createPosition(129, 4, 8),
createPosition(147, 42, 7),
createPosition(155, 6, 1),
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testFunctionDeclarationHighlighting() throws Exception { private void assertEqualMaps(List<String>[] actual, List<String>[] expected) {
setUpSemanticHighlighting(SemanticHighlightings.FUNCTION_DECLARATION); assertEquals(expected.length, actual.length);
Position[] actual= getSemanticHighlightingPositions(); for (int i = 0; i < actual.length; ++i) {
Position[] expected= new Position[] { assertEquals("Expected " + expected[i].size() + " positions on line " + i + ", got " + actual[i].size(),
createPosition(12, 5, 10), expected[i].size(), actual[i].size());
createPosition(13, 12, 16), for (int j = 0; j < actual[i].size(); ++j) {
createPosition(21, 16, 10), assertEquals(expected[i].get(j), actual[i].get(j));
createPosition(102, 8, 13), }
createPosition(137, 4, 1), }
createPosition(144, 10, 1),
createPosition(150, 5, 1),
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
} }
public void testFunctionHighlighting() throws Exception { // void SDKFunction();
setUpSemanticHighlighting(SemanticHighlightings.FUNCTION); // class SDKClass { public: void SDKMethod(); };\n\n";
Position[] actual= getSemanticHighlightingPositions();
Position[] expected= new Position[] {
createPosition(12, 5, 10),
createPosition(13, 12, 16),
createPosition(21, 16, 10),
createPosition(32, 8, 10),
createPosition(102, 8, 13),
createPosition(103, 1, 16),
createPosition(131, 4, 11),
createPosition(137, 4, 1),
createPosition(144, 10, 1),
createPosition(150, 5, 1),
};
if (PRINT_POSITIONS) System.out.println(toString(actual));
assertEqualPositions(expected, actual);
}
public void testGlobalVariableHighlighting() throws Exception { //#define INT int //$macroDefinition
setUpSemanticHighlighting(SemanticHighlightings.GLOBAL_VARIABLE); //#define FUNCTION_MACRO(arg) globalFunc(arg) //$macroDefinition
Position[] actual= getSemanticHighlightingPositions(); //#define EMPTY_MACRO(arg) //$macroDefinition
Position[] expected= new Position[] { //#include "SHTest.h"
createPosition(8, 10, 14), //enum Enumeration { //$enum
createPosition(9, 4, 14), // enumerator //$enumerator
createPosition(10, 11, 20), //};
createPosition(33, 15, 20), //
createPosition(101, 8, 12), //const int globalConstant = 0; //$globalVariable
createPosition(104, 8, 12), //int globalVariable = 0; //$globalVariable
createPosition(151, 15, 14), //static int globalStaticVariable = 0; //$globalVariable
}; //
if (PRINT_POSITIONS) System.out.println(toString(actual)); //void globalFunc(int a); //$functionDeclaration,parameterVariable
assertEqualPositions(expected, actual); //static void globalStaticFunc() { //$functionDeclaration
} // EMPTY_MACRO(n); //$macroSubstitution
//};
public void testMacroDefinitionHighlighting() throws Exception { //
setUpSemanticHighlighting(SemanticHighlightings.MACRO_DEFINITION); //class Base1 {}; //$class
Position[] actual= getSemanticHighlightingPositions(); //class Base2 {}; //$class
Position[] expected= new Position[] { //
createPosition(0, 8, 3), //class ClassContainer : Base1, Base2 { //$class,class,class
createPosition(1, 8, 14), // friend void friendFunc(); //$functionDeclaration
createPosition(2, 8, 11), // friend class FriendClass; //$class
createPosition(143, 8, 5), //
}; //public:
if (PRINT_POSITIONS) System.out.println(toString(actual)); // static int staticPubField; //$staticField
assertEqualPositions(expected, actual); // const int constPubField; //$field
} // const static int constStaticPubField; //$staticField
// int pubField; //$field
public void testMacroReferencesHighlighting() throws Exception { //
setUpSemanticHighlighting(SemanticHighlightings.MACRO_REFERENCE); // static int staticPubMethod(int arg) { //$methodDeclaration,parameterVariable
Position[] actual= getSemanticHighlightingPositions(); // FUNCTION_MACRO(arg); //$macroSubstitution,parameterVariable
Position[] expected= new Position[] { // globalFunc(arg); //$function,parameterVariable
createPosition(14, 4, 11), // return globalStaticVariable; //$globalVariable
createPosition(31, 8, 14), // }
createPosition(108, 0, 3), // int pubMethod(); //$methodDeclaration
createPosition(112, 0, 3), //
createPosition(117, 0, 3), // enum pubEnumeration {pubEnumerator}; //$enum,enumerator
createPosition(125, 4, 14), // class pubClass{}; //$class
createPosition(144, 0, 5), // class pubStruct{}; //$class
}; // class pubUnion{}; //$class
if (PRINT_POSITIONS) System.out.println(toString(actual)); // typedef pubClass pubTypedef; //$class,typedef
assertEqualPositions(expected, actual); //
} //protected:
// static const int constStaticProtField = 12; //$staticField
public void testTypedefHighlighting() throws Exception { // static int staticProtField; //$staticField
setUpSemanticHighlighting(SemanticHighlightings.TYPEDEF); // const int constProtField; //$field
Position[] actual= getSemanticHighlightingPositions(); // int protField; //$field
Position[] expected= new Position[] { //
createPosition(41, 21, 10), // static int staticProtMethod(); //$methodDeclaration
createPosition(56, 22, 11), // int protMethod(); //$methodDeclaration
createPosition(71, 22, 11), //
createPosition(98, 17, 6), // enum protEnumeration {protEnumerator}; //$enum,enumerator
}; // class protClass{}; //$class
if (PRINT_POSITIONS) System.out.println(toString(actual)); // class protStruct{}; //$class
assertEqualPositions(expected, actual); // class protUnion{}; //$class
} // typedef protClass protTypedef; //$class,typedef
//
public void testNamespaceHighlighting() throws Exception { //private:
setUpSemanticHighlighting(SemanticHighlightings.NAMESPACE); // static const int constStaticPrivField = 12; //$staticField
Position[] actual= getSemanticHighlightingPositions(); // static int staticPrivField; //$staticField
Position[] expected= new Position[] { // const int constPrivField; //$field
createPosition(100, 10, 2), // int privField; //$field
}; //
if (PRINT_POSITIONS) System.out.println(toString(actual)); // static int staticPrivMethod(); //$methodDeclaration
assertEqualPositions(expected, actual); // int privMethod(); //$methodDeclaration
} //
// enum privEnumeration {privEnumerator}; //$enum,enumerator
public void testLabelHighlighting() throws Exception { // class privClass{}; //$class
setUpSemanticHighlighting(SemanticHighlightings.LABEL); // class privStruct{}; //$class
Position[] actual= getSemanticHighlightingPositions(); // class privUnion{}; //$class
Position[] expected= new Position[] { // typedef privClass privTypedef; //$class,typedef
createPosition(124, 0, 5), //
createPosition(126, 46, 5), //
}; //};
if (PRINT_POSITIONS) System.out.println(toString(actual)); //
assertEqualPositions(expected, actual); //template<class T1, class T2> class TemplateClass { //$templateParameter,templateParameter,class
} // T1 tArg1; //$templateParameter,field
// T2 tArg2; //$templateParameter,field
public void testEnumeratorHighlighting() throws Exception { // TemplateClass(T1 arg1, T2 arg2) { //$methodDeclaration,templateParameter,parameterVariable,templateParameter,parameterVariable
setUpSemanticHighlighting(SemanticHighlightings.ENUMERATOR); // tArg1 = arg1; //$field,parameterVariable
Position[] actual= getSemanticHighlightingPositions(); // tArg2 = arg2; //$field,parameterVariable
Position[] expected= new Position[] { // }
createPosition(5, 4, 10), //};
createPosition(37, 25, 13), //
createPosition(52, 26, 14), //template<class T1> class PartialInstantiatedClass //$templateParameter,class
createPosition(67, 26, 14), // : TemplateClass<T1, Base1> {}; //$class,templateParameter,class
}; //
if (PRINT_POSITIONS) System.out.println(toString(actual)); //
assertEqualPositions(expected, actual); //struct CppStruct { //$class
} // int structField; //$field
//};
public void testProblemHighlighting() throws Exception { //
setUpSemanticHighlighting(SemanticHighlightings.PROBLEM); //union CppUnion { //$class
Position[] actual= getSemanticHighlightingPositions(); // int unionField; //$field
Position[] expected= new Position[] { // CppUnion operator+(CppUnion); //$class,methodDeclaration,class
createPosition(127, 4, 13), // CppUnion operator[](int); //$class,methodDeclaration
}; //};
if (PRINT_POSITIONS) System.out.println(toString(actual)); //
assertEqualPositions(expected, actual); //typedef CppUnion TUnion; //$class,typedef
} //
//namespace ns { //$namespace
public void testExternalSDKHighlighting() throws Exception { // int namespaceVar = 0; //$globalVariable
setUpSemanticHighlighting(SemanticHighlightings.EXTERNAL_SDK); // int namespaceFunc() { //$functionDeclaration
Position[] actual= getSemanticHighlightingPositions(); // globalStaticFunc(); //$function
Position[] expected= new Position[] { // return namespaceVar; //$globalVariable
createPosition(130, 13, 9), // }
createPosition(131, 4, 11), //}
}; //
if (PRINT_POSITIONS) System.out.println(toString(actual)); //INT ClassContainer::protMethod() { //$macroSubstitution,methodDeclaration
assertEqualPositions(expected, actual); // return protField; //$field
} //}
//
public void testOverloadedOperatorHighlighting() throws Exception { //INT ClassContainer::pubMethod() { //$macroSubstitution,methodDeclaration
setUpSemanticHighlighting(SemanticHighlightings.OVERLOADED_OPERATOR); // int localVar = 0; //$localVariableDeclaration
Position[] actual= getSemanticHighlightingPositions(); // return pubField + localVar; //$field,localVariable
Position[] expected= new Position[] { //}
createPosition(123, 7, 1), //
createPosition(123, 11, 1), //INT ClassContainer::staticPrivMethod() { //$macroSubstitution,methodDeclaration
createPosition(123, 13, 1), // CppStruct* st= new CppStruct(); //$class,localVariableDeclaration,class
}; // st->structField= 1; //$localVariable,field
if (PRINT_POSITIONS) System.out.println(toString(actual)); // CppUnion un; //$class,localVariableDeclaration
assertEqualPositions(expected, actual); // un.unionField= 2; //$localVariable,field
} // staticPubMethod(staticPrivField); //$staticMethod,staticField
// un + un[6]; //$localVariable,overloadedOperator,localVariable,overloadedOperator,overloadedOperator
public void testContextSensitiveKeywordHighlighting() throws Exception { //label: //$label
setUpSemanticHighlighting(ICColorConstants.C_KEYWORD); // FUNCTION_MACRO(0); //$macroSubstitution
Position[] actual= getSemanticHighlightingPositions(); // if (un.unionField < st->structField) //$localVariable,field,localVariable,field
Position[] expected= new Position[] { // goto label; //$label
createPosition(155, 8, 5), // problemMethod(); //$problem
createPosition(156, 23, 5), // // external SDK
createPosition(157, 26, 8), // SDKClass sdkClass; //$class,localVariableDeclaration
}; // sdkClass.SDKMethod(); //$localVariable,externalSDK
if (PRINT_POSITIONS) System.out.println(toString(actual)); // SDKFunction(); //$externalSDK
assertEqualPositions(expected, actual); // return 0;
//}
//
////http://bugs.eclipse.org/209203
//template <int n> //$templateParameter
//int f() //$functionDeclaration
//{
// return n; //$templateParameter
//}
//
////http://bugs.eclipse.org/220392
//#define EMPTY //$macroDefinition
//EMPTY int f(); //$macroSubstitution,functionDeclaration
//
////http://bugs.eclipse.org/340492
//template< template<class> class U > //$templateParameter
//class myClass {}; //$class
//
////http://bugs.eclipse.org/372004
//void g() { //$functionDeclaration
// // declared as global near top
// extern int globalVariable; //$globalVariable
//}
//
////http://bugs.eclipse.org/399149
//class C final { //$class,c_keyword
// void finalMethod() final; //$methodDeclaration,c_keyword
// void overrideMethod() override; //$methodDeclaration,c_keyword
//
// // ordinary field, happens to be named 'final'
// int final; //$field
//};
public void testVariousHighlightings() throws Exception {
makeAssertions();
} }
} }

View file

@ -239,6 +239,32 @@ public class SemanticHighlightingPresenter implements ITextPresentationListener,
/** <code>true</code> iff the current reconcile is canceled. */ /** <code>true</code> iff the current reconcile is canceled. */
private boolean fIsCanceled= false; private boolean fIsCanceled= false;
/**
* A subclass of HighlightedPosition that records which semantic highlighting
* the position is for. Used for testing.
*
*/
public static class TestHighlightedPosition extends HighlightedPosition {
private String fPreferenceKey;
public String getPreferenceKey() {
return fPreferenceKey;
}
public TestHighlightedPosition(int offset, int length, HighlightingStyle highlighting,
Object lock, String preferenceKey) {
super(offset, length, highlighting, lock);
fPreferenceKey = preferenceKey;
}
}
/**
* A flag that is set when this class is exercised by a test.
* When the flag is set, the positions added to the document are of type
* TestHighlightedPosition rather than HighlightedPosition.
*/
public static boolean sIsForTest = false;
/** /**
* Creates and returns a new highlighted position with the given offset, length and highlighting. * Creates and returns a new highlighted position with the given offset, length and highlighting.
* <p> * <p>
@ -247,12 +273,20 @@ public class SemanticHighlightingPresenter implements ITextPresentationListener,
* *
* @param offset The offset * @param offset The offset
* @param length The length * @param length The length
* @param highlighting The highlighting * @param style The highlighting
* @return The new highlighted position * @return The new highlighted position
*/ */
public HighlightedPosition createHighlightedPosition(int offset, int length, HighlightingStyle highlighting) { public HighlightedPosition createHighlightedPosition(int offset, int length, HighlightingStyle style) {
// TODO: reuse deleted positions // TODO: reuse deleted positions
return new HighlightedPosition(offset, length, highlighting, fPositionUpdater); return createHighlightedPosition(offset, length, style, null);
}
public HighlightedPosition createHighlightedPosition(int offset, int length, HighlightingStyle style,
String preferenceKey) {
if (sIsForTest) {
return new TestHighlightedPosition(offset, length, style, fPositionUpdater, preferenceKey);
}
return new HighlightedPosition(offset, length, style, fPositionUpdater);
} }
/** /**

View file

@ -184,9 +184,9 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
SemanticHighlighting semanticHighlighting= fJobSemanticHighlightings[i]; SemanticHighlighting semanticHighlighting= fJobSemanticHighlightings[i];
if (fJobHighlightings[i].isEnabled() && semanticHighlighting.consumes(fToken)) { if (fJobHighlightings[i].isEnabled() && semanticHighlighting.consumes(fToken)) {
if (node instanceof IASTName) { if (node instanceof IASTName) {
addNameLocation((IASTName) node, fJobHighlightings[i]); addNameLocation((IASTName) node, i);
} else { } else {
addNodeLocation(node.getFileLocation(), fJobHighlightings[i]); addNodeLocation(node.getFileLocation(), i);
} }
consumed= true; consumed= true;
break; break;
@ -202,7 +202,7 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
* @param name The name * @param name The name
* @param highlighting The highlighting * @param highlighting The highlighting
*/ */
private void addNameLocation(IASTName name, HighlightingStyle highlightingStyle) { private void addNameLocation(IASTName name, int highlighting) {
IASTImageLocation imageLocation= name.getImageLocation(); IASTImageLocation imageLocation= name.getImageLocation();
if (imageLocation != null) { if (imageLocation != null) {
if (imageLocation.getLocationKind() != IASTImageLocation.MACRO_DEFINITION) { if (imageLocation.getLocationKind() != IASTImageLocation.MACRO_DEFINITION) {
@ -211,7 +211,7 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
int length= imageLocation.getNodeLength(); int length= imageLocation.getNodeLength();
if (offset >= 0 && length > 0) { if (offset >= 0 && length > 0) {
fMinLocation= offset + length; fMinLocation= offset + length;
addPosition(offset, length, highlightingStyle); addPosition(offset, length, highlighting);
} }
} }
} }
@ -219,7 +219,7 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
// Fallback in case no image location available. // Fallback in case no image location available.
IASTNodeLocation[] nodeLocations= name.getNodeLocations(); IASTNodeLocation[] nodeLocations= name.getNodeLocations();
if (nodeLocations.length == 1 && !(nodeLocations[0] instanceof IASTMacroExpansionLocation)) { if (nodeLocations.length == 1 && !(nodeLocations[0] instanceof IASTMacroExpansionLocation)) {
addNodeLocation(nodeLocations[0], highlightingStyle); addNodeLocation(nodeLocations[0], highlighting);
} }
} }
} }
@ -230,7 +230,7 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
* @param nodeLocation The node location * @param nodeLocation The node location
* @param highlighting The highlighting * @param highlighting The highlighting
*/ */
private void addNodeLocation(IASTNodeLocation nodeLocation, HighlightingStyle highlighting) { private void addNodeLocation(IASTNodeLocation nodeLocation, int highlighting) {
if (nodeLocation == null) { if (nodeLocation == null) {
return; return;
} }
@ -251,14 +251,15 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
* @param length The range length * @param length The range length
* @param highlighting The highlighting * @param highlighting The highlighting
*/ */
private void addPosition(int offset, int length, HighlightingStyle highlighting) { private void addPosition(int offset, int length, int highlighting) {
boolean isExisting= false; boolean isExisting= false;
// TODO: use binary search // TODO: use binary search
HighlightingStyle style = fJobHighlightings[highlighting];
for (int i= 0, n= fRemovedPositions.size(); i < n; i++) { for (int i= 0, n= fRemovedPositions.size(); i < n; i++) {
HighlightedPosition position= fRemovedPositions.get(i); HighlightedPosition position= fRemovedPositions.get(i);
if (position == null) if (position == null)
continue; continue;
if (position.isEqual(offset, length, highlighting)) { if (position.isEqual(offset, length, style)) {
isExisting= true; isExisting= true;
fRemovedPositions.set(i, null); fRemovedPositions.set(i, null);
fNOfRemovedPositions--; fNOfRemovedPositions--;
@ -267,7 +268,8 @@ public class SemanticHighlightingReconciler implements ICReconcilingListener {
} }
if (!isExisting) { if (!isExisting) {
HighlightedPosition position= fJobPresenter.createHighlightedPosition(offset, length, highlighting); HighlightedPosition position= fJobPresenter.createHighlightedPosition(offset, length, style,
fJobSemanticHighlightings[highlighting].getPreferenceKey());
fAddedPositions.add(position); fAddedPositions.add(position);
} }
} }