diff --git a/libsolidity/codegen/YulUtilFunctions.cpp b/libsolidity/codegen/YulUtilFunctions.cpp index 69e8a7131..c687924b3 100644 --- a/libsolidity/codegen/YulUtilFunctions.cpp +++ b/libsolidity/codegen/YulUtilFunctions.cpp @@ -1911,8 +1911,23 @@ string YulUtilFunctions::conversionFunction(Type const& _from, Type const& _to) break; } case Type::Category::Struct: - solUnimplementedAssert(false, "Struct conversion not implemented."); + { + solAssert(toCategory == Type::Category::Struct, ""); + auto const& fromStructType = dynamic_cast(_from); + auto const& toStructType = dynamic_cast(_to); + solAssert(fromStructType.structDefinition() == toStructType.structDefinition(), ""); + + solUnimplementedAssert(!fromStructType.isDynamicallyEncoded(), ""); + solUnimplementedAssert(toStructType.location() == DataLocation::Memory, ""); + solUnimplementedAssert(fromStructType.location() == DataLocation::CallData, ""); + + body = Whiskers(R"( + converted := (value, calldatasize()) + )")("abiDecode", ABIFunctions(m_evmVersion, m_revertStrings, m_functionCollector).tupleDecoder( + {&toStructType} + )).render(); break; + } case Type::Category::FixedBytes: { FixedBytesType const& from = dynamic_cast(_from); diff --git a/test/libsolidity/semanticTests/structs/calldata/calldata_struct_to_memory.sol b/test/libsolidity/semanticTests/structs/calldata/calldata_struct_to_memory.sol index db8171a20..04d675371 100644 --- a/test/libsolidity/semanticTests/structs/calldata/calldata_struct_to_memory.sol +++ b/test/libsolidity/semanticTests/structs/calldata/calldata_struct_to_memory.sol @@ -1,6 +1,5 @@ pragma experimental ABIEncoderV2; - contract C { struct S { uint256 a; @@ -13,5 +12,7 @@ contract C { } } +// ==== +// compileViaYul: also // ---- // f((uint256,uint256)): 42, 23 -> 42, 23 diff --git a/test/libsolidity/semanticTests/various/nested_calldata_struct_to_memory.sol b/test/libsolidity/semanticTests/various/nested_calldata_struct_to_memory.sol index e0a25a857..19b2f64a7 100644 --- a/test/libsolidity/semanticTests/various/nested_calldata_struct_to_memory.sol +++ b/test/libsolidity/semanticTests/various/nested_calldata_struct_to_memory.sol @@ -23,5 +23,7 @@ contract C { } } +// ==== +// compileViaYul: also // ---- // f((uint256,uint256,(uint256,uint256),uint256)): 1, 2, 3, 4, 5 -> 1, 2, 3, 4, 5