diff options
Diffstat (limited to 'libsolidity')
-rw-r--r-- | libsolidity/analysis/TypeChecker.cpp | 2 | ||||
-rw-r--r-- | libsolidity/ast/AST.h | 2 | ||||
-rw-r--r-- | libsolidity/codegen/ArrayUtils.cpp | 434 | ||||
-rw-r--r-- | libsolidity/codegen/Compiler.cpp | 90 | ||||
-rw-r--r-- | libsolidity/codegen/CompilerContext.cpp | 4 | ||||
-rw-r--r-- | libsolidity/codegen/CompilerContext.h | 4 | ||||
-rw-r--r-- | libsolidity/codegen/CompilerUtils.cpp | 150 | ||||
-rw-r--r-- | libsolidity/codegen/ExpressionCompiler.cpp | 242 | ||||
-rw-r--r-- | libsolidity/codegen/LValue.cpp | 156 | ||||
-rw-r--r-- | libsolidity/inlineasm/AsmCodeGen.cpp | 11 | ||||
-rw-r--r-- | libsolidity/inlineasm/AsmData.h | 4 | ||||
-rw-r--r-- | libsolidity/inlineasm/AsmParser.cpp | 23 | ||||
-rw-r--r-- | libsolidity/interface/GasEstimator.cpp | 6 |
13 files changed, 564 insertions, 564 deletions
diff --git a/libsolidity/analysis/TypeChecker.cpp b/libsolidity/analysis/TypeChecker.cpp index c63b6b5a..bc342b58 100644 --- a/libsolidity/analysis/TypeChecker.cpp +++ b/libsolidity/analysis/TypeChecker.cpp @@ -595,7 +595,7 @@ bool TypeChecker::visit(InlineAssembly const& _inlineAssembly) if (!varDecl->isLocalVariable()) return false; // only local variables are inline-assemlby lvalues for (unsigned i = 0; i < declaration->type()->sizeOnStack(); ++i) - _assembly.append(eth::Instruction::POP); // remove value just to verify the stack height + _assembly.append(Instruction::POP); // remove value just to verify the stack height } else return false; diff --git a/libsolidity/ast/AST.h b/libsolidity/ast/AST.h index 7bb2529a..bf275869 100644 --- a/libsolidity/ast/AST.h +++ b/libsolidity/ast/AST.h @@ -28,7 +28,7 @@ #include <memory> #include <boost/noncopyable.hpp> #include <libevmasm/SourceLocation.h> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> #include <libsolidity/interface/Utils.h> #include <libsolidity/ast/ASTForward.h> #include <libsolidity/parsing/Token.h> diff --git a/libsolidity/codegen/ArrayUtils.cpp b/libsolidity/codegen/ArrayUtils.cpp index f1acce31..8e568be5 100644 --- a/libsolidity/codegen/ArrayUtils.cpp +++ b/libsolidity/codegen/ArrayUtils.cpp @@ -21,7 +21,7 @@ */ #include <libsolidity/codegen/ArrayUtils.h> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> #include <libsolidity/codegen/CompilerContext.h> #include <libsolidity/codegen/CompilerUtils.h> #include <libsolidity/ast/Types.h> @@ -56,7 +56,7 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons // stack: source_ref [source_length] target_ref // store target_ref for (unsigned i = _sourceType.sizeOnStack(); i > 0; --i) - m_context << eth::swapInstruction(i); + m_context << swapInstruction(i); // stack: target_ref source_ref [source_length] // stack: target_ref source_ref [source_length] // retrieve source length @@ -65,12 +65,12 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons if (_sourceType.location() == DataLocation::Memory && _sourceType.isDynamicallySized()) { // increment source pointer to point to data - m_context << eth::Instruction::SWAP1 << u256(0x20); - m_context << eth::Instruction::ADD << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1 << u256(0x20); + m_context << Instruction::ADD << Instruction::SWAP1; } // stack: target_ref source_ref source_length - m_context << eth::Instruction::DUP3; + m_context << Instruction::DUP3; // stack: target_ref source_ref source_length target_ref retrieveLength(_targetType); // stack: target_ref source_ref source_length target_ref target_length @@ -78,28 +78,28 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons // store new target length if (!_targetType.isByteArray()) // Otherwise, length will be stored below. - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP3 << eth::Instruction::SSTORE; + m_context << Instruction::DUP3 << Instruction::DUP3 << Instruction::SSTORE; if (sourceBaseType->category() == Type::Category::Mapping) { solAssert(targetBaseType->category() == Type::Category::Mapping, ""); solAssert(_sourceType.location() == DataLocation::Storage, ""); // nothing to copy m_context - << eth::Instruction::POP << eth::Instruction::POP - << eth::Instruction::POP << eth::Instruction::POP; + << Instruction::POP << Instruction::POP + << Instruction::POP << Instruction::POP; return; } // stack: target_ref source_ref source_length target_ref target_length // compute hashes (data positions) - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; if (_targetType.isDynamicallySized()) CompilerUtils(m_context).computeHashStatic(); // stack: target_ref source_ref source_length target_length target_data_pos - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; convertLengthToSize(_targetType); - m_context << eth::Instruction::DUP2 << eth::Instruction::ADD; + m_context << Instruction::DUP2 << Instruction::ADD; // stack: target_ref source_ref source_length target_data_pos target_data_end - m_context << eth::Instruction::SWAP3; + m_context << Instruction::SWAP3; // stack: target_ref target_data_end source_length target_data_pos source_ref eth::AssemblyItem copyLoopEndWithoutByteOffset = m_context.newTag(); @@ -108,47 +108,47 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons if (_targetType.isByteArray()) { // stack: target_ref target_data_end source_length target_data_pos source_ref - m_context << eth::Instruction::DUP3 << u256(31) << eth::Instruction::LT; + m_context << Instruction::DUP3 << u256(31) << Instruction::LT; eth::AssemblyItem longByteArray = m_context.appendConditionalJump(); // store the short byte array solAssert(_sourceType.isByteArray(), ""); if (_sourceType.location() == DataLocation::Storage) { // just copy the slot, it contains length and data - m_context << eth::Instruction::DUP1 << eth::Instruction::SLOAD; - m_context << eth::Instruction::DUP6 << eth::Instruction::SSTORE; + m_context << Instruction::DUP1 << Instruction::SLOAD; + m_context << Instruction::DUP6 << Instruction::SSTORE; } else { - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; CompilerUtils(m_context).loadFromMemoryDynamic(*sourceBaseType, fromCalldata, true, false); // stack: target_ref target_data_end source_length target_data_pos source_ref value // clear the lower-order byte - which will hold the length - m_context << u256(0xff) << eth::Instruction::NOT << eth::Instruction::AND; + m_context << u256(0xff) << Instruction::NOT << Instruction::AND; // fetch the length and shift it left by one - m_context << eth::Instruction::DUP4 << eth::Instruction::DUP1 << eth::Instruction::ADD; + m_context << Instruction::DUP4 << Instruction::DUP1 << Instruction::ADD; // combine value and length and store them - m_context << eth::Instruction::OR << eth::Instruction::DUP6 << eth::Instruction::SSTORE; + m_context << Instruction::OR << Instruction::DUP6 << Instruction::SSTORE; } // end of special case, jump right into cleaning target data area m_context.appendJumpTo(copyLoopEndWithoutByteOffset); m_context << longByteArray; // Store length (2*length+1) - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP1 << eth::Instruction::ADD; - m_context << u256(1) << eth::Instruction::ADD; - m_context << eth::Instruction::DUP6 << eth::Instruction::SSTORE; + m_context << Instruction::DUP3 << Instruction::DUP1 << Instruction::ADD; + m_context << u256(1) << Instruction::ADD; + m_context << Instruction::DUP6 << Instruction::SSTORE; } // skip copying if source length is zero - m_context << eth::Instruction::DUP3 << eth::Instruction::ISZERO; + m_context << Instruction::DUP3 << Instruction::ISZERO; m_context.appendConditionalJumpTo(copyLoopEndWithoutByteOffset); if (_sourceType.location() == DataLocation::Storage && _sourceType.isDynamicallySized()) CompilerUtils(m_context).computeHashStatic(); // stack: target_ref target_data_end source_length target_data_pos source_data_pos - m_context << eth::Instruction::SWAP2; + m_context << Instruction::SWAP2; convertLengthToSize(_sourceType); - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << Instruction::DUP3 << Instruction::ADD; // stack: target_ref target_data_end source_data_pos target_data_pos source_data_end if (haveByteOffsetTarget) m_context << u256(0); @@ -159,8 +159,8 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons m_context << copyLoopStart; // check for loop condition m_context - << eth::dupInstruction(3 + byteOffsetSize) << eth::dupInstruction(2 + byteOffsetSize) - << eth::Instruction::GT << eth::Instruction::ISZERO; + << dupInstruction(3 + byteOffsetSize) << dupInstruction(2 + byteOffsetSize) + << Instruction::GT << Instruction::ISZERO; eth::AssemblyItem copyLoopEnd = m_context.appendConditionalJump(); // stack: target_ref target_data_end source_data_pos target_data_pos source_data_end [target_byte_offset] [source_byte_offset] // copy @@ -168,19 +168,19 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons { solAssert(byteOffsetSize == 0, "Byte offset for array as base type."); auto const& sourceBaseArrayType = dynamic_cast<ArrayType const&>(*sourceBaseType); - m_context << eth::Instruction::DUP3; + m_context << Instruction::DUP3; if (sourceBaseArrayType.location() == DataLocation::Memory) - m_context << eth::Instruction::MLOAD; - m_context << eth::Instruction::DUP3; + m_context << Instruction::MLOAD; + m_context << Instruction::DUP3; copyArrayToStorage(dynamic_cast<ArrayType const&>(*targetBaseType), sourceBaseArrayType); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else if (directCopy) { solAssert(byteOffsetSize == 0, "Byte offset for direct copy."); m_context - << eth::Instruction::DUP3 << eth::Instruction::SLOAD - << eth::Instruction::DUP3 << eth::Instruction::SSTORE; + << Instruction::DUP3 << Instruction::SLOAD + << Instruction::DUP3 << Instruction::SSTORE; } else { @@ -188,11 +188,11 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons // We might copy too much if there is padding at the last element, but this way end // checking is easier. // stack: target_ref target_data_end source_data_pos target_data_pos source_data_end [target_byte_offset] [source_byte_offset] - m_context << eth::dupInstruction(3 + byteOffsetSize); + m_context << dupInstruction(3 + byteOffsetSize); if (_sourceType.location() == DataLocation::Storage) { if (haveByteOffsetSource) - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP2; else m_context << u256(0); StorageItem(m_context, *sourceBaseType).retrieveValue(SourceLocation(), true); @@ -207,9 +207,9 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons "Stack too deep, try removing local variables." ); // fetch target storage reference - m_context << eth::dupInstruction(2 + byteOffsetSize + sourceBaseType->sizeOnStack()); + m_context << dupInstruction(2 + byteOffsetSize + sourceBaseType->sizeOnStack()); if (haveByteOffsetTarget) - m_context << eth::dupInstruction(1 + byteOffsetSize + sourceBaseType->sizeOnStack()); + m_context << dupInstruction(1 + byteOffsetSize + sourceBaseType->sizeOnStack()); else m_context << u256(0); StorageItem(m_context, *targetBaseType).storeValue(*sourceBaseType, SourceLocation(), true); @@ -220,7 +220,7 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons incrementByteOffset(sourceBaseType->storageBytes(), 1, haveByteOffsetTarget ? 5 : 4); else { - m_context << eth::swapInstruction(2 + byteOffsetSize); + m_context << swapInstruction(2 + byteOffsetSize); if (sourceIsStorage) m_context << sourceBaseType->storageSize(); else if (_sourceType.location() == DataLocation::Memory) @@ -228,44 +228,44 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons else m_context << sourceBaseType->calldataEncodedSize(true); m_context - << eth::Instruction::ADD - << eth::swapInstruction(2 + byteOffsetSize); + << Instruction::ADD + << swapInstruction(2 + byteOffsetSize); } // increment target if (haveByteOffsetTarget) incrementByteOffset(targetBaseType->storageBytes(), byteOffsetSize, byteOffsetSize + 2); else m_context - << eth::swapInstruction(1 + byteOffsetSize) + << swapInstruction(1 + byteOffsetSize) << targetBaseType->storageSize() - << eth::Instruction::ADD - << eth::swapInstruction(1 + byteOffsetSize); + << Instruction::ADD + << swapInstruction(1 + byteOffsetSize); m_context.appendJumpTo(copyLoopStart); m_context << copyLoopEnd; if (haveByteOffsetTarget) { // clear elements that might be left over in the current slot in target // stack: target_ref target_data_end source_data_pos target_data_pos source_data_end target_byte_offset [source_byte_offset] - m_context << eth::dupInstruction(byteOffsetSize) << eth::Instruction::ISZERO; + m_context << dupInstruction(byteOffsetSize) << Instruction::ISZERO; eth::AssemblyItem copyCleanupLoopEnd = m_context.appendConditionalJump(); - m_context << eth::dupInstruction(2 + byteOffsetSize) << eth::dupInstruction(1 + byteOffsetSize); + m_context << dupInstruction(2 + byteOffsetSize) << dupInstruction(1 + byteOffsetSize); StorageItem(m_context, *targetBaseType).setToZero(SourceLocation(), true); incrementByteOffset(targetBaseType->storageBytes(), byteOffsetSize, byteOffsetSize + 2); m_context.appendJumpTo(copyLoopEnd); m_context << copyCleanupLoopEnd; - m_context << eth::Instruction::POP; // might pop the source, but then target is popped next + m_context << Instruction::POP; // might pop the source, but then target is popped next } if (haveByteOffsetSource) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; m_context << copyLoopEndWithoutByteOffset; // zero-out leftovers in target // stack: target_ref target_data_end source_data_pos target_data_pos_updated source_data_end - m_context << eth::Instruction::POP << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::POP << Instruction::SWAP1 << Instruction::POP; // stack: target_ref target_data_end target_data_pos_updated clearStorageLoop(*targetBaseType); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWordBoundaries) const @@ -285,13 +285,13 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord if (!_sourceType.isDynamicallySized()) m_context << _sourceType.length(); if (baseSize > 1) - m_context << u256(baseSize) << eth::Instruction::MUL; + m_context << u256(baseSize) << Instruction::MUL; // stack: target source_offset source_len - m_context << eth::Instruction::DUP1 << eth::Instruction::DUP3 << eth::Instruction::DUP5; + m_context << Instruction::DUP1 << Instruction::DUP3 << Instruction::DUP5; // stack: target source_offset source_len source_len source_offset target - m_context << eth::Instruction::CALLDATACOPY; - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP2 << eth::Instruction::POP << eth::Instruction::POP; + m_context << Instruction::CALLDATACOPY; + m_context << Instruction::DUP3 << Instruction::ADD; + m_context << Instruction::SWAP2 << Instruction::POP << Instruction::POP; } else if (_sourceType.location() == DataLocation::Memory) { @@ -300,25 +300,25 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord if (!_sourceType.baseType()->isValueType()) { // copy using a loop - m_context << u256(0) << eth::Instruction::SWAP3; + m_context << u256(0) << Instruction::SWAP3; // stack: counter source length target auto repeat = m_context.newTag(); m_context << repeat; - m_context << eth::Instruction::DUP2 << eth::Instruction::DUP5; - m_context << eth::Instruction::LT << eth::Instruction::ISZERO; + m_context << Instruction::DUP2 << Instruction::DUP5; + m_context << Instruction::LT << Instruction::ISZERO; auto loopEnd = m_context.appendConditionalJump(); - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP5; + m_context << Instruction::DUP3 << Instruction::DUP5; accessIndex(_sourceType, false); MemoryItem(m_context, *_sourceType.baseType(), true).retrieveValue(SourceLocation(), true); if (auto baseArray = dynamic_cast<ArrayType const*>(_sourceType.baseType().get())) copyArrayToMemory(*baseArray, _padToWordBoundaries); else utils.storeInMemoryDynamic(*_sourceType.baseType()); - m_context << eth::Instruction::SWAP3 << u256(1) << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP3; + m_context << Instruction::SWAP3 << u256(1) << Instruction::ADD; + m_context << Instruction::SWAP3; m_context.appendJumpTo(repeat); m_context << loopEnd; - m_context << eth::Instruction::SWAP3; + m_context << Instruction::SWAP3; utils.popStackSlots(3); // stack: updated_target_pos return; @@ -328,18 +328,18 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord if (_sourceType.isDynamicallySized()) { // change pointer to data part - m_context << eth::Instruction::SWAP1 << u256(32) << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1 << u256(32) << Instruction::ADD; + m_context << Instruction::SWAP1; } // convert length to size if (baseSize > 1) - m_context << u256(baseSize) << eth::Instruction::MUL; + m_context << u256(baseSize) << Instruction::MUL; // stack: <target> <source> <size> //@TODO do not use ::CALL if less than 32 bytes? - m_context << eth::Instruction::DUP1 << eth::Instruction::DUP4 << eth::Instruction::DUP4; + m_context << Instruction::DUP1 << Instruction::DUP4 << Instruction::DUP4; utils.memoryCopy(); - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; // stack: <target> <size> bool paddingNeeded = false; @@ -350,43 +350,43 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord if (paddingNeeded) { // stack: <target> <size> - m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP2 << eth::Instruction::ADD; + m_context << Instruction::SWAP1 << Instruction::DUP2 << Instruction::ADD; // stack: <length> <target + size> - m_context << eth::Instruction::SWAP1 << u256(31) << eth::Instruction::AND; + m_context << Instruction::SWAP1 << u256(31) << Instruction::AND; // stack: <target + size> <remainder = size % 32> eth::AssemblyItem skip = m_context.newTag(); if (_sourceType.isDynamicallySized()) { - m_context << eth::Instruction::DUP1 << eth::Instruction::ISZERO; + m_context << Instruction::DUP1 << Instruction::ISZERO; m_context.appendConditionalJumpTo(skip); } // round off, load from there. // stack <target + size> <remainder = size % 32> - m_context << eth::Instruction::DUP1 << eth::Instruction::DUP3; - m_context << eth::Instruction::SUB; + m_context << Instruction::DUP1 << Instruction::DUP3; + m_context << Instruction::SUB; // stack: target+size remainder <target + size - remainder> - m_context << eth::Instruction::DUP1 << eth::Instruction::MLOAD; + m_context << Instruction::DUP1 << Instruction::MLOAD; // Now we AND it with ~(2**(8 * (32 - remainder)) - 1) m_context << u256(1); - m_context << eth::Instruction::DUP4 << u256(32) << eth::Instruction::SUB; + m_context << Instruction::DUP4 << u256(32) << Instruction::SUB; // stack: ...<v> 1 <32 - remainder> - m_context << u256(0x100) << eth::Instruction::EXP << eth::Instruction::SUB; - m_context << eth::Instruction::NOT << eth::Instruction::AND; + m_context << u256(0x100) << Instruction::EXP << Instruction::SUB; + m_context << Instruction::NOT << Instruction::AND; // stack: target+size remainder target+size-remainder <v & ...> - m_context << eth::Instruction::DUP2 << eth::Instruction::MSTORE; + m_context << Instruction::DUP2 << Instruction::MSTORE; // stack: target+size remainder target+size-remainder - m_context << u256(32) << eth::Instruction::ADD; + m_context << u256(32) << Instruction::ADD; // stack: target+size remainder <new_padded_end> - m_context << eth::Instruction::SWAP2 << eth::Instruction::POP; + m_context << Instruction::SWAP2 << Instruction::POP; if (_sourceType.isDynamicallySized()) m_context << skip.tag(); // stack <target + "size"> <remainder = size % 32> - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else // stack: <target> <size> - m_context << eth::Instruction::ADD; + m_context << Instruction::ADD; } else { @@ -398,48 +398,48 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord retrieveLength(_sourceType); // stack here: memory_offset storage_offset length // jump to end if length is zero - m_context << eth::Instruction::DUP1 << eth::Instruction::ISZERO; + m_context << Instruction::DUP1 << Instruction::ISZERO; eth::AssemblyItem loopEnd = m_context.appendConditionalJump(); // Special case for tightly-stored byte arrays if (_sourceType.isByteArray()) { // stack here: memory_offset storage_offset length - m_context << eth::Instruction::DUP1 << u256(31) << eth::Instruction::LT; + m_context << Instruction::DUP1 << u256(31) << Instruction::LT; eth::AssemblyItem longByteArray = m_context.appendConditionalJump(); // store the short byte array (discard lower-order byte) - m_context << u256(0x100) << eth::Instruction::DUP1; - m_context << eth::Instruction::DUP4 << eth::Instruction::SLOAD; - m_context << eth::Instruction::DIV << eth::Instruction::MUL; - m_context << eth::Instruction::DUP4 << eth::Instruction::MSTORE; + m_context << u256(0x100) << Instruction::DUP1; + m_context << Instruction::DUP4 << Instruction::SLOAD; + m_context << Instruction::DIV << Instruction::MUL; + m_context << Instruction::DUP4 << Instruction::MSTORE; // stack here: memory_offset storage_offset length // add 32 or length to memory offset - m_context << eth::Instruction::SWAP2; + m_context << Instruction::SWAP2; if (_padToWordBoundaries) m_context << u256(32); else - m_context << eth::Instruction::DUP3; - m_context << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP2; + m_context << Instruction::DUP3; + m_context << Instruction::ADD; + m_context << Instruction::SWAP2; m_context.appendJumpTo(loopEnd); m_context << longByteArray; } // compute memory end offset if (baseSize > 1) // convert length to memory size - m_context << u256(baseSize) << eth::Instruction::MUL; - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD << eth::Instruction::SWAP2; + m_context << u256(baseSize) << Instruction::MUL; + m_context << Instruction::DUP3 << Instruction::ADD << Instruction::SWAP2; if (_sourceType.isDynamicallySized()) { // actual array data is stored at SHA3(storage_offset) - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; utils.computeHashStatic(); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; } // stack here: memory_end_offset storage_data_offset memory_offset bool haveByteOffset = !_sourceType.isByteArray() && storageBytes <= 16; if (haveByteOffset) - m_context << u256(0) << eth::Instruction::SWAP1; + m_context << u256(0) << Instruction::SWAP1; // stack here: memory_end_offset storage_data_offset [storage_byte_offset] memory_offset eth::AssemblyItem loopStart = m_context.newTag(); m_context << loopStart; @@ -447,20 +447,20 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord if (_sourceType.isByteArray()) { // Packed both in storage and memory. - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD; - m_context << eth::Instruction::DUP2 << eth::Instruction::MSTORE; + m_context << Instruction::DUP2 << Instruction::SLOAD; + m_context << Instruction::DUP2 << Instruction::MSTORE; // increment storage_data_offset by 1 - m_context << eth::Instruction::SWAP1 << u256(1) << eth::Instruction::ADD; + m_context << Instruction::SWAP1 << u256(1) << Instruction::ADD; // increment memory offset by 32 - m_context << eth::Instruction::SWAP1 << u256(32) << eth::Instruction::ADD; + m_context << Instruction::SWAP1 << u256(32) << Instruction::ADD; } else { // stack here: memory_end_offset storage_data_offset [storage_byte_offset] memory_offset if (haveByteOffset) - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP3; + m_context << Instruction::DUP3 << Instruction::DUP3; else - m_context << eth::Instruction::DUP2 << u256(0); + m_context << Instruction::DUP2 << u256(0); StorageItem(m_context, *_sourceType.baseType()).retrieveValue(SourceLocation(), true); if (auto baseArray = dynamic_cast<ArrayType const*>(_sourceType.baseType().get())) copyArrayToMemory(*baseArray, _padToWordBoundaries); @@ -471,29 +471,29 @@ void ArrayUtils::copyArrayToMemory(ArrayType const& _sourceType, bool _padToWord incrementByteOffset(storageBytes, 2, 3); else { - m_context << eth::Instruction::SWAP1; - m_context << storageSize << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; + m_context << storageSize << Instruction::ADD; + m_context << Instruction::SWAP1; } } // check for loop condition - m_context << eth::Instruction::DUP1 << eth::dupInstruction(haveByteOffset ? 5 : 4); - m_context << eth::Instruction::GT; + m_context << Instruction::DUP1 << dupInstruction(haveByteOffset ? 5 : 4); + m_context << Instruction::GT; m_context.appendConditionalJumpTo(loopStart); // stack here: memory_end_offset storage_data_offset [storage_byte_offset] memory_offset if (haveByteOffset) - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; if (_padToWordBoundaries && baseSize % 32 != 0) { // memory_end_offset - start is the actual length (we want to compute the ceil of). // memory_offset - start is its next multiple of 32, but it might be off by 32. // so we compute: memory_end_offset += (memory_offset - memory_end_offest) & 31 - m_context << eth::Instruction::DUP3 << eth::Instruction::SWAP1 << eth::Instruction::SUB; - m_context << u256(31) << eth::Instruction::AND; - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP2; + m_context << Instruction::DUP3 << Instruction::SWAP1 << Instruction::SUB; + m_context << u256(31) << Instruction::AND; + m_context << Instruction::DUP3 << Instruction::ADD; + m_context << Instruction::SWAP2; } - m_context << loopEnd << eth::Instruction::POP << eth::Instruction::POP; + m_context << loopEnd << Instruction::POP << Instruction::POP; } } @@ -509,20 +509,20 @@ void ArrayUtils::clearArray(ArrayType const& _type) const if (_type.baseType()->isValueType()) solAssert(_type.baseType()->storageSize() <= 1, "Invalid size for value type."); - m_context << eth::Instruction::POP; // remove byte offset + m_context << Instruction::POP; // remove byte offset if (_type.isDynamicallySized()) clearDynamicArray(_type); else if (_type.length() == 0 || _type.baseType()->category() == Type::Category::Mapping) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; else if (_type.baseType()->isValueType() && _type.storageSize() <= 5) { // unroll loop for small arrays @todo choose a good value // Note that we loop over storage slots here, not elements. for (unsigned i = 1; i < _type.storageSize(); ++i) m_context - << u256(0) << eth::Instruction::DUP2 << eth::Instruction::SSTORE - << u256(1) << eth::Instruction::ADD; - m_context << u256(0) << eth::Instruction::SWAP1 << eth::Instruction::SSTORE; + << u256(0) << Instruction::DUP2 << Instruction::SSTORE + << u256(1) << Instruction::ADD; + m_context << u256(0) << Instruction::SWAP1 << Instruction::SSTORE; } else if (!_type.baseType()->isValueType() && _type.length() <= 4) { @@ -533,22 +533,22 @@ void ArrayUtils::clearArray(ArrayType const& _type) const m_context << u256(0); StorageItem(m_context, *_type.baseType()).setToZero(SourceLocation(), false); m_context - << eth::Instruction::POP - << u256(_type.baseType()->storageSize()) << eth::Instruction::ADD; + << Instruction::POP + << u256(_type.baseType()->storageSize()) << Instruction::ADD; } m_context << u256(0); StorageItem(m_context, *_type.baseType()).setToZero(SourceLocation(), true); } else { - m_context << eth::Instruction::DUP1 << _type.length(); + m_context << Instruction::DUP1 << _type.length(); convertLengthToSize(_type); - m_context << eth::Instruction::ADD << eth::Instruction::SWAP1; + m_context << Instruction::ADD << Instruction::SWAP1; if (_type.baseType()->storageBytes() < 32) clearStorageLoop(IntegerType(256)); else clearStorageLoop(*_type.baseType()); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } solAssert(m_context.stackHeight() == stackHeightStart - 2, ""); } @@ -561,15 +561,15 @@ void ArrayUtils::clearDynamicArray(ArrayType const& _type) const // fetch length retrieveLength(_type); // set length to zero - m_context << u256(0) << eth::Instruction::DUP3 << eth::Instruction::SSTORE; + m_context << u256(0) << Instruction::DUP3 << Instruction::SSTORE; // Special case: short byte arrays are stored togeher with their length eth::AssemblyItem endTag = m_context.newTag(); if (_type.isByteArray()) { // stack: ref old_length - m_context << eth::Instruction::DUP1 << u256(31) << eth::Instruction::LT; + m_context << Instruction::DUP1 << u256(31) << Instruction::LT; eth::AssemblyItem longByteArray = m_context.appendConditionalJump(); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; m_context.appendJumpTo(endTag); m_context.adjustStackOffset(1); // needed because of jump m_context << longByteArray; @@ -577,11 +577,11 @@ void ArrayUtils::clearDynamicArray(ArrayType const& _type) const // stack: ref old_length convertLengthToSize(_type); // compute data positions - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; CompilerUtils(m_context).computeHashStatic(); // stack: len data_pos - m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP2 << eth::Instruction::ADD - << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1 << Instruction::DUP2 << Instruction::ADD + << Instruction::SWAP1; // stack: data_pos_end data_pos if (_type.isByteArray() || _type.baseType()->storageBytes() < 32) clearStorageLoop(IntegerType(256)); @@ -589,7 +589,7 @@ void ArrayUtils::clearDynamicArray(ArrayType const& _type) const clearStorageLoop(*_type.baseType()); // cleanup m_context << endTag; - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } void ArrayUtils::resizeDynamicArray(ArrayType const& _type) const @@ -614,13 +614,13 @@ void ArrayUtils::resizeDynamicArray(ArrayType const& _type) const eth::AssemblyItem regularPath = m_context.newTag(); // We start by a large case-distinction about the old and new length of the byte array. - m_context << eth::Instruction::DUP3 << eth::Instruction::SLOAD; + m_context << Instruction::DUP3 << Instruction::SLOAD; // stack: ref new_length current_length ref_value solAssert(m_context.stackHeight() - stackHeightStart == 4 - 2, "3"); - m_context << eth::Instruction::DUP2 << u256(31) << eth::Instruction::LT; + m_context << Instruction::DUP2 << u256(31) << Instruction::LT; eth::AssemblyItem currentIsLong = m_context.appendConditionalJump(); - m_context << eth::Instruction::DUP3 << u256(31) << eth::Instruction::LT; + m_context << Instruction::DUP3 << u256(31) << Instruction::LT; eth::AssemblyItem newIsLong = m_context.appendConditionalJump(); // Here: short -> short @@ -628,17 +628,17 @@ void ArrayUtils::resizeDynamicArray(ArrayType const& _type) const // Compute 1 << (256 - 8 * new_size) eth::AssemblyItem shortToShort = m_context.newTag(); m_context << shortToShort; - m_context << eth::Instruction::DUP3 << u256(8) << eth::Instruction::MUL; - m_context << u256(0x100) << eth::Instruction::SUB; - m_context << u256(2) << eth::Instruction::EXP; + m_context << Instruction::DUP3 << u256(8) << Instruction::MUL; + m_context << u256(0x100) << Instruction::SUB; + m_context << u256(2) << Instruction::EXP; // Divide and multiply by that value, clearing bits. - m_context << eth::Instruction::DUP1 << eth::Instruction::SWAP2; - m_context << eth::Instruction::DIV << eth::Instruction::MUL; + m_context << Instruction::DUP1 << Instruction::SWAP2; + m_context << Instruction::DIV << Instruction::MUL; // Insert 2*length. - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP1 << eth::Instruction::ADD; - m_context << eth::Instruction::OR; + m_context << Instruction::DUP3 << Instruction::DUP1 << Instruction::ADD; + m_context << Instruction::OR; // Store. - m_context << eth::Instruction::DUP4 << eth::Instruction::SSTORE; + m_context << Instruction::DUP4 << Instruction::SSTORE; solAssert(m_context.stackHeight() - stackHeightStart == 3 - 2, "3"); m_context.appendJumpTo(resizeEnd); @@ -649,24 +649,24 @@ void ArrayUtils::resizeDynamicArray(ArrayType const& _type) const // stack: ref new_length current_length ref_value solAssert(m_context.stackHeight() - stackHeightStart == 4 - 2, "3"); // Zero out lower-order byte. - m_context << u256(0xff) << eth::Instruction::NOT << eth::Instruction::AND; + m_context << u256(0xff) << Instruction::NOT << Instruction::AND; // Store at data location. - m_context << eth::Instruction::DUP4; + m_context << Instruction::DUP4; CompilerUtils(m_context).computeHashStatic(); - m_context << eth::Instruction::SSTORE; + m_context << Instruction::SSTORE; // stack: ref new_length current_length // Store new length: Compule 2*length + 1 and store it. - m_context << eth::Instruction::DUP2 << eth::Instruction::DUP1 << eth::Instruction::ADD; - m_context << u256(1) << eth::Instruction::ADD; + m_context << Instruction::DUP2 << Instruction::DUP1 << Instruction::ADD; + m_context << u256(1) << Instruction::ADD; // stack: ref new_length current_length 2*new_length+1 - m_context << eth::Instruction::DUP4 << eth::Instruction::SSTORE; + m_context << Instruction::DUP4 << Instruction::SSTORE; solAssert(m_context.stackHeight() - stackHeightStart == 3 - 2, "3"); m_context.appendJumpTo(resizeEnd); m_context.adjustStackOffset(1); // we have to do that because of the jumps m_context << currentIsLong; - m_context << eth::Instruction::DUP3 << u256(31) << eth::Instruction::LT; + m_context << Instruction::DUP3 << u256(31) << Instruction::LT; m_context.appendConditionalJumpTo(regularPath); // Here: long -> short @@ -675,51 +675,51 @@ void ArrayUtils::resizeDynamicArray(ArrayType const& _type) const // stack: ref new_length current_length ref_value solAssert(m_context.stackHeight() - stackHeightStart == 4 - 2, "3"); - m_context << eth::Instruction::POP << eth::Instruction::DUP3; + m_context << Instruction::POP << Instruction::DUP3; CompilerUtils(m_context).computeHashStatic(); - m_context << eth::Instruction::DUP1 << eth::Instruction::SLOAD << eth::Instruction::SWAP1; + m_context << Instruction::DUP1 << Instruction::SLOAD << Instruction::SWAP1; // stack: ref new_length current_length first_word data_location - m_context << eth::Instruction::DUP3; + m_context << Instruction::DUP3; convertLengthToSize(_type); - m_context << eth::Instruction::DUP2 << eth::Instruction::ADD << eth::Instruction::SWAP1; + m_context << Instruction::DUP2 << Instruction::ADD << Instruction::SWAP1; // stack: ref new_length current_length first_word data_location_end data_location clearStorageLoop(IntegerType(256)); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; // stack: ref new_length current_length first_word solAssert(m_context.stackHeight() - stackHeightStart == 4 - 2, "3"); m_context.appendJumpTo(shortToShort); m_context << regularPath; // stack: ref new_length current_length ref_value - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } // Change of length for a regular array (i.e. length at location, data at sha3(location)). // stack: ref new_length old_length // store new length - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP2; if (_type.isByteArray()) // For a "long" byte array, store length as 2*length+1 - m_context << eth::Instruction::DUP1 << eth::Instruction::ADD << u256(1) << eth::Instruction::ADD; - m_context<< eth::Instruction::DUP4 << eth::Instruction::SSTORE; + m_context << Instruction::DUP1 << Instruction::ADD << u256(1) << Instruction::ADD; + m_context<< Instruction::DUP4 << Instruction::SSTORE; // skip if size is not reduced - m_context << eth::Instruction::DUP2 << eth::Instruction::DUP2 - << eth::Instruction::ISZERO << eth::Instruction::GT; + m_context << Instruction::DUP2 << Instruction::DUP2 + << Instruction::ISZERO << Instruction::GT; m_context.appendConditionalJumpTo(resizeEnd); // size reduced, clear the end of the array // stack: ref new_length old_length convertLengthToSize(_type); - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP2; convertLengthToSize(_type); // stack: ref new_length old_size new_size // compute data positions - m_context << eth::Instruction::DUP4; + m_context << Instruction::DUP4; CompilerUtils(m_context).computeHashStatic(); // stack: ref new_length old_size new_size data_pos - m_context << eth::Instruction::SWAP2 << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << Instruction::SWAP2 << Instruction::DUP3 << Instruction::ADD; // stack: ref new_length data_pos new_size delete_end - m_context << eth::Instruction::SWAP2 << eth::Instruction::ADD; + m_context << Instruction::SWAP2 << Instruction::ADD; // stack: ref new_length delete_end delete_start if (_type.isByteArray() || _type.baseType()->storageBytes() < 32) clearStorageLoop(IntegerType(256)); @@ -728,7 +728,7 @@ void ArrayUtils::resizeDynamicArray(ArrayType const& _type) const m_context << resizeEnd; // cleanup - m_context << eth::Instruction::POP << eth::Instruction::POP << eth::Instruction::POP; + m_context << Instruction::POP << Instruction::POP << Instruction::POP; solAssert(m_context.stackHeight() == stackHeightStart - 2, ""); } @@ -737,35 +737,35 @@ void ArrayUtils::clearStorageLoop(Type const& _type) const unsigned stackHeightStart = m_context.stackHeight(); if (_type.category() == Type::Category::Mapping) { - m_context << eth::Instruction::POP; + m_context << Instruction::POP; return; } // stack: end_pos pos // jump to and return from the loop to allow for duplicate code removal eth::AssemblyItem returnTag = m_context.pushNewTag(); - m_context << eth::Instruction::SWAP2 << eth::Instruction::SWAP1; + m_context << Instruction::SWAP2 << Instruction::SWAP1; // stack: <return tag> end_pos pos eth::AssemblyItem loopStart = m_context.appendJumpToNew(); m_context << loopStart; // check for loop condition - m_context << eth::Instruction::DUP1 << eth::Instruction::DUP3 - << eth::Instruction::GT << eth::Instruction::ISZERO; + m_context << Instruction::DUP1 << Instruction::DUP3 + << Instruction::GT << Instruction::ISZERO; eth::AssemblyItem zeroLoopEnd = m_context.newTag(); m_context.appendConditionalJumpTo(zeroLoopEnd); // delete m_context << u256(0); StorageItem(m_context, _type).setToZero(SourceLocation(), false); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; // increment - m_context << u256(1) << eth::Instruction::ADD; + m_context << u256(1) << Instruction::ADD; m_context.appendJumpTo(loopStart); // cleanup m_context << zeroLoopEnd; - m_context << eth::Instruction::POP << eth::Instruction::SWAP1; + m_context << Instruction::POP << Instruction::SWAP1; // "return" - m_context << eth::Instruction::JUMP; + m_context << Instruction::JUMP; m_context << returnTag; solAssert(m_context.stackHeight() == stackHeightStart - 1, ""); @@ -779,17 +779,17 @@ void ArrayUtils::convertLengthToSize(ArrayType const& _arrayType, bool _pad) con { unsigned baseBytes = _arrayType.baseType()->storageBytes(); if (baseBytes == 0) - m_context << eth::Instruction::POP << u256(1); + m_context << Instruction::POP << u256(1); else if (baseBytes <= 16) { unsigned itemsPerSlot = 32 / baseBytes; m_context - << u256(itemsPerSlot - 1) << eth::Instruction::ADD - << u256(itemsPerSlot) << eth::Instruction::SWAP1 << eth::Instruction::DIV; + << u256(itemsPerSlot - 1) << Instruction::ADD + << u256(itemsPerSlot) << Instruction::SWAP1 << Instruction::DIV; } } else - m_context << _arrayType.baseType()->storageSize() << eth::Instruction::MUL; + m_context << _arrayType.baseType()->storageSize() << Instruction::MUL; } else { @@ -799,12 +799,12 @@ void ArrayUtils::convertLengthToSize(ArrayType const& _arrayType, bool _pad) con m_context << _arrayType.baseType()->memoryHeadSize(); else m_context << _arrayType.baseType()->calldataEncodedSize(); - m_context << eth::Instruction::MUL; + m_context << Instruction::MUL; } else if (_pad) - m_context << u256(31) << eth::Instruction::ADD - << u256(32) << eth::Instruction::DUP1 - << eth::Instruction::SWAP2 << eth::Instruction::DIV << eth::Instruction::MUL; + m_context << u256(31) << Instruction::ADD + << u256(32) << Instruction::DUP1 + << Instruction::SWAP2 << Instruction::DIV << Instruction::MUL; } } @@ -814,27 +814,27 @@ void ArrayUtils::retrieveLength(ArrayType const& _arrayType, unsigned _stackDept m_context << _arrayType.length(); else { - m_context << eth::dupInstruction(1 + _stackDepth); + m_context << dupInstruction(1 + _stackDepth); switch (_arrayType.location()) { case DataLocation::CallData: // length is stored on the stack break; case DataLocation::Memory: - m_context << eth::Instruction::MLOAD; + m_context << Instruction::MLOAD; break; case DataLocation::Storage: - m_context << eth::Instruction::SLOAD; + m_context << Instruction::SLOAD; if (_arrayType.isByteArray()) { // Retrieve length both for in-place strings and off-place strings: // Computes (x & (0x100 * (ISZERO (x & 1)) - 1)) / 2 // i.e. for short strings (x & 1 == 0) it does (x & 0xff) / 2 and for long strings it // computes (x & (-1)) / 2, which is equivalent to just x / 2. - m_context << u256(1) << eth::Instruction::DUP2 << u256(1) << eth::Instruction::AND; - m_context << eth::Instruction::ISZERO << u256(0x100) << eth::Instruction::MUL; - m_context << eth::Instruction::SUB << eth::Instruction::AND; - m_context << u256(2) << eth::Instruction::SWAP1 << eth::Instruction::DIV; + m_context << u256(1) << Instruction::DUP2 << u256(1) << Instruction::AND; + m_context << Instruction::ISZERO << u256(0x100) << Instruction::MUL; + m_context << Instruction::SUB << Instruction::AND; + m_context << u256(2) << Instruction::SWAP1 << Instruction::DIV; } break; } @@ -852,34 +852,34 @@ void ArrayUtils::accessIndex(ArrayType const& _arrayType, bool _doBoundsCheck) c ArrayUtils::retrieveLength(_arrayType, 1); // Stack: ref [length] index length // check out-of-bounds access - m_context << eth::Instruction::DUP2 << eth::Instruction::LT << eth::Instruction::ISZERO; + m_context << Instruction::DUP2 << Instruction::LT << Instruction::ISZERO; // out-of-bounds access throws exception m_context.appendConditionalJumpTo(m_context.errorTag()); } if (location == DataLocation::CallData && _arrayType.isDynamicallySized()) // remove length if present - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; // stack: <base_ref> <index> - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; // stack: <index> <base_ref> switch (location) { case DataLocation::Memory: if (_arrayType.isDynamicallySized()) - m_context << u256(32) << eth::Instruction::ADD; + m_context << u256(32) << Instruction::ADD; // fall-through case DataLocation::CallData: if (!_arrayType.isByteArray()) { - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; if (location == DataLocation::CallData) m_context << _arrayType.baseType()->calldataEncodedSize(); else m_context << u256(_arrayType.memoryHeadSize()); - m_context << eth::Instruction::MUL; + m_context << Instruction::MUL; } - m_context << eth::Instruction::ADD; + m_context << Instruction::ADD; break; case DataLocation::Storage: { @@ -887,16 +887,16 @@ void ArrayUtils::accessIndex(ArrayType const& _arrayType, bool _doBoundsCheck) c if (_arrayType.isByteArray()) { // Special case of short byte arrays. - m_context << eth::Instruction::SWAP1; - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD; - m_context << u256(1) << eth::Instruction::AND << eth::Instruction::ISZERO; + m_context << Instruction::SWAP1; + m_context << Instruction::DUP2 << Instruction::SLOAD; + m_context << u256(1) << Instruction::AND << Instruction::ISZERO; // No action needed for short byte arrays. m_context.appendConditionalJumpTo(endTag); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; } if (_arrayType.isDynamicallySized()) CompilerUtils(m_context).computeHashStatic(); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; if (_arrayType.baseType()->storageBytes() <= 16) { // stack: <data_ref> <index> @@ -905,22 +905,22 @@ void ArrayUtils::accessIndex(ArrayType const& _arrayType, bool _doBoundsCheck) c unsigned byteSize = _arrayType.baseType()->storageBytes(); solAssert(byteSize != 0, ""); unsigned itemsPerSlot = 32 / byteSize; - m_context << u256(itemsPerSlot) << eth::Instruction::SWAP2; + m_context << u256(itemsPerSlot) << Instruction::SWAP2; // stack: itemsPerSlot index data_ref m_context - << eth::Instruction::DUP3 << eth::Instruction::DUP3 - << eth::Instruction::DIV << eth::Instruction::ADD + << Instruction::DUP3 << Instruction::DUP3 + << Instruction::DIV << Instruction::ADD // stack: itemsPerSlot index (data_ref + index / itemsPerSlot) - << eth::Instruction::SWAP2 << eth::Instruction::SWAP1 - << eth::Instruction::MOD; + << Instruction::SWAP2 << Instruction::SWAP1 + << Instruction::MOD; if (byteSize != 1) - m_context << u256(byteSize) << eth::Instruction::MUL; + m_context << u256(byteSize) << Instruction::MUL; } else { if (_arrayType.baseType()->storageSize() != 1) - m_context << _arrayType.baseType()->storageSize() << eth::Instruction::MUL; - m_context << eth::Instruction::ADD << u256(0); + m_context << _arrayType.baseType()->storageSize() << Instruction::MUL; + m_context << Instruction::ADD << u256(0); } m_context << endTag; break; @@ -942,27 +942,27 @@ void ArrayUtils::incrementByteOffset(unsigned _byteSize, unsigned _byteOffsetPos // byteOffset = 0; // } if (_byteOffsetPosition > 1) - m_context << eth::swapInstruction(_byteOffsetPosition - 1); - m_context << u256(_byteSize) << eth::Instruction::ADD; + m_context << swapInstruction(_byteOffsetPosition - 1); + m_context << u256(_byteSize) << Instruction::ADD; if (_byteOffsetPosition > 1) - m_context << eth::swapInstruction(_byteOffsetPosition - 1); + m_context << swapInstruction(_byteOffsetPosition - 1); // compute, X := (byteOffset + byteSize - 1) / 32, should be 1 iff byteOffset + bytesize > 32 m_context - << u256(32) << eth::dupInstruction(1 + _byteOffsetPosition) << u256(_byteSize - 1) - << eth::Instruction::ADD << eth::Instruction::DIV; + << u256(32) << dupInstruction(1 + _byteOffsetPosition) << u256(_byteSize - 1) + << Instruction::ADD << Instruction::DIV; // increment storage offset if X == 1 (just add X to it) // stack: X m_context - << eth::swapInstruction(_storageOffsetPosition) << eth::dupInstruction(_storageOffsetPosition + 1) - << eth::Instruction::ADD << eth::swapInstruction(_storageOffsetPosition); + << swapInstruction(_storageOffsetPosition) << dupInstruction(_storageOffsetPosition + 1) + << Instruction::ADD << swapInstruction(_storageOffsetPosition); // stack: X // set source_byte_offset to zero if X == 1 (using source_byte_offset *= 1 - X) - m_context << u256(1) << eth::Instruction::SUB; + m_context << u256(1) << Instruction::SUB; // stack: 1 - X if (_byteOffsetPosition == 1) - m_context << eth::Instruction::MUL; + m_context << Instruction::MUL; else m_context - << eth::dupInstruction(_byteOffsetPosition + 1) << eth::Instruction::MUL - << eth::swapInstruction(_byteOffsetPosition) << eth::Instruction::POP; + << dupInstruction(_byteOffsetPosition + 1) << Instruction::MUL + << swapInstruction(_byteOffsetPosition) << Instruction::POP; } diff --git a/libsolidity/codegen/Compiler.cpp b/libsolidity/codegen/Compiler.cpp index 69e23359..8b718fca 100644 --- a/libsolidity/codegen/Compiler.cpp +++ b/libsolidity/codegen/Compiler.cpp @@ -23,7 +23,7 @@ #include <libsolidity/codegen/Compiler.h> #include <algorithm> #include <boost/range/adaptor/reversed.hpp> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> #include <libethcore/ChainOperationParams.h> #include <libevmasm/Assembly.h> #include <libsolidity/inlineasm/AsmCodeGen.h> @@ -92,8 +92,8 @@ void Compiler::compileClone( m_runtimeSub = size_t(runtimeSub.data()); // stack contains sub size - m_context << eth::Instruction::DUP1 << runtimeSub << u256(0) << eth::Instruction::CODECOPY; - m_context << u256(0) << eth::Instruction::RETURN; + m_context << Instruction::DUP1 << runtimeSub << u256(0) << Instruction::CODECOPY; + m_context << u256(0) << Instruction::RETURN; appendFunctionsWithoutCode(); @@ -164,8 +164,8 @@ void Compiler::packIntoContractCreator(ContractDefinition const& _contract, Comp m_runtimeSub = size_t(runtimeSub.data()); // stack contains sub size - m_context << eth::Instruction::DUP1 << runtimeSub << u256(0) << eth::Instruction::CODECOPY; - m_context << u256(0) << eth::Instruction::RETURN; + m_context << Instruction::DUP1 << runtimeSub << u256(0) << Instruction::CODECOPY; + m_context << u256(0) << Instruction::RETURN; // note that we have to include the functions again because of absolute jump labels appendFunctionsWithoutCode(); @@ -208,15 +208,15 @@ void Compiler::appendConstructor(FunctionDefinition const& _constructor) // argument size is dynamic, use CODESIZE to determine it m_context.appendProgramSize(); // program itself // CODESIZE is program plus manually added arguments - m_context << eth::Instruction::CODESIZE << eth::Instruction::SUB; + m_context << Instruction::CODESIZE << Instruction::SUB; } else m_context << u256(argumentSize); // stack: <memptr> <argument size> - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; m_context.appendProgramSize(); - m_context << eth::Instruction::DUP4 << eth::Instruction::CODECOPY; - m_context << eth::Instruction::DUP2 << eth::Instruction::ADD; + m_context << Instruction::DUP4 << Instruction::CODECOPY; + m_context << Instruction::DUP2 << Instruction::ADD; CompilerUtils(m_context).storeFreeMemoryPointer(); // stack: <memptr> appendCalldataUnpacker(FunctionType(_constructor).parameterTypes(), true); @@ -235,7 +235,7 @@ void Compiler::appendFunctionSelector(ContractDefinition const& _contract) // ether with constant gas if (interfaceFunctions.size() > 5 || fallback) { - m_context << eth::Instruction::CALLDATASIZE << eth::Instruction::ISZERO; + m_context << Instruction::CALLDATASIZE << Instruction::ISZERO; m_context.appendConditionalJumpTo(notFound); } @@ -247,7 +247,7 @@ void Compiler::appendFunctionSelector(ContractDefinition const& _contract) for (auto const& it: interfaceFunctions) { callDataUnpackerEntryPoints.insert(std::make_pair(it.first, m_context.newTag())); - m_context << eth::dupInstruction(1) << u256(FixedHash<4>::Arith(it.first)) << eth::Instruction::EQ; + m_context << dupInstruction(1) << u256(FixedHash<4>::Arith(it.first)) << Instruction::EQ; m_context.appendConditionalJumpTo(callDataUnpackerEntryPoints.at(it.first)); } m_context.appendJumpTo(notFound); @@ -264,7 +264,7 @@ void Compiler::appendFunctionSelector(ContractDefinition const& _contract) // Reject invalid library calls and ether sent to a library. m_context.appendJumpTo(m_context.errorTag()); else - m_context << eth::Instruction::STOP; // function not found + m_context << Instruction::STOP; // function not found for (auto const& it: interfaceFunctions) { @@ -288,7 +288,7 @@ void Compiler::appendCalldataUnpacker(TypePointers const& _typeParameters, bool //@todo this does not yet support nested dynamic arrays // Retain the offset pointer as base_offset, the point from which the data offsets are computed. - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; for (TypePointer const& parameterType: _typeParameters) { // stack: v1 v2 ... v(k-1) base_offset current_offset @@ -309,15 +309,15 @@ void Compiler::appendCalldataUnpacker(TypePointers const& _typeParameters, bool if (arrayType.isDynamicallySized()) { // compute data pointer - m_context << eth::Instruction::DUP1 << eth::Instruction::MLOAD; - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP2 << eth::Instruction::SWAP1; - m_context << u256(0x20) << eth::Instruction::ADD; + m_context << Instruction::DUP1 << Instruction::MLOAD; + m_context << Instruction::DUP3 << Instruction::ADD; + m_context << Instruction::SWAP2 << Instruction::SWAP1; + m_context << u256(0x20) << Instruction::ADD; } else { - m_context << eth::Instruction::DUP1; - m_context << u256(arrayType.calldataEncodedSize(true)) << eth::Instruction::ADD; + m_context << Instruction::DUP1; + m_context << u256(arrayType.calldataEncodedSize(true)) << Instruction::ADD; } } else @@ -329,19 +329,19 @@ void Compiler::appendCalldataUnpacker(TypePointers const& _typeParameters, bool // put on stack: data_pointer length CompilerUtils(m_context).loadFromMemoryDynamic(IntegerType(256), !_fromMemory); // stack: base_offset data_offset next_pointer - m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << Instruction::SWAP1 << Instruction::DUP3 << Instruction::ADD; // stack: base_offset next_pointer data_pointer // retrieve length CompilerUtils(m_context).loadFromMemoryDynamic(IntegerType(256), !_fromMemory, true); // stack: base_offset next_pointer length data_pointer - m_context << eth::Instruction::SWAP2; + m_context << Instruction::SWAP2; // stack: base_offset data_pointer length next_pointer } else { // leave the pointer on the stack - m_context << eth::Instruction::DUP1; - m_context << u256(calldataType->calldataEncodedSize()) << eth::Instruction::ADD; + m_context << Instruction::DUP1; + m_context << u256(calldataType->calldataEncodedSize()) << Instruction::ADD; } if (arrayType.location() == DataLocation::Memory) { @@ -355,7 +355,7 @@ void Compiler::appendCalldataUnpacker(TypePointers const& _typeParameters, bool } // move base_offset up CompilerUtils(m_context).moveToStackTop(1 + arrayType.sizeOnStack()); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; } } else @@ -363,18 +363,18 @@ void Compiler::appendCalldataUnpacker(TypePointers const& _typeParameters, bool solAssert(!type->isDynamicallySized(), "Unknown dynamically sized type: " + type->toString()); CompilerUtils(m_context).loadFromMemoryDynamic(*type, !_fromMemory, true); CompilerUtils(m_context).moveToStackTop(1 + type->sizeOnStack()); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; } // stack: v1 v2 ... v(k-1) v(k) base_offset mem_offset } - m_context << eth::Instruction::POP << eth::Instruction::POP; + m_context << Instruction::POP << Instruction::POP; } void Compiler::appendReturnValuePacker(TypePointers const& _typeParameters, bool _isLibrary) { CompilerUtils utils(m_context); if (_typeParameters.empty()) - m_context << eth::Instruction::STOP; + m_context << Instruction::STOP; else { utils.fetchFreeMemoryPointer(); @@ -382,7 +382,7 @@ void Compiler::appendReturnValuePacker(TypePointers const& _typeParameters, bool // its data to add the needed parts and we avoid a memory copy. utils.encodeToMemory(_typeParameters, _typeParameters, true, false, _isLibrary); utils.toSizeAfterFreeMemoryPointer(); - m_context << eth::Instruction::RETURN; + m_context << Instruction::RETURN; } } @@ -476,12 +476,12 @@ bool Compiler::visit(FunctionDefinition const& _function) while (stackLayout.back() != int(stackLayout.size() - 1)) if (stackLayout.back() < 0) { - m_context << eth::Instruction::POP; + m_context << Instruction::POP; stackLayout.pop_back(); } else { - m_context << eth::swapInstruction(stackLayout.size() - stackLayout.back() - 1); + m_context << swapInstruction(stackLayout.size() - stackLayout.back() - 1); swap(stackLayout[stackLayout.back()], stackLayout.back()); } //@todo assert that everything is in place now @@ -532,7 +532,7 @@ bool Compiler::visit(InlineAssembly const& _inlineAssembly) errinfo_comment("Stack too deep, try removing local variables.") ); for (unsigned i = 0; i < variable->type()->sizeOnStack(); ++i) - _assembly.append(eth::dupInstruction(stackDiff)); + _assembly.append(dupInstruction(stackDiff)); } else { @@ -572,8 +572,8 @@ bool Compiler::visit(InlineAssembly const& _inlineAssembly) errinfo_comment("Stack too deep, try removing local variables.") ); for (unsigned i = 0; i < size; ++i) { - _assembly.append(eth::swapInstruction(stackDiff)); - _assembly.append(eth::Instruction::POP); + _assembly.append(swapInstruction(stackDiff)); + _assembly.append(Instruction::POP); } } return true; @@ -588,7 +588,7 @@ bool Compiler::visit(IfStatement const& _ifStatement) StackHeightChecker checker(m_context); CompilerContext::LocationSetter locationSetter(m_context, _ifStatement); compileExpression(_ifStatement.condition()); - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; eth::AssemblyItem falseTag = m_context.appendConditionalJump(); eth::AssemblyItem endTag = falseTag; _ifStatement.trueStatement().accept(*this); @@ -615,7 +615,7 @@ bool Compiler::visit(WhileStatement const& _whileStatement) m_context << loopStart; compileExpression(_whileStatement.condition()); - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; m_context.appendConditionalJumpTo(loopEnd); _whileStatement.body().accept(*this); @@ -649,7 +649,7 @@ bool Compiler::visit(ForStatement const& _forStatement) if (_forStatement.condition()) { compileExpression(*_forStatement.condition()); - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; m_context.appendConditionalJumpTo(loopEnd); } @@ -710,7 +710,7 @@ bool Compiler::visit(Return const& _return) CompilerUtils(m_context).moveToStackVariable(*retVariable); } for (unsigned i = 0; i < m_stackCleanupForReturn; ++i) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; m_context.appendJumpTo(m_returnTag); m_context.adjustStackOffset(m_stackCleanupForReturn); return false; @@ -831,7 +831,7 @@ void Compiler::appendModifierOrFunctionCode() modifier.body().accept(*this); for (unsigned i = 0; i < c_stackSurplus; ++i) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; m_stackCleanupForReturn -= c_stackSurplus; } } @@ -855,20 +855,20 @@ eth::Assembly Compiler::cloneRuntime() { eth::EVMSchedule schedule; eth::Assembly a; - a << eth::Instruction::CALLDATASIZE; - a << u256(0) << eth::Instruction::DUP1 << eth::Instruction::CALLDATACOPY; + a << Instruction::CALLDATASIZE; + a << u256(0) << Instruction::DUP1 << Instruction::CALLDATACOPY; //@todo adjust for larger return values, make this dynamic. - a << u256(0x20) << u256(0) << eth::Instruction::CALLDATASIZE; + a << u256(0x20) << u256(0) << Instruction::CALLDATASIZE; a << u256(0); // this is the address which has to be substituted by the linker. //@todo implement as special "marker" AssemblyItem. a << u256("0xcafecafecafecafecafecafecafecafecafecafe"); - a << u256(schedule.callGas + 10) << eth::Instruction::GAS << eth::Instruction::SUB; - a << eth::Instruction::DELEGATECALL; + a << u256(schedule.callGas + 10) << Instruction::GAS << Instruction::SUB; + a << Instruction::DELEGATECALL; //Propagate error condition (if DELEGATECALL pushes 0 on stack). - a << eth::Instruction::ISZERO; + a << Instruction::ISZERO; a.appendJumpI(a.errorTag()); //@todo adjust for larger return values, make this dynamic. - a << u256(0x20) << u256(0) << eth::Instruction::RETURN; + a << u256(0x20) << u256(0) << Instruction::RETURN; return a; } diff --git a/libsolidity/codegen/CompilerContext.cpp b/libsolidity/codegen/CompilerContext.cpp index 9e2405cc..7810288e 100644 --- a/libsolidity/codegen/CompilerContext.cpp +++ b/libsolidity/codegen/CompilerContext.cpp @@ -166,7 +166,7 @@ pair<u256, unsigned> CompilerContext::storageLocationOfVariable(const Declaratio CompilerContext& CompilerContext::appendJump(eth::AssemblyItem::JumpType _jumpType) { - eth::AssemblyItem item(eth::Instruction::JUMP); + eth::AssemblyItem item(Instruction::JUMP); item.setJumpType(_jumpType); return *this << item; } @@ -182,7 +182,7 @@ void CompilerContext::resetVisitedNodes(ASTNode const* _node) void CompilerContext::injectVersionStampIntoSub(size_t _subIndex) { eth::Assembly& sub = m_asm.sub(_subIndex); - sub.injectStart(eth::Instruction::POP); + sub.injectStart(Instruction::POP); sub.injectStart(fromBigEndian<u256>(binaryVersion())); } diff --git a/libsolidity/codegen/CompilerContext.h b/libsolidity/codegen/CompilerContext.h index bd8fc295..9368dbcf 100644 --- a/libsolidity/codegen/CompilerContext.h +++ b/libsolidity/codegen/CompilerContext.h @@ -25,7 +25,7 @@ #include <ostream> #include <stack> #include <utility> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> #include <libevmasm/Assembly.h> #include <libsolidity/ast/ASTForward.h> #include <libsolidity/ast/Types.h> @@ -126,7 +126,7 @@ public: /// Append elements to the current instruction list and adjust @a m_stackOffset. CompilerContext& operator<<(eth::AssemblyItem const& _item) { m_asm.append(_item); return *this; } - CompilerContext& operator<<(eth::Instruction _instruction) { m_asm.append(_instruction); return *this; } + CompilerContext& operator<<(Instruction _instruction) { m_asm.append(_instruction); return *this; } CompilerContext& operator<<(u256 const& _value) { m_asm.append(_value); return *this; } CompilerContext& operator<<(bytes const& _data) { m_asm.append(_data); return *this; } diff --git a/libsolidity/codegen/CompilerUtils.cpp b/libsolidity/codegen/CompilerUtils.cpp index bd0857f6..36ed480e 100644 --- a/libsolidity/codegen/CompilerUtils.cpp +++ b/libsolidity/codegen/CompilerUtils.cpp @@ -22,7 +22,7 @@ #include <libsolidity/codegen/CompilerUtils.h> #include <libsolidity/ast/AST.h> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> #include <libsolidity/codegen/ArrayUtils.h> #include <libsolidity/codegen/LValue.h> @@ -45,26 +45,26 @@ void CompilerUtils::initialiseFreeMemoryPointer() void CompilerUtils::fetchFreeMemoryPointer() { - m_context << u256(freeMemoryPointer) << eth::Instruction::MLOAD; + m_context << u256(freeMemoryPointer) << Instruction::MLOAD; } void CompilerUtils::storeFreeMemoryPointer() { - m_context << u256(freeMemoryPointer) << eth::Instruction::MSTORE; + m_context << u256(freeMemoryPointer) << Instruction::MSTORE; } void CompilerUtils::allocateMemory() { fetchFreeMemoryPointer(); - m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP2 << eth::Instruction::ADD; + m_context << Instruction::SWAP1 << Instruction::DUP2 << Instruction::ADD; storeFreeMemoryPointer(); } void CompilerUtils::toSizeAfterFreeMemoryPointer() { fetchFreeMemoryPointer(); - m_context << eth::Instruction::DUP1 << eth::Instruction::SWAP2 << eth::Instruction::SUB; - m_context << eth::Instruction::SWAP1; + m_context << Instruction::DUP1 << Instruction::SWAP2 << Instruction::SUB; + m_context << Instruction::SWAP1; } unsigned CompilerUtils::loadFromMemory( @@ -87,7 +87,7 @@ void CompilerUtils::loadFromMemoryDynamic( ) { if (_keepUpdatedMemoryOffset) - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; if (auto arrayType = dynamic_cast<ArrayType const*>(&_type)) { @@ -95,7 +95,7 @@ void CompilerUtils::loadFromMemoryDynamic( solAssert(!_fromCalldata, ""); solAssert(_padToWordBoundaries, ""); if (_keepUpdatedMemoryOffset) - m_context << arrayType->memorySize() << eth::Instruction::ADD; + m_context << arrayType->memorySize() << Instruction::ADD; } else { @@ -104,7 +104,7 @@ void CompilerUtils::loadFromMemoryDynamic( { // update memory counter moveToStackTop(_type.sizeOnStack()); - m_context << u256(numBytes) << eth::Instruction::ADD; + m_context << u256(numBytes) << Instruction::ADD; } } } @@ -113,7 +113,7 @@ void CompilerUtils::storeInMemory(unsigned _offset) { unsigned numBytes = prepareMemoryStore(IntegerType(256), true); if (numBytes > 0) - m_context << u256(_offset) << eth::Instruction::MSTORE; + m_context << u256(_offset) << Instruction::MSTORE; } void CompilerUtils::storeInMemoryDynamic(Type const& _type, bool _padToWordBoundaries) @@ -125,13 +125,13 @@ void CompilerUtils::storeInMemoryDynamic(Type const& _type, bool _padToWordBound } else if (auto str = dynamic_cast<StringLiteralType const*>(&_type)) { - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; storeStringData(bytesConstRef(str->value())); if (_padToWordBoundaries) m_context << u256(((str->value().size() + 31) / 32) * 32); else m_context << u256(str->value().size()); - m_context << eth::Instruction::ADD; + m_context << Instruction::ADD; } else { @@ -142,8 +142,8 @@ void CompilerUtils::storeInMemoryDynamic(Type const& _type, bool _padToWordBound _type.sizeOnStack() == 1, "Memory store of types with stack size != 1 not implemented." ); - m_context << eth::Instruction::DUP2 << eth::Instruction::MSTORE; - m_context << u256(numBytes) << eth::Instruction::ADD; + m_context << Instruction::DUP2 << Instruction::MSTORE; + m_context << u256(numBytes) << Instruction::ADD; } } } @@ -168,7 +168,7 @@ void CompilerUtils::encodeToMemory( // of the ith dynamic parameter, which is filled once the dynamic parts are processed. // store memory start pointer - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; unsigned argSize = CompilerUtils::sizeOnStack(_givenTypes); unsigned stackPos = 0; // advances through the argument values @@ -180,7 +180,7 @@ void CompilerUtils::encodeToMemory( if (targetType->isDynamicallySized() && !_copyDynamicDataInPlace) { // leave end_of_mem as dyn head pointer - m_context << eth::Instruction::DUP1 << u256(32) << eth::Instruction::ADD; + m_context << Instruction::DUP1 << u256(32) << Instruction::ADD; dynPointers++; } else @@ -222,10 +222,10 @@ void CompilerUtils::encodeToMemory( if (targetType->isDynamicallySized() && !_copyDynamicDataInPlace) { // copy tail pointer (=mem_end - mem_start) to memory - m_context << eth::dupInstruction(2 + dynPointers) << eth::Instruction::DUP2; - m_context << eth::Instruction::SUB; - m_context << eth::dupInstruction(2 + dynPointers - thisDynPointer); - m_context << eth::Instruction::MSTORE; + m_context << dupInstruction(2 + dynPointers) << Instruction::DUP2; + m_context << Instruction::SUB; + m_context << dupInstruction(2 + dynPointers - thisDynPointer); + m_context << Instruction::MSTORE; // stack: ... <end_of_mem> if (_givenTypes[i]->category() == Type::Category::StringLiteral) { @@ -243,13 +243,13 @@ void CompilerUtils::encodeToMemory( copyToStackTop(argSize - stackPos + dynPointers + 2, arrayType.sizeOnStack()); // stack: ... <end_of_mem> <value...> // copy length to memory - m_context << eth::dupInstruction(1 + arrayType.sizeOnStack()); + m_context << dupInstruction(1 + arrayType.sizeOnStack()); ArrayUtils(m_context).retrieveLength(arrayType, 1); // stack: ... <end_of_mem> <value...> <end_of_mem'> <length> storeInMemoryDynamic(IntegerType(256), true); // stack: ... <end_of_mem> <value...> <end_of_mem''> // copy the new memory pointer - m_context << eth::swapInstruction(arrayType.sizeOnStack() + 1) << eth::Instruction::POP; + m_context << swapInstruction(arrayType.sizeOnStack() + 1) << Instruction::POP; // stack: ... <end_of_mem''> <value...> // copy data part ArrayUtils(m_context).copyArrayToMemory(arrayType, _padToWordBoundaries); @@ -262,7 +262,7 @@ void CompilerUtils::encodeToMemory( } // remove unneeded stack elements (and retain memory pointer) - m_context << eth::swapInstruction(argSize + dynPointers + 1); + m_context << swapInstruction(argSize + dynPointers + 1); popStackSlots(argSize + dynPointers + 1); } @@ -272,11 +272,11 @@ void CompilerUtils::zeroInitialiseMemoryArray(ArrayType const& _type) m_context << repeat; pushZeroValue(*_type.baseType()); storeInMemoryDynamic(*_type.baseType()); - m_context << eth::Instruction::SWAP1 << u256(1) << eth::Instruction::SWAP1; - m_context << eth::Instruction::SUB << eth::Instruction::SWAP1; - m_context << eth::Instruction::DUP2; + m_context << Instruction::SWAP1 << u256(1) << Instruction::SWAP1; + m_context << Instruction::SUB << Instruction::SWAP1; + m_context << Instruction::DUP2; m_context.appendConditionalJumpTo(repeat); - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; } void CompilerUtils::memoryCopy() @@ -284,16 +284,16 @@ void CompilerUtils::memoryCopy() // Stack here: size target source // stack for call: outsize target size source value contract gas //@TODO do not use ::CALL if less than 32 bytes? - m_context << eth::Instruction::DUP3 << eth::Instruction::SWAP1; + m_context << Instruction::DUP3 << Instruction::SWAP1; m_context << u256(0) << u256(identityContractAddress); // compute gas costs - m_context << u256(32) << eth::Instruction::DUP5 << u256(31) << eth::Instruction::ADD; + m_context << u256(32) << Instruction::DUP5 << u256(31) << Instruction::ADD; static unsigned c_identityGas = 3; static unsigned c_identityWordGas = 15; - m_context << eth::Instruction::DIV << u256(c_identityWordGas) << eth::Instruction::MUL; - m_context << u256(c_identityGas) << eth::Instruction::ADD; - m_context << eth::Instruction::CALL; - m_context << eth::Instruction::POP; // ignore return value + m_context << Instruction::DIV << u256(c_identityWordGas) << Instruction::MUL; + m_context << u256(c_identityGas) << Instruction::ADD; + m_context << Instruction::CALL; + m_context << Instruction::POP; // ignore return value } void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetType, bool _cleanupNeeded) @@ -317,7 +317,7 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp // conversion from bytes to integer. no need to clean the high bit // only to shift right because of opposite alignment IntegerType const& targetIntegerType = dynamic_cast<IntegerType const&>(_targetType); - m_context << (u256(1) << (256 - typeOnStack.numBytes() * 8)) << eth::Instruction::SWAP1 << eth::Instruction::DIV; + m_context << (u256(1) << (256 - typeOnStack.numBytes() * 8)) << Instruction::SWAP1 << Instruction::DIV; if (targetIntegerType.numBits() < typeOnStack.numBytes() * 8) convertType(IntegerType(typeOnStack.numBytes() * 8), _targetType, _cleanupNeeded); } @@ -329,12 +329,12 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp if (targetType.numBytes() < typeOnStack.numBytes()) { if (targetType.numBytes() == 0) - m_context << eth::Instruction::DUP1 << eth::Instruction::XOR; + m_context << Instruction::DUP1 << Instruction::XOR; else { m_context << (u256(1) << (256 - targetType.numBytes() * 8)); - m_context << eth::Instruction::DUP1 << eth::Instruction::SWAP2; - m_context << eth::Instruction::DIV << eth::Instruction::MUL; + m_context << Instruction::DUP1 << Instruction::SWAP2; + m_context << Instruction::DIV << Instruction::MUL; } } } @@ -356,7 +356,7 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp if (auto typeOnStack = dynamic_cast<IntegerType const*>(&_typeOnStack)) if (targetBytesType.numBytes() * 8 > typeOnStack->numBits()) cleanHigherOrderBits(*typeOnStack); - m_context << (u256(1) << (256 - targetBytesType.numBytes() * 8)) << eth::Instruction::MUL; + m_context << (u256(1) << (256 - targetBytesType.numBytes() * 8)) << Instruction::MUL; } else if (targetTypeCategory == Type::Category::Enum) // just clean @@ -406,7 +406,7 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp m_context << storageSize; allocateMemory(); // stack: mempos - m_context << eth::Instruction::DUP1 << u256(data.size()); + m_context << Instruction::DUP1 << u256(data.size()); storeInMemoryDynamic(IntegerType(256)); // stack: mempos datapos storeStringData(data); @@ -445,18 +445,18 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp // allocate memory // stack: <source ref> (variably sized) <length> - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; ArrayUtils(m_context).convertLengthToSize(targetType, true); // stack: <source ref> (variably sized) <length> <size> if (targetType.isDynamicallySized()) - m_context << u256(0x20) << eth::Instruction::ADD; + m_context << u256(0x20) << Instruction::ADD; allocateMemory(); // stack: <source ref> (variably sized) <length> <mem start> - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; moveIntoStack(2 + stackSize); if (targetType.isDynamicallySized()) { - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP2; storeInMemoryDynamic(IntegerType(256)); } // stack: <mem start> <source ref> (variably sized) <length> <mem data pos> @@ -468,12 +468,12 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp } else { - m_context << u256(0) << eth::Instruction::SWAP1; + m_context << u256(0) << Instruction::SWAP1; // stack: <mem start> <source ref> (variably sized) <length> <counter> <mem data pos> auto repeat = m_context.newTag(); m_context << repeat; - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP3; - m_context << eth::Instruction::LT << eth::Instruction::ISZERO; + m_context << Instruction::DUP3 << Instruction::DUP3; + m_context << Instruction::LT << Instruction::ISZERO; auto loopEnd = m_context.appendConditionalJump(); copyToStackTop(3 + stackSize, stackSize); copyToStackTop(2 + stackSize, 1); @@ -482,11 +482,11 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp StorageItem(m_context, *typeOnStack.baseType()).retrieveValue(SourceLocation(), true); convertType(*typeOnStack.baseType(), *targetType.baseType(), _cleanupNeeded); storeInMemoryDynamic(*targetType.baseType(), true); - m_context << eth::Instruction::SWAP1 << u256(1) << eth::Instruction::ADD; - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1 << u256(1) << Instruction::ADD; + m_context << Instruction::SWAP1; m_context.appendJumpTo(repeat); m_context << loopEnd; - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } // stack: <mem start> <source ref> (variably sized) <length> <mem data pos updated> popStackSlots(2 + stackSize); @@ -540,14 +540,14 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp // stack: <source ref> m_context << typeOnStack.memorySize(); allocateMemory(); - m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP2; + m_context << Instruction::SWAP1 << Instruction::DUP2; // stack: <memory ptr> <source ref> <memory ptr> for (auto const& member: typeOnStack.members(nullptr)) { if (!member.type->canLiveOutsideStorage()) continue; pair<u256, unsigned> const& offsets = typeOnStack.storageOffsetsOfMember(member.name); - m_context << offsets.first << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << offsets.first << Instruction::DUP3 << Instruction::ADD; m_context << u256(offsets.second); StorageItem(m_context, *member.type).retrieveValue(SourceLocation(), true); TypePointer targetMemberType = targetType.memberType(member.name); @@ -555,7 +555,7 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp convertType(*member.type, *targetMemberType, true); storeInMemoryDynamic(*targetMemberType, true); } - m_context << eth::Instruction::POP << eth::Instruction::POP; + m_context << Instruction::POP << Instruction::POP; } break; case DataLocation::CallData: @@ -602,13 +602,13 @@ void CompilerUtils::convertType(Type const& _typeOnStack, Type const& _targetTyp // Move it back into its place. for (unsigned j = 0; j < min(sourceSize, targetSize); ++j) m_context << - eth::swapInstruction(depth + targetSize - sourceSize) << - eth::Instruction::POP; + swapInstruction(depth + targetSize - sourceSize) << + Instruction::POP; // Value shrank for (unsigned j = targetSize; j < sourceSize; ++j) { moveToStackTop(depth - 1, 1); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } // Value grew if (targetSize > sourceSize) @@ -639,7 +639,7 @@ void CompilerUtils::pushZeroValue(Type const& _type) m_context << u256(max(32u, _type.calldataEncodedSize())); allocateMemory(); - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; if (auto structType = dynamic_cast<StructType const*>(&_type)) for (auto const& member: structType->members(nullptr)) @@ -657,7 +657,7 @@ void CompilerUtils::pushZeroValue(Type const& _type) } else if (arrayType->length() > 0) { - m_context << arrayType->length() << eth::Instruction::SWAP1; + m_context << arrayType->length() << Instruction::SWAP1; // stack: items_to_do memory_pos zeroInitialiseMemoryArray(*arrayType); // stack: updated_memory_pos @@ -667,7 +667,7 @@ void CompilerUtils::pushZeroValue(Type const& _type) solAssert(false, "Requested initialisation for unknown type: " + _type.toString()); // remove the updated memory pointer - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } void CompilerUtils::moveToStackVariable(VariableDeclaration const& _variable) @@ -683,14 +683,14 @@ void CompilerUtils::moveToStackVariable(VariableDeclaration const& _variable) errinfo_comment("Stack too deep, try removing local variables.") ); for (unsigned i = 0; i < size; ++i) - m_context << eth::swapInstruction(stackPosition - size + 1) << eth::Instruction::POP; + m_context << swapInstruction(stackPosition - size + 1) << Instruction::POP; } void CompilerUtils::copyToStackTop(unsigned _stackDepth, unsigned _itemSize) { solAssert(_stackDepth <= 16, "Stack too deep, try removing local variables."); for (unsigned i = 0; i < _itemSize; ++i) - m_context << eth::dupInstruction(_stackDepth); + m_context << dupInstruction(_stackDepth); } void CompilerUtils::moveToStackTop(unsigned _stackDepth, unsigned _itemSize) @@ -712,14 +712,14 @@ void CompilerUtils::rotateStackUp(unsigned _items) { solAssert(_items - 1 <= 16, "Stack too deep, try removing local variables."); for (unsigned i = 1; i < _items; ++i) - m_context << eth::swapInstruction(_items - i); + m_context << swapInstruction(_items - i); } void CompilerUtils::rotateStackDown(unsigned _items) { solAssert(_items - 1 <= 16, "Stack too deep, try removing local variables."); for (unsigned i = 1; i < _items; ++i) - m_context << eth::swapInstruction(i); + m_context << swapInstruction(i); } void CompilerUtils::popStackElement(Type const& _type) @@ -730,7 +730,7 @@ void CompilerUtils::popStackElement(Type const& _type) void CompilerUtils::popStackSlots(size_t _amount) { for (size_t i = 0; i < _amount; ++i) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } unsigned CompilerUtils::sizeOnStack(vector<shared_ptr<Type const>> const& _variableTypes) @@ -744,7 +744,7 @@ unsigned CompilerUtils::sizeOnStack(vector<shared_ptr<Type const>> const& _varia void CompilerUtils::computeHashStatic() { storeInMemory(0); - m_context << u256(32) << u256(0) << eth::Instruction::SHA3; + m_context << u256(32) << u256(0) << Instruction::SHA3; } void CompilerUtils::storeStringData(bytesConstRef _data) @@ -758,14 +758,14 @@ void CompilerUtils::storeStringData(bytesConstRef _data) m_context << h256::Arith(h256(_data.cropped(i), h256::AlignLeft)); storeInMemoryDynamic(IntegerType(256)); } - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else { // stack: mempos mempos_data m_context.appendData(_data.toBytes()); - m_context << u256(_data.size()) << eth::Instruction::SWAP2; - m_context << eth::Instruction::CODECOPY; + m_context << u256(_data.size()) << Instruction::SWAP2; + m_context << Instruction::CODECOPY; } } @@ -774,18 +774,18 @@ unsigned CompilerUtils::loadFromMemoryHelper(Type const& _type, bool _fromCallda unsigned numBytes = _type.calldataEncodedSize(_padToWordBoundaries); bool leftAligned = _type.category() == Type::Category::FixedBytes; if (numBytes == 0) - m_context << eth::Instruction::POP << u256(0); + m_context << Instruction::POP << u256(0); else { solAssert(numBytes <= 32, "Static memory load of more than 32 bytes requested."); - m_context << (_fromCalldata ? eth::Instruction::CALLDATALOAD : eth::Instruction::MLOAD); + m_context << (_fromCalldata ? Instruction::CALLDATALOAD : Instruction::MLOAD); if (numBytes != 32) { // add leading or trailing zeros by dividing/multiplying depending on alignment u256 shiftFactor = u256(1) << ((32 - numBytes) * 8); - m_context << shiftFactor << eth::Instruction::SWAP1 << eth::Instruction::DIV; + m_context << shiftFactor << Instruction::SWAP1 << Instruction::DIV; if (leftAligned) - m_context << shiftFactor << eth::Instruction::MUL; + m_context << shiftFactor << Instruction::MUL; } } @@ -797,9 +797,9 @@ void CompilerUtils::cleanHigherOrderBits(IntegerType const& _typeOnStack) if (_typeOnStack.numBits() == 256) return; else if (_typeOnStack.isSigned()) - m_context << u256(_typeOnStack.numBits() / 8 - 1) << eth::Instruction::SIGNEXTEND; + m_context << u256(_typeOnStack.numBits() / 8 - 1) << Instruction::SIGNEXTEND; else - m_context << ((u256(1) << _typeOnStack.numBits()) - 1) << eth::Instruction::AND; + m_context << ((u256(1) << _typeOnStack.numBits()) - 1) << Instruction::AND; } unsigned CompilerUtils::prepareMemoryStore(Type const& _type, bool _padToWordBoundaries) const @@ -807,13 +807,13 @@ unsigned CompilerUtils::prepareMemoryStore(Type const& _type, bool _padToWordBou unsigned numBytes = _type.calldataEncodedSize(_padToWordBoundaries); bool leftAligned = _type.category() == Type::Category::FixedBytes; if (numBytes == 0) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; else { solAssert(numBytes <= 32, "Memory store of more than 32 bytes requested."); if (numBytes != 32 && !leftAligned && !_padToWordBoundaries) // shift the value accordingly before storing - m_context << (u256(1) << ((32 - numBytes) * 8)) << eth::Instruction::MUL; + m_context << (u256(1) << ((32 - numBytes) * 8)) << Instruction::MUL; } return numBytes; } diff --git a/libsolidity/codegen/ExpressionCompiler.cpp b/libsolidity/codegen/ExpressionCompiler.cpp index a17ec2f6..ed36fb24 100644 --- a/libsolidity/codegen/ExpressionCompiler.cpp +++ b/libsolidity/codegen/ExpressionCompiler.cpp @@ -75,7 +75,7 @@ void ExpressionCompiler::appendConstStateVariableAccessor(VariableDeclaration co utils().convertType(*_varDecl.value()->annotation().type, *_varDecl.annotation().type); // append return - m_context << eth::dupInstruction(_varDecl.annotation().type->sizeOnStack() + 1); + m_context << dupInstruction(_varDecl.annotation().type->sizeOnStack() + 1); m_context.appendJump(eth::AssemblyItem::JumpType::OutOfFunction); } @@ -103,13 +103,13 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& "Accessors for mapping with dynamically-sized keys not yet implemented." ); // pop offset - m_context << eth::Instruction::POP; + m_context << Instruction::POP; // move storage offset to memory. utils().storeInMemory(32); // move key to memory. utils().copyToStackTop(paramTypes.size() - i, 1); utils().storeInMemory(0); - m_context << u256(64) << u256(0) << eth::Instruction::SHA3; + m_context << u256(64) << u256(0) << Instruction::SHA3; // push offset m_context << u256(0); returnType = mappingType->valueType(); @@ -117,7 +117,7 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& else if (auto arrayType = dynamic_cast<ArrayType const*>(returnType.get())) { // pop offset - m_context << eth::Instruction::POP; + m_context << Instruction::POP; utils().copyToStackTop(paramTypes.size() - i + 1, 1); ArrayUtils(m_context).accessIndex(*arrayType); returnType = arrayType->baseType(); @@ -127,12 +127,12 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& } // remove index arguments. if (paramTypes.size() == 1) - m_context << eth::Instruction::SWAP2 << eth::Instruction::POP << eth::Instruction::SWAP1; + m_context << Instruction::SWAP2 << Instruction::POP << Instruction::SWAP1; else if (paramTypes.size() >= 2) { - m_context << eth::swapInstruction(paramTypes.size()); - m_context << eth::Instruction::POP; - m_context << eth::swapInstruction(paramTypes.size()); + m_context << swapInstruction(paramTypes.size()); + m_context << Instruction::POP; + m_context << swapInstruction(paramTypes.size()); utils().popStackSlots(paramTypes.size() - 1); } unsigned retSizeOnStack = 0; @@ -141,7 +141,7 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& if (StructType const* structType = dynamic_cast<StructType const*>(returnType.get())) { // remove offset - m_context << eth::Instruction::POP; + m_context << Instruction::POP; auto const& names = accessorType.returnParameterNames(); // struct for (size_t i = 0; i < names.size(); ++i) @@ -152,7 +152,7 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& if (!arrayType->isByteArray()) continue; pair<u256, unsigned> const& offsets = structType->storageOffsetsOfMember(names[i]); - m_context << eth::Instruction::DUP1 << u256(offsets.first) << eth::Instruction::ADD << u256(offsets.second); + m_context << Instruction::DUP1 << u256(offsets.first) << Instruction::ADD << u256(offsets.second); TypePointer memberType = structType->memberType(names[i]); StorageItem(m_context, *memberType).retrieveValue(SourceLocation(), true); utils().convertType(*memberType, *returnTypes[i]); @@ -160,7 +160,7 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& retSizeOnStack += returnTypes[i]->sizeOnStack(); } // remove slot - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else { @@ -172,7 +172,7 @@ void ExpressionCompiler::appendStateVariableAccessor(VariableDeclaration const& } solAssert(retSizeOnStack == utils().sizeOnStack(returnTypes), ""); solAssert(retSizeOnStack <= 15, "Stack is too deep."); - m_context << eth::dupInstruction(retSizeOnStack + 1); + m_context << dupInstruction(retSizeOnStack + 1); m_context.appendJump(eth::AssemblyItem::JumpType::OutOfFunction); } @@ -226,7 +226,7 @@ bool ExpressionCompiler::visit(Assignment const& _assignment) solAssert(itemSize + lvalueSize <= 16, "Stack too deep, try removing local variables."); // value [lvalue_ref] updated_value for (unsigned i = 0; i < itemSize; ++i) - m_context << eth::swapInstruction(itemSize + lvalueSize) << eth::Instruction::POP; + m_context << swapInstruction(itemSize + lvalueSize) << Instruction::POP; } } m_currentLValue->storeValue(*type, _assignment.location()); @@ -243,7 +243,7 @@ bool ExpressionCompiler::visit(TupleExpression const& _tuple) solAssert(!arrayType.isDynamicallySized(), "Cannot create dynamically sized inline array."); m_context << max(u256(32u), arrayType.memorySize()); utils().allocateMemory(); - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; for (auto const& component: _tuple.components()) { @@ -252,7 +252,7 @@ bool ExpressionCompiler::visit(TupleExpression const& _tuple) utils().storeInMemoryDynamic(*arrayType.baseType(), true); } - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else { @@ -298,13 +298,13 @@ bool ExpressionCompiler::visit(UnaryOperation const& _unaryOperation) switch (_unaryOperation.getOperator()) { case Token::Not: // ! - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; break; case Token::BitNot: // ~ - m_context << eth::Instruction::NOT; + m_context << Instruction::NOT; break; case Token::After: // after - m_context << eth::Instruction::TIMESTAMP << eth::Instruction::ADD; + m_context << Instruction::TIMESTAMP << Instruction::ADD; break; case Token::Delete: // delete solAssert(!!m_currentLValue, "LValue not retrieved."); @@ -319,20 +319,20 @@ bool ExpressionCompiler::visit(UnaryOperation const& _unaryOperation) { // store value for later solAssert(_unaryOperation.annotation().type->sizeOnStack() == 1, "Stack size != 1 not implemented."); - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; if (m_currentLValue->sizeOnStack() > 0) for (unsigned i = 1 + m_currentLValue->sizeOnStack(); i > 0; --i) - m_context << eth::swapInstruction(i); + m_context << swapInstruction(i); } m_context << u256(1); if (_unaryOperation.getOperator() == Token::Inc) - m_context << eth::Instruction::ADD; + m_context << Instruction::ADD; else - m_context << eth::Instruction::SWAP1 << eth::Instruction::SUB; + m_context << Instruction::SWAP1 << Instruction::SUB; // Stack for prefix: [ref...] (*ref)+-1 // Stack for postfix: *ref [ref...] (*ref)+-1 for (unsigned i = m_currentLValue->sizeOnStack(); i > 0; --i) - m_context << eth::swapInstruction(i); + m_context << swapInstruction(i); m_currentLValue->storeValue( *_unaryOperation.annotation().type, _unaryOperation.location(), !_unaryOperation.isPrefixOperation()); @@ -342,7 +342,7 @@ bool ExpressionCompiler::visit(UnaryOperation const& _unaryOperation) // unary add, so basically no-op break; case Token::Sub: // - - m_context << u256(0) << eth::Instruction::SUB; + m_context << u256(0) << Instruction::SUB; break; default: BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Invalid unary operator: " + @@ -452,7 +452,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) m_context << max(u256(32u), structType.memorySize()); utils().allocateMemory(); - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; for (unsigned i = 0; i < arguments.size(); ++i) { @@ -460,7 +460,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) utils().convertType(*arguments[i]->annotation().type, *functionType->parameterTypes()[i]); utils().storeInMemoryDynamic(*functionType->parameterTypes()[i]); } - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else { @@ -518,21 +518,21 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) utils().fetchFreeMemoryPointer(); // pushes size eth::AssemblyItem subroutine = m_context.addSubroutine(assembly); - m_context << eth::Instruction::DUP1 << subroutine; - m_context << eth::Instruction::DUP4 << eth::Instruction::CODECOPY; + m_context << Instruction::DUP1 << subroutine; + m_context << Instruction::DUP4 << Instruction::CODECOPY; - m_context << eth::Instruction::ADD; + m_context << Instruction::ADD; utils().encodeToMemory(argumentTypes, function.parameterTypes()); // now on stack: memory_end_ptr // need: size, offset, endowment utils().toSizeAfterFreeMemoryPointer(); if (function.valueSet()) - m_context << eth::dupInstruction(3); + m_context << dupInstruction(3); else m_context << u256(0); - m_context << eth::Instruction::CREATE; + m_context << Instruction::CREATE; if (function.valueSet()) - m_context << eth::swapInstruction(1) << eth::Instruction::POP; + m_context << swapInstruction(1) << Instruction::POP; break; } case Location::SetGas: @@ -546,9 +546,9 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) // Its values of gasSet and valueSet is equal to the original function's though. unsigned stackDepth = (function.gasSet() ? 1 : 0) + (function.valueSet() ? 1 : 0); if (stackDepth > 0) - m_context << eth::swapInstruction(stackDepth); + m_context << swapInstruction(stackDepth); if (function.gasSet()) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; break; } case Location::SetValue: @@ -557,7 +557,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) // Note that function is not the original function, but the ".value" function. // Its values of gasSet and valueSet is equal to the original function's though. if (function.valueSet()) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; arguments.front()->accept(*this); break; case Location::Send: @@ -586,7 +586,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) case Location::Selfdestruct: arguments.front()->accept(*this); utils().convertType(*arguments.front()->annotation().type, *function.parameterTypes().front(), true); - m_context << eth::Instruction::SUICIDE; + m_context << Instruction::SUICIDE; break; case Location::SHA3: { @@ -599,7 +599,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) utils().fetchFreeMemoryPointer(); utils().encodeToMemory(argumentTypes, TypePointers(), function.padArguments(), true); utils().toSizeAfterFreeMemoryPointer(); - m_context << eth::Instruction::SHA3; + m_context << Instruction::SHA3; break; } case Location::Log0: @@ -622,7 +622,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) false, true); utils().toSizeAfterFreeMemoryPointer(); - m_context << eth::logInstruction(logNumber); + m_context << logInstruction(logNumber); break; } case Location::Event: @@ -646,7 +646,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) true ); utils().toSizeAfterFreeMemoryPointer(); - m_context << eth::Instruction::SHA3; + m_context << Instruction::SHA3; } else utils().convertType( @@ -676,14 +676,14 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) utils().encodeToMemory(nonIndexedArgTypes, nonIndexedParamTypes); // need: topic1 ... topicn memsize memstart utils().toSizeAfterFreeMemoryPointer(); - m_context << eth::logInstruction(numIndexed); + m_context << logInstruction(numIndexed); break; } case Location::BlockHash: { arguments[0]->accept(*this); utils().convertType(*arguments[0]->annotation().type, *function.parameterTypes()[0], true); - m_context << eth::Instruction::BLOCKHASH; + m_context << Instruction::BLOCKHASH; break; } case Location::AddMod: @@ -695,9 +695,9 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) utils().convertType(*arguments[2 - i]->annotation().type, IntegerType(256)); } if (function.location() == Location::AddMod) - m_context << eth::Instruction::ADDMOD; + m_context << Instruction::ADDMOD; else - m_context << eth::Instruction::MULMOD; + m_context << Instruction::MULMOD; break; } case Location::ECRecover: @@ -710,7 +710,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) {Location::RIPEMD160, 3}}; m_context << contractAddresses.find(function.location())->second; for (unsigned i = function.sizeOnStack(); i > 0; --i) - m_context << eth::swapInstruction(i); + m_context << swapInstruction(i); appendExternalFunctionCall(function, arguments); break; } @@ -727,13 +727,13 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) make_shared<ArrayType>(DataLocation::Storage); // get the current length ArrayUtils(m_context).retrieveLength(*arrayType); - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; // stack: ArrayReference currentLength currentLength - m_context << u256(1) << eth::Instruction::ADD; + m_context << u256(1) << Instruction::ADD; // stack: ArrayReference currentLength newLength - m_context << eth::Instruction::DUP3 << eth::Instruction::DUP2; + m_context << Instruction::DUP3 << Instruction::DUP2; ArrayUtils(m_context).resizeDynamicArray(*arrayType); - m_context << eth::Instruction::SWAP2 << eth::Instruction::SWAP1; + m_context << Instruction::SWAP2 << Instruction::SWAP1; // stack: newLength ArrayReference oldLength ArrayUtils(m_context).accessIndex(*arrayType, false); @@ -766,36 +766,36 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall) // Stack: requested_length // Allocate at max(MSIZE, freeMemoryPointer) utils().fetchFreeMemoryPointer(); - m_context << eth::Instruction::DUP1 << eth::Instruction::MSIZE; - m_context << eth::Instruction::LT; + m_context << Instruction::DUP1 << Instruction::MSIZE; + m_context << Instruction::LT; auto initialise = m_context.appendConditionalJump(); // Free memory pointer does not point to empty memory, use MSIZE. - m_context << eth::Instruction::POP; - m_context << eth::Instruction::MSIZE; + m_context << Instruction::POP; + m_context << Instruction::MSIZE; m_context << initialise; // Stack: requested_length memptr - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; // Stack: memptr requested_length // store length - m_context << eth::Instruction::DUP1 << eth::Instruction::DUP3 << eth::Instruction::MSTORE; + m_context << Instruction::DUP1 << Instruction::DUP3 << Instruction::MSTORE; // Stack: memptr requested_length // update free memory pointer - m_context << eth::Instruction::DUP1 << arrayType.baseType()->memoryHeadSize(); - m_context << eth::Instruction::MUL << u256(32) << eth::Instruction::ADD; - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << Instruction::DUP1 << arrayType.baseType()->memoryHeadSize(); + m_context << Instruction::MUL << u256(32) << Instruction::ADD; + m_context << Instruction::DUP3 << Instruction::ADD; utils().storeFreeMemoryPointer(); // Stack: memptr requested_length // We only have to initialise if the base type is a not a value type. if (dynamic_cast<ReferenceType const*>(arrayType.baseType().get())) { - m_context << eth::Instruction::DUP2 << u256(32) << eth::Instruction::ADD; + m_context << Instruction::DUP2 << u256(32) << Instruction::ADD; utils().zeroInitialiseMemoryArray(arrayType); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else - m_context << eth::Instruction::POP; + m_context << Instruction::POP; break; } default: @@ -876,7 +876,7 @@ void ExpressionCompiler::endVisit(MemberAccess const& _memberAccess) IntegerType(0, IntegerType::Modifier::Address), true ); - m_context << eth::Instruction::BALANCE; + m_context << Instruction::BALANCE; } else if ((set<string>{"send", "call", "callcode", "delegatecall"}).count(member)) utils().convertType( @@ -894,30 +894,30 @@ void ExpressionCompiler::endVisit(MemberAccess const& _memberAccess) case Type::Category::Magic: // we can ignore the kind of magic and only look at the name of the member if (member == "coinbase") - m_context << eth::Instruction::COINBASE; + m_context << Instruction::COINBASE; else if (member == "timestamp") - m_context << eth::Instruction::TIMESTAMP; + m_context << Instruction::TIMESTAMP; else if (member == "difficulty") - m_context << eth::Instruction::DIFFICULTY; + m_context << Instruction::DIFFICULTY; else if (member == "number") - m_context << eth::Instruction::NUMBER; + m_context << Instruction::NUMBER; else if (member == "gaslimit") - m_context << eth::Instruction::GASLIMIT; + m_context << Instruction::GASLIMIT; else if (member == "sender") - m_context << eth::Instruction::CALLER; + m_context << Instruction::CALLER; else if (member == "value") - m_context << eth::Instruction::CALLVALUE; + m_context << Instruction::CALLVALUE; else if (member == "origin") - m_context << eth::Instruction::ORIGIN; + m_context << Instruction::ORIGIN; else if (member == "gas") - m_context << eth::Instruction::GAS; + m_context << Instruction::GAS; else if (member == "gasprice") - m_context << eth::Instruction::GASPRICE; + m_context << Instruction::GASPRICE; else if (member == "data") - m_context << u256(0) << eth::Instruction::CALLDATASIZE; + m_context << u256(0) << Instruction::CALLDATASIZE; else if (member == "sig") - m_context << u256(0) << eth::Instruction::CALLDATALOAD - << (u256(0xffffffff) << (256 - 32)) << eth::Instruction::AND; + m_context << u256(0) << Instruction::CALLDATALOAD + << (u256(0xffffffff) << (256 - 32)) << Instruction::AND; else BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Unknown magic member.")); break; @@ -929,13 +929,13 @@ void ExpressionCompiler::endVisit(MemberAccess const& _memberAccess) case DataLocation::Storage: { pair<u256, unsigned> const& offsets = type.storageOffsetsOfMember(member); - m_context << offsets.first << eth::Instruction::ADD << u256(offsets.second); + m_context << offsets.first << Instruction::ADD << u256(offsets.second); setLValueToStorageItem(_memberAccess); break; } case DataLocation::Memory: { - m_context << type.memoryOffsetOfMember(member) << eth::Instruction::ADD; + m_context << type.memoryOffsetOfMember(member) << Instruction::ADD; setLValue<MemoryItem>(_memberAccess, *_memberAccess.annotation().type); break; } @@ -986,13 +986,13 @@ void ExpressionCompiler::endVisit(MemberAccess const& _memberAccess) switch (type.location()) { case DataLocation::CallData: - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; break; case DataLocation::Storage: setLValue<StorageArrayLength>(_memberAccess, type); break; case DataLocation::Memory: - m_context << eth::Instruction::MLOAD; + m_context << Instruction::MLOAD; break; } } @@ -1046,7 +1046,7 @@ bool ExpressionCompiler::visit(IndexAccess const& _indexAccess) false, true ); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; utils().storeInMemoryDynamic(IntegerType(256)); utils().toSizeAfterFreeMemoryPointer(); } @@ -1054,12 +1054,12 @@ bool ExpressionCompiler::visit(IndexAccess const& _indexAccess) { m_context << u256(0); // memory position appendExpressionCopyToMemory(*keyType, *_indexAccess.indexExpression()); - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; solAssert(CompilerUtils::freeMemoryPointer >= 0x40, ""); utils().storeInMemoryDynamic(IntegerType(256)); m_context << u256(0); } - m_context << eth::Instruction::SHA3; + m_context << Instruction::SHA3; m_context << u256(0); setLValueToStorageItem(_indexAccess); } @@ -1109,12 +1109,12 @@ bool ExpressionCompiler::visit(IndexAccess const& _indexAccess) // stack layout: <value> <index> // check out-of-bounds access m_context << u256(fixedBytesType.numBytes()); - m_context << eth::Instruction::DUP2 << eth::Instruction::LT << eth::Instruction::ISZERO; + m_context << Instruction::DUP2 << Instruction::LT << Instruction::ISZERO; // out-of-bounds access throws exception m_context.appendConditionalJumpTo(m_context.errorTag()); - m_context << eth::Instruction::BYTE; - m_context << (u256(1) << (256 - 8)) << eth::Instruction::MUL; + m_context << Instruction::BYTE; + m_context << (u256(1) << (256 - 8)) << Instruction::MUL; } else if (baseType.category() == Type::Category::TypeType) { @@ -1139,11 +1139,11 @@ void ExpressionCompiler::endVisit(Identifier const& _identifier) case Type::Category::Contract: // "this" or "super" if (!dynamic_cast<ContractType const&>(*magicVar->type()).isSuper()) - m_context << eth::Instruction::ADDRESS; + m_context << Instruction::ADDRESS; break; case Type::Category::Integer: // "now" - m_context << eth::Instruction::TIMESTAMP; + m_context << Instruction::TIMESTAMP; break; default: break; @@ -1208,11 +1208,11 @@ void ExpressionCompiler::appendAndOrOperatorCode(BinaryOperation const& _binaryO solAssert(c_op == Token::Or || c_op == Token::And, ""); _binaryOperation.leftExpression().accept(*this); - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; if (c_op == Token::And) - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; eth::AssemblyItem endLabel = m_context.appendConditionalJump(); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; _binaryOperation.rightExpression().accept(*this); m_context << endLabel; } @@ -1221,9 +1221,9 @@ void ExpressionCompiler::appendCompareOperatorCode(Token::Value _operator, Type { if (_operator == Token::Equal || _operator == Token::NotEqual) { - m_context << eth::Instruction::EQ; + m_context << Instruction::EQ; if (_operator == Token::NotEqual) - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; } else { @@ -1235,19 +1235,19 @@ void ExpressionCompiler::appendCompareOperatorCode(Token::Value _operator, Type { case Token::GreaterThanOrEqual: m_context << - (isSigned ? eth::Instruction::SLT : eth::Instruction::LT) << - eth::Instruction::ISZERO; + (isSigned ? Instruction::SLT : Instruction::LT) << + Instruction::ISZERO; break; case Token::LessThanOrEqual: m_context << - (isSigned ? eth::Instruction::SGT : eth::Instruction::GT) << - eth::Instruction::ISZERO; + (isSigned ? Instruction::SGT : Instruction::GT) << + Instruction::ISZERO; break; case Token::GreaterThan: - m_context << (isSigned ? eth::Instruction::SGT : eth::Instruction::GT); + m_context << (isSigned ? Instruction::SGT : Instruction::GT); break; case Token::LessThan: - m_context << (isSigned ? eth::Instruction::SLT : eth::Instruction::LT); + m_context << (isSigned ? Instruction::SLT : Instruction::LT); break; default: BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Unknown comparison operator.")); @@ -1275,22 +1275,22 @@ void ExpressionCompiler::appendArithmeticOperatorCode(Token::Value _operator, Ty switch (_operator) { case Token::Add: - m_context << eth::Instruction::ADD; + m_context << Instruction::ADD; break; case Token::Sub: - m_context << eth::Instruction::SUB; + m_context << Instruction::SUB; break; case Token::Mul: - m_context << eth::Instruction::MUL; + m_context << Instruction::MUL; break; case Token::Div: - m_context << (c_isSigned ? eth::Instruction::SDIV : eth::Instruction::DIV); + m_context << (c_isSigned ? Instruction::SDIV : Instruction::DIV); break; case Token::Mod: - m_context << (c_isSigned ? eth::Instruction::SMOD : eth::Instruction::MOD); + m_context << (c_isSigned ? Instruction::SMOD : Instruction::MOD); break; case Token::Exp: - m_context << eth::Instruction::EXP; + m_context << Instruction::EXP; break; default: BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Unknown arithmetic operator.")); @@ -1302,13 +1302,13 @@ void ExpressionCompiler::appendBitOperatorCode(Token::Value _operator) switch (_operator) { case Token::BitOr: - m_context << eth::Instruction::OR; + m_context << Instruction::OR; break; case Token::BitAnd: - m_context << eth::Instruction::AND; + m_context << Instruction::AND; break; case Token::BitXor: - m_context << eth::Instruction::XOR; + m_context << Instruction::XOR; break; default: BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Unknown bit operator.")); @@ -1392,7 +1392,7 @@ void ExpressionCompiler::appendExternalFunctionCall( true ); for (unsigned i = 0; i < gasValueSize; ++i) - m_context << eth::swapInstruction(gasValueSize - i); + m_context << swapInstruction(gasValueSize - i); gasStackPos++; valueStackPos++; } @@ -1411,7 +1411,7 @@ void ExpressionCompiler::appendExternalFunctionCall( utils().fetchFreeMemoryPointer(); if (!_functionType.isBareCall() || manualFunctionId) { - m_context << eth::dupInstruction(2 + gasValueSize + CompilerUtils::sizeOnStack(argumentTypes)); + m_context << dupInstruction(2 + gasValueSize + CompilerUtils::sizeOnStack(argumentTypes)); utils().storeInMemoryDynamic(IntegerType(8 * CompilerUtils::dataStartOffset), false); } // If the function takes arbitrary parameters, copy dynamic length data in place. @@ -1437,21 +1437,21 @@ void ExpressionCompiler::appendExternalFunctionCall( // put on stack: <size of output> <memory pos of output> <size of input> <memory pos of input> m_context << u256(retSize); utils().fetchFreeMemoryPointer(); - m_context << eth::Instruction::DUP1 << eth::Instruction::DUP4 << eth::Instruction::SUB; - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP1 << Instruction::DUP4 << Instruction::SUB; + m_context << Instruction::DUP2; // CALL arguments: outSize, outOff, inSize, inOff (already present up to here) // [value,] addr, gas (stack top) if (isDelegateCall) solAssert(!_functionType.valueSet(), "Value set for delegatecall"); else if (_functionType.valueSet()) - m_context << eth::dupInstruction(m_context.baseToCurrentStackOffset(valueStackPos)); + m_context << dupInstruction(m_context.baseToCurrentStackOffset(valueStackPos)); else m_context << u256(0); - m_context << eth::dupInstruction(m_context.baseToCurrentStackOffset(contractStackPos)); + m_context << dupInstruction(m_context.baseToCurrentStackOffset(contractStackPos)); if (_functionType.gasSet()) - m_context << eth::dupInstruction(m_context.baseToCurrentStackOffset(gasStackPos)); + m_context << dupInstruction(m_context.baseToCurrentStackOffset(gasStackPos)); else { eth::EVMSchedule schedule; @@ -1464,15 +1464,15 @@ void ExpressionCompiler::appendExternalFunctionCall( gasNeededByCaller += schedule.callNewAccountGas; // we never know m_context << gasNeededByCaller << - eth::Instruction::GAS << - eth::Instruction::SUB; + Instruction::GAS << + Instruction::SUB; } if (isDelegateCall) - m_context << eth::Instruction::DELEGATECALL; + m_context << Instruction::DELEGATECALL; else if (isCallCode) - m_context << eth::Instruction::CALLCODE; + m_context << Instruction::CALLCODE; else - m_context << eth::Instruction::CALL; + m_context << Instruction::CALL; unsigned remainsSize = 2 + // contract address, input_memory_end @@ -1481,11 +1481,11 @@ void ExpressionCompiler::appendExternalFunctionCall( (!_functionType.isBareCall() || manualFunctionId); if (returnSuccessCondition) - m_context << eth::swapInstruction(remainsSize); + m_context << swapInstruction(remainsSize); else { //Propagate error condition (if CALL pushes 0 on stack). - m_context << eth::Instruction::ISZERO; + m_context << Instruction::ISZERO; m_context.appendConditionalJumpTo(m_context.errorTag()); } @@ -1515,7 +1515,7 @@ void ExpressionCompiler::appendExternalFunctionCall( if (memoryNeeded) utils().storeFreeMemoryPointer(); else - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } } diff --git a/libsolidity/codegen/LValue.cpp b/libsolidity/codegen/LValue.cpp index fdef6937..fcadd2ff 100644 --- a/libsolidity/codegen/LValue.cpp +++ b/libsolidity/codegen/LValue.cpp @@ -21,7 +21,7 @@ */ #include <libsolidity/codegen/LValue.h> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> #include <libsolidity/ast/Types.h> #include <libsolidity/ast/AST.h> #include <libsolidity/codegen/CompilerUtils.h> @@ -49,7 +49,7 @@ void StackVariable::retrieveValue(SourceLocation const& _location, bool) const ); solAssert(stackPos + 1 >= m_size, "Size and stack pos mismatch."); for (unsigned i = 0; i < m_size; ++i) - m_context << eth::dupInstruction(stackPos + 1); + m_context << dupInstruction(stackPos + 1); } void StackVariable::storeValue(Type const&, SourceLocation const& _location, bool _move) const @@ -63,7 +63,7 @@ void StackVariable::storeValue(Type const&, SourceLocation const& _location, boo ); else if (stackDiff > 0) for (unsigned i = 0; i < m_size; ++i) - m_context << eth::swapInstruction(stackDiff) << eth::Instruction::POP; + m_context << swapInstruction(stackDiff) << Instruction::POP; if (!_move) retrieveValue(_location); } @@ -85,11 +85,11 @@ void MemoryItem::retrieveValue(SourceLocation const&, bool _remove) const if (m_dataType->isValueType()) { if (!_remove) - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; CompilerUtils(m_context).loadFromMemoryDynamic(*m_dataType, false, m_padded, false); } else - m_context << eth::Instruction::MLOAD; + m_context << Instruction::MLOAD; } void MemoryItem::storeValue(Type const& _sourceType, SourceLocation const&, bool _move) const @@ -109,13 +109,13 @@ void MemoryItem::storeValue(Type const& _sourceType, SourceLocation const&, bool { solAssert(m_dataType->calldataEncodedSize(false) == 1, "Invalid non-padded type."); if (m_dataType->category() == Type::Category::FixedBytes) - m_context << u256(0) << eth::Instruction::BYTE; - m_context << eth::Instruction::SWAP1 << eth::Instruction::MSTORE8; + m_context << u256(0) << Instruction::BYTE; + m_context << Instruction::SWAP1 << Instruction::MSTORE8; } else { utils.storeInMemoryDynamic(*m_dataType, m_padded); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } } else @@ -124,10 +124,10 @@ void MemoryItem::storeValue(Type const& _sourceType, SourceLocation const&, bool solAssert(m_dataType->sizeOnStack() == 1, ""); if (!_move) - m_context << eth::Instruction::DUP2 << eth::Instruction::SWAP1; + m_context << Instruction::DUP2 << Instruction::SWAP1; // stack: [value] value lvalue // only store the reference - m_context << eth::Instruction::MSTORE; + m_context << Instruction::MSTORE; } } @@ -135,10 +135,10 @@ void MemoryItem::setToZero(SourceLocation const&, bool _removeReference) const { CompilerUtils utils(m_context); if (!_removeReference) - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; utils.pushZeroValue(*m_dataType); utils.storeInMemoryDynamic(*m_dataType, m_padded); - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } StorageItem::StorageItem(CompilerContext& _compilerContext, VariableDeclaration const& _declaration): @@ -165,29 +165,29 @@ void StorageItem::retrieveValue(SourceLocation const&, bool _remove) const { solAssert(m_dataType->sizeOnStack() == 1, "Invalid storage ref size."); if (_remove) - m_context << eth::Instruction::POP; // remove byte offset + m_context << Instruction::POP; // remove byte offset else - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP2; return; } if (!_remove) CompilerUtils(m_context).copyToStackTop(sizeOnStack(), sizeOnStack()); if (m_dataType->storageBytes() == 32) - m_context << eth::Instruction::POP << eth::Instruction::SLOAD; + m_context << Instruction::POP << Instruction::SLOAD; else { m_context - << eth::Instruction::SWAP1 << eth::Instruction::SLOAD << eth::Instruction::SWAP1 - << u256(0x100) << eth::Instruction::EXP << eth::Instruction::SWAP1 << eth::Instruction::DIV; + << Instruction::SWAP1 << Instruction::SLOAD << Instruction::SWAP1 + << u256(0x100) << Instruction::EXP << Instruction::SWAP1 << Instruction::DIV; if (m_dataType->category() == Type::Category::FixedBytes) - m_context << (u256(0x1) << (256 - 8 * m_dataType->storageBytes())) << eth::Instruction::MUL; + m_context << (u256(0x1) << (256 - 8 * m_dataType->storageBytes())) << Instruction::MUL; else if ( m_dataType->category() == Type::Category::Integer && dynamic_cast<IntegerType const&>(*m_dataType).isSigned() ) - m_context << u256(m_dataType->storageBytes() - 1) << eth::Instruction::SIGNEXTEND; + m_context << u256(m_dataType->storageBytes() - 1) << Instruction::SIGNEXTEND; else - m_context << ((u256(0x1) << (8 * m_dataType->storageBytes())) - 1) << eth::Instruction::AND; + m_context << ((u256(0x1) << (8 * m_dataType->storageBytes())) - 1) << Instruction::AND; } } @@ -202,32 +202,32 @@ void StorageItem::storeValue(Type const& _sourceType, SourceLocation const& _loc if (m_dataType->storageBytes() == 32) { // offset should be zero - m_context << eth::Instruction::POP; + m_context << Instruction::POP; if (!_move) - m_context << eth::Instruction::DUP2 << eth::Instruction::SWAP1; - m_context << eth::Instruction::SSTORE; + m_context << Instruction::DUP2 << Instruction::SWAP1; + m_context << Instruction::SSTORE; } else { // OR the value into the other values in the storage slot - m_context << u256(0x100) << eth::Instruction::EXP; + m_context << u256(0x100) << Instruction::EXP; // stack: value storage_ref multiplier // fetch old value - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD; + m_context << Instruction::DUP2 << Instruction::SLOAD; // stack: value storege_ref multiplier old_full_value // clear bytes in old value m_context - << eth::Instruction::DUP2 << ((u256(1) << (8 * m_dataType->storageBytes())) - 1) - << eth::Instruction::MUL; - m_context << eth::Instruction::NOT << eth::Instruction::AND; + << Instruction::DUP2 << ((u256(1) << (8 * m_dataType->storageBytes())) - 1) + << Instruction::MUL; + m_context << Instruction::NOT << Instruction::AND; // stack: value storage_ref multiplier cleared_value m_context - << eth::Instruction::SWAP1 << eth::Instruction::DUP4; + << Instruction::SWAP1 << Instruction::DUP4; // stack: value storage_ref cleared_value multiplier value if (m_dataType->category() == Type::Category::FixedBytes) m_context << (u256(0x1) << (256 - 8 * dynamic_cast<FixedBytesType const&>(*m_dataType).numBytes())) - << eth::Instruction::SWAP1 << eth::Instruction::DIV; + << Instruction::SWAP1 << Instruction::DIV; else if ( m_dataType->category() == Type::Category::Integer && dynamic_cast<IntegerType const&>(*m_dataType).isSigned() @@ -235,15 +235,15 @@ void StorageItem::storeValue(Type const& _sourceType, SourceLocation const& _loc // remove the higher order bits m_context << (u256(1) << (8 * (32 - m_dataType->storageBytes()))) - << eth::Instruction::SWAP1 - << eth::Instruction::DUP2 - << eth::Instruction::MUL - << eth::Instruction::DIV; - m_context << eth::Instruction::MUL << eth::Instruction::OR; + << Instruction::SWAP1 + << Instruction::DUP2 + << Instruction::MUL + << Instruction::DIV; + m_context << Instruction::MUL << Instruction::OR; // stack: value storage_ref updated_value - m_context << eth::Instruction::SWAP1 << eth::Instruction::SSTORE; + m_context << Instruction::SWAP1 << Instruction::SSTORE; if (_move) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } } else @@ -253,19 +253,19 @@ void StorageItem::storeValue(Type const& _sourceType, SourceLocation const& _loc "Wrong type conversation for assignment."); if (m_dataType->category() == Type::Category::Array) { - m_context << eth::Instruction::POP; // remove byte offset + m_context << Instruction::POP; // remove byte offset ArrayUtils(m_context).copyArrayToStorage( dynamic_cast<ArrayType const&>(*m_dataType), dynamic_cast<ArrayType const&>(_sourceType) ); if (_move) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } else if (m_dataType->category() == Type::Category::Struct) { // stack layout: source_ref target_ref target_offset // note that we have structs, so offset should be zero and are ignored - m_context << eth::Instruction::POP; + m_context << Instruction::POP; auto const& structType = dynamic_cast<StructType const&>(*m_dataType); auto const& sourceType = dynamic_cast<StructType const&>(_sourceType); solAssert( @@ -284,7 +284,7 @@ void StorageItem::storeValue(Type const& _sourceType, SourceLocation const& _loc { // stack layout: source_ref target_ref pair<u256, unsigned> const& offsets = sourceType.storageOffsetsOfMember(member.name); - m_context << offsets.first << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << offsets.first << Instruction::DUP3 << Instruction::ADD; m_context << u256(offsets.second); // stack: source_ref target_ref source_member_ref source_member_off StorageItem(m_context, *sourceMemberType).retrieveValue(_location, true); @@ -296,13 +296,13 @@ void StorageItem::storeValue(Type const& _sourceType, SourceLocation const& _loc // stack layout: source_ref target_ref TypePointer sourceMemberType = sourceType.memberType(member.name); m_context << sourceType.memoryOffsetOfMember(member.name); - m_context << eth::Instruction::DUP3 << eth::Instruction::ADD; + m_context << Instruction::DUP3 << Instruction::ADD; MemoryItem(m_context, *sourceMemberType).retrieveValue(_location, true); // stack layout: source_ref target_ref source_value... } unsigned stackSize = sourceMemberType->sizeOnStack(); pair<u256, unsigned> const& offsets = structType.storageOffsetsOfMember(member.name); - m_context << eth::dupInstruction(1 + stackSize) << offsets.first << eth::Instruction::ADD; + m_context << dupInstruction(1 + stackSize) << offsets.first << Instruction::ADD; m_context << u256(offsets.second); // stack: source_ref target_ref target_off source_value... target_member_ref target_member_byte_off StorageItem(m_context, *memberType).storeValue(*sourceMemberType, _location, true); @@ -312,7 +312,7 @@ void StorageItem::storeValue(Type const& _sourceType, SourceLocation const& _loc if (_move) utils.popStackSlots(2); else - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; } else BOOST_THROW_EXCEPTION( @@ -344,12 +344,12 @@ void StorageItem::setToZero(SourceLocation const&, bool _removeReference) const continue; pair<u256, unsigned> const& offsets = structType.storageOffsetsOfMember(member.name); m_context - << offsets.first << eth::Instruction::DUP3 << eth::Instruction::ADD + << offsets.first << Instruction::DUP3 << Instruction::ADD << u256(offsets.second); StorageItem(m_context, *memberType).setToZero(); } if (_removeReference) - m_context << eth::Instruction::POP << eth::Instruction::POP; + m_context << Instruction::POP << Instruction::POP; } else { @@ -360,23 +360,23 @@ void StorageItem::setToZero(SourceLocation const&, bool _removeReference) const { // offset should be zero m_context - << eth::Instruction::POP << u256(0) - << eth::Instruction::SWAP1 << eth::Instruction::SSTORE; + << Instruction::POP << u256(0) + << Instruction::SWAP1 << Instruction::SSTORE; } else { - m_context << u256(0x100) << eth::Instruction::EXP; + m_context << u256(0x100) << Instruction::EXP; // stack: storage_ref multiplier // fetch old value - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD; + m_context << Instruction::DUP2 << Instruction::SLOAD; // stack: storege_ref multiplier old_full_value // clear bytes in old value m_context - << eth::Instruction::SWAP1 << ((u256(1) << (8 * m_dataType->storageBytes())) - 1) - << eth::Instruction::MUL; - m_context << eth::Instruction::NOT << eth::Instruction::AND; + << Instruction::SWAP1 << ((u256(1) << (8 * m_dataType->storageBytes())) - 1) + << Instruction::MUL; + m_context << Instruction::NOT << Instruction::AND; // stack: storage_ref cleared_value - m_context << eth::Instruction::SWAP1 << eth::Instruction::SSTORE; + m_context << Instruction::SWAP1 << Instruction::SSTORE; } } } @@ -393,48 +393,48 @@ void StorageByteArrayElement::retrieveValue(SourceLocation const&, bool _remove) { // stack: ref byte_number if (_remove) - m_context << eth::Instruction::SWAP1 << eth::Instruction::SLOAD - << eth::Instruction::SWAP1 << eth::Instruction::BYTE; + m_context << Instruction::SWAP1 << Instruction::SLOAD + << Instruction::SWAP1 << Instruction::BYTE; else - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD - << eth::Instruction::DUP2 << eth::Instruction::BYTE; - m_context << (u256(1) << (256 - 8)) << eth::Instruction::MUL; + m_context << Instruction::DUP2 << Instruction::SLOAD + << Instruction::DUP2 << Instruction::BYTE; + m_context << (u256(1) << (256 - 8)) << Instruction::MUL; } void StorageByteArrayElement::storeValue(Type const&, SourceLocation const&, bool _move) const { // stack: value ref byte_number - m_context << u256(31) << eth::Instruction::SUB << u256(0x100) << eth::Instruction::EXP; + m_context << u256(31) << Instruction::SUB << u256(0x100) << Instruction::EXP; // stack: value ref (1<<(8*(31-byte_number))) - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD; + m_context << Instruction::DUP2 << Instruction::SLOAD; // stack: value ref (1<<(8*(31-byte_number))) old_full_value // clear byte in old value - m_context << eth::Instruction::DUP2 << u256(0xff) << eth::Instruction::MUL - << eth::Instruction::NOT << eth::Instruction::AND; + m_context << Instruction::DUP2 << u256(0xff) << Instruction::MUL + << Instruction::NOT << Instruction::AND; // stack: value ref (1<<(32-byte_number)) old_full_value_with_cleared_byte - m_context << eth::Instruction::SWAP1; - m_context << (u256(1) << (256 - 8)) << eth::Instruction::DUP5 << eth::Instruction::DIV - << eth::Instruction::MUL << eth::Instruction::OR; + m_context << Instruction::SWAP1; + m_context << (u256(1) << (256 - 8)) << Instruction::DUP5 << Instruction::DIV + << Instruction::MUL << Instruction::OR; // stack: value ref new_full_value - m_context << eth::Instruction::SWAP1 << eth::Instruction::SSTORE; + m_context << Instruction::SWAP1 << Instruction::SSTORE; if (_move) - m_context << eth::Instruction::POP; + m_context << Instruction::POP; } void StorageByteArrayElement::setToZero(SourceLocation const&, bool _removeReference) const { // stack: ref byte_number if (!_removeReference) - m_context << eth::Instruction::DUP2 << eth::Instruction::DUP2; - m_context << u256(31) << eth::Instruction::SUB << u256(0x100) << eth::Instruction::EXP; + m_context << Instruction::DUP2 << Instruction::DUP2; + m_context << u256(31) << Instruction::SUB << u256(0x100) << Instruction::EXP; // stack: ref (1<<(8*(31-byte_number))) - m_context << eth::Instruction::DUP2 << eth::Instruction::SLOAD; + m_context << Instruction::DUP2 << Instruction::SLOAD; // stack: ref (1<<(8*(31-byte_number))) old_full_value // clear byte in old value - m_context << eth::Instruction::SWAP1 << u256(0xff) << eth::Instruction::MUL; - m_context << eth::Instruction::NOT << eth::Instruction::AND; + m_context << Instruction::SWAP1 << u256(0xff) << Instruction::MUL; + m_context << Instruction::NOT << Instruction::AND; // stack: ref old_full_value_with_cleared_byte - m_context << eth::Instruction::SWAP1 << eth::Instruction::SSTORE; + m_context << Instruction::SWAP1 << Instruction::SSTORE; } StorageArrayLength::StorageArrayLength(CompilerContext& _compilerContext, const ArrayType& _arrayType): @@ -448,22 +448,22 @@ void StorageArrayLength::retrieveValue(SourceLocation const&, bool _remove) cons { ArrayUtils(m_context).retrieveLength(m_arrayType); if (_remove) - m_context << eth::Instruction::SWAP1 << eth::Instruction::POP; + m_context << Instruction::SWAP1 << Instruction::POP; } void StorageArrayLength::storeValue(Type const&, SourceLocation const&, bool _move) const { if (_move) - m_context << eth::Instruction::SWAP1; + m_context << Instruction::SWAP1; else - m_context << eth::Instruction::DUP2; + m_context << Instruction::DUP2; ArrayUtils(m_context).resizeDynamicArray(m_arrayType); } void StorageArrayLength::setToZero(SourceLocation const&, bool _removeReference) const { if (!_removeReference) - m_context << eth::Instruction::DUP1; + m_context << Instruction::DUP1; ArrayUtils(m_context).clearDynamicArray(m_arrayType); } diff --git a/libsolidity/inlineasm/AsmCodeGen.cpp b/libsolidity/inlineasm/AsmCodeGen.cpp index 89e95bc1..5fa04087 100644 --- a/libsolidity/inlineasm/AsmCodeGen.cpp +++ b/libsolidity/inlineasm/AsmCodeGen.cpp @@ -25,6 +25,7 @@ #include <functional> #include <libevmasm/Assembly.h> #include <libevmasm/SourceLocation.h> +#include <libevmasm/Instruction.h> #include <libsolidity/inlineasm/AsmParser.h> #include <libsolidity/inlineasm/AsmData.h> @@ -116,7 +117,7 @@ public: m_identifierAccess = [](assembly::Identifier const&, eth::Assembly&, CodeGenerator::IdentifierContext) { return false; }; } - void operator()(Instruction const& _instruction) + void operator()(dev::solidity::assembly::Instruction const& _instruction) { m_state.assembly.append(_instruction.instruction); } @@ -145,7 +146,7 @@ public: "Variable inaccessible, too deep inside stack (" + boost::lexical_cast<string>(heightDiff) + ")" ); else - m_state.assembly.append(eth::dupInstruction(heightDiff)); + m_state.assembly.append(solidity::dupInstruction(heightDiff)); return; } else if (eth::AssemblyItem const* label = m_state.findLabel(_identifier.name)) @@ -196,7 +197,7 @@ public: //@TODO check height before and after while (m_state.variables.size() > numVariables) { - m_state.assembly.append(eth::Instruction::POP); + m_state.assembly.append(solidity::Instruction::POP); m_state.variables.pop_back(); } } @@ -215,8 +216,8 @@ private: ); else { - m_state.assembly.append(eth::swapInstruction(heightDiff)); - m_state.assembly.append(eth::Instruction::POP); + m_state.assembly.append(solidity::swapInstruction(heightDiff)); + m_state.assembly.append(solidity::Instruction::POP); } return; } diff --git a/libsolidity/inlineasm/AsmData.h b/libsolidity/inlineasm/AsmData.h index 0361a4c2..42f0ae31 100644 --- a/libsolidity/inlineasm/AsmData.h +++ b/libsolidity/inlineasm/AsmData.h @@ -23,7 +23,7 @@ #pragma once #include <boost/variant.hpp> -#include <libevmcore/Instruction.h> +#include <libevmasm/Instruction.h> namespace dev { @@ -35,7 +35,7 @@ namespace assembly /// What follows are the AST nodes for assembly. /// Direct EVM instruction (except PUSHi and JUMPDEST) -struct Instruction { eth::Instruction instruction; }; +struct Instruction { solidity::Instruction instruction; }; /// Literal number or string (up to 32 bytes) struct Literal { bool isNumber; std::string value; }; /// External / internal identifier or label reference diff --git a/libsolidity/inlineasm/AsmParser.cpp b/libsolidity/inlineasm/AsmParser.cpp index 124a5d26..68050733 100644 --- a/libsolidity/inlineasm/AsmParser.cpp +++ b/libsolidity/inlineasm/AsmParser.cpp @@ -23,7 +23,6 @@ #include <libsolidity/inlineasm/AsmParser.h> #include <ctype.h> #include <algorithm> -#include <libevmcore/Instruction.h> #include <libsolidity/parsing/Scanner.h> using namespace std; @@ -121,17 +120,17 @@ assembly::Statement Parser::parseExpression() assembly::Statement Parser::parseElementaryOperation(bool _onlySinglePusher) { // Allowed instructions, lowercase names. - static map<string, eth::Instruction> s_instructions; + static map<string, dev::solidity::Instruction> s_instructions; if (s_instructions.empty()) - for (auto const& instruction: eth::c_instructions) + for (auto const& instruction: solidity::c_instructions) { if ( - instruction.second == eth::Instruction::JUMPDEST || - (eth::Instruction::PUSH1 <= instruction.second && instruction.second <= eth::Instruction::PUSH32) + instruction.second == solidity::Instruction::JUMPDEST || + (solidity::Instruction::PUSH1 <= instruction.second && instruction.second <= solidity::Instruction::PUSH32) ) continue; string name = instruction.first; - if (instruction.second == eth::Instruction::SUICIDE) + if (instruction.second == solidity::Instruction::SUICIDE) name = "selfdestruct"; transform(name.begin(), name.end(), name.begin(), [](unsigned char _c) { return tolower(_c); }); s_instructions[name] = instruction.second; @@ -152,10 +151,10 @@ assembly::Statement Parser::parseElementaryOperation(bool _onlySinglePusher) // first search the set of instructions. if (s_instructions.count(literal)) { - eth::Instruction const& instr = s_instructions[literal]; + dev::solidity::Instruction const& instr = s_instructions[literal]; if (_onlySinglePusher) { - eth::InstructionInfo info = eth::instructionInfo(instr); + InstructionInfo info = dev::solidity::instructionInfo(instr); if (info.ret != 1) fatalParserError("Instruction " + info.name + " not allowed in this context."); } @@ -200,11 +199,11 @@ FunctionalInstruction Parser::parseFunctionalInstruction(assembly::Statement con { if (_instruction.type() != typeid(Instruction)) fatalParserError("Assembly instruction required in front of \"(\")"); - eth::Instruction instr = boost::get<Instruction>(_instruction).instruction; - eth::InstructionInfo instrInfo = eth::instructionInfo(instr); - if (eth::Instruction::DUP1 <= instr && instr <= eth::Instruction::DUP16) + solidity::Instruction instr = boost::get<solidity::assembly::Instruction>(_instruction).instruction; + InstructionInfo instrInfo = instructionInfo(instr); + if (solidity::Instruction::DUP1 <= instr && instr <= solidity::Instruction::DUP16) fatalParserError("DUPi instructions not allowed for functional notation"); - if (eth::Instruction::SWAP1 <= instr && instr <= eth::Instruction::SWAP16) + if (solidity::Instruction::SWAP1 <= instr && instr <= solidity::Instruction::SWAP16) fatalParserError("SWAPi instructions not allowed for functional notation"); expectToken(Token::LParen); diff --git a/libsolidity/interface/GasEstimator.cpp b/libsolidity/interface/GasEstimator.cpp index d460ba76..99ed75bc 100644 --- a/libsolidity/interface/GasEstimator.cpp +++ b/libsolidity/interface/GasEstimator.cpp @@ -137,8 +137,8 @@ GasEstimator::GasConsumption GasEstimator::functionalEstimation( using Id = ExpressionClasses::Id; using Ids = vector<Id>; Id hashValue = classes.find(u256(FixedHash<4>::Arith(FixedHash<4>(dev::sha3(_signature))))); - Id calldata = classes.find(eth::Instruction::CALLDATALOAD, Ids{classes.find(u256(0))}); - classes.forceEqual(hashValue, eth::Instruction::DIV, Ids{ + Id calldata = classes.find(Instruction::CALLDATALOAD, Ids{classes.find(u256(0))}); + classes.forceEqual(hashValue, Instruction::DIV, Ids{ calldata, classes.find(u256(1) << (8 * 28)) }); @@ -165,7 +165,7 @@ GasEstimator::GasConsumption GasEstimator::functionalEstimation( AssemblyItem invalidTag(PushTag, u256(-0x10)); state->feedItem(invalidTag, true); if (parametersSize > 0) - state->feedItem(eth::swapInstruction(parametersSize)); + state->feedItem(swapInstruction(parametersSize)); return PathGasMeter(_items).estimateMax(_offset, state); } |