mirror of
https://github.com/ethereum/solidity
synced 2023-10-03 13:03:40 +00:00
Remove clone feature.
This commit is contained in:
parent
d33e5683f5
commit
71e26f6adb
@ -34,6 +34,7 @@ Breaking Changes:
|
|||||||
* General: C99-style scoping rules are enforced now. This was already the case in the experimental 0.5.0 mode.
|
* General: C99-style scoping rules are enforced now. This was already the case in the experimental 0.5.0 mode.
|
||||||
* General: Disallow combining hex numbers with unit denominations (e.g. ``0x1e wei``). This was already the case in the experimental 0.5.0 mode.
|
* General: Disallow combining hex numbers with unit denominations (e.g. ``0x1e wei``). This was already the case in the experimental 0.5.0 mode.
|
||||||
* JSON AST: Remove ``constant`` and ``payable`` fields (the information is encoded in the ``stateMutability`` field).
|
* JSON AST: Remove ``constant`` and ``payable`` fields (the information is encoded in the ``stateMutability`` field).
|
||||||
|
* Interface: Remove "clone contract" feature. The ``--clone-bin`` and ``--combined-json clone-bin`` commandline options are not available anymore.
|
||||||
* Name Resolver: Do not exclude public state variables when looking for conflicting declarations.
|
* Name Resolver: Do not exclude public state variables when looking for conflicting declarations.
|
||||||
* Optimizer: Remove the no-op ``PUSH1 0 NOT AND`` sequence.
|
* Optimizer: Remove the no-op ``PUSH1 0 NOT AND`` sequence.
|
||||||
* Parser: Disallow trailing dots that are not followed by a number.
|
* Parser: Disallow trailing dots that are not followed by a number.
|
||||||
|
@ -46,19 +46,6 @@ void Compiler::compileContract(
|
|||||||
m_context.optimise(m_optimize, m_optimizeRuns);
|
m_context.optimise(m_optimize, m_optimizeRuns);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Compiler::compileClone(
|
|
||||||
ContractDefinition const& _contract,
|
|
||||||
map<ContractDefinition const*, eth::Assembly const*> const& _contracts
|
|
||||||
)
|
|
||||||
{
|
|
||||||
solAssert(!_contract.isLibrary(), "");
|
|
||||||
ContractCompiler runtimeCompiler(nullptr, m_runtimeContext, m_optimize);
|
|
||||||
ContractCompiler cloneCompiler(&runtimeCompiler, m_context, m_optimize);
|
|
||||||
m_runtimeSub = cloneCompiler.compileClone(_contract, _contracts);
|
|
||||||
|
|
||||||
m_context.optimise(m_optimize, m_optimizeRuns);
|
|
||||||
}
|
|
||||||
|
|
||||||
eth::AssemblyItem Compiler::functionEntryLabel(FunctionDefinition const& _function) const
|
eth::AssemblyItem Compiler::functionEntryLabel(FunctionDefinition const& _function) const
|
||||||
{
|
{
|
||||||
return m_runtimeContext.functionEntryLabelIfExists(_function);
|
return m_runtimeContext.functionEntryLabelIfExists(_function);
|
||||||
|
@ -50,12 +50,6 @@ public:
|
|||||||
std::map<ContractDefinition const*, eth::Assembly const*> const& _contracts,
|
std::map<ContractDefinition const*, eth::Assembly const*> const& _contracts,
|
||||||
bytes const& _metadata
|
bytes const& _metadata
|
||||||
);
|
);
|
||||||
/// Compiles a contract that uses DELEGATECALL to call into a pre-deployed version of the given
|
|
||||||
/// contract at runtime, but contains the full creation-time code.
|
|
||||||
void compileClone(
|
|
||||||
ContractDefinition const& _contract,
|
|
||||||
std::map<ContractDefinition const*, eth::Assembly const*> const& _contracts
|
|
||||||
);
|
|
||||||
/// @returns Entire assembly.
|
/// @returns Entire assembly.
|
||||||
eth::Assembly const& assembly() const { return m_context.assembly(); }
|
eth::Assembly const& assembly() const { return m_context.assembly(); }
|
||||||
/// @returns The entire assembled object (with constructor).
|
/// @returns The entire assembled object (with constructor).
|
||||||
|
@ -94,27 +94,6 @@ size_t ContractCompiler::compileConstructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ContractCompiler::compileClone(
|
|
||||||
ContractDefinition const& _contract,
|
|
||||||
map<ContractDefinition const*, eth::Assembly const*> const& _contracts
|
|
||||||
)
|
|
||||||
{
|
|
||||||
initializeContext(_contract, _contracts);
|
|
||||||
|
|
||||||
appendInitAndConstructorCode(_contract);
|
|
||||||
|
|
||||||
//@todo determine largest return size of all runtime functions
|
|
||||||
auto runtimeSub = m_context.addSubroutine(cloneRuntime());
|
|
||||||
|
|
||||||
// stack contains sub size
|
|
||||||
m_context << Instruction::DUP1 << runtimeSub << u256(0) << Instruction::CODECOPY;
|
|
||||||
m_context << u256(0) << Instruction::RETURN;
|
|
||||||
|
|
||||||
appendMissingFunctions();
|
|
||||||
|
|
||||||
return size_t(runtimeSub.data());
|
|
||||||
}
|
|
||||||
|
|
||||||
void ContractCompiler::initializeContext(
|
void ContractCompiler::initializeContext(
|
||||||
ContractDefinition const& _contract,
|
ContractDefinition const& _contract,
|
||||||
map<ContractDefinition const*, eth::Assembly const*> const& _compiledContracts
|
map<ContractDefinition const*, eth::Assembly const*> const& _compiledContracts
|
||||||
@ -980,29 +959,6 @@ void ContractCompiler::compileExpression(Expression const& _expression, TypePoin
|
|||||||
CompilerUtils(m_context).convertType(*_expression.annotation().type, *_targetType);
|
CompilerUtils(m_context).convertType(*_expression.annotation().type, *_targetType);
|
||||||
}
|
}
|
||||||
|
|
||||||
eth::AssemblyPointer ContractCompiler::cloneRuntime() const
|
|
||||||
{
|
|
||||||
eth::Assembly a;
|
|
||||||
a << Instruction::CALLDATASIZE;
|
|
||||||
a << u256(0) << Instruction::DUP1 << Instruction::CALLDATACOPY;
|
|
||||||
//@todo adjust for larger return values, make this dynamic.
|
|
||||||
a << u256(0x20) << u256(0) << Instruction::CALLDATASIZE;
|
|
||||||
a << u256(0);
|
|
||||||
// this is the address which has to be substituted by the linker.
|
|
||||||
//@todo implement as special "marker" AssemblyItem.
|
|
||||||
a << u256("0xcafecafecafecafecafecafecafecafecafecafe");
|
|
||||||
a << u256(eth::GasCosts::callGas(m_context.evmVersion()) + 10) << Instruction::GAS << Instruction::SUB;
|
|
||||||
a << Instruction::DELEGATECALL;
|
|
||||||
//Propagate error condition (if DELEGATECALL pushes 0 on stack).
|
|
||||||
a << Instruction::ISZERO;
|
|
||||||
a << Instruction::ISZERO;
|
|
||||||
eth::AssemblyItem afterTag = a.appendJumpI().tag();
|
|
||||||
a << Instruction::INVALID << afterTag;
|
|
||||||
//@todo adjust for larger return values, make this dynamic.
|
|
||||||
a << u256(0x20) << u256(0) << Instruction::RETURN;
|
|
||||||
return make_shared<eth::Assembly>(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ContractCompiler::popScopedVariables(ASTNode const* _node)
|
void ContractCompiler::popScopedVariables(ASTNode const* _node)
|
||||||
{
|
{
|
||||||
unsigned blockHeight = m_scopeStackHeight.at(m_modifierDepth).at(_node);
|
unsigned blockHeight = m_scopeStackHeight.at(m_modifierDepth).at(_node);
|
||||||
|
@ -56,13 +56,6 @@ public:
|
|||||||
ContractDefinition const& _contract,
|
ContractDefinition const& _contract,
|
||||||
std::map<ContractDefinition const*, eth::Assembly const*> const& _contracts
|
std::map<ContractDefinition const*, eth::Assembly const*> const& _contracts
|
||||||
);
|
);
|
||||||
/// Compiles a contract that uses DELEGATECALL to call into a pre-deployed version of the given
|
|
||||||
/// contract at runtime, but contains the full creation-time code.
|
|
||||||
/// @returns the identifier of the runtime sub-assembly.
|
|
||||||
size_t compileClone(
|
|
||||||
ContractDefinition const& _contract,
|
|
||||||
std::map<ContractDefinition const*, eth::Assembly const*> const& _contracts
|
|
||||||
);
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/// Registers the non-function objects inside the contract with the context and stores the basic
|
/// Registers the non-function objects inside the contract with the context and stores the basic
|
||||||
@ -122,9 +115,6 @@ private:
|
|||||||
void appendStackVariableInitialisation(VariableDeclaration const& _variable);
|
void appendStackVariableInitialisation(VariableDeclaration const& _variable);
|
||||||
void compileExpression(Expression const& _expression, TypePointer const& _targetType = TypePointer());
|
void compileExpression(Expression const& _expression, TypePointer const& _targetType = TypePointer());
|
||||||
|
|
||||||
/// @returns the runtime assembly for clone contracts.
|
|
||||||
eth::AssemblyPointer cloneRuntime() const;
|
|
||||||
|
|
||||||
/// Frees the variables of a certain scope (to be used when leaving).
|
/// Frees the variables of a certain scope (to be used when leaving).
|
||||||
void popScopedVariables(ASTNode const* _node);
|
void popScopedVariables(ASTNode const* _node);
|
||||||
|
|
||||||
|
@ -329,7 +329,6 @@ void CompilerStack::link()
|
|||||||
{
|
{
|
||||||
contract.second.object.link(m_libraries);
|
contract.second.object.link(m_libraries);
|
||||||
contract.second.runtimeObject.link(m_libraries);
|
contract.second.runtimeObject.link(m_libraries);
|
||||||
contract.second.cloneObject.link(m_libraries);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -408,11 +407,6 @@ eth::LinkerObject const& CompilerStack::runtimeObject(string const& _contractNam
|
|||||||
return contract(_contractName).runtimeObject;
|
return contract(_contractName).runtimeObject;
|
||||||
}
|
}
|
||||||
|
|
||||||
eth::LinkerObject const& CompilerStack::cloneObject(string const& _contractName) const
|
|
||||||
{
|
|
||||||
return contract(_contractName).cloneObject;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// FIXME: cache this string
|
/// FIXME: cache this string
|
||||||
string CompilerStack::assemblyString(string const& _contractName, StringMap _sourceCodes) const
|
string CompilerStack::assemblyString(string const& _contractName, StringMap _sourceCodes) const
|
||||||
{
|
{
|
||||||
@ -767,23 +761,6 @@ void CompilerStack::compileContract(
|
|||||||
}
|
}
|
||||||
|
|
||||||
_compiledContracts[compiledContract.contract] = &compiler->assembly();
|
_compiledContracts[compiledContract.contract] = &compiler->assembly();
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (!_contract.isLibrary())
|
|
||||||
{
|
|
||||||
Compiler cloneCompiler(m_evmVersion, m_optimize, m_optimizeRuns);
|
|
||||||
cloneCompiler.compileClone(_contract, _compiledContracts);
|
|
||||||
compiledContract.cloneObject = cloneCompiler.assembledObject();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (eth::AssemblyException const&)
|
|
||||||
{
|
|
||||||
// In some cases (if the constructor requests a runtime function), it is not
|
|
||||||
// possible to compile the clone.
|
|
||||||
|
|
||||||
// TODO: Report error / warning
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
string const CompilerStack::lastContractName() const
|
string const CompilerStack::lastContractName() const
|
||||||
|
@ -190,12 +190,6 @@ public:
|
|||||||
/// @returns the runtime object for the contract.
|
/// @returns the runtime object for the contract.
|
||||||
eth::LinkerObject const& runtimeObject(std::string const& _contractName) const;
|
eth::LinkerObject const& runtimeObject(std::string const& _contractName) const;
|
||||||
|
|
||||||
/// @returns the bytecode of a contract that uses an already deployed contract via DELEGATECALL.
|
|
||||||
/// The returned bytes will contain a sequence of 20 bytes of the format "XXX...XXX" which have to
|
|
||||||
/// substituted by the actual address. Note that this sequence starts end ends in three X
|
|
||||||
/// characters but can contain anything in between.
|
|
||||||
eth::LinkerObject const& cloneObject(std::string const& _contractName) const;
|
|
||||||
|
|
||||||
/// @returns normal contract assembly items
|
/// @returns normal contract assembly items
|
||||||
eth::AssemblyItems const* assemblyItems(std::string const& _contractName) const;
|
eth::AssemblyItems const* assemblyItems(std::string const& _contractName) const;
|
||||||
|
|
||||||
@ -258,7 +252,6 @@ private:
|
|||||||
std::shared_ptr<Compiler> compiler;
|
std::shared_ptr<Compiler> compiler;
|
||||||
eth::LinkerObject object; ///< Deployment object (includes the runtime sub-object).
|
eth::LinkerObject object; ///< Deployment object (includes the runtime sub-object).
|
||||||
eth::LinkerObject runtimeObject; ///< Runtime object.
|
eth::LinkerObject runtimeObject; ///< Runtime object.
|
||||||
eth::LinkerObject cloneObject; ///< Clone object (deprecated).
|
|
||||||
std::string metadata; ///< The metadata json that will be hashed into the chain.
|
std::string metadata; ///< The metadata json that will be hashed into the chain.
|
||||||
mutable std::unique_ptr<Json::Value const> abi;
|
mutable std::unique_ptr<Json::Value const> abi;
|
||||||
mutable std::unique_ptr<Json::Value const> userDocumentation;
|
mutable std::unique_ptr<Json::Value const> userDocumentation;
|
||||||
|
@ -80,7 +80,6 @@ static string const g_strAstJson = "ast-json";
|
|||||||
static string const g_strAstCompactJson = "ast-compact-json";
|
static string const g_strAstCompactJson = "ast-compact-json";
|
||||||
static string const g_strBinary = "bin";
|
static string const g_strBinary = "bin";
|
||||||
static string const g_strBinaryRuntime = "bin-runtime";
|
static string const g_strBinaryRuntime = "bin-runtime";
|
||||||
static string const g_strCloneBinary = "clone-bin";
|
|
||||||
static string const g_strCombinedJson = "combined-json";
|
static string const g_strCombinedJson = "combined-json";
|
||||||
static string const g_strCompactJSON = "compact-format";
|
static string const g_strCompactJSON = "compact-format";
|
||||||
static string const g_strContracts = "contracts";
|
static string const g_strContracts = "contracts";
|
||||||
@ -128,7 +127,6 @@ static string const g_argAstCompactJson = g_strAstCompactJson;
|
|||||||
static string const g_argAstJson = g_strAstJson;
|
static string const g_argAstJson = g_strAstJson;
|
||||||
static string const g_argBinary = g_strBinary;
|
static string const g_argBinary = g_strBinary;
|
||||||
static string const g_argBinaryRuntime = g_strBinaryRuntime;
|
static string const g_argBinaryRuntime = g_strBinaryRuntime;
|
||||||
static string const g_argCloneBinary = g_strCloneBinary;
|
|
||||||
static string const g_argCombinedJson = g_strCombinedJson;
|
static string const g_argCombinedJson = g_strCombinedJson;
|
||||||
static string const g_argCompactJSON = g_strCompactJSON;
|
static string const g_argCompactJSON = g_strCompactJSON;
|
||||||
static string const g_argGas = g_strGas;
|
static string const g_argGas = g_strGas;
|
||||||
@ -161,7 +159,6 @@ static set<string> const g_combinedJsonArgs
|
|||||||
g_strAst,
|
g_strAst,
|
||||||
g_strBinary,
|
g_strBinary,
|
||||||
g_strBinaryRuntime,
|
g_strBinaryRuntime,
|
||||||
g_strCloneBinary,
|
|
||||||
g_strCompactJSON,
|
g_strCompactJSON,
|
||||||
g_strInterface,
|
g_strInterface,
|
||||||
g_strMetadata,
|
g_strMetadata,
|
||||||
@ -213,7 +210,6 @@ static bool needsHumanTargetedStdout(po::variables_map const& _args)
|
|||||||
g_argAstJson,
|
g_argAstJson,
|
||||||
g_argBinary,
|
g_argBinary,
|
||||||
g_argBinaryRuntime,
|
g_argBinaryRuntime,
|
||||||
g_argCloneBinary,
|
|
||||||
g_argMetadata,
|
g_argMetadata,
|
||||||
g_argNatspecUser,
|
g_argNatspecUser,
|
||||||
g_argNatspecDev,
|
g_argNatspecDev,
|
||||||
@ -237,16 +233,6 @@ void CommandLineInterface::handleBinary(string const& _contract)
|
|||||||
cout << m_compiler->object(_contract).toHex() << endl;
|
cout << m_compiler->object(_contract).toHex() << endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (m_args.count(g_argCloneBinary))
|
|
||||||
{
|
|
||||||
if (m_args.count(g_argOutputDir))
|
|
||||||
createFile(m_compiler->filesystemFriendlyName(_contract) + ".clone_bin", m_compiler->cloneObject(_contract).toHex());
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cout << "Clone Binary: " << endl;
|
|
||||||
cout << m_compiler->cloneObject(_contract).toHex() << endl;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (m_args.count(g_argBinaryRuntime))
|
if (m_args.count(g_argBinaryRuntime))
|
||||||
{
|
{
|
||||||
if (m_args.count(g_argOutputDir))
|
if (m_args.count(g_argOutputDir))
|
||||||
@ -275,7 +261,7 @@ void CommandLineInterface::handleBytecode(string const& _contract)
|
|||||||
{
|
{
|
||||||
if (m_args.count(g_argOpcodes))
|
if (m_args.count(g_argOpcodes))
|
||||||
handleOpcode(_contract);
|
handleOpcode(_contract);
|
||||||
if (m_args.count(g_argBinary) || m_args.count(g_argCloneBinary) || m_args.count(g_argBinaryRuntime))
|
if (m_args.count(g_argBinary) || m_args.count(g_argBinaryRuntime))
|
||||||
handleBinary(_contract);
|
handleBinary(_contract);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -631,7 +617,6 @@ Allowed options)",
|
|||||||
(g_argOpcodes.c_str(), "Opcodes of the contracts.")
|
(g_argOpcodes.c_str(), "Opcodes of the contracts.")
|
||||||
(g_argBinary.c_str(), "Binary of the contracts in hex.")
|
(g_argBinary.c_str(), "Binary of the contracts in hex.")
|
||||||
(g_argBinaryRuntime.c_str(), "Binary of the runtime part of the contracts in hex.")
|
(g_argBinaryRuntime.c_str(), "Binary of the runtime part of the contracts in hex.")
|
||||||
(g_argCloneBinary.c_str(), "Binary of the clone contracts in hex.")
|
|
||||||
(g_argAbi.c_str(), "ABI specification of the contracts.")
|
(g_argAbi.c_str(), "ABI specification of the contracts.")
|
||||||
(g_argSignatureHashes.c_str(), "Function signature hashes of the contracts.")
|
(g_argSignatureHashes.c_str(), "Function signature hashes of the contracts.")
|
||||||
(g_argNatspecUser.c_str(), "Natspec user documentation of all contracts.")
|
(g_argNatspecUser.c_str(), "Natspec user documentation of all contracts.")
|
||||||
@ -910,8 +895,6 @@ void CommandLineInterface::handleCombinedJSON()
|
|||||||
contractData[g_strBinary] = m_compiler->object(contractName).toHex();
|
contractData[g_strBinary] = m_compiler->object(contractName).toHex();
|
||||||
if (requests.count(g_strBinaryRuntime))
|
if (requests.count(g_strBinaryRuntime))
|
||||||
contractData[g_strBinaryRuntime] = m_compiler->runtimeObject(contractName).toHex();
|
contractData[g_strBinaryRuntime] = m_compiler->runtimeObject(contractName).toHex();
|
||||||
if (requests.count(g_strCloneBinary))
|
|
||||||
contractData[g_strCloneBinary] = m_compiler->cloneObject(contractName).toHex();
|
|
||||||
if (requests.count(g_strOpcodes))
|
if (requests.count(g_strOpcodes))
|
||||||
contractData[g_strOpcodes] = solidity::disassemble(m_compiler->object(contractName).bytecode);
|
contractData[g_strOpcodes] = solidity::disassemble(m_compiler->object(contractName).bytecode);
|
||||||
if (requests.count(g_strAsm))
|
if (requests.count(g_strAsm))
|
||||||
|
@ -32,7 +32,7 @@ REPO_ROOT=$(cd $(dirname "$0")/.. && pwd)
|
|||||||
echo $REPO_ROOT
|
echo $REPO_ROOT
|
||||||
SOLC="$REPO_ROOT/build/solc/solc"
|
SOLC="$REPO_ROOT/build/solc/solc"
|
||||||
|
|
||||||
FULLARGS="--optimize --ignore-missing --combined-json abi,asm,ast,bin,bin-runtime,clone-bin,compact-format,devdoc,hashes,interface,metadata,opcodes,srcmap,srcmap-runtime,userdoc"
|
FULLARGS="--optimize --ignore-missing --combined-json abi,asm,ast,bin,bin-runtime,compact-format,devdoc,hashes,interface,metadata,opcodes,srcmap,srcmap-runtime,userdoc"
|
||||||
|
|
||||||
echo "Checking that the bug list is up to date..."
|
echo "Checking that the bug list is up to date..."
|
||||||
"$REPO_ROOT"/scripts/update_bugs_by_version.py
|
"$REPO_ROOT"/scripts/update_bugs_by_version.py
|
||||||
|
Loading…
Reference in New Issue
Block a user