aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Changelog.md1
-rw-r--r--libsolidity/analysis/StaticAnalyzer.cpp2
-rw-r--r--libsolidity/ast/ASTEnums.h4
-rw-r--r--libsolidity/interface/ABI.cpp2
-rw-r--r--libsolidity/parsing/Parser.cpp2
-rw-r--r--libsolidity/parsing/Token.h4
-rw-r--r--test/libsolidity/SolidityParser.cpp10
7 files changed, 21 insertions, 4 deletions
diff --git a/Changelog.md b/Changelog.md
index 1ea3f6c8..fbbf0761 100644
--- a/Changelog.md
+++ b/Changelog.md
@@ -1,6 +1,7 @@
### 0.4.16 (unreleased)
Features:
+ * Introduce ``pure`` functions. The pureness is not enforced yet, use with care.
* ABI JSON: Include new field ``statemutability`` with values ``view``, ``nonpayable`` and ``payable``.
* Analyzer: Experimental partial support for Z3 SMT checker.
* Parser: Display previous visibility specifier in error if multiple are found.
diff --git a/libsolidity/analysis/StaticAnalyzer.cpp b/libsolidity/analysis/StaticAnalyzer.cpp
index ab1cbb52..2f130414 100644
--- a/libsolidity/analysis/StaticAnalyzer.cpp
+++ b/libsolidity/analysis/StaticAnalyzer.cpp
@@ -57,6 +57,8 @@ bool StaticAnalyzer::visit(FunctionDefinition const& _function)
solAssert(m_localVarUseCount.empty(), "");
m_nonPayablePublic = _function.isPublic() && !_function.isPayable();
m_constructor = _function.isConstructor();
+ if (_function.stateMutability() == StateMutability::Pure)
+ m_errorReporter.warning(_function.location(), "Function is marked pure. Be careful, pureness is not enforced yet.");
return true;
}
diff --git a/libsolidity/ast/ASTEnums.h b/libsolidity/ast/ASTEnums.h
index f7c75878..5ba21907 100644
--- a/libsolidity/ast/ASTEnums.h
+++ b/libsolidity/ast/ASTEnums.h
@@ -31,12 +31,14 @@ namespace solidity
{
// How a function can mutate the EVM state.
-enum class StateMutability { View, NonPayable, Payable };
+enum class StateMutability { Pure, View, NonPayable, Payable };
inline std::string stateMutabilityToString(StateMutability const& _stateMutability)
{
switch(_stateMutability)
{
+ case StateMutability::Pure:
+ return "pure";
case StateMutability::View:
return "view";
case StateMutability::NonPayable:
diff --git a/libsolidity/interface/ABI.cpp b/libsolidity/interface/ABI.cpp
index 6e8563f7..dd56ff6d 100644
--- a/libsolidity/interface/ABI.cpp
+++ b/libsolidity/interface/ABI.cpp
@@ -36,7 +36,7 @@ Json::Value ABI::generate(ContractDefinition const& _contractDef)
method["type"] = "function";
method["name"] = it.second->declaration().name();
// TODO: deprecate constant in a future release
- method["constant"] = it.second->stateMutability() == StateMutability::View;
+ method["constant"] = it.second->stateMutability() == StateMutability::Pure || it.second->stateMutability() == StateMutability::View;
method["payable"] = it.second->isPayable();
method["statemutability"] = stateMutabilityToString(it.second->stateMutability());
method["inputs"] = formatTypeList(
diff --git a/libsolidity/parsing/Parser.cpp b/libsolidity/parsing/Parser.cpp
index cd0d6157..ddfdb667 100644
--- a/libsolidity/parsing/Parser.cpp
+++ b/libsolidity/parsing/Parser.cpp
@@ -321,6 +321,8 @@ StateMutability Parser::parseStateMutability(Token::Value _token)
// FIXME: constant should be removed at the next breaking release
else if (_token == Token::View || _token == Token::Constant)
stateMutability = StateMutability::View;
+ else if (_token == Token::Pure)
+ stateMutability = StateMutability::Pure;
else
solAssert(false, "Invalid state mutability specifier.");
m_scanner->next();
diff --git a/libsolidity/parsing/Token.h b/libsolidity/parsing/Token.h
index 3bc52f1d..805fbf5d 100644
--- a/libsolidity/parsing/Token.h
+++ b/libsolidity/parsing/Token.h
@@ -169,6 +169,7 @@ namespace solidity
K(Public, "public", 0) \
K(Pragma, "pragma", 0) \
K(Private, "private", 0) \
+ K(Pure, "pure", 0) \
K(Return, "return", 0) \
K(Returns, "returns", 0) \
K(Storage, "storage", 0) \
@@ -230,7 +231,6 @@ namespace solidity
K(Match, "match", 0) \
K(NullLiteral, "null", 0) \
K(Of, "of", 0) \
- K(Pure, "pure", 0) \
K(Relocatable, "relocatable", 0) \
K(Static, "static", 0) \
K(Switch, "switch", 0) \
@@ -290,7 +290,7 @@ public:
static bool isVisibilitySpecifier(Value op) { return isVariableVisibilitySpecifier(op) || op == External; }
static bool isVariableVisibilitySpecifier(Value op) { return op == Public || op == Private || op == Internal; }
static bool isLocationSpecifier(Value op) { return op == Memory || op == Storage; }
- static bool isStateMutabilitySpecifier(Value op) { return op == Constant || op == View || op == Payable; }
+ static bool isStateMutabilitySpecifier(Value op) { return op == Pure || op == Constant || op == View || op == Payable; }
static bool isEtherSubdenomination(Value op) { return op == SubWei || op == SubSzabo || op == SubFinney || op == SubEther; }
static bool isTimeSubdenomination(Value op) { return op == SubSecond || op == SubMinute || op == SubHour || op == SubDay || op == SubWeek || op == SubYear; }
static bool isReservedKeyword(Value op) { return (Abstract <= op && op <= TypeOf); }
diff --git a/test/libsolidity/SolidityParser.cpp b/test/libsolidity/SolidityParser.cpp
index 8e84ead1..a39e0958 100644
--- a/test/libsolidity/SolidityParser.cpp
+++ b/test/libsolidity/SolidityParser.cpp
@@ -928,6 +928,16 @@ BOOST_AUTO_TEST_CASE(multiple_statemutability_specifiers)
function f() payable constant {}
})";
CHECK_PARSE_ERROR(text, "State mutability already specified as \"payable\".");
+ text = R"(
+ contract c {
+ function f() pure payable {}
+ })";
+ CHECK_PARSE_ERROR(text, "State mutability already specified as \"pure\".");
+ text = R"(
+ contract c {
+ function f() pure constant {}
+ })";
+ CHECK_PARSE_ERROR(text, "State mutability already specified as \"pure\".");
}
BOOST_AUTO_TEST_CASE(literal_constants_with_ether_subdenominations)