From 4c1739169a08353a04b52f520ee5df0b7531ad79 Mon Sep 17 00:00:00 2001 From: Christian Date: Wed, 8 Oct 2014 20:53:50 +0200 Subject: [PATCH] Parse everything up to function bodies and report parser errors with location. --- libsolidity/AST.h | 91 +++++++++++++++++++------- libsolidity/BaseTypes.h | 17 ++--- libsolidity/Parser.cpp | 137 +++++++++++++++++++++++++++++++++------ libsolidity/Parser.h | 8 ++- libsolidity/Scanner.cpp | 48 ++++++++++++-- libsolidity/Scanner.h | 16 +++++ libsolidity/Token.h | 1 + libsolidity/grammar.txt | 14 ++-- test/solidityParser.cpp | 103 ++++++++++++++++++++++++++--- test/solidityScanner.cpp | 24 +++---- 10 files changed, 370 insertions(+), 89 deletions(-) diff --git a/libsolidity/AST.h b/libsolidity/AST.h index f71b5b346..86c5022d8 100644 --- a/libsolidity/AST.h +++ b/libsolidity/AST.h @@ -32,6 +32,9 @@ namespace dev { namespace solidity { +// Used as pointers to AST nodes, to be replaced by more clever pointers, e.g. pointers which do +// not do reference counting but point to a special memory area that is completely released +// explicitly. template using ptr = std::shared_ptr; template @@ -47,9 +50,11 @@ class Expression; class ASTNode { public: - explicit ASTNode(const Location& _location) + explicit ASTNode(Location const& _location) : m_location(_location) {} + + Location getLocation() const { return m_location; } private: Location m_location; }; @@ -57,13 +62,12 @@ private: class ContractDefinition : public ASTNode { public: - ContractDefinition(const Location& _location, - const std::string& _name, - const vecptr& _definedStructs, - const vecptr& _stateVariables, - const vecptr& _definedFunctions) - : ASTNode(_location), - m_name(_name), + ContractDefinition(Location const& _location, + std::string const& _name, + vecptr const& _definedStructs, + vecptr const& _stateVariables, + vecptr const& _definedFunctions) + : ASTNode(_location), m_name(_name), m_definedStructs(_definedStructs), m_stateVariables(_stateVariables), m_definedFunctions(_definedFunctions) @@ -78,33 +82,61 @@ private: class StructDefinition : public ASTNode { +public: + StructDefinition(Location const& _location, + std::string const& _name, + vecptr const& _members) + : ASTNode(_location), m_name(_name), m_members(_members) + {} private: std::string m_name; vecptr m_members; }; +/// Used as function parameter list and return list +/// None of the parameters is allowed to contain mappings (not even recursively +/// inside structs) +class ParameterList : public ASTNode +{ +public: + ParameterList(Location const& _location, vecptr const& _parameters) + : ASTNode(_location), m_parameters(_parameters) + {} +private: + vecptr m_parameters; +}; + class FunctionDefinition : public ASTNode { +public: + FunctionDefinition(Location const& _location, std::string const& _name, bool _isPublic, + ptr const& _parameters, + bool _isDeclaredConst, + ptr const& _returnParameters, + ptr const& _body) + : ASTNode(_location), m_name(_name), m_isPublic(_isPublic), m_parameters(_parameters), + m_isDeclaredConst(_isDeclaredConst), m_returnParameters(_returnParameters), + m_body(_body) + {} private: std::string m_name; - vecptr m_arguments; + bool m_isPublic; + ptr m_parameters; bool m_isDeclaredConst; - vecptr m_returns; + ptr m_returnParameters; ptr m_body; }; class VariableDeclaration : public ASTNode { public: - VariableDeclaration(const Location& _location, - const ptr& _type, - const std::string& _name) - : ASTNode(_location), - m_type(_type), - m_name(_name) + VariableDeclaration(Location const& _location, + ptr const& _type, + std::string const& _name) + : ASTNode(_location), m_type(_type), m_name(_name) {} private: - ptr m_type; /// m_type; ///< can be empty ("var") std::string m_name; }; @@ -114,7 +146,7 @@ private: class TypeName : public ASTNode { public: - explicit TypeName(const Location& _location) + explicit TypeName(Location const& _location) : ASTNode(_location) {} }; @@ -123,7 +155,7 @@ public: class ElementaryTypeName : public TypeName { public: - explicit ElementaryTypeName(const Location& _location, Token::Value _type) + explicit ElementaryTypeName(Location const& _location, Token::Value _type) : TypeName(_location), m_type(_type) {} private: @@ -133,18 +165,19 @@ private: class UserDefinedTypeName : public TypeName { public: - UserDefinedTypeName(const Location& _location, const std::string& _name) + UserDefinedTypeName(Location const& _location, std::string const& _name) : TypeName(_location), m_name(_name) {} private: std::string m_name; }; -class MappingTypeName : public TypeName +class Mapping : public TypeName { public: - explicit MappingTypeName(const Location& _location) - : TypeName(_location) + Mapping(Location const& _location, ptr const& _keyType, + ptr const& _valueType) + : TypeName(_location), m_keyType(_keyType), m_valueType(_valueType) {} private: ptr m_keyType; @@ -158,10 +191,18 @@ private: class Statement : public ASTNode { +public: + explicit Statement(Location const& _location) + : ASTNode(_location) + {} }; class Block : public Statement { +public: + explicit Block(Location const& _location) + : Statement(_location) + {} private: vecptr m_statements; }; @@ -245,10 +286,12 @@ private: Token::Value m_operator; }; +/// Can be ordinary function call, type cast or struct construction. class FunctionCall : public Expression { private: - std::string m_functionName; // TODO only calls to fixed, named functions for now + // if m_functionName is the name of a type, store the token directly + std::string m_functionName; // "in place" calls of return values are not possible for now vecptr m_arguments; }; diff --git a/libsolidity/BaseTypes.h b/libsolidity/BaseTypes.h index 0cc7f8534..2e92b07e8 100644 --- a/libsolidity/BaseTypes.h +++ b/libsolidity/BaseTypes.h @@ -4,19 +4,16 @@ namespace dev { namespace solidity { -// Representation of an interval of source positions. +/// Representation of an interval of source positions. +/// The interval includes start and excludes end. struct Location { - Location(int b, int e) : beg_pos(b), end_pos(e) { } - Location() : beg_pos(0), end_pos(0) { } + Location(int _start, int _end) : start(_start), end(_end) { } + Location() : start(-1), end(-1) { } - bool IsValid() const { - return beg_pos >= 0 && end_pos >= beg_pos; - } + bool IsValid() const { return start >= 0 && end >= start; } - static Location invalid() { return Location(-1, -1); } - - int beg_pos; - int end_pos; + int start; + int end; }; } } diff --git a/libsolidity/Parser.cpp b/libsolidity/Parser.cpp index 09ea86045..2df1b5762 100644 --- a/libsolidity/Parser.cpp +++ b/libsolidity/Parser.cpp @@ -20,6 +20,7 @@ * Solidity parser. */ +#include "libdevcore/Log.h" #include "libsolidity/BaseTypes.h" #include "libsolidity/Parser.h" #include "libsolidity/Scanner.h" @@ -27,9 +28,9 @@ namespace dev { namespace solidity { -ptr Parser::parse(Scanner& _scanner) +ptr Parser::parse(std::shared_ptr const& _scanner) { - m_scanner = &_scanner; + m_scanner = _scanner; return parseContractDefinition(); } @@ -41,20 +42,22 @@ class Parser::ASTNodeFactory { public: ASTNodeFactory(const Parser& _parser) - : m_parser(_parser), - m_location(_parser.getPosition(), -1) + : m_parser(_parser), m_location(_parser.getPosition(), -1) {} - void markEndPosition() + void markEndPosition() { m_location.end = m_parser.getEndPosition(); } + + /// Set the end position to the one of the given node. + void setEndPositionFromNode(const ptr& _node) { - m_location.end_pos = m_parser.getEndPosition(); + m_location.end = _node->getLocation().end; } /// @todo: check that this actually uses perfect forwarding template ptr createNode(Args&&... _args) { - if (m_location.end_pos < 0) markEndPosition(); + if (m_location.end < 0) markEndPosition(); return std::make_shared(m_location, std::forward(_args)...); } @@ -65,12 +68,12 @@ private: int Parser::getPosition() const { - return m_scanner->getCurrentLocation().beg_pos; + return m_scanner->getCurrentLocation().start; } int Parser::getEndPosition() const { - return m_scanner->getCurrentLocation().end_pos; + return m_scanner->getCurrentLocation().end; } @@ -98,7 +101,6 @@ ptr Parser::parseContractDefinition() functions.push_back(parseFunctionDefinition(visibilityIsPublic)); } else if (currentToken == Token::STRUCT) { structs.push_back(parseStructDefinition()); - expectToken(Token::SEMICOLON); } else if (currentToken == Token::IDENTIFIER || currentToken == Token::MAPPING || Token::IsElementaryTypeName(currentToken)) { stateVariables.push_back(parseVariableDeclaration()); @@ -117,19 +119,57 @@ ptr Parser::parseContractDefinition() ptr Parser::parseFunctionDefinition(bool _isPublic) { - (void) _isPublic; - throwExpectationError("Function parsing is not yet implemented."); + ASTNodeFactory nodeFactory(*this); + + expectToken(Token::FUNCTION); + std::string name(expectIdentifier()); + ptr parameters(parseParameterList()); + bool isDeclaredConst = false; + if (m_scanner->getCurrentToken() == Token::CONST) { + isDeclaredConst = true; + m_scanner->next(); + } + ptr returnParameters; + if (m_scanner->getCurrentToken() == Token::RETURNS) { + m_scanner->next(); + returnParameters = parseParameterList(); + } + ptr block = parseBlock(); + nodeFactory.setEndPositionFromNode(block); + return nodeFactory.createNode(name, _isPublic, parameters, + isDeclaredConst, returnParameters, block); } ptr Parser::parseStructDefinition() { - throwExpectationError("Struct definition parsing is not yet implemented."); + ASTNodeFactory nodeFactory(*this); + + expectToken(Token::STRUCT); + std::string name = expectIdentifier(); + vecptr members; + expectToken(Token::LBRACE); + while (m_scanner->getCurrentToken() != Token::RBRACE) { + members.push_back(parseVariableDeclaration()); + expectToken(Token::SEMICOLON); + } + nodeFactory.markEndPosition(); + expectToken(Token::RBRACE); + + return nodeFactory.createNode(name, members); } ptr Parser::parseVariableDeclaration() { ASTNodeFactory nodeFactory(*this); + ptr type = parseTypeName(); + nodeFactory.markEndPosition(); + std::string name = expectIdentifier(); + return nodeFactory.createNode(type, name); +} + +ptr Parser::parseTypeName() +{ ptr type; Token::Value token = m_scanner->getCurrentToken(); if (Token::IsElementaryTypeName(token)) { @@ -139,17 +179,67 @@ ptr Parser::parseVariableDeclaration() type = ASTNodeFactory(*this).createNode(); m_scanner->next(); } else if (token == Token::MAPPING) { - // TODO - throwExpectationError("mappings are not yet implemented"); + type = parseMapping(); } else if (token == Token::IDENTIFIER) { type = ASTNodeFactory(*this).createNode(m_scanner->getCurrentLiteral()); m_scanner->next(); } else { - throwExpectationError("Expected variable declaration"); + throwExpectationError("Expected type name"); } + + return type; +} + +ptr Parser::parseMapping() +{ + ASTNodeFactory nodeFactory(*this); + + expectToken(Token::MAPPING); + expectToken(Token::LPAREN); + + if (!Token::IsElementaryTypeName(m_scanner->getCurrentToken())) + throwExpectationError("Expected elementary type name for mapping key type"); + ptr keyType; + keyType = ASTNodeFactory(*this).createNode(m_scanner->getCurrentToken()); + m_scanner->next(); + + expectToken(Token::ARROW); + ptr valueType = parseTypeName(); nodeFactory.markEndPosition(); - std::string name = expectIdentifier(); - return nodeFactory.createNode(type, name); + expectToken(Token::RPAREN); + + return nodeFactory.createNode(keyType, valueType); +} + +ptr Parser::parseParameterList() +{ + ASTNodeFactory nodeFactory(*this); + + vecptr parameters; + expectToken(Token::LPAREN); + if (m_scanner->getCurrentToken() != Token::RPAREN) { + parameters.push_back(parseVariableDeclaration()); + while (m_scanner->getCurrentToken() != Token::RPAREN) { + expectToken(Token::COMMA); + parameters.push_back(parseVariableDeclaration()); + } + } + nodeFactory.markEndPosition(); + m_scanner->next(); + return nodeFactory.createNode(parameters); +} + +ptr Parser::parseBlock() +{ + ASTNodeFactory nodeFactory(*this); + expectToken(Token::LBRACE); + while (m_scanner->getCurrentToken() != Token::RBRACE) { + m_scanner->next(); + // @todo + } + nodeFactory.markEndPosition(); + expectToken(Token::RBRACE); + return nodeFactory.createNode(); } void Parser::expectToken(Token::Value _value) @@ -171,9 +261,16 @@ std::string Parser::expectIdentifier() void Parser::throwExpectationError(const std::string& _description) { - (void) _description; + int line, column; + std::tie(line, column) = m_scanner->translatePositionToLineColumn(getPosition()); + cwarn << "Solidity parser error: " << _description + << "at line " << (line + 1) + << ", column " << (column + 1); + cwarn << m_scanner->getLineAtPosition(getPosition()); + cwarn << std::string(column, ' ') << "^"; + /// @todo make a proper exception hierarchy - throw std::exception();//_description); + throw std::exception(); } diff --git a/libsolidity/Parser.h b/libsolidity/Parser.h index 4a48dace5..96f1d6883 100644 --- a/libsolidity/Parser.h +++ b/libsolidity/Parser.h @@ -32,7 +32,7 @@ class Scanner; class Parser { public: - ptr parse(Scanner& _scanner); + ptr parse(std::shared_ptr const& _scanner); private: class ASTNodeFactory; @@ -48,6 +48,10 @@ private: ptr parseFunctionDefinition(bool _isPublic); ptr parseStructDefinition(); ptr parseVariableDeclaration(); + ptr parseTypeName(); + ptr parseMapping(); + ptr parseParameterList(); + ptr parseBlock(); /// @} /// Helper functions @@ -58,7 +62,7 @@ private: void throwExpectationError(const std::string& _description); /// @} - Scanner* m_scanner; + std::shared_ptr m_scanner; }; } } diff --git a/libsolidity/Scanner.cpp b/libsolidity/Scanner.cpp index a936e24f5..836e0d092 100644 --- a/libsolidity/Scanner.cpp +++ b/libsolidity/Scanner.cpp @@ -40,6 +40,9 @@ // You should have received a copy of the GNU General Public License // along with cpp-ethereum. If not, see . +#include +#include + #include namespace dev { @@ -121,6 +124,7 @@ Token::Value Scanner::next() return m_current_token.token; } + bool Scanner::skipWhitespace() { const int start_position = getSourcePos(); @@ -182,7 +186,7 @@ void Scanner::scanToken() Token::Value token; do { // Remember the position of the next token - m_next_token.location.beg_pos = getSourcePos(); + m_next_token.location.start = getSourcePos(); switch (m_char) { case '\n': @@ -401,7 +405,7 @@ void Scanner::scanToken() // whitespace. } while (token == Token::WHITESPACE); - m_next_token.location.end_pos = getSourcePos(); + m_next_token.location.end = getSourcePos(); m_next_token.token = token; } @@ -546,7 +550,7 @@ Token::Value Scanner::scanNumber(bool _periodSeen) #define KEYWORDS(KEYWORD_GROUP, KEYWORD) \ KEYWORD_GROUP('a') \ - KEYWORD("address", Token::BREAK) \ + KEYWORD("address", Token::ADDRESS) \ KEYWORD_GROUP('b') \ KEYWORD("break", Token::BREAK) \ KEYWORD("bool", Token::BOOL) \ @@ -588,8 +592,8 @@ Token::Value Scanner::scanNumber(bool _periodSeen) KEYWORD("interface", Token::FUTURE_STRICT_RESERVED_WORD) \ KEYWORD_GROUP('l') \ KEYWORD_GROUP('m') \ - KEYWORD_GROUP('n') \ KEYWORD("mapping", Token::MAPPING) \ + KEYWORD_GROUP('n') \ KEYWORD("new", Token::NEW) \ KEYWORD("null", Token::NULL_LITERAL) \ KEYWORD_GROUP('p') \ @@ -600,8 +604,9 @@ Token::Value Scanner::scanNumber(bool _periodSeen) KEYWORD_GROUP('r') \ KEYWORD("real", Token::REAL) \ KEYWORD("return", Token::RETURN) \ + KEYWORD("returns", Token::RETURNS) \ KEYWORD_GROUP('s') \ - KEYWORD("string", Token::STRING_TYPE) \ + KEYWORD("string", Token::STRING_TYPE) \ KEYWORD("struct", Token::STRUCT) \ KEYWORD("switch", Token::SWITCH) \ KEYWORD_GROUP('t') \ @@ -671,5 +676,38 @@ Token::Value Scanner::scanIdentifierOrKeyword() return KeywordOrIdentifierToken(m_next_token.literal); } +std::string CharStream::getLineAtPosition(int _position) const +{ + // if _position points to \n, it returns the line before the \n + using size_type = std::string::size_type; + size_type searchStart = std::min(m_source.size(), _position); + if (searchStart > 0) searchStart--; + size_type lineStart = m_source.rfind('\n', searchStart); + if (lineStart == std::string::npos) + lineStart = 0; + else + lineStart++; + return m_source.substr(lineStart, + std::min(m_source.find('\n', lineStart), + m_source.size()) - lineStart); +} + +std::tuple CharStream::translatePositionToLineColumn(int _position) const +{ + using size_type = std::string::size_type; + size_type searchPosition = std::min(m_source.size(), _position); + int lineNumber = std::count(m_source.begin(), m_source.begin() + searchPosition, '\n'); + + size_type lineStart; + if (searchPosition == 0) { + lineStart = 0; + } else { + lineStart = m_source.rfind('\n', searchPosition - 1); + lineStart = lineStart == std::string::npos ? 0 : lineStart + 1; + } + + return std::tuple(lineNumber, searchPosition - lineStart); +} + } } diff --git a/libsolidity/Scanner.h b/libsolidity/Scanner.h index d2dcad29d..7b1408c0b 100644 --- a/libsolidity/Scanner.h +++ b/libsolidity/Scanner.h @@ -82,6 +82,12 @@ public: return get(); } + /// Functions that help pretty-printing parse errors + /// Do only use in error cases, they are quite expensive. + /// @{ + std::string getLineAtPosition(int _position) const; + std::tuple translatePositionToLineColumn(int _position) const; + /// @} private: std::string m_source; size_t m_pos; @@ -134,6 +140,16 @@ public: Location peekLocation() const { return m_next_token.location; } const std::string& peekLiteral() const { return m_next_token.literal; } + /// Functions that help pretty-printing parse errors. + /// Do only use in error cases, they are quite expensive. + /// @{ + std::string getLineAtPosition(int _position) const { return m_source.getLineAtPosition(_position); } + std::tuple translatePositionToLineColumn(int _position) const + { + return m_source.translatePositionToLineColumn(_position); + } + /// @} + // Returns true if there was a line terminator before the peek'ed token, // possibly inside a multi-line comment. bool hasAnyLineTerminatorBeforeNext() const { diff --git a/libsolidity/Token.h b/libsolidity/Token.h index 7a39b989f..4476b3837 100644 --- a/libsolidity/Token.h +++ b/libsolidity/Token.h @@ -169,6 +169,7 @@ namespace solidity { K(PUBLIC, "public", 0) \ K(PRIVATE, "private", 0) \ K(RETURN, "return", 0) \ + K(RETURNS, "returns", 0) \ K(STRUCT, "struct", 0) \ K(SWITCH, "switch", 0) \ K(THIS, "this", 0) \ diff --git a/libsolidity/grammar.txt b/libsolidity/grammar.txt index aec02489e..1946325f4 100644 --- a/libsolidity/grammar.txt +++ b/libsolidity/grammar.txt @@ -1,18 +1,18 @@ ContractDefinition = 'contract' Identifier '{' ContractPart* '}' -ContractPart = VariableDeclaration ';' | StructDefinition ';' | - FunctionDefinition ';' | 'public:' | 'private:' +ContractPart = VariableDeclaration ';' | StructDefinition | + FunctionDefinition | 'public:' | 'private:' StructDefinition = 'struct' Identifier '{' ( VariableDeclaration (';' VariableDeclaration)* )? '} -FunctionDefinition = 'function' Identifier ArgumentList 'const'? - 'returns' ArgumentList Block -ArgumentList = '(' ( VariableDeclaration (',' VariableDeclaration)* )? ')' +FunctionDefinition = 'function' Identifier ParameterList 'const'? + ( 'returns' ParameterList )? Block +ParameterList = '(' ( VariableDeclaration (',' VariableDeclaration)* )? ')' // semantic restriction: mappings and structs (recursively) containing mappings // are not allowed in argument lists VariableDeclaration = TypeName Identifier -TypeName = PredefinedType | Identifier | MappingType -MappingType = 'mapping' '(' SimplePredefinedType '=>' TypeName ')' +TypeName = ElementaryTypeName | Identifier | Mapping +Mapping = 'mapping' '(' ElementaryTypeName '=>' TypeName ')' Block = '{' Statement* '}' Statement = IfStatement | WhileStatement | Continue | Break | Return | VariableAssignment | Expression ';' | Block diff --git a/test/solidityParser.cpp b/test/solidityParser.cpp index f42506767..91247a3b7 100644 --- a/test/solidityParser.cpp +++ b/test/solidityParser.cpp @@ -22,6 +22,7 @@ #include +#include #include #include #include @@ -30,19 +31,103 @@ namespace dev { namespace solidity { namespace test { +namespace { + ptr parseText(const std::string& _source) + { + Parser parser; + return parser.parse(std::make_shared(CharStream(_source))); + } +} + BOOST_AUTO_TEST_SUITE(SolidityParser) BOOST_AUTO_TEST_CASE(smoke_test) { - std::string text = "contract test123 {\n" - "\tuint256 stateVariable1;\n" - "}\n"; - Parser parser; - CharStream str(text); - // @todo: figure out why this does not compile - //Scanner scanner(CharStream(text)); - Scanner scanner(str); - BOOST_CHECK_NO_THROW(parser.parse(scanner)); + char const* text = "contract test {\n" + " uint256 stateVariable1;\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(missing_variable_name_in_declaration) +{ + char const* text = "contract test {\n" + " uint256 ;\n" + "}\n"; + cwarn << "The next error is expected."; + BOOST_CHECK_THROW(parseText(text), std::exception); +} + +BOOST_AUTO_TEST_CASE(empty_function) +{ + char const* text = "contract test {\n" + " uint256 stateVar;\n" + " function functionName(hash160 arg1, address addr) const\n" + " returns (int id)\n" + " { }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(no_function_params) +{ + char const* text = "contract test {\n" + " uint256 stateVar;\n" + " function functionName() {}\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(single_function_param) +{ + char const* text = "contract test {\n" + " uint256 stateVar;\n" + " function functionName(hash hashin) returns (hash hashout) {}\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(struct_definition) +{ + char const* text = "contract test {\n" + " uint256 stateVar;\n" + " struct MyStructName {\n" + " address addr;\n" + " uint256 count;\n" + " }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(mapping) +{ + char const* text = "contract test {\n" + " mapping(address => string) names;\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(mapping_in_struct) +{ + char const* text = "contract test {\n" + " struct test_struct {\n" + " address addr;\n" + " uint256 count;\n" + " mapping(hash => test_struct) self_reference;\n" + " }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(mapping_to_mapping_in_struct) +{ + char const* text = "contract test {\n" + " struct test_struct {\n" + " address addr;\n" + " mapping (uint64 => mapping (hash => uint)) complex_mapping;\n" + " }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); } diff --git a/test/solidityScanner.cpp b/test/solidityScanner.cpp index 7f84146a3..759d2f101 100644 --- a/test/solidityScanner.cpp +++ b/test/solidityScanner.cpp @@ -98,23 +98,23 @@ BOOST_AUTO_TEST_CASE(locations) { Scanner scanner(CharStream("function_identifier has ; -0x743/*comment*/\n ident //comment")); BOOST_CHECK_EQUAL(scanner.getCurrentToken(), Token::IDENTIFIER); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().beg_pos, 0); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end_pos, 19); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().start, 0); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end, 19); BOOST_CHECK_EQUAL(scanner.next(), Token::IDENTIFIER); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().beg_pos, 20); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end_pos, 23); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().start, 20); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end, 23); BOOST_CHECK_EQUAL(scanner.next(), Token::SEMICOLON); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().beg_pos, 24); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end_pos, 25); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().start, 24); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end, 25); BOOST_CHECK_EQUAL(scanner.next(), Token::SUB); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().beg_pos, 26); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end_pos, 27); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().start, 26); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end, 27); BOOST_CHECK_EQUAL(scanner.next(), Token::NUMBER); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().beg_pos, 27); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end_pos, 32); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().start, 27); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end, 32); BOOST_CHECK_EQUAL(scanner.next(), Token::IDENTIFIER); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().beg_pos, 45); - BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end_pos, 50); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().start, 45); + BOOST_CHECK_EQUAL(scanner.getCurrentLocation().end, 50); BOOST_CHECK_EQUAL(scanner.next(), Token::EOS); }