diff --git a/Changelog.md b/Changelog.md index a86365bfc..41f76a24e 100644 --- a/Changelog.md +++ b/Changelog.md @@ -19,6 +19,7 @@ Compiler Features: Bugfixes: + * Antlr Grammar: Fix parsing of import paths involving properly distinguishing between empty and non-empty string literals in general. * AST Output: Fix ``kind`` field of ``ModifierInvocation`` for base constructor calls. * SMTChecker: Fix false positive and false negative on ``push`` as LHS of a compound assignment. * SMTChecker: Fix false positive in contracts that cannot be deployed. diff --git a/docs/grammar.rst b/docs/grammar.rst index d69f86b08..788b6d695 100644 --- a/docs/grammar.rst +++ b/docs/grammar.rst @@ -2,12 +2,12 @@ Language Grammar **************** -.. a4:autogrammar:: Solidity - :only-reachable-from: Solidity.sourceUnit +.. a4:autogrammar:: SolidityParser + :only-reachable-from: SolidityParser.sourceUnit :undocumented: :cc-to-dash: .. a4:autogrammar:: SolidityLexer - :only-reachable-from: Solidity.sourceUnit + :only-reachable-from: SolidityParser.sourceUnit :fragments: :cc-to-dash: \ No newline at end of file diff --git a/docs/grammar/SolidityLexer.g4 b/docs/grammar/SolidityLexer.g4 index 0d16dcfa2..f21640264 100644 --- a/docs/grammar/SolidityLexer.g4 +++ b/docs/grammar/SolidityLexer.g4 @@ -155,15 +155,20 @@ Not: '!'; BitNot: '~'; Inc: '++'; Dec: '--'; +//@doc:inline +DoubleQuote: '"'; +//@doc:inline +SingleQuote: '\''; /** - * A single quoted string literal restricted to printable characters. - */ -StringLiteral: '"' DoubleQuotedStringCharacter* '"' | '\'' SingleQuotedStringCharacter* '\''; -/** - * A single non-empty quoted string literal. + * A non-empty quoted string literal restricted to printable characters. */ NonEmptyStringLiteral: '"' DoubleQuotedStringCharacter+ '"' | '\'' SingleQuotedStringCharacter+ '\''; +/** + * An empty string literal + */ +EmptyStringLiteral: '"' '"' | '\'' '\''; + // Note that this will also be used for Yul string literals. //@doc:inline fragment DoubleQuotedStringCharacter: DoubleQuotedPrintable | EscapeSequence; @@ -200,6 +205,7 @@ fragment DoubleQuotedUnicodeStringCharacter: ~["\r\n\\] | EscapeSequence; //@doc:inline fragment SingleQuotedUnicodeStringCharacter: ~['\r\n\\] | EscapeSequence; +// Note that this will also be used for Yul hex string literals. /** * Hex strings need to consist of an even number of hex digits that may be grouped using underscores. */ @@ -315,6 +321,7 @@ YulDecimalNumber: '0' | ([1-9] [0-9]*); YulStringLiteral: '"' DoubleQuotedStringCharacter* '"' | '\'' SingleQuotedStringCharacter* '\''; +//@doc:inline YulHexStringLiteral: HexString; YulWS: [ \t\r\n\u000C]+ -> skip ; diff --git a/docs/grammar/Solidity.g4 b/docs/grammar/SolidityParser.g4 similarity index 99% rename from docs/grammar/Solidity.g4 rename to docs/grammar/SolidityParser.g4 index 7962cea77..0dbc7339d 100644 --- a/docs/grammar/Solidity.g4 +++ b/docs/grammar/SolidityParser.g4 @@ -1,7 +1,7 @@ /** * Solidity is a statically typed, contract-oriented, high-level language for implementing smart contracts on the Ethereum platform. */ -grammar Solidity; +parser grammar SolidityParser; options { tokenVocab=SolidityLexer; } @@ -388,7 +388,7 @@ booleanLiteral: True | False; /** * A full string literal consists of either one or several consecutive quoted strings. */ -stringLiteral: StringLiteral+; +stringLiteral: (NonEmptyStringLiteral | EmptyStringLiteral)+; /** * A full hex string literal that consists of either one or several consecutive hex strings. */ diff --git a/scripts/test_antlr_grammar.sh b/scripts/test_antlr_grammar.sh index 4b02f6585..51e0df0cb 100755 --- a/scripts/test_antlr_grammar.sh +++ b/scripts/test_antlr_grammar.sh @@ -39,19 +39,15 @@ prepare_workdir() prepare_workdir download_antlr4 -if [[ ! -f "${WORKDIR}/target/SolidityParser.class" ]] || \ - [ "${GRAMMAR_FILE}" -nt "${WORKDIR}/target/SolidityParser.class" ] -then - echo "Creating parser" - ( - cd "${ROOT_DIR}"/docs/grammar - # Create lexer/parser from grammar - java -jar "${ANTLR_JAR}" Solidity.g4 SolidityLexer.g4 -o "${WORKDIR}/src/" +echo "Creating parser" +( +cd "${ROOT_DIR}"/docs/grammar +# Create lexer/parser from grammar +java -jar "${ANTLR_JAR}" SolidityParser.g4 SolidityLexer.g4 -o "${WORKDIR}/src/" - # Compile lexer/parser sources - javac -classpath "${ANTLR_JAR}" "${WORKDIR}/src/"*.java -d "${WORKDIR}/target/" - ) -fi +# Compile lexer/parser sources +javac -classpath "${ANTLR_JAR}" "${WORKDIR}/src/"*.java -d "${WORKDIR}/target/" +) # Run tests failed_count=0 @@ -67,11 +63,11 @@ test_file() local output if [[ "${solOrYul}" == "sol" ]]; then output=$( - java \ + grep -v "^==== ExternalSource:" "${SOL_FILE}" | java \ -classpath "${ANTLR_JAR}:${WORKDIR}/target/" \ "org.antlr.v4.gui.TestRig" \ Solidity \ - sourceUnit <"${SOL_FILE}" 2>&1 + sourceUnit 2>&1 ) else output=$( @@ -113,7 +109,7 @@ while IFS='' read -r line do SOL_FILES+=("$line") done < <( - grep -riL -E \ + grep --include "*.sol" -riL -E \ "^\/\/ (Syntax|Type|Declaration)Error|^\/\/ ParserError (1684|2837|3716|3997|5333|6275|6281|6933|7319)|^==== Source:" \ "${ROOT_DIR}/test/libsolidity/syntaxTests" \ "${ROOT_DIR}/test/libsolidity/semanticTests" | diff --git a/test/libsolidity/syntaxTests/inlineAssembly/storage_slot_assign.yul b/test/libsolidity/syntaxTests/inlineAssembly/storage_slot_assign.sol similarity index 100% rename from test/libsolidity/syntaxTests/inlineAssembly/storage_slot_assign.yul rename to test/libsolidity/syntaxTests/inlineAssembly/storage_slot_assign.sol diff --git a/test/libsolidity/syntaxTests/inlineAssembly/string_literal_switch_case.yul b/test/libsolidity/syntaxTests/inlineAssembly/string_literal_switch_case.sol similarity index 100% rename from test/libsolidity/syntaxTests/inlineAssembly/string_literal_switch_case.yul rename to test/libsolidity/syntaxTests/inlineAssembly/string_literal_switch_case.sol