diff options
author | Lefteris Karapetsas <lefteris@refu.co> | 2015-02-04 23:37:54 +0800 |
---|---|---|
committer | Lefteris Karapetsas <lefteris@refu.co> | 2015-02-05 00:52:28 +0800 |
commit | dca5f7b57bb5b535930d437c806f48a25cf6b569 (patch) | |
tree | 04ee06c48c7ca6c4f012c6778bb9ea01248582d9 | |
parent | db263bd9d751f69f9d8d9484ff916d38b86c68c4 (diff) | |
download | dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.tar dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.tar.gz dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.tar.bz2 dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.tar.lz dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.tar.xz dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.tar.zst dexon-solidity-dca5f7b57bb5b535930d437c806f48a25cf6b569.zip |
Adding ether subdenominations after constan literals
-rw-r--r-- | AST.cpp | 11 | ||||
-rwxr-xr-x | AST.h | 16 | ||||
-rw-r--r-- | Parser.cpp | 6 | ||||
-rw-r--r-- | Token.h | 5 | ||||
-rw-r--r-- | Types.cpp | 27 |
5 files changed, 57 insertions, 8 deletions
@@ -594,6 +594,17 @@ void ElementaryTypeNameExpression::checkTypeRequirements() m_type = make_shared<TypeType>(Type::fromElementaryTypeName(m_typeToken)); } +Literal::Literal(Location const& _location, Token::Value _token, + ASTPointer<ASTString> const& _value, + Token::Value _sub): + PrimaryExpression(_location), m_token(_token), m_value(_value) +{ + solAssert(_sub == Token::ILLEGAL || _sub == Token::ETH_SUB_WEI || + _sub == Token::ETH_SUB_SZABO || _sub == Token::ETH_SUB_FINNEY || + _sub == Token::ETH_SUB_ETHER, "Illegal Token::Value given to Literal ctor"); + m_subDenomination =static_cast<Literal::ethSubDenomination>(_sub); +} + void Literal::checkTypeRequirements() { m_type = Type::forLiteral(*this); @@ -1112,13 +1112,20 @@ private: }; /** - * A literal string or number. @see Type::literalToBigEndian is used to actually parse its value. + * A literal string or number. @see ExpressionCompiler::endVisit() is used to actually parse its value. */ class Literal: public PrimaryExpression { public: - Literal(Location const& _location, Token::Value _token, ASTPointer<ASTString> const& _value): - PrimaryExpression(_location), m_token(_token), m_value(_value) {} + enum class ethSubDenomination { + NONE = Token::ILLEGAL, + WEI = Token::ETH_SUB_WEI, + SZABO = Token::ETH_SUB_SZABO, + FINNEY = Token::ETH_SUB_FINNEY, + ETHER = Token::ETH_SUB_ETHER}; + Literal(Location const& _location, Token::Value _token, + ASTPointer<ASTString> const& _value, + Token::Value _sub = Token::ILLEGAL); virtual void accept(ASTVisitor& _visitor) override; virtual void accept(ASTConstVisitor& _visitor) const override; virtual void checkTypeRequirements() override; @@ -1127,9 +1134,12 @@ public: /// @returns the non-parsed value of the literal ASTString const& getValue() const { return *m_value; } + ethSubDenomination getSubDenomination() const { return m_subDenomination; } + private: Token::Value m_token; ASTPointer<ASTString> m_value; + ethSubDenomination m_subDenomination; }; /// @} @@ -180,7 +180,7 @@ ASTPointer<InheritanceSpecifier> Parser::parseInheritanceSpecifier() Declaration::Visibility Parser::parseVisibilitySpecifier(Token::Value _token) { - Declaration::Visibility visibility; + Declaration::Visibility visibility = Declaration::Visibility::DEFAULT; if (_token == Token::PUBLIC) visibility = Declaration::Visibility::PUBLIC; else if (_token == Token::PROTECTED) @@ -684,6 +684,7 @@ ASTPointer<Expression> Parser::parsePrimaryExpression() ASTNodeFactory nodeFactory(*this); Token::Value token = m_scanner->getCurrentToken(); ASTPointer<Expression> expression; + Token::Value nextToken = Token::ILLEGAL; switch (token) { case Token::TRUE_LITERAL: @@ -691,9 +692,10 @@ ASTPointer<Expression> Parser::parsePrimaryExpression() expression = nodeFactory.createNode<Literal>(token, getLiteralAndAdvance()); break; case Token::NUMBER: + nextToken = m_scanner->peekNextToken(); case Token::STRING_LITERAL: nodeFactory.markEndPosition(); - expression = nodeFactory.createNode<Literal>(token, getLiteralAndAdvance()); + expression = nodeFactory.createNode<Literal>(token, getLiteralAndAdvance(), nextToken); break; case Token::IDENTIFIER: nodeFactory.markEndPosition(); @@ -174,6 +174,11 @@ namespace solidity K(WHILE, "while", 0) \ \ \ + /* Ether subdenominations */ \ + K(ETH_SUB_WEI, "wei", 0) \ + K(ETH_SUB_SZABO, "szabo", 0) \ + K(ETH_SUB_FINNEY, "finney", 0) \ + K(ETH_SUB_ETHER, "ether", 0) \ /* type keywords, keep them in this order, keep int as first keyword * the implementation in Types.cpp has to be synced to this here * TODO more to be added */ \ @@ -326,15 +326,36 @@ string IntegerConstantType::toString() const return "int_const " + m_value.str(); } -u256 IntegerConstantType::literalValue(Literal const*) const +u256 IntegerConstantType::literalValue(Literal const* _literal) const { + Literal::ethSubDenomination sub =_literal->getSubDenomination(); + u256 value; // we ignore the literal and hope that the type was correctly determined solAssert(m_value <= u256(-1), "Integer constant too large."); solAssert(m_value >= -(bigint(1) << 255), "Integer constant too small."); + + if (m_value >= 0) - return u256(m_value); + value = u256(m_value); else - return s2u(s256(m_value)); + value = s2u(s256(m_value)); + + switch(sub) { + case Literal::ethSubDenomination::WEI: + case Literal::ethSubDenomination::NONE: + break; + case Literal::ethSubDenomination::SZABO: + value *= u256(1000000000000); + break; + case Literal::ethSubDenomination::FINNEY: + value *= u256(1000000000000000); + break; + case Literal::ethSubDenomination::ETHER: + value *= u256(1000000000000000000); + break; + } + + return value; } shared_ptr<IntegerType const> IntegerConstantType::getIntegerType() const |