Amélioration du parser Bakefile : gestion des espaces et des commentaires dans les dépendances, commandes et variables
This commit is contained in:
parent
bfeec38854
commit
87662825fa
@ -6,6 +6,7 @@ import java.nio.file.Paths;
|
|||||||
import java.util.*;
|
import java.util.*;
|
||||||
import java.util.regex.Matcher;
|
import java.util.regex.Matcher;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
public class BakefileParser {
|
public class BakefileParser {
|
||||||
/**
|
/**
|
||||||
@ -17,19 +18,19 @@ public class BakefileParser {
|
|||||||
* Regex pour détecter les targets et leurs dépendances.
|
* Regex pour détecter les targets et leurs dépendances.
|
||||||
* Format : "nom : dépendance1 dépendance2"
|
* Format : "nom : dépendance1 dépendance2"
|
||||||
*/
|
*/
|
||||||
private static final Pattern TARGET_PATTERN = Pattern.compile("^(\\S+)\\s*:\\s*(.*)$");
|
private static final Pattern TARGET_PATTERN = Pattern.compile("^(\\S+)\\s*:\\s*([^#]*?)\\s*(?:#.*)?$");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Regex pour détecter les lignes de commande associées à une target.
|
* Regex pour détecter les lignes de commande associées à une target.
|
||||||
* Format : " gcc -o program program.c" (ligne indentée)
|
* Format : " gcc -o program program.c" (ligne indentée)
|
||||||
*/
|
*/
|
||||||
private static final Pattern COMMAND_PATTERN = Pattern.compile("^\\t(.+)$");
|
private static final Pattern COMMAND_PATTERN = Pattern.compile("^\\t(.+?)(?:#.*)?$");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Regex pour détecter les définitions de variables.
|
* Regex pour détecter les définitions de variables.
|
||||||
* Format : "FLAGS = -ansi -pedantic"
|
* Format : "FLAGS = -ansi -pedantic"
|
||||||
*/
|
*/
|
||||||
private static final Pattern VARIABLE_PATTERN = Pattern.compile("^(\\w+)\\s*=\\s*(.*)$");
|
private static final Pattern VARIABLE_PATTERN = Pattern.compile("^(\\w+)\\s*=\\s*([^#]*?)\\s*(?:#.*)?$");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Première cible trouvée dans le fichier Bakefile.
|
* Première cible trouvée dans le fichier Bakefile.
|
||||||
@ -47,6 +48,22 @@ public class BakefileParser {
|
|||||||
firstTarget = null;
|
firstTarget = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private List<String> splitDependencies(String depStr) {
|
||||||
|
if (depStr == null || depStr.trim().isEmpty()) {
|
||||||
|
return new ArrayList<>();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remplacer les variables avant de split
|
||||||
|
String resolvedStr = replaceVariables(depStr.trim());
|
||||||
|
|
||||||
|
// Split sur un ou plusieurs espaces et filtrer les chaînes vides
|
||||||
|
return Arrays.stream(resolvedStr.split("\\s+"))
|
||||||
|
.map(String::trim)
|
||||||
|
.filter(s -> !s.isEmpty())
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
public List<Rule> parse() {
|
public List<Rule> parse() {
|
||||||
List<Rule> rules = new ArrayList<>();
|
List<Rule> rules = new ArrayList<>();
|
||||||
Set<String> phonyTargets = new HashSet<>();
|
Set<String> phonyTargets = new HashSet<>();
|
||||||
@ -74,31 +91,32 @@ public class BakefileParser {
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (line.matches("^ +.*$")) { // Détecte les lignes commençant par des espaces
|
if (line.matches("^ +.*$")) {
|
||||||
System.err.println(filename + ":" + lineNumber + ": *** missing separator. Stop.");
|
System.err.println(filename + ":" + lineNumber + ": *** missing separator. Stop.");
|
||||||
System.exit(1);
|
System.exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (varMatcher.matches()) {
|
if (varMatcher.matches()) {
|
||||||
variables.put(varMatcher.group(1), varMatcher.group(2));
|
// Stocke la variable en enlevant les espaces en début et fin
|
||||||
|
variables.put(varMatcher.group(1), varMatcher.group(2).trim());
|
||||||
} else if (targetMatcher.matches()) {
|
} else if (targetMatcher.matches()) {
|
||||||
if (currentTarget != null) {
|
if (currentTarget != null) {
|
||||||
rules.add(new Rule(
|
rules.add(new Rule(
|
||||||
replaceVariables(currentTarget),
|
replaceVariables(currentTarget.trim()),
|
||||||
replaceVariablesInList(dependencies),
|
splitDependencies(dependencies.stream()
|
||||||
replaceVariablesInList(commands),
|
.collect(Collectors.joining(" "))),
|
||||||
phonyTargets.contains(currentTarget)
|
replaceVariablesInList(commands),
|
||||||
));
|
phonyTargets.contains(currentTarget.trim())
|
||||||
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
currentTarget = targetMatcher.group(1);
|
currentTarget = targetMatcher.group(1);
|
||||||
String depStr = targetMatcher.group(2).trim();
|
String depStr = targetMatcher.group(2);
|
||||||
dependencies = depStr.isEmpty() ? new ArrayList<>() : new ArrayList<>(Arrays.asList(depStr.split("\\s+")));
|
dependencies = splitDependencies(depStr);
|
||||||
|
|
||||||
if (firstTarget == null) {
|
if (firstTarget == null) {
|
||||||
firstTarget = replaceVariables(currentTarget);
|
firstTarget = replaceVariables(currentTarget.trim());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (currentTarget.equals("clean")) {
|
if (currentTarget.equals("clean")) {
|
||||||
phonyTargets.add(currentTarget);
|
phonyTargets.add(currentTarget);
|
||||||
@ -106,16 +124,16 @@ public class BakefileParser {
|
|||||||
|
|
||||||
commands = new ArrayList<>();
|
commands = new ArrayList<>();
|
||||||
} else if (commandMatcher.matches()) {
|
} else if (commandMatcher.matches()) {
|
||||||
commands.add(commandMatcher.group(1));
|
commands.add(commandMatcher.group(1).trim());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (currentTarget != null) {
|
if (currentTarget != null) {
|
||||||
rules.add(new Rule(
|
rules.add(new Rule(
|
||||||
replaceVariables(currentTarget),
|
replaceVariables(currentTarget.trim()),
|
||||||
replaceVariablesInList(dependencies),
|
replaceVariablesInList(dependencies),
|
||||||
replaceVariablesInList(commands),
|
replaceVariablesInList(commands),
|
||||||
phonyTargets.contains(currentTarget)
|
phonyTargets.contains(currentTarget.trim())
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -134,14 +152,13 @@ public class BakefileParser {
|
|||||||
for (Map.Entry<String, String> entry : variables.entrySet()) {
|
for (Map.Entry<String, String> entry : variables.entrySet()) {
|
||||||
String key = "$(" + entry.getKey() + ")";
|
String key = "$(" + entry.getKey() + ")";
|
||||||
if (result.contains(key)) {
|
if (result.contains(key)) {
|
||||||
result = result.replace(key, entry.getValue());
|
result = result.replace(key, entry.getValue().trim());
|
||||||
replaced = true;
|
replaced = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (replaced);
|
} while (replaced);
|
||||||
return result;
|
return result.trim();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private List<String> replaceVariablesInList(List<String> items) {
|
private List<String> replaceVariablesInList(List<String> items) {
|
||||||
List<String> resolved = new ArrayList<>();
|
List<String> resolved = new ArrayList<>();
|
||||||
|
Loading…
x
Reference in New Issue
Block a user