diff options
author | chriseth <chris@ethereum.org> | 2017-11-24 00:42:06 +0800 |
---|---|---|
committer | Alex Beregszaszi <alex@rtfs.hu> | 2018-02-06 22:48:47 +0800 |
commit | 33abdfab766da674514f490904c351286b1784c1 (patch) | |
tree | fe0ec1ad054e0ce135d6a83e440c73b0a25cf8c4 /libjulia/optimiser/InlinableFunctionFilter.cpp | |
parent | d786d652434d2010d9af4ef0bf0aa1fdb15c80e8 (diff) | |
download | dexon-solidity-33abdfab766da674514f490904c351286b1784c1.tar dexon-solidity-33abdfab766da674514f490904c351286b1784c1.tar.gz dexon-solidity-33abdfab766da674514f490904c351286b1784c1.tar.bz2 dexon-solidity-33abdfab766da674514f490904c351286b1784c1.tar.lz dexon-solidity-33abdfab766da674514f490904c351286b1784c1.tar.xz dexon-solidity-33abdfab766da674514f490904c351286b1784c1.tar.zst dexon-solidity-33abdfab766da674514f490904c351286b1784c1.zip |
Inlinable function filter.
Diffstat (limited to 'libjulia/optimiser/InlinableFunctionFilter.cpp')
-rw-r--r-- | libjulia/optimiser/InlinableFunctionFilter.cpp | 68 |
1 files changed, 68 insertions, 0 deletions
diff --git a/libjulia/optimiser/InlinableFunctionFilter.cpp b/libjulia/optimiser/InlinableFunctionFilter.cpp new file mode 100644 index 00000000..db9f812d --- /dev/null +++ b/libjulia/optimiser/InlinableFunctionFilter.cpp @@ -0,0 +1,68 @@ +/* + This file is part of solidity. + + solidity is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + solidity is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with solidity. If not, see <http://www.gnu.org/licenses/>. +*/ +/** + * Optimiser component that identifies functions to be inlined. + */ + +#include <libjulia/optimiser/InlinableFunctionFilter.h> + +#include <libsolidity/inlineasm/AsmData.h> + +#include <libsolidity/interface/Exceptions.h> + +using namespace std; +using namespace dev; +using namespace dev::julia; + +void InlinableFunctionFilter::operator()(Identifier const& _identifier) +{ + checkAllowed(_identifier.name); + ASTWalker::operator()(_identifier); +} + +void InlinableFunctionFilter::operator()(FunctionCall const& _funCall) +{ + checkAllowed(_funCall.functionName.name); + ASTWalker::operator()(_funCall); +} + +void InlinableFunctionFilter::operator()(FunctionDefinition const& _function) +{ + if (_function.returnVariables.size() == 1 && _function.body.statements.size() == 1) + { + string const& retVariable = _function.returnVariables.front().name; + Statement const& bodyStatement = _function.body.statements.front(); + if (bodyStatement.type() == typeid(Assignment)) + { + Assignment const& assignment = boost::get<Assignment>(bodyStatement); + if (assignment.variableNames.size() == 1 && assignment.variableNames.front().name == retVariable) + { + // We cannot overwrite previous settings, because this function definition + // would not be valid here if we were searching inside a functionally inlinable + // function body. + solAssert(m_disallowedIdentifiers.empty() && !m_foundDisallowedIdentifier, ""); + m_disallowedIdentifiers = set<string>{retVariable, _function.name}; + boost::apply_visitor(*this, *assignment.value); + if (!m_foundDisallowedIdentifier) + m_inlinableFunctions[_function.name] = &_function; + m_disallowedIdentifiers.clear(); + m_foundDisallowedIdentifier = false; + } + } + } + ASTWalker::operator()(_function.body); +} |