aboutsummaryrefslogtreecommitdiffstats
path: root/libsolidity/ast
diff options
context:
space:
mode:
authorYoichi Hirai <i@yoichihirai.com>2016-12-14 23:31:28 +0800
committerGitHub <noreply@github.com>2016-12-14 23:31:27 +0800
commit18f8f29c0a3ed9404f2950c11d77f85d0117c6d5 (patch)
tree11fcb5408f609ab3e8f35d7e41fd7a42df0d1837 /libsolidity/ast
parente53d12557162275a135a4ae086ae05691bc23fa3 (diff)
parent08a11e309f241e602cc4754b6322e4bb0da57b17 (diff)
downloaddexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.tar
dexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.tar.gz
dexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.tar.bz2
dexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.tar.lz
dexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.tar.xz
dexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.tar.zst
dexon-solidity-18f8f29c0a3ed9404f2950c11d77f85d0117c6d5.zip
Merge pull request #1487 from ethereum/shift-ops
Shift operators
Diffstat (limited to 'libsolidity/ast')
-rw-r--r--libsolidity/ast/Types.cpp32
1 files changed, 32 insertions, 0 deletions
diff --git a/libsolidity/ast/Types.cpp b/libsolidity/ast/Types.cpp
index d9660bc0..03ff8471 100644
--- a/libsolidity/ast/Types.cpp
+++ b/libsolidity/ast/Types.cpp
@@ -251,6 +251,19 @@ MemberList::MemberMap Type::boundFunctions(Type const& _type, ContractDefinition
return members;
}
+bool isValidShiftAndAmountType(Token::Value _operator, Type const& _shiftAmountType)
+{
+ // Disable >>> here.
+ if (_operator == Token::SHR)
+ return false;
+ else if (IntegerType const* otherInt = dynamic_cast<decltype(otherInt)>(&_shiftAmountType))
+ return !otherInt->isAddress();
+ else if (RationalNumberType const* otherRat = dynamic_cast<decltype(otherRat)>(&_shiftAmountType))
+ return otherRat->integerType() && !otherRat->integerType()->isSigned();
+ else
+ return false;
+}
+
IntegerType::IntegerType(int _bits, IntegerType::Modifier _modifier):
m_bits(_bits), m_modifier(_modifier)
{
@@ -340,6 +353,17 @@ TypePointer IntegerType::binaryOperatorResult(Token::Value _operator, TypePointe
_other->category() != category()
)
return TypePointer();
+ if (Token::isShiftOp(_operator))
+ {
+ // Shifts are not symmetric with respect to the type
+ if (isAddress())
+ return TypePointer();
+ if (isValidShiftAndAmountType(_operator, *_other))
+ return shared_from_this();
+ else
+ return TypePointer();
+ }
+
auto commonType = Type::commonType(shared_from_this(), _other); //might be a integer or fixed point
if (!commonType)
return TypePointer();
@@ -954,6 +978,14 @@ TypePointer FixedBytesType::unaryOperatorResult(Token::Value _operator) const
TypePointer FixedBytesType::binaryOperatorResult(Token::Value _operator, TypePointer const& _other) const
{
+ if (Token::isShiftOp(_operator))
+ {
+ if (isValidShiftAndAmountType(_operator, *_other))
+ return shared_from_this();
+ else
+ return TypePointer();
+ }
+
auto commonType = dynamic_pointer_cast<FixedBytesType const>(Type::commonType(shared_from_this(), _other));
if (!commonType)
return TypePointer();