Provide access to the name of contracts.

This commit is contained in:
Alex Beregszaszi
2019-02-26 14:07:03 +00:00
parent 1169004cec
commit d2f493268b
10 changed files with 93 additions and 8 deletions
+2
View File
@@ -2154,6 +2154,8 @@ bool TypeChecker::visit(MemberAccess const& _memberAccess)
"Circular reference for contract code access."
);
}
else if (magicType->kind() == MagicType::Kind::MetaType && memberName == "name")
annotation.isPure = true;
}
return false;
+2 -1
View File
@@ -340,7 +340,8 @@ void ViewPureChecker::endVisit(MemberAccess const& _memberAccess)
{MagicType::Kind::Message, "data"},
{MagicType::Kind::Message, "sig"},
{MagicType::Kind::MetaType, "creationCode"},
{MagicType::Kind::MetaType, "runtimeCode"}
{MagicType::Kind::MetaType, "runtimeCode"},
{MagicType::Kind::MetaType, "name"},
};
set<MagicMember> static const payableMembers{
{MagicType::Kind::Message, "value"}
+3 -2
View File
@@ -3490,8 +3490,9 @@ MemberList::MemberMap MagicType::nativeMembers(ContractDefinition const*) const
ContractDefinition const& contract = dynamic_cast<ContractType const&>(*m_typeArgument).contractDefinition();
if (contract.canBeDeployed())
return MemberList::MemberMap({
{"creationCode", std::make_shared<ArrayType>(DataLocation::Memory)},
{"runtimeCode", std::make_shared<ArrayType>(DataLocation::Memory)}
{"creationCode", make_shared<ArrayType>(DataLocation::Memory)},
{"runtimeCode", make_shared<ArrayType>(DataLocation::Memory)},
{"name", make_shared<ArrayType>(DataLocation::Memory, true)},
});
else
return {};
+5 -5
View File
@@ -186,6 +186,11 @@ public:
/// Stack post:
void memoryCopy();
/// Stores the given string in memory.
/// Stack pre: mempos
/// Stack post:
void storeStringData(bytesConstRef _data);
/// Converts the combined and left-aligned (right-aligned if @a _rightAligned is true)
/// external function type <address><function identifier> into two stack slots:
/// address (right aligned), function identifier (right aligned)
@@ -285,11 +290,6 @@ private:
/// Address of the precompiled identity contract.
static unsigned const identityContractAddress;
/// Stores the given string in memory.
/// Stack pre: mempos
/// Stack post:
void storeStringData(bytesConstRef _data);
/// Appends code that cleans higher-order bits for integer types.
void cleanHigherOrderBits(IntegerType const& _typeOnStack);
@@ -1361,6 +1361,18 @@ bool ExpressionCompiler::visit(MemberAccess const& _memberAccess)
);
m_context << Instruction::POP;
}
else if (member == "name")
{
TypePointer arg = dynamic_cast<MagicType const&>(*_memberAccess.expression().annotation().type).typeArgument();
ContractDefinition const& contract = dynamic_cast<ContractType const&>(*arg).contractDefinition();
m_context << u256(contract.name().length() + 32);
utils().allocateMemory();
// store string length
m_context << u256(contract.name().length()) << Instruction::DUP2 << Instruction::MSTORE;
// adjust pointer
m_context << Instruction::DUP1 << u256(32) << Instruction::ADD;
utils().storeStringData(contract.name());
}
else
solAssert(false, "Unknown magic member.");
break;