Browse Source

Fixed problem with alloc.

cl-refactor
Gav Wood 11 years ago
parent
commit
d1802c9b79
  1. 3
      alethzero/Main.ui
  2. 4
      alethzero/MainWin.cpp
  3. 4
      libethcore/TrieDB.h
  4. 2
      libethential/CMakeLists.txt
  5. 13
      libethereum/Client.h
  6. 5
      libevm/All.h
  7. 5
      liblll/Assembly.cpp
  8. 2
      liblll/Assembly.h
  9. 39
      liblll/CodeFragment.cpp
  10. 7
      liblll/CodeFragment.h
  11. 4
      liblll/Compiler.cpp
  12. 3
      liblll/CompilerState.cpp
  13. 1
      liblll/CompilerState.h
  14. 2
      sc/cmdline.cpp

3
alethzero/Main.ui

@ -1288,7 +1288,8 @@ font-size: 14pt</string>
<property name="styleSheet"> <property name="styleSheet">
<string notr="true">background: white; <string notr="true">background: white;
border: 0; border: 0;
font-family: Monospace, Ubuntu Mono, Lucida Console, Courier New</string> font-family: Monospace, Ubuntu Mono, Lucida Console, Courier New;
font-size: 12pt</string>
</property> </property>
<property name="inputMask"> <property name="inputMask">
<string/> <string/>

4
alethzero/MainWin.cpp

