Allow indexed structs in events with encoder v2.

This commit is contained in:
chriseth 2019-01-24 14:40:22 +01:00
parent 0c2d623ee4
commit a8d0ef4bad
2 changed files with 9 additions and 14 deletions

View File

@ -578,17 +578,7 @@ bool TypeChecker::visit(EventDefinition const& _eventDef)
for (ASTPointer<VariableDeclaration> const& var: _eventDef.parameters())
{
if (var->isIndexed())
{
numIndexed++;
if (
_eventDef.sourceUnit().annotation().experimentalFeatures.count(ExperimentalFeature::ABIEncoderV2) &&
dynamic_cast<ReferenceType const*>(type(*var).get())
)
m_errorReporter.typeError(
var->location(),
"Indexed reference types cannot yet be used with ABIEncoderV2."
);
}
if (!type(*var)->canLiveOutsideStorage())
m_errorReporter.typeError(var->location(), "Type is required to live outside storage.");
if (!type(*var)->interfaceType(false))

View File

@ -731,6 +731,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall)
}
arguments.front()->accept(*this);
utils().fetchFreeMemoryPointer();
solAssert(function.parameterTypes().front()->isValueType(), "");
utils().packedEncode(
{arguments.front()->annotation().type},
{function.parameterTypes().front()}
@ -744,28 +745,32 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall)
_functionCall.expression().accept(*this);
auto const& event = dynamic_cast<EventDefinition const&>(function.declaration());
unsigned numIndexed = 0;
TypePointers paramTypes = function.parameterTypes();
// All indexed arguments go to the stack
for (unsigned arg = arguments.size(); arg > 0; --arg)
if (event.parameters()[arg - 1]->isIndexed())
{
++numIndexed;
arguments[arg - 1]->accept(*this);
if (auto const& arrayType = dynamic_pointer_cast<ArrayType const>(function.parameterTypes()[arg - 1]))
if (auto const& referenceType = dynamic_pointer_cast<ReferenceType const>(paramTypes[arg - 1]))
{
utils().fetchFreeMemoryPointer();
utils().packedEncode(
{arguments[arg - 1]->annotation().type},
{arrayType}
{referenceType}
);
utils().toSizeAfterFreeMemoryPointer();
m_context << Instruction::KECCAK256;
}
else
{
solAssert(paramTypes[arg - 1]->isValueType(), "");
utils().convertType(
*arguments[arg - 1]->annotation().type,
*function.parameterTypes()[arg - 1],
*paramTypes[arg - 1],
true
);
}
}
if (!event.isAnonymous())
{
@ -782,7 +787,7 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall)
{
arguments[arg]->accept(*this);
nonIndexedArgTypes.push_back(arguments[arg]->annotation().type);
nonIndexedParamTypes.push_back(function.parameterTypes()[arg]);
nonIndexedParamTypes.push_back(paramTypes[arg]);
}
utils().fetchFreeMemoryPointer();
utils().abiEncode(nonIndexedArgTypes, nonIndexedParamTypes);