Contract Name:
DisposableNXMaster
Contract Source Code:
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
interface ILegacyClaimsReward {
/// @dev Decides the next course of action for a given claim.
function changeClaimStatus(uint claimid) external;
function transferRewards() external;
function getCurrencyAssetAddress(bytes4 currency) external view returns (address);
function upgrade(address _newAdd) external;
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
interface IMasterAwareV2 {
// TODO: if you update this enum, update lib/constants.js as well
enum ID {
TC, // TokenController.sol
P1, // Pool.sol
MR, // MemberRoles.sol
MC, // MCR.sol
CO, // Cover.sol
SP, // StakingProducts.sol
PS, // LegacyPooledStaking.sol
GV, // Governance.sol
GW, // LegacyGateway.sol - removed
CL, // CoverMigrator.sol - removed
AS, // Assessment.sol
CI, // IndividualClaims.sol - Claims for Individuals
CG, // YieldTokenIncidents.sol - Claims for Groups
RA, // Ramm.sol
ST, // SafeTracker.sol
CP // CoverProducts.sol
}
function changeMasterAddress(address masterAddress) external;
function changeDependentContractAddress() external;
function internalContracts(uint) external view returns (address payable);
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
interface IMemberRoles {
enum Role {Unassigned, AdvisoryBoard, Member, Owner, Auditor}
function join(address _userAddress, uint nonce, bytes calldata signature) external payable;
function switchMembership(address _newAddress) external;
function switchMembershipAndAssets(
address newAddress,
uint[] calldata coverIds,
uint[] calldata stakingTokenIds
) external;
function switchMembershipOf(address member, address _newAddress) external;
function totalRoles() external view returns (uint256);
function changeAuthorized(uint _roleId, address _newAuthorized) external;
function setKycAuthAddress(address _add) external;
function members(uint _memberRoleId) external view returns (uint, address[] memory memberArray);
function numberOfMembers(uint _memberRoleId) external view returns (uint);
function authorized(uint _memberRoleId) external view returns (address);
function roles(address _memberAddress) external view returns (uint[] memory);
function checkRole(address _memberAddress, uint _roleId) external view returns (bool);
function getMemberLengthForAllRoles() external view returns (uint[] memory totalMembers);
function memberAtIndex(uint _memberRoleId, uint index) external view returns (address, bool);
function membersLength(uint _memberRoleId) external view returns (uint);
event MemberRole(uint256 indexed roleId, bytes32 roleName, string roleDescription);
event MemberJoined(address indexed newMember, uint indexed nonce);
event switchedMembership(address indexed previousMember, address indexed newMember, uint timeStamp);
event MembershipWithdrawn(address indexed member, uint timestamp);
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
import "./IPriceFeedOracle.sol";
struct SwapDetails {
uint104 minAmount;
uint104 maxAmount;
uint32 lastSwapTime;
// 2 decimals of precision. 0.01% -> 0.0001 -> 1e14
uint16 maxSlippageRatio;
}
struct Asset {
address assetAddress;
bool isCoverAsset;
bool isAbandoned;
}
interface IPool {
function swapOperator() external view returns (address);
function getAsset(uint assetId) external view returns (Asset memory);
function getAssets() external view returns (Asset[] memory);
function transferAssetToSwapOperator(address asset, uint amount) external;
function setSwapDetailsLastSwapTime(address asset, uint32 lastSwapTime) external;
function getAssetSwapDetails(address assetAddress) external view returns (SwapDetails memory);
function sendPayout(uint assetIndex, address payable payoutAddress, uint amount, uint ethDepositAmount) external;
function sendEth(address payoutAddress, uint amount) external;
function upgradeCapitalPool(address payable newPoolAddress) external;
function priceFeedOracle() external view returns (IPriceFeedOracle);
function getPoolValueInEth() external view returns (uint);
function calculateMCRRatio(uint totalAssetValue, uint mcrEth) external pure returns (uint);
function getInternalTokenPriceInAsset(uint assetId) external view returns (uint tokenPrice);
function getInternalTokenPriceInAssetAndUpdateTwap(uint assetId) external returns (uint tokenPrice);
function getTokenPrice() external view returns (uint tokenPrice);
function getMCRRatio() external view returns (uint);
function setSwapValue(uint value) external;
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
interface Aggregator {
function decimals() external view returns (uint8);
function latestAnswer() external view returns (int);
}
interface IPriceFeedOracle {
struct OracleAsset {
Aggregator aggregator;
uint8 decimals;
}
function ETH() external view returns (address);
function assets(address) external view returns (Aggregator, uint8);
function getAssetToEthRate(address asset) external view returns (uint);
function getAssetForEth(address asset, uint ethIn) external view returns (uint);
function getEthForAsset(address asset, uint amount) external view returns (uint);
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
interface ISAFURAMaster {
function tokenAddress() external view returns (address);
function owner() external view returns (address);
function emergencyAdmin() external view returns (address);
function masterInitialized() external view returns (bool);
function isInternal(address _add) external view returns (bool);
function isPause() external view returns (bool check);
function isMember(address _add) external view returns (bool);
function checkIsAuthToGoverned(address _add) external view returns (bool);
function getLatestAddress(bytes2 _contractName) external view returns (address payable contractAddress);
function contractAddresses(bytes2 code) external view returns (address payable);
function upgradeMultipleContracts(
bytes2[] calldata _contractCodes,
address payable[] calldata newAddresses
) external;
function removeContracts(bytes2[] calldata contractCodesToRemove) external;
function addNewInternalContracts(
bytes2[] calldata _contractCodes,
address payable[] calldata newAddresses,
uint[] calldata _types
) external;
function updateOwnerParameters(bytes8 code, address payable val) external;
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
interface ISAFURAToken {
function burn(uint256 amount) external returns (bool);
function burnFrom(address from, uint256 value) external returns (bool);
function operatorTransfer(address from, uint256 value) external returns (bool);
function mint(address account, uint256 amount) external;
function isLockedForMV(address member) external view returns (uint);
function whiteListed(address member) external view returns (bool);
function addToWhiteList(address _member) external returns (bool);
function removeFromWhiteList(address _member) external returns (bool);
function changeOperator(address _newOperator) external returns (bool);
function lockForMemberVote(address _of, uint _days) external;
/**
* @dev Returns the amount of tokens in existence.
*/
function totalSupply() external view returns (uint256);
/**
* @dev Returns the amount of tokens owned by `account`.
*/
function balanceOf(address account) external view returns (uint256);
/**
* @dev Moves `amount` tokens from the caller's account to `recipient`.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* Emits a {Transfer} event.
*/
function transfer(address recipient, uint256 amount) external returns (bool);
/**
* @dev Returns the remaining number of tokens that `spender` will be
* allowed to spend on behalf of `owner` through {transferFrom}. This is
* zero by default.
*
* This value changes when {approve} or {transferFrom} are called.
*/
function allowance(address owner, address spender) external view returns (uint256);
/**
* @dev Sets `amount` as the allowance of `spender` over the caller's tokens.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* IMPORTANT: Beware that changing an allowance with this method brings the risk
* that someone may use both the old and the new allowance by unfortunate
* transaction ordering. One possible solution to mitigate this race
* condition is to first reduce the spender's allowance to 0 and set the
* desired value afterwards:
* https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729
*
* Emits an {Approval} event.
*/
function approve(address spender, uint256 amount) external returns (bool);
/**
* @dev Moves `amount` tokens from `sender` to `recipient` using the
* allowance mechanism. `amount` is then deducted from the caller's
* allowance.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* Emits a {Transfer} event.
*/
function transferFrom(address sender, address recipient, uint256 amount) external returns (bool);
/**
* @dev Emitted when `value` tokens are moved from one account (`from`) to
* another (`to`).
*
* Note that `value` may be zero.
*/
event Transfer(address indexed from, address indexed to, uint256 value);
/**
* @dev Emitted when the allowance of a `spender` for an `owner` is set by
* a call to {approve}. `value` is the new allowance.
*/
event Approval(address indexed owner, address indexed spender, uint256 value);
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity >=0.5.0;
import "./ISAFURAToken.sol";
interface ITokenController {
struct StakingPoolNXMBalances {
uint128 rewards;
uint128 deposits;
}
struct CoverInfo {
uint16 claimCount;
bool hasOpenClaim;
bool hasAcceptedClaim;
uint96 requestedPayoutAmount;
// note: still 128 bits available here, can be used later
}
struct StakingPoolOwnershipOffer {
address proposedManager;
uint96 deadline;
}
function coverInfo(uint id) external view returns (
uint16 claimCount,
bool hasOpenClaim,
bool hasAcceptedClaim,
uint96 requestedPayoutAmount
);
function withdrawCoverNote(
address _of,
uint[] calldata _coverIds,
uint[] calldata _indexes
) external;
function changeOperator(address _newOperator) external;
function operatorTransfer(address _from, address _to, uint _value) external returns (bool);
function burnFrom(address _of, uint amount) external returns (bool);
function addToWhitelist(address _member) external;
function removeFromWhitelist(address _member) external;
function mint(address _member, uint _amount) external;
function lockForMemberVote(address _of, uint _days) external;
function withdrawClaimAssessmentTokens(address[] calldata users) external;
function getLockReasons(address _of) external view returns (bytes32[] memory reasons);
function totalSupply() external view returns (uint);
function totalBalanceOf(address _of) external view returns (uint amount);
function totalBalanceOfWithoutDelegations(address _of) external view returns (uint amount);
function getTokenPrice() external view returns (uint tokenPrice);
function token() external view returns (ISAFURAToken);
function getStakingPoolManager(uint poolId) external view returns (address manager);
function getManagerStakingPools(address manager) external view returns (uint[] memory poolIds);
function isStakingPoolManager(address member) external view returns (bool);
function getStakingPoolOwnershipOffer(uint poolId) external view returns (address proposedManager, uint deadline);
function transferStakingPoolsOwnership(address from, address to) external;
function assignStakingPoolManager(uint poolId, address manager) external;
function createStakingPoolOwnershipOffer(uint poolId, address proposedManager, uint deadline) external;
function acceptStakingPoolOwnershipOffer(uint poolId) external;
function cancelStakingPoolOwnershipOffer(uint poolId) external;
function mintStakingPoolNXMRewards(uint amount, uint poolId) external;
function burnStakingPoolNXMRewards(uint amount, uint poolId) external;
function depositStakedNXM(address from, uint amount, uint poolId) external;
function withdrawNXMStakeAndRewards(address to, uint stakeToWithdraw, uint rewardsToWithdraw, uint poolId) external;
function burnStakedNXM(uint amount, uint poolId) external;
function stakingPoolNXMBalances(uint poolId) external view returns(uint128 rewards, uint128 deposits);
function tokensLocked(address _of, bytes32 _reason) external view returns (uint256 amount);
function getWithdrawableCoverNotes(
address coverOwner
) external view returns (
uint[] memory coverIds,
bytes32[] memory lockReasons,
uint withdrawableAmount
);
function getPendingRewards(address member) external view returns (uint);
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity ^0.8.18;
import "../../modules/governance/NXMaster.sol";
contract DisposableNXMaster is NXMaster {
function initialize(
address _owner,
address _tokenAddress,
address _emergencyAdmin,
bytes2[] calldata _contractNames,
uint8[] calldata _contractTypes, // 0 - eternal storage, 1 - "upgradable", 2 - proxy
address payable[] calldata _contractAddresses
) external {
require(!masterInitialized, "!init");
masterInitialized = true;
owner = _owner;
tokenAddress = _tokenAddress;
emergencyAdmin = _emergencyAdmin;
contractsActive[address(this)] = true;
require(
_contractNames.length == _contractTypes.length,
"check names & types arrays length"
);
for (uint i = 0; i < _contractNames.length; i++) {
bytes2 name = _contractNames[i];
address payable contractAddress = _contractAddresses[i];
contractCodes.push(name);
contractAddresses[name] = contractAddress;
contractsActive[contractAddress] = true;
if (_contractTypes[i] == 1) {
isReplaceable[name] = true;
} else if (_contractTypes[i] == 2) {
isProxy[name] = true;
}
}
}
function switchGovernanceAddress(address payable newGV) external {
{// change governance address
address currentGV = contractAddresses["GV"];
contractAddresses["GV"] = newGV;
contractsActive[currentGV] = false;
contractsActive[newGV] = true;
}
// notify all contracts about address change
for (uint i = 0; i < contractCodes.length; i++) {
address _address = contractAddresses[contractCodes[i]];
IMasterAwareV2 up = IMasterAwareV2(_address);
up.changeMasterAddress(address(this));
up.changeDependentContractAddress();
}
}
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity ^0.8.18;
import "./UpgradeabilityProxy.sol";
/**
* @title OwnedUpgradeabilityProxy
* @dev This contract combines an upgradeability proxy with basic authorization control functionalities
*/
contract OwnedUpgradeabilityProxy is UpgradeabilityProxy {
/**
* @dev Event to show ownership has been transferred
* @param previousOwner representing the address of the previous owner
* @param newOwner representing the address of the new owner
*/
event ProxyOwnershipTransferred(address previousOwner, address newOwner);
// Storage position of the owner of the contract
bytes32 private constant PROXY_OWNER_POSITION = keccak256("org.govblocks.proxy.owner");
/**
* @dev the constructor sets the original owner of the contract to the sender account.
*/
constructor(address _implementation) {
_setUpgradeabilityOwner(msg.sender);
_upgradeTo(_implementation);
}
/**
* @dev Throws if called by any account other than the owner.
*/
modifier onlyProxyOwner() {
require(msg.sender == proxyOwner());
_;
}
/**
* @dev Tells the address of the owner
* @return owner - the address of the owner
*/
function proxyOwner() public view returns (address owner) {
bytes32 position = PROXY_OWNER_POSITION;
// solhint-disable-next-line no-inline-assembly
assembly {
owner := sload(position)
}
}
/**
* @dev Allows the current owner to transfer control of the contract to a newOwner.
* @param _newOwner The address to transfer ownership to.
*/
function transferProxyOwnership(address _newOwner) public onlyProxyOwner {
require(_newOwner != address(0));
_setUpgradeabilityOwner(_newOwner);
emit ProxyOwnershipTransferred(proxyOwner(), _newOwner);
}
/**
* @dev Allows the proxy owner to upgrade the current version of the proxy.
* @param _implementation representing the address of the new implementation to be set.
*/
function upgradeTo(address _implementation) public onlyProxyOwner {
_upgradeTo(_implementation);
}
/**
* @dev Sets the address of the owner
*/
function _setUpgradeabilityOwner(address _newProxyOwner) internal {
bytes32 position = PROXY_OWNER_POSITION;
// solhint-disable-next-line no-inline-assembly
assembly {
sstore(position, _newProxyOwner)
}
}
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity ^0.8.18;
/**
* @title Proxy
* @dev Gives the possibility to delegate any call to a foreign implementation.
*/
abstract contract Proxy {
/**
* @dev Delegates the current call to `implementation`.
*/
function _delegate() internal {
address _impl = implementation();
require(_impl != address(0));
// solhint-disable-next-line no-inline-assembly
assembly {
let ptr := mload(0x40)
calldatacopy(ptr, 0, calldatasize())
let result := delegatecall(gas(), _impl, ptr, calldatasize(), 0, 0)
let size := returndatasize()
returndatacopy(ptr, 0, size)
switch result
case 0 {revert(ptr, size)}
default {return (ptr, size)}
}
}
/**
* @dev Fallback function allowing to perform a delegatecall to the given implementation.
* This function will return whatever the implementation call returns
*/
fallback() external payable {
_delegate();
}
/**
* @dev Receive function allowing to perform a delegatecall to the given implementation.
* This function will return whatever the implementation call returns
*/
receive() external payable {
_delegate();
}
/**
* @dev Tells the address of the implementation where every call will be delegated.
* @return address of the implementation to which it will be delegated
*/
function implementation() virtual public view returns (address);
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity ^0.8.18;
import "./Proxy.sol";
/**
* @title UpgradeabilityProxy
* @dev This contract represents a proxy where the implementation address to which it will delegate can be upgraded
*/
contract UpgradeabilityProxy is Proxy {
/**
* @dev This event will be emitted every time the implementation gets upgraded
* @param implementation representing the address of the upgraded implementation
*/
event Upgraded(address indexed implementation);
// Storage position of the address of the current implementation
bytes32 private constant IMPLEMENTATION_POSITION = keccak256("org.govblocks.proxy.implementation");
/**
* @dev Constructor function
*/
// solhint-disable-next-line no-empty-blocks
constructor() {}
/**
* @dev Tells the address of the current implementation
* @return impl - address of the current implementation
*/
function implementation() public override view returns (address impl) {
bytes32 position = IMPLEMENTATION_POSITION;
// solhint-disable-next-line no-inline-assembly
assembly {
impl := sload(position)
}
}
/**
* @dev Sets the address of the current implementation
* @param _newImplementation address representing the new implementation to be set
*/
function _setImplementation(address _newImplementation) internal {
bytes32 position = IMPLEMENTATION_POSITION;
// solhint-disable-next-line no-inline-assembly
assembly {
sstore(position, _newImplementation)
}
}
/**
* @dev Upgrades the implementation address
* @param _newImplementation representing the address of the new implementation to be set
*/
function _upgradeTo(address _newImplementation) internal {
address currentImplementation = implementation();
require(currentImplementation != _newImplementation);
_setImplementation(_newImplementation);
emit Upgraded(_newImplementation);
}
}
// SPDX-License-Identifier: GPL-3.0-only
pragma solidity ^0.8.18;
import "../../interfaces/IMasterAwareV2.sol";
import "../../interfaces/IMemberRoles.sol";
import "../../interfaces/ISAFURAMaster.sol";
import "../../interfaces/IPool.sol";
import "./external/OwnedUpgradeabilityProxy.sol";
import "../../interfaces/ITokenController.sol";
import "../../interfaces/ILegacyClaimsReward.sol";
contract NXMaster is ISAFURAMaster {
address public _unusedM; // Governed contract masterAddress slot
uint public _unused0;
bytes2[] public contractCodes;
mapping(address => bool) public contractsActive;
mapping(bytes2 => address payable) public contractAddresses;
mapping(bytes2 => bool) public isProxy;
mapping(bytes2 => bool) public isReplaceable;
address public tokenAddress;
bool internal reentrancyLock;
bool public masterInitialized;
address public owner;
uint public _unused1;
address public emergencyAdmin;
bool public paused;
enum ContractType { Undefined, Replaceable, Proxy }
event InternalContractAdded(bytes2 indexed code, address contractAddress, ContractType indexed contractType);
event ContractUpgraded(bytes2 indexed code, address newAddress, address previousAddress, ContractType indexed contractType);
event ContractRemoved(bytes2 indexed code, address contractAddress);
event PauseConfigured(bool paused);
modifier onlyAuthorizedToGovern() {
require(getLatestAddress("GV") == msg.sender, "Not authorized");
_;
}
modifier noReentrancy() {
require(!reentrancyLock, "Reentrant call.");
reentrancyLock = true;
_;
reentrancyLock = false;
}
modifier onlyEmergencyAdmin() {
require(msg.sender == emergencyAdmin, "NXMaster: Not emergencyAdmin");
_;
}
function initializeEmergencyAdmin() external {
if (emergencyAdmin == address(0)) {
emergencyAdmin = 0x422D71fb8040aBEF53f3a05d21A9B85eebB2995D;
}
}
function addNewInternalContracts(
bytes2[] calldata newContractCodes,
address payable[] calldata newAddresses,
uint[] calldata _types
) external onlyAuthorizedToGovern {
require(newContractCodes.length == newAddresses.length, "NXMaster: newContractCodes.length != newAddresses.length.");
require(newContractCodes.length == _types.length, "NXMaster: newContractCodes.length != _types.length");
for (uint i = 0; i < newContractCodes.length; i++) {
addNewInternalContract(newContractCodes[i], newAddresses[i], _types[i]);
}
updateAllDependencies();
}
/// @dev Adds new internal contract
/// @param contractCode contract code for new contract
/// @param contractAddress contract address for new contract
/// @param _type pass 1 if contract is replaceable, 2 if contract is proxy
function addNewInternalContract(
bytes2 contractCode,
address payable contractAddress,
uint _type
) internal {
require(contractAddresses[contractCode] == address(0), "NXMaster: Code already in use");
require(contractAddress != address(0), "NXMaster: Contract address is 0");
contractCodes.push(contractCode);
address payable newInternalContract;
uint contractType = uint8(_type);
if (contractType == uint(ContractType.Replaceable)) {
newInternalContract = contractAddress;
isReplaceable[contractCode] = true;
} else if (contractType == uint(ContractType.Proxy)) {
uint salt = _type >> 8;
if (salt == 0) {
// contractCode will use the 16 most significant bits (leftmost)
// block.number will use the least significant bits (rightmost)
// example: contractCode = "XX" = 0x5858, block.number = 13565952 = 0xcf0000
// result: 0x5858000000000000000000000000000000000000000000000000000000cf0000
salt = uint(bytes32(contractCode)) + block.number;
}
// using the max address as the initial implementation to avoid revert in upgradeTo
OwnedUpgradeabilityProxy proxy = new OwnedUpgradeabilityProxy{salt: bytes32(salt)}(address(type(uint160).max));
proxy.upgradeTo(contractAddress);
newInternalContract = payable(proxy);
isProxy[contractCode] = true;
} else {
revert("NXMaster: Unsupported contract type");
}
contractAddresses[contractCode] = newInternalContract;
contractsActive[newInternalContract] = true;
IMasterAwareV2 up = IMasterAwareV2(newInternalContract);
up.changeMasterAddress(address(this));
emit InternalContractAdded(contractCode, contractAddress, ContractType(contractType));
}
/// @dev upgrades multiple contracts at a time
function upgradeMultipleContracts(
bytes2[] calldata _contractCodes,
address payable[] calldata newAddresses
) external onlyAuthorizedToGovern {
require(_contractCodes.length == newAddresses.length, "NXMaster: _contractCodes.length != newAddresses.length");
for (uint i = 0; i < _contractCodes.length; i++) {
address payable newAddress = newAddresses[i];
bytes2 code = _contractCodes[i];
require(newAddress != address(0), "NXMaster: Contract address is 0");
if (isProxy[code]) {
OwnedUpgradeabilityProxy proxy = OwnedUpgradeabilityProxy(contractAddresses[code]);
address previousAddress = proxy.implementation();
proxy.upgradeTo(newAddress);
emit ContractUpgraded(code, newAddress, previousAddress, ContractType.Proxy);
continue;
}
if (isReplaceable[code]) {
address previousAddress = getLatestAddress(code);
replaceContract(code, newAddress);
emit ContractUpgraded(code, newAddress, previousAddress, ContractType.Replaceable);
continue;
}
revert("NXMaster: Non-existant or non-upgradeable contract code");
}
updateAllDependencies();
}
function replaceContract(bytes2 code, address payable newAddress) internal {
if (code == "CR") {
ITokenController tc = ITokenController(getLatestAddress("TC"));
tc.addToWhitelist(newAddress);
tc.removeFromWhitelist(contractAddresses["CR"]);
ILegacyClaimsReward cr = ILegacyClaimsReward(contractAddresses["CR"]);
cr.upgrade(newAddress);
} else if (code == "P1") {
IPool p1 = IPool(contractAddresses["P1"]);
p1.upgradeCapitalPool(newAddress);
}
address payable oldAddress = contractAddresses[code];
contractsActive[oldAddress] = false;
contractAddresses[code] = newAddress;
contractsActive[newAddress] = true;
IMasterAwareV2 up = IMasterAwareV2(contractAddresses[code]);
up.changeMasterAddress(address(this));
}
function removeContracts(bytes2[] calldata contractCodesToRemove) external onlyAuthorizedToGovern {
for (uint i = 0; i < contractCodesToRemove.length; i++) {
bytes2 code = contractCodesToRemove[i];
address contractAddress = contractAddresses[code];
require(contractAddress != address(0), "NXMaster: Address is 0");
require(isInternal(contractAddress), "NXMaster: Contract not internal");
contractsActive[contractAddress] = false;
contractAddresses[code] = payable(0);
if (isProxy[code]) {
isProxy[code] = false;
}
if (isReplaceable[code]) {
isReplaceable[code] = false;
}
emit ContractRemoved(code, contractAddress);
}
// delete elements from contractCodes
for (uint i = 0; i < contractCodes.length;) {
for (uint j = 0; j < contractCodesToRemove.length; j++) {
if (contractCodes[i] == contractCodesToRemove[j]) {
contractCodes[i] = contractCodes[contractCodes.length - 1];
contractCodes.pop();
unchecked { i--; }
break;
}
}
unchecked { i++; }
}
updateAllDependencies();
}
function updateAllDependencies() internal {
for (uint i = 0; i < contractCodes.length; i++) {
IMasterAwareV2 up = IMasterAwareV2(contractAddresses[contractCodes[i]]);
up.changeDependentContractAddress();
}
}
/**
* @dev set Emergency pause
* @param _paused to toggle emergency pause ON/OFF
*/
function setEmergencyPause(bool _paused) public onlyEmergencyAdmin {
paused = _paused;
emit PauseConfigured(_paused);
}
/// @dev checks whether the address is an internal contract address.
function isInternal(address _contractAddress) public view returns (bool) {
return contractsActive[_contractAddress];
}
/// @dev Checks whether emergency pause is on/not.
function isPause() public view returns (bool) {
return paused;
}
/// @dev checks whether the address is a member of the mutual or not.
function isMember(address _add) public view returns (bool) {
IMemberRoles mr = IMemberRoles(getLatestAddress("MR"));
return mr.checkRole(_add, uint(IMemberRoles.Role.Member));
}
/// @dev Gets current contract codes and their addresses
/// @return _contractCodes - all stored contract codes
/// @return _contractAddresses - all stored contract addresses
function getInternalContracts() public view returns (
bytes2[] memory _contractCodes,
address[] memory _contractAddresses
) {
_contractCodes = contractCodes;
_contractAddresses = new address[](contractCodes.length);
for (uint i = 0; i < _contractCodes.length; i++) {
_contractAddresses[i] = contractAddresses[contractCodes[i]];
}
}
/**
* @dev returns the address of token controller
* @return address is returned
*/
function dAppLocker() public view returns (address) {
return getLatestAddress("TC");
}
/// @dev Gets latest contract address
/// @param _contractName Contract name to fetch
function getLatestAddress(bytes2 _contractName) public view returns (address payable contractAddress) {
contractAddress = contractAddresses[_contractName];
}
/**
* @dev to check if the address is authorized to govern or not
* @param _add is the address in concern
* @return the boolean status status for the check
*/
function checkIsAuthToGoverned(address _add) public view returns (bool) {
return getLatestAddress("GV") == _add;
}
/**
* @dev to update the owner parameters
* @param code is the associated code
* @param val is value to be set
*/
function updateOwnerParameters(bytes8 code, address payable val) public onlyAuthorizedToGovern {
if (code == "EMADMIN") {
emergencyAdmin = val;
} else {
revert("Invalid param code");
}
}
}