Report warning for non-boolean CLI argument passed multiple times
Only if its values are different, see the test
This commit is contained in:
+6
@@ -20,7 +20,9 @@ import com.intellij.util.SmartList;
|
|||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
|
import java.util.LinkedHashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
public abstract class CommonCompilerArguments implements Serializable {
|
public abstract class CommonCompilerArguments implements Serializable {
|
||||||
public static final long serialVersionUID = 0L;
|
public static final long serialVersionUID = 0L;
|
||||||
@@ -105,6 +107,10 @@ public abstract class CommonCompilerArguments implements Serializable {
|
|||||||
// Names of extra (-X...) arguments which have been passed in an obsolete form ("-Xaaa bbb", instead of "-Xaaa=bbb")
|
// Names of extra (-X...) arguments which have been passed in an obsolete form ("-Xaaa bbb", instead of "-Xaaa=bbb")
|
||||||
public List<String> extraArgumentsPassedInObsoleteForm = new SmartList<>();
|
public List<String> extraArgumentsPassedInObsoleteForm = new SmartList<>();
|
||||||
|
|
||||||
|
// Non-boolean arguments which have been passed multiple times, possibly with different values.
|
||||||
|
// The key in the map is the name of the argument, the value is the last passed value.
|
||||||
|
public Map<String, String> duplicateArguments = new LinkedHashMap<>();
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static CommonCompilerArguments createDefaultInstance() {
|
public static CommonCompilerArguments createDefaultInstance() {
|
||||||
return new DummyImpl();
|
return new DummyImpl();
|
||||||
|
|||||||
+7
@@ -30,6 +30,7 @@ val Argument.isAdvanced: Boolean
|
|||||||
|
|
||||||
private val ADVANCED_ARGUMENT_PREFIX = "-X"
|
private val ADVANCED_ARGUMENT_PREFIX = "-X"
|
||||||
|
|
||||||
|
// Parses arguments in the passed [result] object, or throws an [IllegalArgumentException] with the message to be displayed to the user
|
||||||
fun <A : CommonCompilerArguments> parseCommandLineArguments(args: Array<String>, result: A) {
|
fun <A : CommonCompilerArguments> parseCommandLineArguments(args: Array<String>, result: A) {
|
||||||
data class ArgumentField(val field: Field, val argument: Argument)
|
data class ArgumentField(val field: Field, val argument: Argument)
|
||||||
|
|
||||||
@@ -38,6 +39,8 @@ fun <A : CommonCompilerArguments> parseCommandLineArguments(args: Array<String>,
|
|||||||
if (argument != null) ArgumentField(field, argument) else null
|
if (argument != null) ArgumentField(field, argument) else null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
val visitedArgs = mutableSetOf<String>()
|
||||||
|
|
||||||
var i = 0
|
var i = 0
|
||||||
while (i < args.size) {
|
while (i < args.size) {
|
||||||
val arg = args[i++]
|
val arg = args[i++]
|
||||||
@@ -74,6 +77,10 @@ fun <A : CommonCompilerArguments> parseCommandLineArguments(args: Array<String>,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!field.type.isArray && !visitedArgs.add(argument.value) && value is String && field.get(result) != value) {
|
||||||
|
result.duplicateArguments.put(argument.value, value)
|
||||||
|
}
|
||||||
|
|
||||||
updateField(field, result, value)
|
updateField(field, result, value)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -136,7 +136,7 @@ public abstract class CLICompiler<A extends CommonCompilerArguments> {
|
|||||||
messageCollector = new FilteringMessageCollector(messageCollector, Predicate.isEqual(WARNING));
|
messageCollector = new FilteringMessageCollector(messageCollector, Predicate.isEqual(WARNING));
|
||||||
}
|
}
|
||||||
|
|
||||||
reportUnknownAndObsoleteExtraFlags(messageCollector, arguments);
|
reportArgumentParseProblems(messageCollector, arguments);
|
||||||
|
|
||||||
GroupingMessageCollector groupingCollector = new GroupingMessageCollector(messageCollector);
|
GroupingMessageCollector groupingCollector = new GroupingMessageCollector(messageCollector);
|
||||||
|
|
||||||
@@ -311,7 +311,7 @@ public abstract class CLICompiler<A extends CommonCompilerArguments> {
|
|||||||
@NotNull CompilerConfiguration configuration, @NotNull A arguments, @NotNull Services services
|
@NotNull CompilerConfiguration configuration, @NotNull A arguments, @NotNull Services services
|
||||||
);
|
);
|
||||||
|
|
||||||
private void reportUnknownAndObsoleteExtraFlags(@NotNull MessageCollector collector, @NotNull A arguments) {
|
private void reportArgumentParseProblems(@NotNull MessageCollector collector, @NotNull A arguments) {
|
||||||
for (String flag : arguments.unknownExtraFlags) {
|
for (String flag : arguments.unknownExtraFlags) {
|
||||||
collector.report(STRONG_WARNING, "Flag is not supported by this version of the compiler: " + flag, null);
|
collector.report(STRONG_WARNING, "Flag is not supported by this version of the compiler: " + flag, null);
|
||||||
}
|
}
|
||||||
@@ -319,6 +319,10 @@ public abstract class CLICompiler<A extends CommonCompilerArguments> {
|
|||||||
collector.report(STRONG_WARNING, "Advanced option value is passed in an obsolete form. Please use the '=' character " +
|
collector.report(STRONG_WARNING, "Advanced option value is passed in an obsolete form. Please use the '=' character " +
|
||||||
"to specify the value: " + argument + "=...", null);
|
"to specify the value: " + argument + "=...", null);
|
||||||
}
|
}
|
||||||
|
for (Map.Entry<String, String> argument : arguments.duplicateArguments.entrySet()) {
|
||||||
|
collector.report(STRONG_WARNING, "Argument " + argument.getKey() + " is passed multiple times. " +
|
||||||
|
"Only the last value will be used: " + argument.getValue(), null);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
@@ -0,0 +1,16 @@
|
|||||||
|
$TESTDATA_DIR$/simple.kt
|
||||||
|
-cp
|
||||||
|
$TESTDATA_DIR$
|
||||||
|
-cp
|
||||||
|
$TESTDATA_DIR$
|
||||||
|
-java-parameters
|
||||||
|
-java-parameters
|
||||||
|
-Xno-inline
|
||||||
|
-d
|
||||||
|
$TEMP_DIR$
|
||||||
|
-java-parameters
|
||||||
|
-Xno-inline
|
||||||
|
-module-name
|
||||||
|
aaa
|
||||||
|
-module-name
|
||||||
|
bbb
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
warning: argument -module-name is passed multiple times. Only the last value will be used: bbb
|
||||||
|
OK
|
||||||
@@ -1,4 +0,0 @@
|
|||||||
$TESTDATA_DIR$/simple.kt
|
|
||||||
-Xcoroutines=enable
|
|
||||||
-Xcoroutines=warn
|
|
||||||
-Xcoroutines=error
|
|
||||||
@@ -1,2 +0,0 @@
|
|||||||
error: the -Xcoroutines can only have one value
|
|
||||||
COMPILATION_ERROR
|
|
||||||
+3
-1
@@ -1,3 +1,5 @@
|
|||||||
$TESTDATA_DIR$/simple.kt
|
$TESTDATA_DIR$/simple.kt
|
||||||
-Xcoroutines=error
|
-Xcoroutines=error
|
||||||
-Xcoroutines=enable
|
-Xcoroutines=enable
|
||||||
|
-d
|
||||||
|
$TEMP_DIR$
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
warning: argument -Xcoroutines is passed multiple times. Only the last value will be used: enable
|
||||||
|
OK
|
||||||
@@ -1,2 +0,0 @@
|
|||||||
error: the -Xcoroutines can only have one value
|
|
||||||
COMPILATION_ERROR
|
|
||||||
Vendored
Vendored
@@ -1,3 +0,0 @@
|
|||||||
$TESTDATA_DIR$/simple.kt
|
|
||||||
-Xcoroutines=warn
|
|
||||||
-Xcoroutines=enable
|
|
||||||
@@ -1,2 +0,0 @@
|
|||||||
error: the -Xcoroutines can only have one value
|
|
||||||
COMPILATION_ERROR
|
|
||||||
@@ -1,3 +0,0 @@
|
|||||||
$TESTDATA_DIR$/simple.kt
|
|
||||||
-Xcoroutines=warn
|
|
||||||
-Xcoroutines=error
|
|
||||||
@@ -1,2 +0,0 @@
|
|||||||
error: the -Xcoroutines can only have one value
|
|
||||||
COMPILATION_ERROR
|
|
||||||
@@ -74,6 +74,12 @@ public class CliTestGenerated extends AbstractCliTest {
|
|||||||
doJvmTest(fileName);
|
doJvmTest(fileName);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("argumentPassedMultipleTimes.args")
|
||||||
|
public void testArgumentPassedMultipleTimes() throws Exception {
|
||||||
|
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/argumentPassedMultipleTimes.args");
|
||||||
|
doJvmTest(fileName);
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("classAndFileClassClash.args")
|
@TestMetadata("classAndFileClassClash.args")
|
||||||
public void testClassAndFileClassClash() throws Exception {
|
public void testClassAndFileClassClash() throws Exception {
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/classAndFileClassClash.args");
|
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/classAndFileClassClash.args");
|
||||||
@@ -128,39 +134,21 @@ public class CliTestGenerated extends AbstractCliTest {
|
|||||||
doJvmTest(fileName);
|
doJvmTest(fileName);
|
||||||
}
|
}
|
||||||
|
|
||||||
@TestMetadata("coroutinesEnableWarnAndErrorClash.args")
|
|
||||||
public void testCoroutinesEnableWarnAndErrorClash() throws Exception {
|
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesEnableWarnAndErrorClash.args");
|
|
||||||
doJvmTest(fileName);
|
|
||||||
}
|
|
||||||
|
|
||||||
@TestMetadata("coroutinesError.args")
|
@TestMetadata("coroutinesError.args")
|
||||||
public void testCoroutinesError() throws Exception {
|
public void testCoroutinesError() throws Exception {
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesError.args");
|
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesError.args");
|
||||||
doJvmTest(fileName);
|
doJvmTest(fileName);
|
||||||
}
|
}
|
||||||
|
|
||||||
@TestMetadata("coroutinesErrorAndEnableClash.args")
|
@TestMetadata("coroutinesErrorAndEnable.args")
|
||||||
public void testCoroutinesErrorAndEnableClash() throws Exception {
|
public void testCoroutinesErrorAndEnable() throws Exception {
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesErrorAndEnableClash.args");
|
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesErrorAndEnable.args");
|
||||||
doJvmTest(fileName);
|
doJvmTest(fileName);
|
||||||
}
|
}
|
||||||
|
|
||||||
@TestMetadata("coroutinesWarnAndEnableClash.args")
|
@TestMetadata("coroutinesWarn.args")
|
||||||
public void testCoroutinesWarnAndEnableClash() throws Exception {
|
public void testCoroutinesWarn() throws Exception {
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesWarnAndEnableClash.args");
|
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesWarn.args");
|
||||||
doJvmTest(fileName);
|
|
||||||
}
|
|
||||||
|
|
||||||
@TestMetadata("coroutinesWarnAndErrorClash.args")
|
|
||||||
public void testCoroutinesWarnAndErrorClash() throws Exception {
|
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesWarnAndErrorClash.args");
|
|
||||||
doJvmTest(fileName);
|
|
||||||
}
|
|
||||||
|
|
||||||
@TestMetadata("coroutinesWarninig.args")
|
|
||||||
public void testCoroutinesWarninig() throws Exception {
|
|
||||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesWarninig.args");
|
|
||||||
doJvmTest(fileName);
|
doJvmTest(fileName);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user