aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorchriseth <c@ethdev.com>2015-06-01 18:32:59 +0800
committerchriseth <c@ethdev.com>2015-06-05 23:34:26 +0800
commit9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32 (patch)
tree090d80e157083121e5df163acc4dd8ba44635255
parent4987eec3d1e87868e091850d31af58e054ab5ee5 (diff)
downloaddexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.tar
dexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.tar.gz
dexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.tar.bz2
dexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.tar.lz
dexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.tar.xz
dexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.tar.zst
dexon-solidity-9efd5374ed5d3e2c5abf6d85907e1e3ac5ce5b32.zip
Compute constants
-rw-r--r--Compiler.cpp8
-rw-r--r--Compiler.h17
-rw-r--r--CompilerContext.h5
-rw-r--r--CompilerStack.cpp6
-rw-r--r--CompilerStack.h2
5 files changed, 26 insertions, 12 deletions
diff --git a/Compiler.cpp b/Compiler.cpp
index 6425367d..6dc72840 100644
--- a/Compiler.cpp
+++ b/Compiler.cpp
@@ -69,6 +69,8 @@ void Compiler::compileContract(ContractDefinition const& _contract,
swap(m_context, m_runtimeContext);
initializeContext(_contract, _contracts);
packIntoContractCreator(_contract, m_runtimeContext);
+ if (m_optimize)
+ m_context.optimise(m_optimizeRuns);
}
eth::AssemblyItem Compiler::getFunctionEntryLabel(FunctionDefinition const& _function) const
@@ -120,9 +122,11 @@ void Compiler::packIntoContractCreator(ContractDefinition const& _contract, Comp
else if (auto c = m_context.getNextConstructor(_contract))
appendBaseConstructor(*c);
- eth::AssemblyItem sub = m_context.addSubroutine(_runtimeContext.getAssembly());
+ eth::AssemblyItem runtimeSub = m_context.addSubroutine(_runtimeContext.getAssembly());
+ solAssert(runtimeSub.data() < numeric_limits<size_t>::max(), "");
+ m_runtimeSub = size_t(runtimeSub.data());
// stack contains sub size
- m_context << eth::Instruction::DUP1 << sub << u256(0) << eth::Instruction::CODECOPY;
+ m_context << eth::Instruction::DUP1 << runtimeSub << u256(0) << eth::Instruction::CODECOPY;
m_context << u256(0) << eth::Instruction::RETURN;
// note that we have to include the functions again because of absolute jump labels
diff --git a/Compiler.h b/Compiler.h
index 13b8639d..670c7467 100644
--- a/Compiler.h
+++ b/Compiler.h
@@ -34,13 +34,18 @@ namespace solidity {
class Compiler: private ASTConstVisitor
{
public:
- explicit Compiler(bool _optimize = false): m_optimize(_optimize), m_context(),
- m_returnTag(m_context.newTag()) {}
+ explicit Compiler(bool _optimize = false, unsigned _runs = 200):
+ m_optimize(_optimize),
+ m_optimizeRuns(_runs),
+ m_context(),
+ m_returnTag(m_context.newTag())
+ {
+ }
void compileContract(ContractDefinition const& _contract,
std::map<ContractDefinition const*, bytes const*> const& _contracts);
- bytes getAssembledBytecode() { return m_context.getAssembledBytecode(m_optimize); }
- bytes getRuntimeBytecode() { return m_runtimeContext.getAssembledBytecode(m_optimize);}
+ bytes getAssembledBytecode() { return m_context.getAssembledBytecode(); }
+ bytes getRuntimeBytecode() { return m_context.getAssembledRuntimeBytecode(m_runtimeSub); }
/// @arg _sourceCodes is the map of input files to source code strings
/// @arg _inJsonFromat shows whether the out should be in Json format
Json::Value streamAssembly(std::ostream& _stream, StringMap const& _sourceCodes = StringMap(), bool _inJsonFormat = false) const
@@ -50,7 +55,7 @@ public:
/// @returns Assembly items of the normal compiler context
eth::AssemblyItems const& getAssemblyItems() const { return m_context.getAssembly().getItems(); }
/// @returns Assembly items of the runtime compiler context
- eth::AssemblyItems const& getRuntimeAssemblyItems() const { return m_runtimeContext.getAssembly().getItems(); }
+ eth::AssemblyItems const& getRuntimeAssemblyItems() const { return m_context.getAssembly().getSub(m_runtimeSub).getItems(); }
/// @returns the entry label of the given function. Might return an AssemblyItem of type
/// UndefinedItem if it does not exist yet.
@@ -93,7 +98,9 @@ private:
void compileExpression(Expression const& _expression, TypePointer const& _targetType = TypePointer());
bool const m_optimize;
+ unsigned const m_optimizeRuns;
CompilerContext m_context;
+ size_t m_runtimeSub = size_t(-1); ///< Identifier of the runtime sub-assembly
CompilerContext m_runtimeContext;
std::vector<eth::AssemblyItem> m_breakTags; ///< tag to jump to for a "break" statement
std::vector<eth::AssemblyItem> m_continueTags; ///< tag to jump to for a "continue" statement
diff --git a/CompilerContext.h b/CompilerContext.h
index 573e0b57..998b0a2f 100644
--- a/CompilerContext.h
+++ b/CompilerContext.h
@@ -126,6 +126,8 @@ public:
CompilerContext& operator<<(u256 const& _value) { m_asm.append(_value); return *this; }
CompilerContext& operator<<(bytes const& _data) { m_asm.append(_data); return *this; }
+ void optimise(unsigned _runs = 200) { m_asm.optimise(true, true, _runs); }
+
eth::Assembly const& getAssembly() const { return m_asm; }
/// @arg _sourceCodes is the map of input files to source code strings
/// @arg _inJsonFormat shows whether the out should be in Json format
@@ -134,7 +136,8 @@ public:
return m_asm.stream(_stream, "", _sourceCodes, _inJsonFormat);
}
- bytes getAssembledBytecode(bool _optimize = false) { return m_asm.optimise(_optimize).assemble(); }
+ bytes getAssembledBytecode() { return m_asm.assemble(); }
+ bytes getAssembledRuntimeBytecode(size_t _subIndex) { m_asm.assemble(); return m_asm.data(u256(_subIndex)); }
/**
* Helper class to pop the visited nodes stack when a scope closes
diff --git a/CompilerStack.cpp b/CompilerStack.cpp
index ebb98876..a3399823 100644
--- a/CompilerStack.cpp
+++ b/CompilerStack.cpp
@@ -145,7 +145,7 @@ vector<string> CompilerStack::getContractNames() const
}
-void CompilerStack::compile(bool _optimize)
+void CompilerStack::compile(bool _optimize, unsigned _runs)
{
if (!m_parseSuccessful)
parse();
@@ -157,9 +157,9 @@ void CompilerStack::compile(bool _optimize)
{
if (!contract->isFullyImplemented())
continue;
- shared_ptr<Compiler> compiler = make_shared<Compiler>(_optimize);
+ shared_ptr<Compiler> compiler = make_shared<Compiler>(_optimize, _runs);
compiler->compileContract(*contract, contractBytecode);
- Contract& compiledContract = m_contracts[contract->getName()];
+ Contract& compiledContract = m_contracts.at(contract->getName());
compiledContract.bytecode = compiler->getAssembledBytecode();
compiledContract.runtimeBytecode = compiler->getRuntimeBytecode();
compiledContract.compiler = move(compiler);
diff --git a/CompilerStack.h b/CompilerStack.h
index 6be45aec..a7c6ea3b 100644
--- a/CompilerStack.h
+++ b/CompilerStack.h
@@ -90,7 +90,7 @@ public:
std::string defaultContractName() const;
/// Compiles the source units that were previously added and parsed.
- void compile(bool _optimize = false);
+ void compile(bool _optimize = false, unsigned _runs = 200);
/// Parses and compiles the given source code.
/// @returns the compiled bytecode
bytes const& compile(std::string const& _sourceCode, bool _optimize = false);