Lazy-initialize string and bytes types.

This commit is contained in:
chriseth 2019-04-16 19:45:25 +02:00
parent 4656d7ca7d
commit 2761aed1d3
2 changed files with 50 additions and 13 deletions

View File

@ -26,10 +26,14 @@ using namespace solidity;
BoolType const TypeProvider::m_boolType{}; BoolType const TypeProvider::m_boolType{};
InaccessibleDynamicType const TypeProvider::m_inaccessibleDynamicType{}; InaccessibleDynamicType const TypeProvider::m_inaccessibleDynamicType{};
ArrayType const TypeProvider::m_bytesStorageType{DataLocation::Storage, false};
ArrayType const TypeProvider::m_bytesMemoryType{DataLocation::Memory, false}; /// The string and bytes unique_ptrs are initialized when they are first used because
ArrayType const TypeProvider::m_stringStorageType{DataLocation::Storage, true}; /// they rely on `byte` being available which we cannot guarantee in the static init context.
ArrayType const TypeProvider::m_stringMemoryType{DataLocation::Memory, true}; std::unique_ptr<ArrayType> TypeProvider::m_bytesStorageType;
std::unique_ptr<ArrayType> TypeProvider::m_bytesMemoryType;
std::unique_ptr<ArrayType> TypeProvider::m_stringStorageType;
std::unique_ptr<ArrayType> TypeProvider::m_stringMemoryType;
TupleType const TypeProvider::m_emptyTupleType{}; TupleType const TypeProvider::m_emptyTupleType{};
AddressType const TypeProvider::m_payableAddressType{StateMutability::Payable}; AddressType const TypeProvider::m_payableAddressType{StateMutability::Payable};
AddressType const TypeProvider::m_addressType{StateMutability::NonPayable}; AddressType const TypeProvider::m_addressType{StateMutability::NonPayable};
@ -155,6 +159,8 @@ inline void clearCache(Type const& type)
template <typename T> template <typename T>
inline void clearCache(unique_ptr<T> const& type) inline void clearCache(unique_ptr<T> const& type)
{ {
// Some lazy-initialized types might not exist yet.
if (type)
type->clearCache(); type->clearCache();
} }
@ -287,6 +293,34 @@ TypePointer TypeProvider::fromElementaryTypeName(string const& _name)
} }
} }
ArrayType const* TypeProvider::bytesType()
{
if (!m_bytesStorageType)
m_bytesStorageType = make_unique<ArrayType>(DataLocation::Storage, false);
return m_bytesStorageType.get();
}
ArrayType const* TypeProvider::bytesMemoryType()
{
if (!m_bytesMemoryType)
m_bytesMemoryType = make_unique<ArrayType>(DataLocation::Memory, false);
return m_bytesMemoryType.get();
}
ArrayType const* TypeProvider::stringType()
{
if (!m_stringStorageType)
m_stringStorageType = make_unique<ArrayType>(DataLocation::Storage, true);
return m_stringStorageType.get();
}
ArrayType const* TypeProvider::stringMemoryType()
{
if (!m_stringMemoryType)
m_stringMemoryType = make_unique<ArrayType>(DataLocation::Memory, true);
return m_stringMemoryType.get();
}
TypePointer TypeProvider::forLiteral(Literal const& _literal) TypePointer TypeProvider::forLiteral(Literal const& _literal)
{ {
switch (_literal.token()) switch (_literal.token())

View File

@ -66,10 +66,10 @@ public:
static FixedBytesType const* byteType() { return fixedBytesType(1); } static FixedBytesType const* byteType() { return fixedBytesType(1); }
static FixedBytesType const* fixedBytesType(unsigned m) { return m_bytesM.at(m - 1).get(); } static FixedBytesType const* fixedBytesType(unsigned m) { return m_bytesM.at(m - 1).get(); }
static ArrayType const* bytesType() noexcept { return &m_bytesStorageType; } static ArrayType const* bytesType();
static ArrayType const* bytesMemoryType() noexcept { return &m_bytesMemoryType; } static ArrayType const* bytesMemoryType();
static ArrayType const* stringType() noexcept { return &m_stringStorageType; } static ArrayType const* stringType();
static ArrayType const* stringMemoryType() noexcept { return &m_stringMemoryType; } static ArrayType const* stringMemoryType();
/// Constructor for a byte array ("bytes") and string. /// Constructor for a byte array ("bytes") and string.
static ArrayType const* arrayType(DataLocation _location, bool _isString = false); static ArrayType const* arrayType(DataLocation _location, bool _isString = false);
@ -199,10 +199,13 @@ private:
static BoolType const m_boolType; static BoolType const m_boolType;
static InaccessibleDynamicType const m_inaccessibleDynamicType; static InaccessibleDynamicType const m_inaccessibleDynamicType;
static ArrayType const m_bytesStorageType;
static ArrayType const m_bytesMemoryType; /// These are lazy-initialized because they depend on `byte` being available.
static ArrayType const m_stringStorageType; static std::unique_ptr<ArrayType> m_bytesStorageType;
static ArrayType const m_stringMemoryType; static std::unique_ptr<ArrayType> m_bytesMemoryType;
static std::unique_ptr<ArrayType> m_stringStorageType;
static std::unique_ptr<ArrayType> m_stringMemoryType;
static TupleType const m_emptyTupleType; static TupleType const m_emptyTupleType;
static AddressType const m_payableAddressType; static AddressType const m_payableAddressType;
static AddressType const m_addressType; static AddressType const m_addressType;