@ -118,7 +118,7 @@ Main::Main(QWidget *parent) :
connect(ui->ourAccounts->model(), SIGNAL(rowsMoved(const QModelIndex &, int, int, const QModelIndex &, int)), SLOT(ourAccountsRowsMoved())); connect(ui->ourAccounts->model(), SIGNAL(rowsMoved(const QModelIndex &, int, int, const QModelIndex &, int)), SLOT(ourAccountsRowsMoved()));
#if ETH_DEBUG #if 0&&ETH_DEBUG
m_servers.append("192.168.0.10:30301"); m_servers.append("192.168.0.10:30301");
#else #else
int pocnumber = QString(eth::EthVersion).section('.', 1, 1).toInt(); int pocnumber = QString(eth::EthVersion).section('.', 1, 1).toInt();
@ -985,7 +985,7 @@ void Main::on_data_textChanged()
{ {
try try
{ {
m_data = eth::asBytes(compile(src)); m_data = compile(src);
for (auto& i: errors) for (auto& i: errors)
i = "(LLL " + i + ")"; i = "(LLL " + i + ")";
} }

4
libethcore/TrieDB.h

@ -42,7 +42,7 @@ extern const h256 c_shaNull;
/** /**
* @brief Merkle Patricia Tree "Trie": a modifed base-16 Radix tree. * @brief Merkle Patricia Tree "Trie": a modifed base-16 Radix tree.
* This version uses an LDB backend * This version uses an database backend.
* Usage: * Usage:
* @code * @code
* GenericTrieDB<MyDB> t(&myDB); * GenericTrieDB<MyDB> t(&myDB);
@ -153,6 +153,7 @@ public:
std::string at(bytesConstRef _key) const; std::string at(bytesConstRef _key) const;
void insert(bytesConstRef _key, bytesConstRef _value); void insert(bytesConstRef _key, bytesConstRef _value);
void remove(bytesConstRef _key); void remove(bytesConstRef _key);
void contains(bytesConstRef _key) { return !at(_key).empty(); }
class iterator class iterator
{ {
@ -274,6 +275,7 @@ public:
std::string operator[](KeyType _k) const { return at(_k); } std::string operator[](KeyType _k) const { return at(_k); }
bool contains(KeyType _k) const { return GenericTrieDB<DB>::contains(bytesConstRef((byte const*)&_k, sizeof(KeyType))); }
std::string at(KeyType _k) const { return GenericTrieDB<DB>::at(bytesConstRef((byte const*)&_k, sizeof(KeyType))); } std::string at(KeyType _k) const { return GenericTrieDB<DB>::at(bytesConstRef((byte const*)&_k, sizeof(KeyType))); }
void insert(KeyType _k, bytesConstRef _value) { GenericTrieDB<DB>::insert(bytesConstRef((byte const*)&_k, sizeof(KeyType)), _value); } void insert(KeyType _k, bytesConstRef _value) { GenericTrieDB<DB>::insert(bytesConstRef((byte const*)&_k, sizeof(KeyType)), _value); }
void insert(KeyType _k, bytes const& _value) { insert(_k, bytesConstRef(&_value)); } void insert(KeyType _k, bytes const& _value) { insert(_k, bytesConstRef(&_value)); }

2
libethential/CMakeLists.txt

@ -1,4 +1,5 @@
cmake_policy(SET CMP0015 NEW) cmake_policy(SET CMP0015 NEW)
cmake_policy(SET CMP0022 NEW)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DSTATICLIB") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DSTATICLIB")
@ -16,7 +17,6 @@ include_directories(..)
target_link_libraries(${EXECUTABLE} ethential) target_link_libraries(${EXECUTABLE} ethential)
target_link_libraries(${EXECUTABLE} gmp) target_link_libraries(${EXECUTABLE} gmp)
if(${TARGET_PLATFORM} STREQUAL "w64") if(${TARGET_PLATFORM} STREQUAL "w64")
include_directories(/usr/x86_64-w64-mingw32/include/cryptopp) include_directories(/usr/x86_64-w64-mingw32/include/cryptopp)
target_link_libraries(${EXECUTABLE} boost_thread_win32-mt-s) target_link_libraries(${EXECUTABLE} boost_thread_win32-mt-s)

13
libethereum/Client.h

@ -140,14 +140,13 @@ public:
BlockChain const& blockChain() const { return m_bc; } BlockChain const& blockChain() const { return m_bc; }
// [NEW API] // [NEW API]
/*
u256 balanceAt(Address _a, unsigned _age = 1) const;
u256 countAt(Address _a, unsigned _age = 1) const;
u256 stateAt(Address _a, u256 _l, unsigned _age = 1) const;
bytes codeAt(Address _a, unsigned _age = 1) const;
Transactions transactions(Addresses const& _from, Addresses const& _to, std::vector<std::pair<u256, u256>> const& _stateAlterations, Addresses const& _altered, unsigned _ageFrom = 0, unsigned _ageTo, unsigned _max) const; u256 balanceAt(Address _a, int _block = -1) const;
*/ u256 countAt(Address _a, int _block = -1) const;
u256 stateAt(Address _a, u256 _l, int _block = -1) const;
bytes codeAt(Address _a, int _block = -1) const;
Transactions transactions(Addresses const& _from, Addresses const& _to, std::vector<std::pair<u256, u256>> const& _stateAlterations, Addresses const& _altered, int _blockFrom = 0, int _blockTo = -1, unsigned _max = 10) const;
// Misc stuff: // Misc stuff:
void setClientVersion(std::string const& _name) { m_clientVersion = _name; } void setClientVersion(std::string const& _name) { m_clientVersion = _name; }

5
libevm/All.h

@ -0,0 +1,5 @@
#pragma once
#include "ExtVMFace.h"
#include "FeeStructure.h"
#include "VM.h"

5
liblll/Assembly.cpp

@ -176,6 +176,11 @@ AssemblyItem const& Assembly::append(AssemblyItem const& _i)
return back(); return back();
} }
void Assembly::injectStart(AssemblyItem const& _i)
{
m_items.insert(m_items.begin(), _i);
}
inline bool matches(AssemblyItemsConstRef _a, AssemblyItemsConstRef _b) inline bool matches(AssemblyItemsConstRef _a, AssemblyItemsConstRef _b)
{ {
if (_a.size() != _b.size()) if (_a.size() != _b.size())

2
liblll/Assembly.h

@ -98,6 +98,8 @@ public:
void popTo(int _deposit) { while (m_deposit > _deposit) append(Instruction::POP); } void popTo(int _deposit) { while (m_deposit > _deposit) append(Instruction::POP); }
void injectStart(AssemblyItem const& _i);
std::string out() const { std::stringstream ret; streamOut(ret); return ret.str(); } std::string out() const { std::stringstream ret; streamOut(ret); return ret.str(); }
int deposit() const { return m_deposit; } int deposit() const { return m_deposit; }
bytes assemble() const; bytes assemble() const;

39
liblll/CodeFragment.cpp

@ -19,7 +19,6 @@
* @date 2014 * @date 2014
*/ */
#include "Parser.h"
#include "CodeFragment.h" #include "CodeFragment.h"
#include <boost/algorithm/string.hpp> #include <boost/algorithm/string.hpp>
@ -27,12 +26,30 @@
#include <libethential/Log.h> #include <libethential/Log.h>
#include <libevmface/Instruction.h> #include <libevmface/Instruction.h>
#include "CompilerState.h" #include "CompilerState.h"
#include "Parser.h"
using namespace std; using namespace std;
using namespace eth; using namespace eth;
namespace qi = boost::spirit::qi; namespace qi = boost::spirit::qi;
namespace px = boost::phoenix; namespace px = boost::phoenix;
namespace sp = boost::spirit; namespace sp = boost::spirit;
void CodeFragment::finalise(CompilerState const& _cs)
{
if (_cs.usedAlloc && _cs.vars.size() && !m_finalised)
{
m_finalised = true;
m_asm.injectStart(Instruction::MSTORE8);
m_asm.injectStart((u256)((_cs.vars.size() + 2) * 32) - 1);
m_asm.injectStart((u256)1);
}
}
bytes CodeFragment::code(CompilerState const& _cs)
{
finalise(_cs);
return m_asm.assemble();
}
CodeFragment::CodeFragment(sp::utree const& _t, CompilerState& _s, bool _allowASM) CodeFragment::CodeFragment(sp::utree const& _t, CompilerState& _s, bool _allowASM)
{ {
/* cdebug << "CodeFragment. Locals:"; /* cdebug << "CodeFragment. Locals:";
@ -317,6 +334,7 @@ void CodeFragment::constructOperation(sp::utree const& _t, CompilerState& _s)
vector<CodeFragment> code; vector<CodeFragment> code;
CompilerState ns = _s; CompilerState ns = _s;
ns.vars.clear(); ns.vars.clear();
ns.usedAlloc = false;
int c = _t.tag() ? 1 : 0; int c = _t.tag() ? 1 : 0;
for (auto const& i: _t) for (auto const& i: _t)
if (c++) if (c++)
@ -456,13 +474,30 @@ void CodeFragment::constructOperation(sp::utree const& _t, CompilerState& _s)
m_asm.appendJump(begin); m_asm.appendJump(begin);
m_asm << end.tag(); m_asm << end.tag();
} }
else if (us == "ALLOC")
{
requireSize(1);
requireDeposit(0, 1);
m_asm.append(Instruction::MEMSIZE);
m_asm.append(u256(0));
m_asm.append(u256(1));
m_asm.append(code[0].m_asm, 1);
m_asm.append(Instruction::MEMSIZE);
m_asm.append(Instruction::ADD);
m_asm.append(Instruction::SUB);
m_asm.append(Instruction::MSTORE8);
_s.usedAlloc = true;
}
else if (us == "LLL") else if (us == "LLL")
{ {
requireMinSize(2); requireMinSize(2);
requireMaxSize(3); requireMaxSize(3);
requireDeposit(1, 1); requireDeposit(1, 1);
bytes const& subcode = code[0].code(); code[0].optimise();
bytes subcode = code[0].code(ns);
m_asm.append((u256)subcode.size()); m_asm.append((u256)subcode.size());
m_asm.append(Instruction::DUP); m_asm.append(Instruction::DUP);

7
liblll/CodeFragment.h

@ -43,18 +43,21 @@ public:
static CodeFragment compile(std::string const& _src, CompilerState& _s); static CodeFragment compile(std::string const& _src, CompilerState& _s);
/// Consolidates data and compiles code. /// Consolidates data and compiles code.
bytes code() const { return m_asm.assemble(); } bytes code(CompilerState const& _cs);
/// Consolidates data and compiles code. /// Consolidates data and compiles code.
std::string assembly() const { return m_asm.out(); } std::string assembly(CompilerState const& _cs) { finalise(_cs); return m_asm.out(); }
/// Optimise the code. Best do this just before calling code() or assembly(). /// Optimise the code. Best do this just before calling code() or assembly().
void optimise() { m_asm.optimise(); } void optimise() { m_asm.optimise(); }
private: private:
void finalise(CompilerState const& _cs);
template <class T> void error() const { throw T(); } template <class T> void error() const { throw T(); }
void constructOperation(sp::utree const& _t, CompilerState& _s); void constructOperation(sp::utree const& _t, CompilerState& _s);
bool m_finalised = false;
Assembly m_asm; Assembly m_asm;
}; };

4
liblll/Compiler.cpp

@ -36,7 +36,7 @@ bytes eth::compileLLL(string const& _src, bool _opt, vector<string>* _errors)
auto f = CodeFragment::compile(_src, cs); auto f = CodeFragment::compile(_src, cs);
if (_opt) if (_opt)
f.optimise(); f.optimise();
bytes ret = f.code(); bytes ret = f.code(cs);
for (auto i: cs.treesToKill) for (auto i: cs.treesToKill)
killBigints(i); killBigints(i);
return ret; return ret;
@ -63,7 +63,7 @@ std::string eth::compileLLLToAsm(std::string const& _src, bool _opt, std::vector
auto f = CodeFragment::compile(_src, cs); auto f = CodeFragment::compile(_src, cs);
if (_opt) if (_opt)
f.optimise(); f.optimise();
string ret = f.assembly(); string ret = f.assembly(cs);
for (auto i: cs.treesToKill) for (auto i: cs.treesToKill)
killBigints(i); killBigints(i);
return ret; return ret;

3
liblll/CompilerState.cpp

@ -52,8 +52,7 @@ void CompilerState::populateStandard()
"(def 'regname (name) { [0]:name (call (- (gas) 21) namereg 0 0 32 0 0) })" "(def 'regname (name) { [0]:name (call (- (gas) 21) namereg 0 0 32 0 0) })"
"(def 'send (to value) (call (- (gas) 21) to value 0 0 0 0))" "(def 'send (to value) (call (- (gas) 21) to value 0 0 0 0))"
"(def 'send (gaslimit to value) (call gaslimit to value 0 0 0 0))" "(def 'send (gaslimit to value) (call gaslimit to value 0 0 0 0))"
"(def 'alloc (len) (asm msize 0 1 len msize add sub mstore8))" "(def 'msg (gaslimit to value data datasize outsize) { (set x outsize) (set y (alloc @32)) (call gaslimit to value data datasize @0 @32) @0 })"
"(def 'msg (gaslimit to value data datasize outsize) { [32]:outsize [0]:(alloc @32) (call gaslimit to value data datasize @0 @32) @0 })"
"(def 'msg (gaslimit to value data datasize) { (call gaslimit to value data datasize 0 32) @0 })" "(def 'msg (gaslimit to value data datasize) { (call gaslimit to value data datasize 0 32) @0 })"
"(def 'msg (gaslimit to value data) { [0]:data (msg gaslimit to value 0 32) })" "(def 'msg (gaslimit to value data) { [0]:data (msg gaslimit to value 0 32) })"
"(def 'msg (to value data) { [0]:data (msg 0 to value 0 32) })" "(def 'msg (to value data) { [0]:data (msg 0 to value 0 32) })"

1
liblll/CompilerState.h

@ -48,6 +48,7 @@ struct CompilerState
std::map<std::string, CodeFragment> outers; std::map<std::string, CodeFragment> outers;
std::map<std::pair<std::string, unsigned>, Macro> macros; std::map<std::pair<std::string, unsigned>, Macro> macros;
std::vector<boost::spirit::utree> treesToKill; std::vector<boost::spirit::utree> treesToKill;
bool usedAlloc = false;
}; };
} }

2
sc/cmdline.cpp

@ -10,7 +10,7 @@ int main(int argv, char** argc) {
if (argv == 1) { if (argv == 1) {
std::cerr << "Must provide a command and arguments! Try parse, rewrite, compile, assemble\n"; std::cerr << "Must provide a command and arguments! Try parse, rewrite, compile, assemble\n";
return 0; return 0;
} }
std::string flag = ""; std::string flag = "";
std::string command = argc[1]; std::string command = argc[1];
std::string input; std::string input;

Loading…
Cancel
Save