aboutsummaryrefslogtreecommitdiffstats
path: root/ArrayUtils.cpp
diff options
context:
space:
mode:
authorchriseth <c@ethdev.com>2015-03-06 20:00:54 +0800
committerchriseth <c@ethdev.com>2015-03-06 20:17:52 +0800
commit11e943fc6a23c78279fcda01fb5acdc28c6fd6e3 (patch)
tree86445b5d10a62387c4231ce6f446a8e321763492 /ArrayUtils.cpp
parentd8b156ecbbb4d470ba3432975694585dd5a019e2 (diff)
downloaddexon-solidity-11e943fc6a23c78279fcda01fb5acdc28c6fd6e3.tar.gz
dexon-solidity-11e943fc6a23c78279fcda01fb5acdc28c6fd6e3.tar.zst
dexon-solidity-11e943fc6a23c78279fcda01fb5acdc28c6fd6e3.zip
Fix for arrays containing mappings.
Diffstat (limited to 'ArrayUtils.cpp')
-rw-r--r--ArrayUtils.cpp19
1 files changed, 17 insertions, 2 deletions
diff --git a/ArrayUtils.cpp b/ArrayUtils.cpp
index 3619b540..f0d7d6a8 100644
--- a/ArrayUtils.cpp
+++ b/ArrayUtils.cpp
@@ -65,6 +65,16 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons
if (_targetType.isDynamicallySized())
// store new target length
m_context << eth::Instruction::DUP3 << eth::Instruction::DUP3 << eth::Instruction::SSTORE;
+ if (sourceBaseType->getCategory() == Type::Category::Mapping)
+ {
+ solAssert(targetBaseType->getCategory() == Type::Category::Mapping, "");
+ solAssert(_sourceType.getLocation() == ArrayType::Location::Storage, "");
+ // nothing to copy
+ m_context
+ << eth::Instruction::POP << eth::Instruction::POP
+ << eth::Instruction::POP << eth::Instruction::POP;
+ return;
+ }
// compute hashes (data positions)
m_context << eth::Instruction::SWAP1;
if (_targetType.isDynamicallySized())
@@ -114,7 +124,7 @@ void ArrayUtils::copyArrayToStorage(ArrayType const& _targetType, ArrayType cons
else if (sourceBaseType->isValueType())
CompilerUtils(m_context).loadFromMemoryDynamic(*sourceBaseType, true, true, false);
else
- solAssert(false, "Copying of unknown type requested.");
+ solAssert(false, "Copying of unknown type requested: " + sourceBaseType->toString());
m_context << eth::dupInstruction(2 + sourceBaseType->getSizeOnStack());
StorageItem(m_context, *targetBaseType).storeValue(*sourceBaseType, SourceLocation(), true);
}
@@ -148,7 +158,7 @@ void ArrayUtils::clearArray(ArrayType const& _type) const
solAssert(_type.getLocation() == ArrayType::Location::Storage, "");
if (_type.isDynamicallySized())
clearDynamicArray(_type);
- else if (_type.getLength() == 0)
+ else if (_type.getLength() == 0 || _type.getBaseType()->getCategory() == Type::Category::Mapping)
m_context << eth::Instruction::POP;
else if (_type.getLength() < 5) // unroll loop for small arrays @todo choose a good value
{
@@ -242,6 +252,11 @@ void ArrayUtils::resizeDynamicArray(const ArrayType& _type) const
void ArrayUtils::clearStorageLoop(Type const& _type) const
{
+ if (_type.getCategory() == Type::Category::Mapping)
+ {
+ m_context << eth::Instruction::POP;
+ return;
+ }
// stack: end_pos pos
eth::AssemblyItem loopStart = m_context.newTag();
m_context << loopStart;