mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-04-23 22:52:11 +02:00
Fix for 196823, JUnit failures of scanner discovery
This commit is contained in:
parent
5c594b778c
commit
238ca43d28
11 changed files with 383 additions and 543 deletions
|
@ -81,7 +81,7 @@ public abstract class BaseBOPConsoleParserTests extends BaseTestCase {
|
|||
}
|
||||
|
||||
public void testParsingSymbolDefinitions_bug80271() {
|
||||
fOutputParser.processLine("gcc -DMACRO1 -I ..\\inc -c ..\\source\\source.c"); // PR 80271 //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -DMACRO1 -I ..\\inc -c ..\\perfilescdtest\\source.c"); // PR 80271 //$NON-NLS-1$
|
||||
|
||||
List sumSymbols = fCollector.getCollectedScannerInfo(null, ScannerInfoTypes.SYMBOL_DEFINITIONS);
|
||||
assertTrue(sumSymbols.contains("MACRO1")); //$NON-NLS-1$
|
||||
|
@ -90,14 +90,14 @@ public abstract class BaseBOPConsoleParserTests extends BaseTestCase {
|
|||
|
||||
public void testParsingUnbalancedDoubleQuote_Bug186065() throws Exception {
|
||||
fOutputParser.processLine("../src/bug186065.cc:8: error: missing terminating \" character"); // PR 80271 //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -DBUG186065_IS_FIXED"); //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -DBUG186065_IS_FIXED test.c"); //$NON-NLS-1$
|
||||
|
||||
List sumSymbols = fCollector.getCollectedScannerInfo(null, ScannerInfoTypes.SYMBOL_DEFINITIONS);
|
||||
assertTrue(sumSymbols.contains("BUG186065_IS_FIXED")); //$NON-NLS-1$
|
||||
assertTrue(sumSymbols.size() == 1);
|
||||
}
|
||||
|
||||
public void _testCompilerCommand_bug194394() throws Exception {
|
||||
public void testCompilerCommand_bug194394() throws Exception {
|
||||
fOutputParser.processLine("/usr/bin/gcc -DA test1.c"); //$NON-NLS-1$
|
||||
fOutputParser.processLine("/usr/gcc-installs/gcc -DB test2.c"); //$NON-NLS-1$
|
||||
fOutputParser.processLine("/usr/gcc/gcc -DC test3.c"); //$NON-NLS-1$
|
||||
|
|
|
@ -55,19 +55,4 @@ public class GCCPerFileBOPConsoleParserTests extends BaseBOPConsoleParserTests {
|
|||
CProjectHelper.delete(fCProject);
|
||||
}
|
||||
}
|
||||
|
||||
public void testParsingSymbolDefinitions() {}
|
||||
public void _testParsingSymbolDefinitions() {
|
||||
super.testParsingSymbolDefinitions();
|
||||
}
|
||||
|
||||
public void testParsingSymbolDefinitions_bug80271() {}
|
||||
public void _testParsingSymbolDefinitions_bug80271() {
|
||||
super.testParsingSymbolDefinitions_bug80271();
|
||||
}
|
||||
|
||||
public void testParsingUnbalancedDoubleQuote_Bug186065() {}
|
||||
public void _testParsingUnbalancedDoubleQuote_Bug186065() throws Exception {
|
||||
super.testParsingUnbalancedDoubleQuote_Bug186065();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -58,7 +58,7 @@ public class GCCScannerInfoConsoleParserTests extends BaseBOPConsoleParserTests
|
|||
fOutputParser.processLine("gcc '-I /with spaces 1' -I'/with spaces 2' -c test.c"); // dirs with spaces 1,2 //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc \"-I /with spaces 3\" -I \"/with spaces 4\" -c test.c"); // dirs with spaces 3,4 //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -I /with\\ spaces\\ 5 -c test.c"); // dirs with spaces 5 //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -I '\\\\server1\\include' '-I\\\\server2\\include' -I \"\\\\server3\\include\" -c test.c"); // UNC paths //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -I '\\\\server1\\include' '-I\\\\server2\\include' -I \"\\\\\\\\server3\\\\include\" -c test.c"); // UNC paths //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -I //server4/include -I '//server5/include' '-I//server6/include' -c test.c"); // UNC paths //$NON-NLS-1$
|
||||
fOutputParser.processLine("gcc -I \\"); //$NON-NLS-1$
|
||||
fOutputParser.processLine("/multiline\\"); //$NON-NLS-1$
|
||||
|
@ -91,10 +91,4 @@ public class GCCScannerInfoConsoleParserTests extends BaseBOPConsoleParserTests
|
|||
assertTrue(sumIncludes.contains("/multiline/dir")); //$NON-NLS-1$
|
||||
assertTrue(sumIncludes.size() == 24);
|
||||
}
|
||||
|
||||
public void testCommandsWithSemicolon_bug194394() {}
|
||||
public void _testCommandsWithSemicolon_bug194394() throws Exception {
|
||||
super.testCommandsWithSemicolon_bug194394();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -6,10 +6,13 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* IBM - Initial API and implementation
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig.gnu;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.eclipse.cdt.make.core.scannerconfig.IScannerInfoCollector;
|
||||
import org.eclipse.cdt.make.core.scannerconfig.IScannerInfoConsoleParser;
|
||||
import org.eclipse.cdt.make.internal.core.scannerconfig.util.TraceUtil;
|
||||
|
@ -27,6 +30,9 @@ public abstract class AbstractGCCBOPConsoleParser implements IScannerInfoConsole
|
|||
private static final String[] COMPILER_INVOCATION = {
|
||||
"gcc", "g++", "cc", "c++" //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
|
||||
};
|
||||
protected static final String DASHIDASH= "-I-"; //$NON-NLS-1$
|
||||
protected static final String DASHI= "-I"; //$NON-NLS-1$
|
||||
protected static final String DASHD= "-D"; //$NON-NLS-1$
|
||||
|
||||
private IProject project;
|
||||
private IScannerInfoCollector collector;
|
||||
|
@ -34,6 +40,8 @@ public abstract class AbstractGCCBOPConsoleParser implements IScannerInfoConsole
|
|||
private boolean bMultiline = false;
|
||||
private String sMultiline = ""; //$NON-NLS-1$
|
||||
|
||||
private String[] fCompilerCommands;
|
||||
|
||||
/**
|
||||
* @return Returns the project.
|
||||
*/
|
||||
|
@ -50,6 +58,7 @@ public abstract class AbstractGCCBOPConsoleParser implements IScannerInfoConsole
|
|||
public void startup(IProject project, IScannerInfoCollector collector) {
|
||||
this.project = project;
|
||||
this.collector = collector;
|
||||
fCompilerCommands= computeCompilerCommands();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -57,7 +66,7 @@ public abstract class AbstractGCCBOPConsoleParser implements IScannerInfoConsole
|
|||
*
|
||||
* @return String[]
|
||||
*/
|
||||
public String[] getCompilerCommands() {
|
||||
private String[] computeCompilerCommands() {
|
||||
if (project != null) {
|
||||
SCProfileInstance profileInstance = ScannerConfigProfileManager.getInstance().
|
||||
getSCProfileInstance(project, ScannerConfigProfileManager.NULL_PROFILE_ID);
|
||||
|
@ -143,7 +152,6 @@ public abstract class AbstractGCCBOPConsoleParser implements IScannerInfoConsole
|
|||
return num;
|
||||
}
|
||||
|
||||
protected abstract boolean processSingleLine(String line);
|
||||
protected abstract AbstractGCCBOPConsoleParserUtility getUtility();
|
||||
|
||||
/* (non-Javadoc)
|
||||
|
@ -154,4 +162,157 @@ public abstract class AbstractGCCBOPConsoleParser implements IScannerInfoConsole
|
|||
getUtility().reportProblems();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Tokenizes a line into an array of commands. Commands are separated by
|
||||
* ';', '&&' or '||'. Tokens are separated by whitespace unless found inside
|
||||
* of quotes, back-quotes, or double quotes.
|
||||
* Outside of single-, double- or back-quotes a backslash escapes white-spaces, all quotes,
|
||||
* the backslash, '&' and '|'.
|
||||
* A backslash used for escaping is removed.
|
||||
* Quotes other than the back-quote plus '&&', '||', ';' are removed, also.
|
||||
* @param line to tokenize
|
||||
* @return array of commands
|
||||
*/
|
||||
protected String[][] tokenize(String line, boolean escapeInsideDoubleQuotes) {
|
||||
ArrayList commands= new ArrayList();
|
||||
ArrayList tokens= new ArrayList();
|
||||
StringBuffer token= new StringBuffer();
|
||||
|
||||
final char[] input= line.toCharArray();
|
||||
boolean nextEscaped= false;
|
||||
char currentQuote= 0;
|
||||
for (int i = 0; i < input.length; i++) {
|
||||
final char c = input[i];
|
||||
final boolean escaped= nextEscaped; nextEscaped= false;
|
||||
|
||||
if (currentQuote != 0) {
|
||||
if (c == currentQuote) {
|
||||
if (escaped) {
|
||||
token.append(c);
|
||||
}
|
||||
else {
|
||||
if (c=='`') {
|
||||
token.append(c); // preserve back-quotes
|
||||
}
|
||||
endToken(token, tokens);
|
||||
currentQuote= 0;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (escapeInsideDoubleQuotes && currentQuote == '"' && c == '\\') {
|
||||
nextEscaped= !escaped;
|
||||
if (escaped) {
|
||||
token.append(c);
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (escaped) {
|
||||
token.append('\\');
|
||||
}
|
||||
token.append(c);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
switch(c) {
|
||||
case '\\':
|
||||
if (escaped) {
|
||||
token.append(c);
|
||||
}
|
||||
else {
|
||||
nextEscaped= true;
|
||||
}
|
||||
break;
|
||||
case '\'': case '"': case '`':
|
||||
if (escaped) {
|
||||
token.append(c);
|
||||
}
|
||||
else {
|
||||
if (c == '`') {
|
||||
token.append(c);
|
||||
}
|
||||
currentQuote= c;
|
||||
}
|
||||
break;
|
||||
case ';':
|
||||
if (escaped) {
|
||||
token.append(c);
|
||||
}
|
||||
else {
|
||||
endCommand(token, tokens, commands);
|
||||
}
|
||||
break;
|
||||
case '&': case '|':
|
||||
if (escaped || i+1 >= input.length || input[i+1] != c) {
|
||||
token.append(c);
|
||||
}
|
||||
else {
|
||||
i++;
|
||||
endCommand(token, tokens, commands);
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
if (Character.isWhitespace(c)) {
|
||||
if (escaped) {
|
||||
token.append(c);
|
||||
}
|
||||
else {
|
||||
endToken(token, tokens);
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (escaped) {
|
||||
token.append('\\'); // for windows put backslash back onto the token.
|
||||
}
|
||||
token.append(c);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
endCommand(token, tokens, commands);
|
||||
return (String[][]) commands.toArray(new String[commands.size()][]);
|
||||
}
|
||||
|
||||
private void endCommand(StringBuffer token, ArrayList tokens, ArrayList commands) {
|
||||
endToken(token, tokens);
|
||||
if (!tokens.isEmpty()) {
|
||||
commands.add(tokens.toArray(new String[tokens.size()]));
|
||||
tokens.clear();
|
||||
}
|
||||
}
|
||||
private void endToken(StringBuffer token, ArrayList tokens) {
|
||||
if (token.length() > 0) {
|
||||
tokens.add(token.toString());
|
||||
token.setLength(0);
|
||||
}
|
||||
}
|
||||
|
||||
protected boolean processSingleLine(String line) {
|
||||
boolean rc= false;
|
||||
String[][] tokens= tokenize(line, true);
|
||||
for (int i = 0; i < tokens.length; i++) {
|
||||
String[] command = tokens[i];
|
||||
if (processCommand(command)) {
|
||||
rc= true;
|
||||
}
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
protected int findCompilerInvocation(String[] tokens) {
|
||||
for (int i = 0; i < tokens.length; i++) {
|
||||
final String token = tokens[i].toLowerCase();
|
||||
final int searchFromOffset= Math.max(token.lastIndexOf('/'), token.lastIndexOf('\\')) + 1;
|
||||
for (int j=0; j < fCompilerCommands.length; j++) {
|
||||
if (token.indexOf(fCompilerCommands[j], searchFromOffset) != -1) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
abstract protected boolean processCommand(String[] command);
|
||||
}
|
||||
|
|
|
@ -6,9 +6,10 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* Tianchao Li (tianchao.li@gmail.com) - arbitrary build directory (bug #136136)
|
||||
* Gerhard Schaber (Wind River Systems) - bug 187910
|
||||
* IBM - Initial API and implementation
|
||||
* Tianchao Li (tianchao.li@gmail.com) - arbitrary build directory (bug #136136)
|
||||
* Gerhard Schaber (Wind River Systems) - bug 187910
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig.gnu;
|
||||
|
||||
|
@ -39,7 +40,6 @@ public class GCCPerFileBOPConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
};
|
||||
private final static List FILE_EXTENSIONS_LIST = Arrays.asList(FILE_EXTENSIONS);
|
||||
|
||||
private String[] compilerInvocation;
|
||||
private GCCPerFileBOPConsoleParserUtility fUtil;
|
||||
|
||||
/* (non-Javadoc)
|
||||
|
@ -49,9 +49,6 @@ public class GCCPerFileBOPConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
fUtil = (project != null && workingDirectory != null && markerGenerator != null) ?
|
||||
new GCCPerFileBOPConsoleParserUtility(project, workingDirectory, markerGenerator) : null;
|
||||
super.startup(project, collector);
|
||||
|
||||
// check additional compiler commands from extension point manifest
|
||||
compilerInvocation = getCompilerCommands();
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
|
@ -64,76 +61,46 @@ public class GCCPerFileBOPConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
/* (non-Javadoc)
|
||||
* @see org.eclipse.cdt.make.internal.core.scannerconfig.gnu.AbstractGCCBOPConsoleParser#processSingleLine(java.lang.String)
|
||||
*/
|
||||
protected boolean processSingleLine(String line) {
|
||||
boolean rc = false;
|
||||
protected boolean processCommand(String[] tokens) {
|
||||
// GCC C/C++ compiler invocation
|
||||
int compilerInvocationIndex = -1;
|
||||
for (int cii = 0; cii < compilerInvocation.length; ++cii) {
|
||||
compilerInvocationIndex = line.indexOf(compilerInvocation[cii]);
|
||||
if (compilerInvocationIndex != -1)
|
||||
break;
|
||||
int compilerInvocationIndex= findCompilerInvocation(tokens);
|
||||
if (compilerInvocationIndex < 0) {
|
||||
return false;
|
||||
}
|
||||
if (compilerInvocationIndex == -1)
|
||||
return rc;
|
||||
|
||||
// split and unquote all segments; supports build command such as
|
||||
// sh -c 'gcc -g -O0 -I"includemath" -I "include abc" -Iincludeprint -c impl/testmath.c'
|
||||
ArrayList split = splitLine(line, compilerInvocationIndex);
|
||||
|
||||
// get the position of the compiler command in the build command
|
||||
for (compilerInvocationIndex=0; compilerInvocationIndex<split.size(); compilerInvocationIndex++) {
|
||||
String command = (String)split.get(compilerInvocationIndex);
|
||||
// verify that it is compiler invocation
|
||||
int idx = lastIndexOfCompilerCommand(command);
|
||||
if (idx >= 0)
|
||||
break;
|
||||
}
|
||||
if (compilerInvocationIndex >= split.size()) {
|
||||
TraceUtil.outputTrace("Error identifying compiler command", line, TraceUtil.EOL); //$NON-NLS-1$
|
||||
return rc;
|
||||
}
|
||||
// find a file name
|
||||
int extensionsIndex = -1;
|
||||
boolean found = false;
|
||||
String filePath = null;
|
||||
for (int i = compilerInvocationIndex+1; i < split.size(); ++i) {
|
||||
String segment = (String)split.get(i);
|
||||
int k = segment.lastIndexOf('.');
|
||||
if (k != -1 && (segment.length() - k < 5)) {
|
||||
String fileExtension = segment.substring(k);
|
||||
for (int i = compilerInvocationIndex+1; i < tokens.length; i++) {
|
||||
String token= tokens[i];
|
||||
int k = token.lastIndexOf('.');
|
||||
if (k != -1 && (token.length() - k < 5)) {
|
||||
String fileExtension = token.substring(k);
|
||||
extensionsIndex = FILE_EXTENSIONS_LIST.indexOf(fileExtension);
|
||||
if (extensionsIndex != -1) {
|
||||
filePath = segment;
|
||||
filePath = token;
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
// for (int j = 0; j < FILE_EXTENSIONS.length; ++j) {
|
||||
// if (split[i].endsWith(FILE_EXTENSIONS[j])) {
|
||||
// filePath = split[i];
|
||||
// extensionsIndex = j;
|
||||
// found = true;
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// if (found) break;
|
||||
if (!found) {
|
||||
TraceUtil.outputTrace("Error identifying file name :1", line, TraceUtil.EOL); //$NON-NLS-1$
|
||||
return rc;
|
||||
TraceUtil.outputTrace("Error identifying file name :1", tokens, TraceUtil.EOL); //$NON-NLS-1$
|
||||
return true;
|
||||
}
|
||||
// sanity check
|
||||
if (filePath.indexOf(FILE_EXTENSIONS[extensionsIndex]) == -1) {
|
||||
TraceUtil.outputTrace("Error identifying file name :2", line, TraceUtil.EOL); //$NON-NLS-1$
|
||||
return rc;
|
||||
TraceUtil.outputTrace("Error identifying file name :2", tokens, TraceUtil.EOL); //$NON-NLS-1$
|
||||
return true;
|
||||
}
|
||||
if (fUtil != null) {
|
||||
IPath pFilePath = fUtil.getAbsolutePath(filePath);
|
||||
String shortFileName = pFilePath.removeFileExtension().lastSegment();
|
||||
|
||||
// generalize occurances of the file name
|
||||
for (int i = 0; i < split.size(); i++) {
|
||||
String token = (String)split.get(i);
|
||||
// generalize occurrences of the file name
|
||||
for (int i = compilerInvocationIndex+1; i < tokens.length; i++) {
|
||||
String token = tokens[i];
|
||||
if (token.equals("-include")) { //$NON-NLS-1$
|
||||
++i;
|
||||
}
|
||||
|
@ -141,14 +108,14 @@ public class GCCPerFileBOPConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
++i;
|
||||
}
|
||||
else if (token.equals(filePath)) {
|
||||
split.set(i, "LONG_NAME"); //$NON-NLS-1$
|
||||
tokens[i]= "LONG_NAME"; //$NON-NLS-1$
|
||||
}
|
||||
else if (token.startsWith(shortFileName)) {
|
||||
split.set(i, token.replaceFirst(shortFileName, "SHORT_NAME")); //$NON-NLS-1$
|
||||
tokens[i]= token.replaceFirst(shortFileName, "SHORT_NAME"); //$NON-NLS-1$
|
||||
}
|
||||
}
|
||||
|
||||
CCommandDSC cmd = fUtil.getNewCCommandDSC((String[])split.toArray(new String[split.size()]), extensionsIndex > 0);
|
||||
CCommandDSC cmd = fUtil.getNewCCommandDSC(tokens, extensionsIndex > 0);
|
||||
IPath baseDirectory = fUtil.getBaseDirectory();
|
||||
if (baseDirectory.isPrefixOf(pFilePath)) {
|
||||
List cmdList = new ArrayList();
|
||||
|
@ -157,7 +124,7 @@ public class GCCPerFileBOPConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
sc.put(ScannerInfoTypes.COMPILER_COMMAND, cmdList);
|
||||
|
||||
IPath relPath = pFilePath.removeFirstSegments(baseDirectory.segmentCount());
|
||||
//Note: We add the scannerconfig even if the resource doesnt actually
|
||||
//Note: We add the scanner-config even if the resource doesn't actually
|
||||
//exist below this project (which may happen when reading existing
|
||||
//build logs, because resources can be created as part of the build
|
||||
//and may not exist at the time of analyzing the config but re-built
|
||||
|
@ -166,161 +133,13 @@ public class GCCPerFileBOPConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
IFile file = getProject().getFile(relPath);
|
||||
getCollector().contributeToScannerConfig(file, sc);
|
||||
} else {
|
||||
//TODO limiting to pathes below this project means not being
|
||||
//TODO limiting to paths below this project means not being
|
||||
//able to work with linked resources. Linked resources could
|
||||
//be checked through IWorkspaceRoot.findFilesForLocation().
|
||||
TraceUtil.outputError("Build command for file outside project: "+pFilePath.toString(), line); //$NON-NLS-1$
|
||||
TraceUtil.outputError("Build command for file outside project: "+pFilePath.toString(), tokens); //$NON-NLS-1$
|
||||
}
|
||||
// fUtil.addGenericCommandForFile2(longFileName, genericLine);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
private int lastIndexOfCompilerCommand(String command) {
|
||||
int cii2 = -1;
|
||||
for (int cii = 0; cii < compilerInvocation.length; ++cii) {
|
||||
cii2 = command.lastIndexOf(compilerInvocation[cii]);
|
||||
if (cii2 >= 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return cii2;
|
||||
}
|
||||
|
||||
/**
|
||||
* Splits and unquotes all compiler command segments; supports build command such as
|
||||
* sh -c 'gcc -g -O0 -I"includemath" -I "include abc" -Iincludeprint -c impl/testmath.c'
|
||||
*/
|
||||
private ArrayList splitLine(String line, int compilerInvocationIndex) {
|
||||
ArrayList split = new ArrayList();
|
||||
boolean bSingleQuotes = false;
|
||||
boolean bIgnoreSingleQuotes = false;
|
||||
boolean bDoubleQuotes = false;
|
||||
boolean bIgnoreDoubleQuotes = false;
|
||||
char[] chars = line.toCharArray();
|
||||
int charPos = 0;
|
||||
int length = line.length();
|
||||
boolean quit = false;
|
||||
boolean acceptExtraSingleQuote = false;
|
||||
boolean acceptExtraDoubleQuote = false;
|
||||
|
||||
// eat whitespace
|
||||
while (charPos < length) {
|
||||
char ch = chars[charPos];
|
||||
if (!Character.isWhitespace(ch)) {
|
||||
break;
|
||||
}
|
||||
charPos++;
|
||||
}
|
||||
// read token
|
||||
while (charPos<length && !quit) {
|
||||
int startPos = -1;
|
||||
int endPos = -1;
|
||||
while (charPos<length && !quit) {
|
||||
char ch = chars[charPos];
|
||||
if (ch == '\'') {
|
||||
// ignore quotes before the actual compiler command (the command itself including its options
|
||||
// could be within quotes--in this case we nevertheless want to split the compiler command into segments)
|
||||
if (charPos <= compilerInvocationIndex) {
|
||||
bIgnoreSingleQuotes = !bIgnoreSingleQuotes;
|
||||
}
|
||||
else {
|
||||
if (bIgnoreSingleQuotes) {
|
||||
bIgnoreSingleQuotes = false;
|
||||
if (startPos >= 0) {
|
||||
endPos = charPos; // end of a token
|
||||
}
|
||||
quit = true; // quit after closed quote containing the actual compiler command
|
||||
}
|
||||
else {
|
||||
bSingleQuotes = !bSingleQuotes;
|
||||
}
|
||||
}
|
||||
// do split token here: allow -DMYKEY='MYVALUE' or-DMYKEY=\'MYVALUE\'
|
||||
if (startPos >= 0) {
|
||||
char prevch = charPos > 0 ? chars[charPos-1] : '\0';
|
||||
if (acceptExtraSingleQuote) {
|
||||
acceptExtraSingleQuote = false;
|
||||
}
|
||||
else if (prevch != '=' && prevch != '\\') {
|
||||
endPos = charPos; // end of a token
|
||||
}
|
||||
else {
|
||||
acceptExtraSingleQuote = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (ch == '"') {
|
||||
// ignore quotes before the actual compiler command (the command itself including its options
|
||||
// could be within quotes--in this case we nevertheless want to split the compiler command into segments)
|
||||
if (charPos <= compilerInvocationIndex) {
|
||||
bIgnoreDoubleQuotes = !bIgnoreDoubleQuotes;
|
||||
}
|
||||
else {
|
||||
if (bIgnoreDoubleQuotes) {
|
||||
bIgnoreDoubleQuotes = false;
|
||||
if (startPos >= 0) {
|
||||
endPos = charPos; // end of a token
|
||||
}
|
||||
quit = true; // quit after closed quote containing the actual compiler command
|
||||
}
|
||||
else {
|
||||
bDoubleQuotes = !bDoubleQuotes;
|
||||
}
|
||||
}
|
||||
// do split token here: allow -DMYKEY="MYVALUE" or-DMYKEY=\"MYVALUE\"
|
||||
if (startPos >= 0) {
|
||||
char prevch = charPos > 0 ? chars[charPos-1] : '\0';
|
||||
if (acceptExtraDoubleQuote) {
|
||||
acceptExtraDoubleQuote = false;
|
||||
}
|
||||
else if (prevch != '=' && prevch != '\\') {
|
||||
endPos = charPos; // end of a token
|
||||
}
|
||||
else {
|
||||
acceptExtraDoubleQuote = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (Character.isWhitespace(ch) || ch == ';') {
|
||||
if (startPos < 0 && (bSingleQuotes || bDoubleQuotes)) {
|
||||
startPos = charPos;
|
||||
}
|
||||
else if (startPos >= 0 && !bSingleQuotes && !bDoubleQuotes) {
|
||||
endPos = charPos; // end of a token
|
||||
}
|
||||
}
|
||||
else { // a valid character, starts or continues a token
|
||||
if (startPos < 0) {
|
||||
startPos = charPos;
|
||||
}
|
||||
if (charPos == length-1) {
|
||||
endPos = charPos+1; // end of token
|
||||
}
|
||||
}
|
||||
charPos++;
|
||||
// a complete token has been found
|
||||
if (startPos >= 0 && endPos > startPos) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (startPos >= 0 && endPos >= 0) {
|
||||
String cmdFragment = line.substring(startPos, endPos);
|
||||
if (startPos >= compilerInvocationIndex) { // the compiler name or one of its options
|
||||
split.add(cmdFragment);
|
||||
}
|
||||
else if (endPos > compilerInvocationIndex) {
|
||||
// compiler name is found within another command fragment--we have to check, whether this
|
||||
// is a valid compiler invocation (e.g., C:/Programs/gcc/gcc.exe) or only a part
|
||||
// of a command that contains by chance the compiler name (e.g., cat testgccsettings.txt)
|
||||
int idx = lastIndexOfCompilerCommand(cmdFragment);
|
||||
if (idx == 0 ||
|
||||
(idx > 0 && (cmdFragment.charAt(idx-1) == '\\' || cmdFragment.charAt(idx-1) == '/'))) {
|
||||
split.add(cmdFragment);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return split;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,9 +6,10 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* Martin Oberhuber (Wind River Systems) - bug 155096
|
||||
* Gerhard Schaber (Wind River Systems)
|
||||
* IBM - Initial API and implementation
|
||||
* Martin Oberhuber (Wind River Systems) - bug 155096
|
||||
* Gerhard Schaber (Wind River Systems)
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig.gnu;
|
||||
|
||||
|
@ -177,9 +178,8 @@ public class GCCPerFileBOPConsoleParserUtility extends AbstractGCCBOPConsolePars
|
|||
else {
|
||||
// ex. -I /dir
|
||||
// take a next token
|
||||
++i;
|
||||
if (i < tokens.length && !tokens[i].startsWith("-")) { //$NON-NLS-1$
|
||||
option = tokens[i];
|
||||
if (i+1 < tokens.length && !tokens[i+1].startsWith("-")) { //$NON-NLS-1$
|
||||
option = tokens[++i];
|
||||
}
|
||||
else break;
|
||||
}
|
||||
|
|
|
@ -6,16 +6,15 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* Martin Oberhuber (Wind River Systems) - bug 155096
|
||||
* Sergey Prigogin (Google)
|
||||
* IBM - Initial API and implementation
|
||||
* Martin Oberhuber (Wind River Systems) - bug 155096
|
||||
* Sergey Prigogin (Google)
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig.gnu;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
|
@ -35,13 +34,8 @@ import org.eclipse.core.runtime.Path;
|
|||
* @author vhirsl
|
||||
*/
|
||||
public class GCCScannerInfoConsoleParser extends AbstractGCCBOPConsoleParser {
|
||||
private final static String SINGLE_QUOTE_STRING = "\'"; //$NON-NLS-1$
|
||||
private final static String DOUBLE_QUOTE_STRING = "\""; //$NON-NLS-1$
|
||||
private final static char[] matchingChars = {'`', '\'', '\"'};
|
||||
|
||||
private String[] compilerInvocation;
|
||||
|
||||
private ScannerInfoConsoleParserUtility fUtil = null;
|
||||
private ScannerInfoConsoleParserUtility fUtil = null;
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.eclipse.cdt.make.core.scannerconfig.IScannerInfoConsoleParser#startup(org.eclipse.core.resources.IProject, org.eclipse.core.runtime.IPath, org.eclipse.cdt.make.core.scannerconfig.IScannerInfoCollector, org.eclipse.cdt.core.IMarkerGenerator)
|
||||
|
@ -50,9 +44,6 @@ public class GCCScannerInfoConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
fUtil = (project != null && workingDirectory != null && markerGenerator != null) ?
|
||||
new ScannerInfoConsoleParserUtility(project, workingDirectory, markerGenerator) : null;
|
||||
super.startup(project, collector);
|
||||
|
||||
// check additional compiler commands from extension point manifest
|
||||
compilerInvocation = getCompilerCommands();
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
|
@ -62,290 +53,144 @@ public class GCCScannerInfoConsoleParser extends AbstractGCCBOPConsoleParser {
|
|||
return fUtil;
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.eclipse.cdt.make.internal.core.scannerconfig.gnu.AbstractGCCBOPConsoleParser#processSingleLine(java.lang.String)
|
||||
*/
|
||||
protected boolean processSingleLine(String line) {
|
||||
boolean rc = false;
|
||||
// Known patterns:
|
||||
// (a) gcc|g++ ... -Dxxx -Iyyy ...
|
||||
List allTokens = tokenize(line);
|
||||
// ArrayList allTokens = new ArrayList(Arrays.asList(line.split("\\s+")));//$NON-NLS-1$
|
||||
if (allTokens.size() <= 1)
|
||||
return false;
|
||||
protected boolean processCommand(String[] tokens) {
|
||||
int compilerInvocationIdx= findCompilerInvocation(tokens);
|
||||
if (compilerInvocationIdx<0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
boolean found = false;
|
||||
Iterator I = allTokens.iterator();
|
||||
String token;
|
||||
for (int ti = 0; ti < 2; ++ti) {
|
||||
token = ((String) I.next()).toLowerCase();
|
||||
for (int i = 0; i < compilerInvocation.length; i++) {
|
||||
if (token.indexOf(compilerInvocation[i]) != -1) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (found)
|
||||
break;
|
||||
}
|
||||
|
||||
if (found) {
|
||||
// Recognized gcc or g++ compiler invocation
|
||||
List includes = new ArrayList();
|
||||
List symbols = new ArrayList();
|
||||
List targetSpecificOptions = new ArrayList();
|
||||
// Recognized gcc or g++ compiler invocation
|
||||
List includes = new ArrayList();
|
||||
List symbols = new ArrayList();
|
||||
List targetSpecificOptions = new ArrayList();
|
||||
|
||||
rc = true;
|
||||
String fileName = null;
|
||||
// discover all -I options
|
||||
parseLineForIncludePaths(line, includes);
|
||||
// discover all -D options
|
||||
parseLineForSymbolDefinitions(line, symbols);
|
||||
|
||||
while (I.hasNext()) {
|
||||
token = (String) I.next();
|
||||
if (token.startsWith("-m") || //$NON-NLS-1$
|
||||
token.equals("-ansi") || //$NON-NLS-1$
|
||||
token.equals("-nostdinc") || //$NON-NLS-1$
|
||||
token.equals("-posix") || //$NON-NLS-1$
|
||||
token.equals("-pthread") || //$NON-NLS-1$
|
||||
token.startsWith("-O") || //$NON-NLS-1$
|
||||
token.equals("-fno-inline") || //$NON-NLS-1$
|
||||
token.startsWith("-finline") || //$NON-NLS-1$
|
||||
token.equals("-fno-exceptions") || //$NON-NLS-1$
|
||||
token.equals("-fexceptions") || //$NON-NLS-1$
|
||||
token.equals("-fshort-wchar") || //$NON-NLS-1$
|
||||
token.equals("-fshort-double") || //$NON-NLS-1$
|
||||
token.equals("-fno-signed-char") || //$NON-NLS-1$
|
||||
token.equals("-fsigned-char") || //$NON-NLS-1$
|
||||
token.startsWith("-fabi-version=") //$NON-NLS-1$
|
||||
) {
|
||||
if (!targetSpecificOptions.contains(token))
|
||||
targetSpecificOptions.add(token);
|
||||
String fileName = null;
|
||||
for (int j= compilerInvocationIdx+1; j < tokens.length; j++) {
|
||||
String token = tokens[j];
|
||||
if (token.equals(DASHIDASH)) {
|
||||
}
|
||||
else if (token.startsWith(DASHI)) {
|
||||
String candidate= null;
|
||||
if (token.length() > 2) {
|
||||
candidate= token.substring(2).trim();
|
||||
}
|
||||
else if (fileName == null) {
|
||||
String possibleFileName = token.toLowerCase();
|
||||
if (possibleFileName.length() >= 5 && // Two quotes plus 3 characters for file name.
|
||||
(possibleFileName.startsWith(DOUBLE_QUOTE_STRING) &&
|
||||
possibleFileName.endsWith(DOUBLE_QUOTE_STRING)) ||
|
||||
(possibleFileName.startsWith(SINGLE_QUOTE_STRING) &&
|
||||
possibleFileName.endsWith(SINGLE_QUOTE_STRING))) {
|
||||
possibleFileName = possibleFileName.substring(1, possibleFileName.length()-1).trim();
|
||||
}
|
||||
if (possibleFileName.endsWith(".c") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".cpp") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".cc") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".cxx") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".C") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".CPP") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".CC") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".CXX") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".c++")) { //$NON-NLS-1$
|
||||
|
||||
fileName = token;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (fileName != null && fileName.startsWith("/cygdrive/")) { //$NON-NLS-1$
|
||||
fileName= AbstractGCCBOPConsoleParserUtility.convertCygpath(new Path(fileName)).toOSString();
|
||||
}
|
||||
|
||||
IProject project = getProject();
|
||||
IFile file = null;
|
||||
List translatedIncludes = includes;
|
||||
if (includes.size() > 0) {
|
||||
if (fileName != null) {
|
||||
if (fUtil != null) {
|
||||
file = fUtil.findFile(fileName);
|
||||
if (file != null) {
|
||||
project = file.getProject();
|
||||
translatedIncludes = fUtil.translateRelativePaths(file, fileName, includes);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
final String error = MakeMessages.getString("ConsoleParser.Filename_Missing_Error_Message"); //$NON-NLS-1$
|
||||
TraceUtil.outputError(error, line);
|
||||
if (fUtil != null) {
|
||||
fUtil.generateMarker(getProject(), -1, error + line, IMarkerGenerator.SEVERITY_WARNING, null);
|
||||
}
|
||||
}
|
||||
if (file == null && fUtil != null) { // real world case
|
||||
// remove include paths since there was no chance to translate them
|
||||
translatedIncludes.clear();
|
||||
}
|
||||
}
|
||||
// Contribute discovered includes and symbols to the ScannerInfoCollector
|
||||
if (translatedIncludes.size() > 0 || symbols.size() > 0) {
|
||||
Map scannerInfo = new HashMap();
|
||||
scannerInfo.put(ScannerInfoTypes.INCLUDE_PATHS, translatedIncludes);
|
||||
scannerInfo.put(ScannerInfoTypes.SYMBOL_DEFINITIONS, symbols);
|
||||
scannerInfo.put(ScannerInfoTypes.TARGET_SPECIFIC_OPTION, targetSpecificOptions);
|
||||
getCollector().contributeToScannerConfig(project, scannerInfo);
|
||||
|
||||
TraceUtil.outputTrace("Discovered scanner info for file \'" + fileName + '\'', //$NON-NLS-1$
|
||||
"Include paths", includes, translatedIncludes, "Defined symbols", symbols); //$NON-NLS-1$ //$NON-NLS-2$
|
||||
}
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param line
|
||||
* @return list of tokens
|
||||
*/
|
||||
private List tokenize(String line) {
|
||||
List rv = new ArrayList(2);
|
||||
// find special characters that need to be matched: `, ' and "
|
||||
// First Matching Chararcter
|
||||
int prevFmc = line.length();
|
||||
int emc = -1;
|
||||
char matchingChar = 0;
|
||||
for (int i = 0; i < matchingChars.length; ++i) {
|
||||
char ch = matchingChars[i];
|
||||
int fmc = line.indexOf(ch);
|
||||
if (fmc > -1 && fmc < prevFmc) {
|
||||
emc = line.indexOf(ch, fmc+1);
|
||||
if (emc > fmc) {
|
||||
matchingChar = ch;
|
||||
prevFmc = fmc;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (matchingChar != 0) { // found matched chars
|
||||
String prefix = line.substring(0, prevFmc).trim();
|
||||
rv.addAll(Arrays.asList(prefix.split("\\s+")));//$NON-NLS-1$
|
||||
|
||||
rv.add(line.substring(prevFmc, emc+1));
|
||||
|
||||
// recursion
|
||||
rv.addAll(tokenize(line.substring(emc+1).trim()));
|
||||
}
|
||||
else {
|
||||
rv.addAll(Arrays.asList(line.split("\\s+")));//$NON-NLS-1$
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param line
|
||||
* @param includes
|
||||
*/
|
||||
private void parseLineForIncludePaths(String line, List includes) {
|
||||
final String fDashI = "-I"; //$NON-NLS-1$
|
||||
int prevIndex = 0;
|
||||
for (int index = line.indexOf(fDashI, prevIndex); index != -1;
|
||||
prevIndex = index+2, index = line.indexOf(fDashI, prevIndex)) {
|
||||
String delimiter = "\\s+"; //$NON-NLS-1$
|
||||
if (line.charAt(index-1) == '\'' || line.charAt(index-1) == '\"') {
|
||||
// look for only one more ' or "
|
||||
delimiter = String.valueOf(line.charAt(index-1));
|
||||
}
|
||||
String postfix = line.substring(index+2).trim();
|
||||
if (postfix.charAt(0) == '-') { // empty -I
|
||||
continue;
|
||||
}
|
||||
if (postfix.startsWith(SINGLE_QUOTE_STRING) || postfix.startsWith(DOUBLE_QUOTE_STRING)) {
|
||||
delimiter = postfix.substring(0, 1);
|
||||
}
|
||||
String[] tokens = postfix.split(delimiter);
|
||||
int tokIndex = (tokens.length > 1 && tokens[0].length() == 0) ? 1 : 0;
|
||||
String iPath = tokens[tokIndex];
|
||||
String temp = iPath;
|
||||
// check for '\ '
|
||||
for (++tokIndex; (temp.endsWith("\\") && tokIndex < tokens.length && //$NON-NLS-1$
|
||||
tokens[tokIndex].length() > 0 && !tokens[tokIndex].startsWith("-")); //$NON-NLS-1$
|
||||
++tokIndex) {
|
||||
int beg = postfix.indexOf(temp)+temp.length();
|
||||
int end = postfix.indexOf(tokens[tokIndex])+tokens[tokIndex].length();
|
||||
iPath = iPath.substring(0, iPath.length()-1) + postfix.substring(beg, end);
|
||||
temp += postfix.substring(beg, end);
|
||||
}
|
||||
String nPath = iPath;
|
||||
if (fUtil != null) {
|
||||
nPath = fUtil.normalizePath(iPath);
|
||||
}
|
||||
if (!includes.contains(nPath)) {
|
||||
includes.add(nPath);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param line
|
||||
* @param symbols
|
||||
*/
|
||||
private void parseLineForSymbolDefinitions(String line, List symbols) {
|
||||
final String fDashD = "-D"; //$NON-NLS-1$
|
||||
int prevIndex = 0;
|
||||
String delimiter = null;
|
||||
String splitRegex = "\\s+"; //$NON-NLS-1$
|
||||
for (int index = line.indexOf(fDashD, prevIndex); index != -1;
|
||||
prevIndex = index+2, index = line.indexOf(fDashD, prevIndex)) {
|
||||
int nDelimiterSymbols = 2;
|
||||
String postfix = line.substring(index+2).trim();
|
||||
if (postfix.charAt(0) == '-') { // empty -D
|
||||
continue;
|
||||
}
|
||||
if (line.charAt(index-1) == '\'' || line.charAt(index-1) == '\"') {
|
||||
// look for only one more ' or "
|
||||
delimiter = String.valueOf(line.charAt(index-1));
|
||||
nDelimiterSymbols = 1;
|
||||
}
|
||||
else {
|
||||
String[] tokens = postfix.split(splitRegex, 2);
|
||||
if (tokens.length > 0 && tokens[0].length() > 0) {
|
||||
int sQuoteIndex = tokens[0].indexOf(SINGLE_QUOTE_STRING);
|
||||
int dQuoteIndex = tokens[0].indexOf(DOUBLE_QUOTE_STRING);
|
||||
if (sQuoteIndex == -1 && dQuoteIndex == -1) {
|
||||
// simple case, no quotes
|
||||
if (!symbols.contains(tokens[0])) {
|
||||
symbols.add(tokens[0]);
|
||||
}
|
||||
continue;
|
||||
else if (j+1 < tokens.length) {
|
||||
candidate= tokens[j+1];
|
||||
if (candidate.startsWith("-")) { //$NON-NLS-1$
|
||||
candidate= null;
|
||||
}
|
||||
else {
|
||||
delimiter = (sQuoteIndex != -1 && (dQuoteIndex == -1 || sQuoteIndex < dQuoteIndex)) ? SINGLE_QUOTE_STRING : DOUBLE_QUOTE_STRING;
|
||||
j++;
|
||||
}
|
||||
}
|
||||
else
|
||||
continue;
|
||||
}
|
||||
|
||||
// find next matching delimiter
|
||||
int nextDelimiterIndex = -1;
|
||||
int prevDelimiterIndex = -1;
|
||||
do {
|
||||
nextDelimiterIndex = postfix.indexOf(delimiter, nextDelimiterIndex+1);
|
||||
if (nextDelimiterIndex == 0 || (nextDelimiterIndex > 0 && postfix.charAt(nextDelimiterIndex-1) != '\\')) {
|
||||
--nDelimiterSymbols;
|
||||
if (nDelimiterSymbols > 0) {
|
||||
prevDelimiterIndex = nextDelimiterIndex;
|
||||
if (candidate != null && candidate.length() > 0) {
|
||||
if (fUtil != null) {
|
||||
candidate= fUtil.normalizePath(candidate);
|
||||
}
|
||||
if (!includes.contains(candidate)) {
|
||||
includes.add(candidate);
|
||||
}
|
||||
}
|
||||
}
|
||||
while (nDelimiterSymbols > 0 && nextDelimiterIndex != -1);
|
||||
if (nDelimiterSymbols > 0)
|
||||
continue; // non matching delimiter
|
||||
}
|
||||
else if (token.startsWith(DASHD)) {
|
||||
String candidate= null;
|
||||
if (token.length() > 2) {
|
||||
candidate= token.substring(2).trim();
|
||||
}
|
||||
else if (j+1 < tokens.length) {
|
||||
candidate= tokens[j+1];
|
||||
if (candidate.startsWith("-")) { //$NON-NLS-1$
|
||||
candidate= null;
|
||||
}
|
||||
else {
|
||||
j++;
|
||||
}
|
||||
}
|
||||
if (candidate != null && candidate.length() > 0) {
|
||||
if (!symbols.contains(candidate)) {
|
||||
symbols.add(candidate);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (token.startsWith("-m") || //$NON-NLS-1$
|
||||
token.equals("-ansi") || //$NON-NLS-1$
|
||||
token.equals("-nostdinc") || //$NON-NLS-1$
|
||||
token.equals("-posix") || //$NON-NLS-1$
|
||||
token.equals("-pthread") || //$NON-NLS-1$
|
||||
token.startsWith("-O") || //$NON-NLS-1$
|
||||
token.equals("-fno-inline") || //$NON-NLS-1$
|
||||
token.startsWith("-finline") || //$NON-NLS-1$
|
||||
token.equals("-fno-exceptions") || //$NON-NLS-1$
|
||||
token.equals("-fexceptions") || //$NON-NLS-1$
|
||||
token.equals("-fshort-wchar") || //$NON-NLS-1$
|
||||
token.equals("-fshort-double") || //$NON-NLS-1$
|
||||
token.equals("-fno-signed-char") || //$NON-NLS-1$
|
||||
token.equals("-fsigned-char") || //$NON-NLS-1$
|
||||
token.startsWith("-fabi-version=")) { //$NON-NLS-1$
|
||||
if (!targetSpecificOptions.contains(token))
|
||||
targetSpecificOptions.add(token);
|
||||
}
|
||||
else if (fileName == null) {
|
||||
String possibleFileName = token.toLowerCase();
|
||||
if (possibleFileName.endsWith(".c") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".cpp") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".cc") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".cxx") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".C") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".CPP") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".CC") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".CXX") || //$NON-NLS-1$
|
||||
possibleFileName.endsWith(".c++")) { //$NON-NLS-1$
|
||||
fileName = token;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// take everything up to the last delimiter
|
||||
boolean bStartsWithDelimiter = postfix.startsWith(delimiter);
|
||||
String symbol = postfix.substring(bStartsWithDelimiter ? 1 : 0, nextDelimiterIndex);
|
||||
if (!bStartsWithDelimiter) {
|
||||
// there is still a delimiter to be removed
|
||||
if (prevDelimiterIndex != -1) {
|
||||
symbol = symbol.substring(0, prevDelimiterIndex) + symbol.substring(prevDelimiterIndex+1);
|
||||
if (fileName != null && fileName.startsWith("/cygdrive/")) { //$NON-NLS-1$
|
||||
fileName= AbstractGCCBOPConsoleParserUtility.convertCygpath(new Path(fileName)).toOSString();
|
||||
}
|
||||
|
||||
IProject project = getProject();
|
||||
IFile file = null;
|
||||
List translatedIncludes = includes;
|
||||
if (includes.size() > 0) {
|
||||
if (fileName != null) {
|
||||
if (fUtil != null) {
|
||||
file = fUtil.findFile(fileName);
|
||||
if (file != null) {
|
||||
project = file.getProject();
|
||||
translatedIncludes = fUtil.translateRelativePaths(file, fileName, includes);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
StringBuffer line= new StringBuffer();
|
||||
for (int j = 0; j < tokens.length; j++) {
|
||||
line.append(tokens[j]);
|
||||
line.append(' ');
|
||||
}
|
||||
}
|
||||
// transform '\"' into '"'
|
||||
if (delimiter.equals(DOUBLE_QUOTE_STRING)) {
|
||||
symbol = symbol.replaceAll("\\\\\"", DOUBLE_QUOTE_STRING); //$NON-NLS-1$
|
||||
}
|
||||
if (!symbols.contains(symbol)) {
|
||||
symbols.add(symbol);
|
||||
}
|
||||
}
|
||||
final String error = MakeMessages.getString("ConsoleParser.Filename_Missing_Error_Message"); //$NON-NLS-1$
|
||||
TraceUtil.outputError(error, line.toString());
|
||||
if (fUtil != null) {
|
||||
fUtil.generateMarker(getProject(), -1, error + line.toString(), IMarkerGenerator.SEVERITY_WARNING, null);
|
||||
}
|
||||
}
|
||||
if (file == null && fUtil != null) { // real world case
|
||||
// remove include paths since there was no chance to translate them
|
||||
translatedIncludes.clear();
|
||||
}
|
||||
}
|
||||
// Contribute discovered includes and symbols to the ScannerInfoCollector
|
||||
if (translatedIncludes.size() > 0 || symbols.size() > 0) {
|
||||
Map scannerInfo = new HashMap();
|
||||
scannerInfo.put(ScannerInfoTypes.INCLUDE_PATHS, translatedIncludes);
|
||||
scannerInfo.put(ScannerInfoTypes.SYMBOL_DEFINITIONS, symbols);
|
||||
scannerInfo.put(ScannerInfoTypes.TARGET_SPECIFIC_OPTION, targetSpecificOptions);
|
||||
getCollector().contributeToScannerConfig(project, scannerInfo);
|
||||
|
||||
TraceUtil.outputTrace("Discovered scanner info for file \'" + fileName + '\'', //$NON-NLS-1$
|
||||
"Include paths", includes, translatedIncludes, "Defined symbols", symbols); //$NON-NLS-1$ //$NON-NLS-2$
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -6,9 +6,9 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* Markus Schorn (Wind River Systems)
|
||||
* Gerhard Schaber (Wind River Systems)
|
||||
* IBM - Initial API and implementation
|
||||
* Markus Schorn (Wind River Systems)
|
||||
* Gerhard Schaber (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig.util;
|
||||
|
||||
|
@ -131,7 +131,7 @@ public class CCommandDSC {
|
|||
* @param quoteIncludePaths whether or not paths for includes must be put inside double quotes.
|
||||
* @return the command line to run the scanner discovery.
|
||||
*/
|
||||
public String getSCDRunnableCommand(boolean quoteIncludePaths) {
|
||||
public String getSCDRunnableCommand(boolean quoteIncludePaths, boolean quoteDefines) {
|
||||
String commandAsString = new String();
|
||||
for (Iterator i = compilerCommand.iterator(); i.hasNext(); ) {
|
||||
KVStringPair optionPair = (KVStringPair)i.next();
|
||||
|
@ -152,6 +152,15 @@ public class CCommandDSC {
|
|||
value= "\"" + value + "\""; //$NON-NLS-1$ //$NON-NLS-2$
|
||||
}
|
||||
}
|
||||
else if (quoteDefines && optionPair.getKey().equals(SCDOptionsEnum.DEFINE.toString())) {
|
||||
if (value.indexOf('\'') == -1) {
|
||||
value= "'" + value + "'"; //$NON-NLS-1$//$NON-NLS-2$
|
||||
}
|
||||
else {
|
||||
value= value.replaceAll("\"", "\\\\\""); //$NON-NLS-1$//$NON-NLS-2$
|
||||
value= "\"" + value + "\""; //$NON-NLS-1$ //$NON-NLS-2$
|
||||
}
|
||||
}
|
||||
commandAsString += optionPair.getKey() + SINGLE_SPACE + value + SINGLE_SPACE;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,7 +6,8 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* IBM - Initial API and implementation
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig.util;
|
||||
|
||||
|
@ -42,9 +43,19 @@ public class TraceUtil {
|
|||
return SCANNER_CONFIG;
|
||||
}
|
||||
|
||||
public static void outputTrace(String prefix, String[] tokens, String postfix) {
|
||||
if (isTracing()) {
|
||||
System.out.print(prefix + ' ');
|
||||
for (int i = 0; i < tokens.length; i++) {
|
||||
System.out.print(tokens[i] + ' ');
|
||||
|
||||
}
|
||||
System.out.println(postfix);
|
||||
}
|
||||
}
|
||||
|
||||
public static void outputTrace(String prefix, String msg, String postfix) {
|
||||
if (isTracing()) {
|
||||
//System.out.println();
|
||||
System.out.println(prefix + ' ' + msg + ' ' + postfix);
|
||||
}
|
||||
}
|
||||
|
@ -94,6 +105,17 @@ public class TraceUtil {
|
|||
}
|
||||
}
|
||||
|
||||
public static void outputError(String string, String[] tokens) {
|
||||
if (isTracing()) {
|
||||
System.out.println();
|
||||
System.out.print("Error: " + string); //$NON-NLS-1$
|
||||
for (int i = 0; i < tokens.length; i++) {
|
||||
System.out.print(tokens[i] + ' ');
|
||||
}
|
||||
System.out.println();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param title
|
||||
* @param subtitlePrefix
|
||||
|
|
|
@ -6,7 +6,8 @@
|
|||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*
|
||||
* Contributors:
|
||||
* IBM - Initial API and implementation
|
||||
* IBM - Initial API and implementation
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.make.internal.core.scannerconfig2;
|
||||
|
||||
|
@ -84,7 +85,7 @@ public class SCDMakefileGenerator extends DefaultRunSIProvider {
|
|||
buffer.append(':');
|
||||
buffer.append(ENDL);
|
||||
buffer.append("\t@echo begin generating scanner info for $@"+ENDL+"\t"); //$NON-NLS-1$ //$NON-NLS-2$
|
||||
buffer.append(cmd.getSCDRunnableCommand(true)); // quoteIncludePaths
|
||||
buffer.append(cmd.getSCDRunnableCommand(true, true)); // quote includes and defines
|
||||
buffer.append(" -E -P -v -dD "); //$NON-NLS-1$
|
||||
buffer.append(cmd.appliesToCPPFileType() ? "specs.cpp" : "specs.c"); //$NON-NLS-1$ //$NON-NLS-2$
|
||||
buffer.append(ENDL);
|
||||
|
|
|
@ -16,9 +16,10 @@ import java.lang.reflect.Method;
|
|||
import java.lang.reflect.Modifier;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Vector;
|
||||
import java.util.Set;
|
||||
|
||||
import junit.framework.AssertionFailedError;
|
||||
import junit.framework.Test;
|
||||
|
@ -67,12 +68,12 @@ public class BaseTestCase extends TestCase {
|
|||
|
||||
private static Test getFailingTests(Class clazz, String prefix) {
|
||||
TestSuite suite= new TestSuite("Failing Tests");
|
||||
Vector names= new Vector();
|
||||
HashSet names= new HashSet();
|
||||
Class superClass= clazz;
|
||||
while (Test.class.isAssignableFrom(superClass) && !TestCase.class.equals(superClass)) {
|
||||
Method[] methods= superClass.getDeclaredMethods();
|
||||
for (int i= 0; i < methods.length; i++) {
|
||||
addFailingMethod(suite, methods[i], clazz, prefix);
|
||||
addFailingMethod(suite, methods[i], names, clazz, prefix);
|
||||
}
|
||||
superClass= superClass.getSuperclass();
|
||||
}
|
||||
|
@ -82,8 +83,11 @@ public class BaseTestCase extends TestCase {
|
|||
return suite;
|
||||
}
|
||||
|
||||
private static void addFailingMethod(TestSuite suite, Method m, Class clazz, String prefix) {
|
||||
private static void addFailingMethod(TestSuite suite, Method m, Set names, Class clazz, String prefix) {
|
||||
String name= m.getName();
|
||||
if (!names.add(name)) {
|
||||
return;
|
||||
}
|
||||
if (name.startsWith("test") || (prefix != null && !name.startsWith(prefix))) {
|
||||
return;
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue