Feature Tip: Add private address tag to any address under My Name Tag !
Overview
ETH Balance
0.005733875 ETH
Eth Value
$11.69 (@ $2,038.72/ETH)Latest 1 from a total of 1 transactions
| Transaction Hash |
Method
|
Block
|
From
|
|
To
|
||||
|---|---|---|---|---|---|---|---|---|---|
| Transfer | 11329477 | 1917 days ago | IN | 0.02 ETH | 0.00046023 |
Loading...
Loading
Loading...
Loading
Cross-Chain Transactions
Loading...
Loading
Minimal Proxy Contract for 0xe5857440bbff64c98ceb70d650805e1e96adde7a
Contract Name:
WalletImpl
Compiler Version
v0.7.0+commit.9e61f92b
Contract Source Code (Solidity)
/**
*Submitted for verification at Etherscan.io on 2020-11-08
*/
// SPDX-License-Identifier: Apache-2.0
pragma solidity ^0.7.0;
// File: contracts/lib/Ownable.sol
// Copyright 2017 Loopring Technology Limited.
/// @title Ownable
/// @author Brecht Devos - <brecht@loopring.org>
/// @dev The Ownable contract has an owner address, and provides basic
/// authorization control functions, this simplifies the implementation of
/// "user permissions".
contract Ownable
{
address public owner;
event OwnershipTransferred(
address indexed previousOwner,
address indexed newOwner
);
/// @dev The Ownable constructor sets the original `owner` of the contract
/// to the sender.
constructor()
{
owner = msg.sender;
}
/// @dev Throws if called by any account other than the owner.
modifier onlyOwner()
{
require(msg.sender == owner, "UNAUTHORIZED");
_;
}
/// @dev Allows the current owner to transfer control of the contract to a
/// new owner.
/// @param newOwner The address to transfer ownership to.
function transferOwnership(
address newOwner
)
public
virtual
onlyOwner
{
require(newOwner != address(0), "ZERO_ADDRESS");
emit OwnershipTransferred(owner, newOwner);
owner = newOwner;
}
function renounceOwnership()
public
onlyOwner
{
emit OwnershipTransferred(owner, address(0));
owner = address(0);
}
}
// File: contracts/iface/Wallet.sol
// Copyright 2017 Loopring Technology Limited.
/// @title Wallet
/// @dev Base contract for smart wallets.
/// Sub-contracts must NOT use non-default constructor to initialize
/// wallet states, instead, `init` shall be used. This is to enable
/// proxies to be deployed in front of the real wallet contract for
/// saving gas.
///
/// @author Daniel Wang - <daniel@loopring.org>
interface Wallet
{
function version() external pure returns (string memory);
function owner() external view returns (address);
/// @dev Set a new owner.
function setOwner(address newOwner) external;
/// @dev Adds a new module. The `init` method of the module
/// will be called with `address(this)` as the parameter.
/// This method must throw if the module has already been added.
/// @param _module The module's address.
function addModule(address _module) external;
/// @dev Removes an existing module. This method must throw if the module
/// has NOT been added or the module is the wallet's only module.
/// @param _module The module's address.
function removeModule(address _module) external;
/// @dev Checks if a module has been added to this wallet.
/// @param _module The module to check.
/// @return True if the module exists; False otherwise.
function hasModule(address _module) external view returns (bool);
/// @dev Binds a method from the given module to this
/// wallet so the method can be invoked using this wallet's default
/// function.
/// Note that this method must throw when the given module has
/// not been added to this wallet.
/// @param _method The method's 4-byte selector.
/// @param _module The module's address. Use address(0) to unbind the method.
function bindMethod(bytes4 _method, address _module) external;
/// @dev Returns the module the given method has been bound to.
/// @param _method The method's 4-byte selector.
/// @return _module The address of the bound module. If no binding exists,
/// returns address(0) instead.
function boundMethodModule(bytes4 _method) external view returns (address _module);
/// @dev Performs generic transactions. Any module that has been added to this
/// wallet can use this method to transact on any third-party contract with
/// msg.sender as this wallet itself.
///
/// Note: 1) this method must ONLY allow invocations from a module that has
/// been added to this wallet. The wallet owner shall NOT be permitted
/// to call this method directly. 2) Reentrancy inside this function should
/// NOT cause any problems.
///
/// @param mode The transaction mode, 1 for CALL, 2 for DELEGATECALL.
/// @param to The desitination address.
/// @param value The amount of Ether to transfer.
/// @param data The data to send over using `to.call{value: value}(data)`
/// @return returnData The transaction's return value.
function transact(
uint8 mode,
address to,
uint value,
bytes calldata data
)
external
returns (bytes memory returnData);
}
// File: contracts/iface/Module.sol
// Copyright 2017 Loopring Technology Limited.
/// @title Module
/// @dev Base contract for all smart wallet modules.
///
/// @author Daniel Wang - <daniel@loopring.org>
interface Module
{
/// @dev Activates the module for the given wallet (msg.sender) after the module is added.
/// Warning: this method shall ONLY be callable by a wallet.
function activate() external;
/// @dev Deactivates the module for the given wallet (msg.sender) before the module is removed.
/// Warning: this method shall ONLY be callable by a wallet.
function deactivate() external;
}
// File: contracts/lib/ERC20.sol
// Copyright 2017 Loopring Technology Limited.
/// @title ERC20 Token Interface
/// @dev see https://github.com/ethereum/EIPs/issues/20
/// @author Daniel Wang - <daniel@loopring.org>
abstract contract ERC20
{
function totalSupply()
public
view
virtual
returns (uint);
function balanceOf(
address who
)
public
view
virtual
returns (uint);
function allowance(
address owner,
address spender
)
public
view
virtual
returns (uint);
function transfer(
address to,
uint value
)
public
virtual
returns (bool);
function transferFrom(
address from,
address to,
uint value
)
public
virtual
returns (bool);
function approve(
address spender,
uint value
)
public
virtual
returns (bool);
}
// File: contracts/lib/ReentrancyGuard.sol
// Copyright 2017 Loopring Technology Limited.
/// @title ReentrancyGuard
/// @author Brecht Devos - <brecht@loopring.org>
/// @dev Exposes a modifier that guards a function against reentrancy
/// Changing the value of the same storage value multiple times in a transaction
/// is cheap (starting from Istanbul) so there is no need to minimize
/// the number of times the value is changed
contract ReentrancyGuard
{
//The default value must be 0 in order to work behind a proxy.
uint private _guardValue;
modifier nonReentrant()
{
require(_guardValue == 0, "REENTRANCY");
_guardValue = 1;
_;
_guardValue = 0;
}
}
// File: contracts/iface/ModuleRegistry.sol
// Copyright 2017 Loopring Technology Limited.
/// @title ModuleRegistry
/// @dev A registry for modules.
///
/// @author Daniel Wang - <daniel@loopring.org>
interface ModuleRegistry
{
/// @dev Registers and enables a new module.
function registerModule(address module) external;
/// @dev Disables a module
function disableModule(address module) external;
/// @dev Returns true if the module is registered and enabled.
function isModuleEnabled(address module) external view returns (bool);
/// @dev Returns the list of enabled modules.
function enabledModules() external view returns (address[] memory _modules);
/// @dev Returns the number of enbaled modules.
function numOfEnabledModules() external view returns (uint);
/// @dev Returns true if the module is ever registered.
function isModuleRegistered(address module) external view returns (bool);
}
// File: contracts/base/Controller.sol
// Copyright 2017 Loopring Technology Limited.
/// @title Controller
///
/// @author Daniel Wang - <daniel@loopring.org>
abstract contract Controller
{
function moduleRegistry()
external
view
virtual
returns (ModuleRegistry);
function walletFactory()
external
view
virtual
returns (address);
}
// File: contracts/base/BaseWallet.sol
// Copyright 2017 Loopring Technology Limited.
/// @title BaseWallet
/// @dev This contract provides basic implementation for a Wallet.
///
/// @author Daniel Wang - <daniel@loopring.org>
abstract contract BaseWallet is ReentrancyGuard, Wallet
{
// WARNING: do not delete wallet state data to make this implementation
// compatible with early versions.
//
// ----- DATA LAYOUT BEGINS -----
address internal _owner;
mapping (address => bool) private modules;
Controller public controller;
mapping (bytes4 => address) internal methodToModule;
// ----- DATA LAYOUT ENDS -----
event OwnerChanged (address newOwner);
event ControllerChanged (address newController);
event ModuleAdded (address module);
event ModuleRemoved (address module);
event MethodBound (bytes4 method, address module);
event WalletSetup (address owner);
modifier onlyFromModule
{
require(modules[msg.sender], "MODULE_UNAUTHORIZED");
_;
}
modifier onlyFromFactory
{
require(
msg.sender == controller.walletFactory(),
"UNAUTHORIZED"
);
_;
}
/// @dev We need to make sure the Factory address cannot be changed without wallet owner's
/// explicit authorization.
modifier onlyFromFactoryOrModule
{
require(
modules[msg.sender] || msg.sender == controller.walletFactory(),
"UNAUTHORIZED"
);
_;
}
/// @dev Set up this wallet by assigning an original owner
///
/// Note that calling this method more than once will throw.
///
/// @param _initialOwner The owner of this wallet, must not be address(0).
function initOwner(
address _initialOwner
)
external
onlyFromFactory
{
require(controller != Controller(0), "NO_CONTROLLER");
require(_owner == address(0), "INITIALIZED_ALREADY");
require(_initialOwner != address(0), "ZERO_ADDRESS");
_owner = _initialOwner;
emit WalletSetup(_initialOwner);
}
/// @dev Set up this wallet by assigning a controller and initial modules.
///
/// Note that calling this method more than once will throw.
/// And this method must be invoked before owner is initialized
///
/// @param _controller The Controller instance.
/// @param _modules The initial modules.
function init(
Controller _controller,
address[] calldata _modules
)
external
{
require(
_owner == address(0) &&
controller == Controller(0) &&
_controller != Controller(0),
"CONTROLLER_INIT_FAILED"
);
controller = _controller;
ModuleRegistry moduleRegistry = controller.moduleRegistry();
for (uint i = 0; i < _modules.length; i++) {
_addModule(_modules[i], moduleRegistry);
}
}
function owner()
override
public
view
returns (address)
{
return _owner;
}
function setOwner(address newOwner)
external
override
onlyFromModule
{
require(newOwner != address(0), "ZERO_ADDRESS");
require(newOwner != address(this), "PROHIBITED");
require(newOwner != _owner, "SAME_ADDRESS");
_owner = newOwner;
emit OwnerChanged(newOwner);
}
function setController(Controller newController)
external
onlyFromModule
{
require(newController != controller, "SAME_CONTROLLER");
require(newController != Controller(0), "INVALID_CONTROLLER");
controller = newController;
emit ControllerChanged(address(newController));
}
function addModule(address _module)
external
override
onlyFromFactoryOrModule
{
_addModule(_module, controller.moduleRegistry());
}
function removeModule(address _module)
external
override
onlyFromModule
{
// Allow deactivate to fail to make sure the module can be removed
require(modules[_module], "MODULE_NOT_EXISTS");
try Module(_module).deactivate() {} catch {}
delete modules[_module];
emit ModuleRemoved(_module);
}
function hasModule(address _module)
public
view
override
returns (bool)
{
return modules[_module];
}
function bindMethod(bytes4 _method, address _module)
external
override
onlyFromModule
{
require(_method != bytes4(0), "BAD_METHOD");
if (_module != address(0)) {
require(modules[_module], "MODULE_UNAUTHORIZED");
}
methodToModule[_method] = _module;
emit MethodBound(_method, _module);
}
function boundMethodModule(bytes4 _method)
public
view
override
returns (address)
{
return methodToModule[_method];
}
function transact(
uint8 mode,
address to,
uint value,
bytes calldata data
)
external
override
onlyFromFactoryOrModule
returns (bytes memory returnData)
{
bool success;
(success, returnData) = _call(mode, to, value, data);
if (!success) {
assembly {
returndatacopy(0, 0, returndatasize())
revert(0, returndatasize())
}
}
}
receive()
external
payable
{
}
/// @dev This default function can receive Ether or perform queries to modules
/// using bound methods.
fallback()
external
payable
{
address module = methodToModule[msg.sig];
require(modules[module], "MODULE_UNAUTHORIZED");
(bool success, bytes memory returnData) = module.call{value: msg.value}(msg.data);
assembly {
switch success
case 0 { revert(add(returnData, 32), mload(returnData)) }
default { return(add(returnData, 32), mload(returnData)) }
}
}
function _addModule(address _module, ModuleRegistry moduleRegistry)
internal
{
require(_module != address(0), "NULL_MODULE");
require(modules[_module] == false, "MODULE_EXISTS");
require(
moduleRegistry.isModuleEnabled(_module),
"INVALID_MODULE"
);
modules[_module] = true;
emit ModuleAdded(_module);
Module(_module).activate();
}
function _call(
uint8 mode,
address target,
uint value,
bytes calldata data
)
private
returns (
bool success,
bytes memory returnData
)
{
if (mode == 1) {
// solium-disable-next-line security/no-call-value
(success, returnData) = target.call{value: value}(data);
} else if (mode == 2) {
// solium-disable-next-line security/no-call-value
(success, returnData) = target.delegatecall(data);
} else if (mode == 3) {
require(value == 0, "INVALID_VALUE");
// solium-disable-next-line security/no-call-value
(success, returnData) = target.staticcall(data);
} else {
revert("UNSUPPORTED_MODE");
}
}
}
// File: contracts/modules/WalletImpl.sol
// Copyright 2017 Loopring Technology Limited.
/// @title WalletImpl
contract WalletImpl is BaseWallet {
function version()
public
override
pure
returns (string memory)
{
// 使用中国省会作为别名
return "1.2.0 (daqing)";
}
}Contract ABI
API[{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"newController","type":"address"}],"name":"ControllerChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes4","name":"method","type":"bytes4"},{"indexed":false,"internalType":"address","name":"module","type":"address"}],"name":"MethodBound","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"module","type":"address"}],"name":"ModuleAdded","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"module","type":"address"}],"name":"ModuleRemoved","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnerChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"owner","type":"address"}],"name":"WalletSetup","type":"event"},{"stateMutability":"payable","type":"fallback"},{"inputs":[{"internalType":"address","name":"_module","type":"address"}],"name":"addModule","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"_method","type":"bytes4"},{"internalType":"address","name":"_module","type":"address"}],"name":"bindMethod","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"_method","type":"bytes4"}],"name":"boundMethodModule","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"controller","outputs":[{"internalType":"contract Controller","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_module","type":"address"}],"name":"hasModule","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"contract Controller","name":"_controller","type":"address"},{"internalType":"address[]","name":"_modules","type":"address[]"}],"name":"init","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_initialOwner","type":"address"}],"name":"initOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_module","type":"address"}],"name":"removeModule","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"contract Controller","name":"newController","type":"address"}],"name":"setController","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"setOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint8","name":"mode","type":"uint8"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"value","type":"uint256"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"transact","outputs":[{"internalType":"bytes","name":"returnData","type":"bytes"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"version","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"pure","type":"function"},{"stateMutability":"payable","type":"receive"}]Loading...
Loading
Loading...
Loading
Net Worth in USD
$11.69
Net Worth in ETH
0.005734
Token Allocations
ETH
100.00%
Multichain Portfolio | 34 Chains
| Chain | Token | Portfolio % | Price | Amount | Value |
|---|---|---|---|---|---|
| ETH | 100.00% | $2,038.72 | 0.00573388 | $11.69 |
Loading...
Loading
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
[ Download: CSV Export ]
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.