mirror of
https://github.com/zkemail/zk-email-verify.git
synced 2026-01-06 20:23:54 -05:00
feat: Implement ERC-7969 DKIM Registry Standard (#278)
* Implement ERC-7969 DKIM Registry Standard * Nits and update abi * Nits and update abi
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
pragma solidity ^0.8.0;
|
||||
|
||||
import "@openzeppelin/contracts/access/Ownable.sol";
|
||||
import "./interfaces/IDKIMRegistry.sol";
|
||||
import "./interfaces/IERC7969.sol";
|
||||
|
||||
/**
|
||||
A Registry that store the hash(dkim_public_key) for each domain
|
||||
@@ -13,41 +13,25 @@ import "./interfaces/IDKIMRegistry.sol";
|
||||
Input is DKIM pub key split into 17 chunks of 121 bits. You can use `helpers` package to fetch/split DKIM keys
|
||||
*/
|
||||
contract DKIMRegistry is IDKIMRegistry, Ownable {
|
||||
constructor(address _signer) Ownable(_signer) { }
|
||||
constructor(address _signer) Ownable(_signer) {}
|
||||
|
||||
event DKIMPublicKeyHashRegistered(string domainName, bytes32 publicKeyHash);
|
||||
event DKIMPublicKeyHashRevoked(bytes32 publicKeyHash);
|
||||
|
||||
// Mapping from domain name to DKIM public key hash
|
||||
mapping(string => mapping(bytes32 => bool)) public dkimPublicKeyHashes;
|
||||
// Mapping from domain name hash to DKIM public key hash
|
||||
mapping(bytes32 => mapping(bytes32 => bool)) public dkimPublicKeyHashes;
|
||||
|
||||
// DKIM public that are revoked (eg: in case of private key compromise)
|
||||
mapping(bytes32 => bool) public revokedDKIMPublicKeyHashes;
|
||||
|
||||
function _stringEq(
|
||||
string memory a,
|
||||
string memory b
|
||||
) internal pure returns (bool) {
|
||||
return keccak256(abi.encodePacked(a)) == keccak256(abi.encodePacked(b));
|
||||
}
|
||||
|
||||
function isDKIMPublicKeyHashValid(
|
||||
string memory domainName,
|
||||
function isKeyHashValid(
|
||||
bytes32 domainNameHash,
|
||||
bytes32 publicKeyHash
|
||||
) public view returns (bool) {
|
||||
if (revokedDKIMPublicKeyHashes[publicKeyHash]) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (dkimPublicKeyHashes[domainName][publicKeyHash]) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
return
|
||||
dkimPublicKeyHashes[domainNameHash][publicKeyHash] ||
|
||||
!revokedDKIMPublicKeyHashes[publicKeyHash];
|
||||
}
|
||||
|
||||
function setDKIMPublicKeyHash(
|
||||
string memory domainName,
|
||||
bytes32 domainHash,
|
||||
bytes32 publicKeyHash
|
||||
) public onlyOwner {
|
||||
require(
|
||||
@@ -55,23 +39,22 @@ contract DKIMRegistry is IDKIMRegistry, Ownable {
|
||||
"cannot set revoked pubkey"
|
||||
);
|
||||
|
||||
dkimPublicKeyHashes[domainName][publicKeyHash] = true;
|
||||
|
||||
emit DKIMPublicKeyHashRegistered(domainName, publicKeyHash);
|
||||
dkimPublicKeyHashes[domainHash][publicKeyHash] = true;
|
||||
emit KeyHashRegistered(domainHash, publicKeyHash);
|
||||
}
|
||||
|
||||
function setDKIMPublicKeyHashes(
|
||||
string memory domainName,
|
||||
bytes32 domainHash,
|
||||
bytes32[] memory publicKeyHashes
|
||||
) public onlyOwner {
|
||||
for (uint256 i = 0; i < publicKeyHashes.length; i++) {
|
||||
setDKIMPublicKeyHash(domainName, publicKeyHashes[i]);
|
||||
setDKIMPublicKeyHash(domainHash, publicKeyHashes[i]);
|
||||
}
|
||||
}
|
||||
|
||||
function revokeDKIMPublicKeyHash(bytes32 publicKeyHash) public onlyOwner {
|
||||
revokedDKIMPublicKeyHashes[publicKeyHash] = true;
|
||||
|
||||
emit DKIMPublicKeyHashRevoked(publicKeyHash);
|
||||
emit KeyHashRevoked(publicKeyHash);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
pragma solidity ^0.8.0;
|
||||
|
||||
import "@openzeppelin/contracts/access/Ownable.sol";
|
||||
import "./interfaces/IDKIMRegistry.sol";
|
||||
import "./interfaces/IERC7969.sol";
|
||||
import "@openzeppelin/contracts/utils/cryptography/ECDSA.sol";
|
||||
import {MessageHashUtils} from "@openzeppelin/contracts/utils/cryptography/MessageHashUtils.sol";
|
||||
import {IERC1271} from "@openzeppelin/contracts/interfaces/IERC1271.sol";
|
||||
@@ -24,21 +24,8 @@ contract UserOverrideableDKIMRegistry is
|
||||
using Strings for *;
|
||||
using ECDSA for *;
|
||||
|
||||
/// @notice Emitted when a DKIM public key hash is successfully set.
|
||||
event DKIMPublicKeyHashRegistered(
|
||||
string indexed domainName,
|
||||
bytes32 indexed publicKeyHash,
|
||||
address indexed authorizer
|
||||
);
|
||||
|
||||
/// @notice Emitted when a DKIM public key hash is successfully revoked.
|
||||
event DKIMPublicKeyHashRevoked(
|
||||
bytes32 indexed publicKeyHash,
|
||||
address indexed authorizer
|
||||
);
|
||||
|
||||
/// @notice Emitted when a DKIM public key hash is successfully reactivated.
|
||||
event DKIMPublicKeyHashReactivated(
|
||||
event KeyHashReactivated(
|
||||
bytes32 indexed publicKeyHash,
|
||||
address indexed authorizer
|
||||
);
|
||||
@@ -53,7 +40,7 @@ contract UserOverrideableDKIMRegistry is
|
||||
uint public setTimestampDelay;
|
||||
|
||||
/// @notice DKIM public key hashes that are set
|
||||
mapping(string => mapping(bytes32 => mapping(address => bool)))
|
||||
mapping(bytes32 => mapping(bytes32 => mapping(address => bool)))
|
||||
public dkimPublicKeyHashes;
|
||||
|
||||
/// @notice DKIM public key hashes that are revoked (eg: in case of private key compromise)
|
||||
@@ -87,34 +74,33 @@ contract UserOverrideableDKIMRegistry is
|
||||
setTimestampDelay = _setTimestampDelay;
|
||||
}
|
||||
|
||||
/// @notice Checks if a DKIM public key hash is valid for a given domain.
|
||||
/// @param domainName The domain name for which the DKIM public key hash is being checked.
|
||||
/// @notice Checks if a DKIM public key hash is valid for a given domain hash.
|
||||
/// @param domainNameHash The hash of the domain name for which the DKIM public key hash is being checked.
|
||||
/// @param publicKeyHash The hash of the DKIM public key to be checked.
|
||||
/// @return bool True if the DKIM public key hash is valid, false otherwise.
|
||||
/// @dev This function returns true if the owner of the given `msg.sender` approves the public key hash before `enabledTimeOfDKIMPublicKeyHash` and neither `mainAuthorizer` nor the owner of `msg.sender` revokes the public key hash. However, after `enabledTimeOfDKIMPublicKeyHash`, only one of their approvals is required. In addition, if the public key hash is reactivated by the owner of `msg.sender`, the public key hash revoked only by `mainAuthorizer` is considered valid.
|
||||
function isDKIMPublicKeyHashValid(
|
||||
string memory domainName,
|
||||
function isKeyHashValid(
|
||||
bytes32 domainNameHash,
|
||||
bytes32 publicKeyHash
|
||||
) public view returns (bool) {
|
||||
address ownerOfSender = Ownable(msg.sender).owner();
|
||||
return
|
||||
isDKIMPublicKeyHashValid(domainName, publicKeyHash, ownerOfSender);
|
||||
return isKeyHashValid(domainNameHash, publicKeyHash, ownerOfSender);
|
||||
}
|
||||
|
||||
/// @notice Checks if a DKIM public key hash is valid for a given domain.
|
||||
/// @param domainName The domain name for which the DKIM public key hash is being checked.
|
||||
/// @param domainNameHash The hash of the domain name for which the DKIM public key hash is being checked.
|
||||
/// @param publicKeyHash The hash of the DKIM public key to be checked.
|
||||
/// @param authorizer The address of the expected authorizer
|
||||
/// @return bool True if the DKIM public key hash is valid, false otherwise.
|
||||
/// @dev This function returns true if 1) at least the given `authorizer` approves the public key hash before `enabledTimeOfDKIMPublicKeyHash` and 2) neither `mainAuthorizer` nor `authorizer` revokes the public key hash. However, after `enabledTimeOfDKIMPublicKeyHash`, only one of their approvals is required. In addition, if the public key hash is reactivated by the `authorizer`, the public key hash revoked only by `mainAuthorizer` is considered valid.
|
||||
/// @dev The domain name, public key hash, and authorizer address must not be zero.
|
||||
/// @dev The authorizer address cannot be the mainAuthorizer.
|
||||
function isDKIMPublicKeyHashValid(
|
||||
string memory domainName,
|
||||
function isKeyHashValid(
|
||||
bytes32 domainNameHash,
|
||||
bytes32 publicKeyHash,
|
||||
address authorizer
|
||||
) public view returns (bool) {
|
||||
require(bytes(domainName).length > 0, "domain name cannot be zero");
|
||||
require(domainNameHash != bytes32(0), "domain name cannot be zero");
|
||||
require(publicKeyHash != bytes32(0), "public key hash cannot be zero");
|
||||
require(authorizer != address(0), "authorizer address cannot be zero");
|
||||
require(
|
||||
@@ -126,7 +112,7 @@ contract UserOverrideableDKIMRegistry is
|
||||
authorizer
|
||||
);
|
||||
uint256 setThreshold = _computeSetThreshold(
|
||||
domainName,
|
||||
domainNameHash,
|
||||
publicKeyHash,
|
||||
authorizer
|
||||
);
|
||||
@@ -160,8 +146,10 @@ contract UserOverrideableDKIMRegistry is
|
||||
require(bytes(domainName).length > 0, "domain name cannot be zero");
|
||||
require(publicKeyHash != bytes32(0), "public key hash cannot be zero");
|
||||
require(authorizer != address(0), "authorizer address cannot be zero");
|
||||
bytes32 domainNameHash = keccak256(bytes(domainName));
|
||||
require(
|
||||
dkimPublicKeyHashes[domainName][publicKeyHash][authorizer] == false,
|
||||
dkimPublicKeyHashes[domainNameHash][publicKeyHash][authorizer] ==
|
||||
false,
|
||||
"public key hash is already set"
|
||||
);
|
||||
require(
|
||||
@@ -192,19 +180,19 @@ contract UserOverrideableDKIMRegistry is
|
||||
}
|
||||
}
|
||||
|
||||
dkimPublicKeyHashes[domainName][publicKeyHash][authorizer] = true;
|
||||
dkimPublicKeyHashes[domainNameHash][publicKeyHash][authorizer] = true;
|
||||
if (authorizer == mainAuthorizer) {
|
||||
enabledTimeOfDKIMPublicKeyHash[publicKeyHash] =
|
||||
block.timestamp +
|
||||
setTimestampDelay;
|
||||
}
|
||||
|
||||
emit DKIMPublicKeyHashRegistered(domainName, publicKeyHash, authorizer);
|
||||
emit KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Sets the DKIM public key hashes in batch.
|
||||
* @param domainNames An array of the domain name for which the DKIM public key hash is being set.
|
||||
* @param domainNames An array of the domain names for which the DKIM public key hash is being set.
|
||||
* @param publicKeyHashes An array of the hash of the DKIM public key to be set.
|
||||
* @param authorizers An array of the address of the authorizer who can set the DKIM public key hash.
|
||||
* @param signatures An array of the signature proving the authorization to set the DKIM public key hash.
|
||||
@@ -291,7 +279,7 @@ contract UserOverrideableDKIMRegistry is
|
||||
}
|
||||
revokedDKIMPublicKeyHashes[publicKeyHash][authorizer] = true;
|
||||
|
||||
emit DKIMPublicKeyHashRevoked(publicKeyHash, authorizer);
|
||||
emit KeyHashRevoked(keccak256(bytes(domainName)));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -304,7 +292,7 @@ contract UserOverrideableDKIMRegistry is
|
||||
* @custom:require The domain name, public key hash, and authorizer address must not be zero.
|
||||
* @custom:require The public key hash must be revoked by the main authorizer.
|
||||
* @custom:require The signature must be valid according to EIP-1271 if the authorizer is a contract, or ECDSA if the authorizer is an EOA.
|
||||
* @custom:event DKIMPublicKeyHashReactivated Emitted when a DKIM public key hash is successfully reactivated.
|
||||
* @custom:event KeyHashReactivated Emitted when a DKIM public key hash is successfully reactivated.
|
||||
*/
|
||||
function reactivateDKIMPublicKeyHash(
|
||||
string memory domainName,
|
||||
@@ -328,7 +316,8 @@ contract UserOverrideableDKIMRegistry is
|
||||
"revoke threshold must be one"
|
||||
);
|
||||
require(
|
||||
_computeSetThreshold(domainName, publicKeyHash, authorizer) >= 2,
|
||||
_computeSetThreshold(keccak256(bytes(domainName)), publicKeyHash, authorizer) >=
|
||||
2,
|
||||
"set threshold must be larger than two"
|
||||
);
|
||||
if (msg.sender != authorizer) {
|
||||
@@ -356,7 +345,7 @@ contract UserOverrideableDKIMRegistry is
|
||||
}
|
||||
reactivatedDKIMPublicKeyHashes[publicKeyHash][authorizer] = true;
|
||||
|
||||
emit DKIMPublicKeyHashReactivated(publicKeyHash, authorizer);
|
||||
emit KeyHashReactivated(publicKeyHash, authorizer);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -405,14 +394,15 @@ contract UserOverrideableDKIMRegistry is
|
||||
}
|
||||
|
||||
function _computeSetThreshold(
|
||||
string memory domainName,
|
||||
bytes32 domainNameHash,
|
||||
bytes32 publicKeyHash,
|
||||
address authorizer
|
||||
) private view returns (uint256) {
|
||||
uint256 threshold = 0;
|
||||
if (
|
||||
dkimPublicKeyHashes[domainName][publicKeyHash][mainAuthorizer] ==
|
||||
true
|
||||
dkimPublicKeyHashes[domainNameHash][publicKeyHash][
|
||||
mainAuthorizer
|
||||
] == true
|
||||
) {
|
||||
if (
|
||||
block.timestamp < enabledTimeOfDKIMPublicKeyHash[publicKeyHash]
|
||||
@@ -423,7 +413,8 @@ contract UserOverrideableDKIMRegistry is
|
||||
}
|
||||
}
|
||||
if (
|
||||
dkimPublicKeyHashes[domainName][publicKeyHash][authorizer] == true
|
||||
dkimPublicKeyHashes[domainNameHash][publicKeyHash][authorizer] ==
|
||||
true
|
||||
) {
|
||||
threshold += 2;
|
||||
}
|
||||
@@ -450,13 +441,6 @@ contract UserOverrideableDKIMRegistry is
|
||||
return threshold;
|
||||
}
|
||||
|
||||
function _stringEq(
|
||||
string memory a,
|
||||
string memory b
|
||||
) internal pure returns (bool) {
|
||||
return keccak256(abi.encodePacked(a)) == keccak256(abi.encodePacked(b));
|
||||
}
|
||||
|
||||
/// @notice Upgrade the implementation of the proxy.
|
||||
/// @param newImplementation Address of the new implementation.
|
||||
function _authorizeUpgrade(
|
||||
|
||||
@@ -1,9 +0,0 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
pragma solidity ^0.8.0;
|
||||
|
||||
interface IDKIMRegistry {
|
||||
function isDKIMPublicKeyHashValid(
|
||||
string memory domainName,
|
||||
bytes32 publicKeyHash
|
||||
) external view returns (bool);
|
||||
}
|
||||
31
packages/contracts/interfaces/IERC7969.sol
Normal file
31
packages/contracts/interfaces/IERC7969.sol
Normal file
@@ -0,0 +1,31 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
pragma solidity ^0.8.20;
|
||||
|
||||
/**
|
||||
* @title ERC-7969 DKIM Registry Interface.
|
||||
*
|
||||
* @dev This interface provides a standard way to register and validate DKIM public key hashes onchain
|
||||
* Domain owners can register their DKIM public key hashes and third parties can verify their validity
|
||||
* The interface enables email-based account abstraction and secure account recovery mechanisms.
|
||||
*
|
||||
* NOTE: The ERC-165 identifier for this interface is `0xdee3d600`.
|
||||
*/
|
||||
interface IDKIMRegistry {
|
||||
/// @dev Emitted when a new DKIM public key hash is registered for a domain
|
||||
/// @param domainHash The keccak256 hash of the lowercase domain name
|
||||
/// @param keyHash The keccak256 hash of the DKIM public key
|
||||
event KeyHashRegistered(bytes32 domainHash, bytes32 keyHash);
|
||||
|
||||
/// @dev Emitted when a DKIM public key hash is revoked for a domain
|
||||
/// @param domainHash The keccak256 hash of the domain name
|
||||
event KeyHashRevoked(bytes32 domainHash);
|
||||
|
||||
/// @dev Checks if a DKIM key hash is valid for a given domain
|
||||
/// @param domainHash The keccak256 hash of the lowercase domain name
|
||||
/// @param keyHash The keccak256 hash of the DKIM public key
|
||||
/// @return True if the key hash is valid for the domain, false otherwise
|
||||
function isKeyHashValid(
|
||||
bytes32 domainHash,
|
||||
bytes32 keyHash
|
||||
) external view returns (bool);
|
||||
}
|
||||
@@ -4,7 +4,7 @@ pragma solidity ^0.8.12;
|
||||
import "@openzeppelin/contracts/utils/Strings.sol";
|
||||
import "forge-std/src/Test.sol";
|
||||
import "forge-std/src/console.sol";
|
||||
import "../interfaces/IDKIMRegistry.sol";
|
||||
import "../interfaces/IERC7969.sol";
|
||||
import "../DKIMRegistry.sol";
|
||||
|
||||
/// @title ECDSAOwnedDKIMRegistry
|
||||
|
||||
@@ -10,6 +10,7 @@ import {MessageHashUtils} from "@openzeppelin/contracts/utils/cryptography/Messa
|
||||
import "./helpers/ExampleERC1271.sol";
|
||||
import "./helpers/ExampleOwnable.sol";
|
||||
import {ERC1967Proxy} from "@openzeppelin/contracts/proxy/ERC1967/ERC1967Proxy.sol";
|
||||
import {IDKIMRegistry} from "../interfaces/IERC7969.sol";
|
||||
|
||||
contract UserOverrideableDKIMRegistryTest is Test {
|
||||
UserOverrideableDKIMRegistry registry;
|
||||
@@ -18,6 +19,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
using Strings for *;
|
||||
|
||||
string public domainName = "example.com";
|
||||
bytes32 public domainNameHash = keccak256(bytes(domainName));
|
||||
bytes32 public publicKeyHash = bytes32(uint256(1));
|
||||
bytes32 public publicKeyHash2 = bytes32(uint256(2));
|
||||
uint256 public setTimestampDelay = 1 days;
|
||||
@@ -73,11 +75,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(user1);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
user1
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -88,7 +86,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -98,11 +96,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(mainAuthorizer);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -114,11 +108,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(user1);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
user1
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -130,7 +120,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 3
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -140,11 +130,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(mainAuthorizer);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -157,7 +143,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.warp(block.timestamp + setTimestampDelay);
|
||||
// setThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -178,11 +164,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -194,11 +176,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(user1);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
user1
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -210,7 +188,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -231,11 +209,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -248,7 +222,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.warp(block.timestamp + setTimestampDelay);
|
||||
// setThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -269,11 +243,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
address(mainAuthorizerContract)
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registryWithContract.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -285,11 +255,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(user1);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
user1
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registryWithContract.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -301,10 +267,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 2
|
||||
require(
|
||||
registryWithContract.isDKIMPublicKeyHashValid(
|
||||
domainName,
|
||||
publicKeyHash
|
||||
),
|
||||
registryWithContract.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -325,11 +288,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
address(mainAuthorizerContract)
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registryWithContract.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -342,10 +301,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.warp(block.timestamp + setTimestampDelay);
|
||||
// setThreshold = 2
|
||||
require(
|
||||
registryWithContract.isDKIMPublicKeyHashValid(
|
||||
domainName,
|
||||
publicKeyHash
|
||||
),
|
||||
registryWithContract.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -354,10 +310,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
function testRevokeDKIMPublicKeyHashByUser1() public {
|
||||
vm.startPrank(user1);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRevoked(
|
||||
publicKeyHash,
|
||||
user1
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRevoked(domainNameHash);
|
||||
registry.revokeDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -368,7 +321,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
require(
|
||||
!registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
!registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"public key hash is not revoked"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -377,10 +330,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
function testRevokeDKIMPublicKeyHashByMainAuthorizer() public {
|
||||
vm.startPrank(mainAuthorizer);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRevoked(
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRevoked(domainNameHash);
|
||||
registry.revokeDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -391,7 +341,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
require(
|
||||
!registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
!registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"public key hash is not revoked"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -412,10 +362,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRevoked(
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRevoked(domainNameHash);
|
||||
registry.revokeDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -426,7 +373,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
require(
|
||||
!registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
!registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"public key hash is not revoked"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -447,10 +394,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRevoked(
|
||||
publicKeyHash,
|
||||
address(mainAuthorizerContract)
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRevoked(domainNameHash);
|
||||
registryWithContract.revokeDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -461,10 +405,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
require(
|
||||
!registryWithContract.isDKIMPublicKeyHashValid(
|
||||
domainName,
|
||||
publicKeyHash
|
||||
),
|
||||
!registryWithContract.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"public key hash is not revoked"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -485,7 +426,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 0
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -518,7 +459,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
// revokeThreshold = 1
|
||||
// reactivated
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -551,7 +492,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
// revokeThreshold = 1
|
||||
// reactivated
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -584,7 +525,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
// revokeThreshold = 1
|
||||
// not reactivated
|
||||
require(
|
||||
!registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
!registry.isKeyHashValid(domainNameHash, publicKeyHash),
|
||||
"public key hash must be valid"
|
||||
);
|
||||
vm.stopPrank();
|
||||
@@ -606,29 +547,20 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser2() public {
|
||||
function testIsKeyHashValidByUser2() public {
|
||||
testSetDKIMPublicKeyHashByUser1();
|
||||
|
||||
vm.startPrank(address(exampleOwnable2));
|
||||
// setThreshold = 0
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashBeforeEnabledWithoutUserConfirm()
|
||||
public
|
||||
{
|
||||
function testIsDKIMPublicKeyHashBeforeEnabledWithoutUserConfirm() public {
|
||||
vm.startPrank(mainAuthorizer);
|
||||
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -639,14 +571,11 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashBeforeEnabledWithoutUserConfirmECDSA()
|
||||
function testIsDKIMPublicKeyHashBeforeEnabledWithoutUserConfirmECDSA()
|
||||
public
|
||||
{
|
||||
vm.startPrank(deployer);
|
||||
@@ -662,11 +591,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
mainAuthorizer
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registry.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -677,14 +602,11 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashBeforeEnabledWithoutUserConfirmContract()
|
||||
function testIsDKIMPublicKeyHashBeforeEnabledWithoutUserConfirmContract()
|
||||
public
|
||||
{
|
||||
vm.startPrank(deployer);
|
||||
@@ -700,11 +622,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
(uint8 v, bytes32 r, bytes32 s) = vm.sign(9, digest);
|
||||
bytes memory signature = abi.encodePacked(r, s, v);
|
||||
vm.expectEmit();
|
||||
emit UserOverrideableDKIMRegistry.DKIMPublicKeyHashRegistered(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
address(mainAuthorizerContract)
|
||||
);
|
||||
emit IDKIMRegistry.KeyHashRegistered(domainNameHash, publicKeyHash);
|
||||
registryWithContract.setDKIMPublicKeyHash(
|
||||
domainName,
|
||||
publicKeyHash,
|
||||
@@ -715,12 +633,8 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// setThreshold = 1
|
||||
require(
|
||||
registryWithContract.isDKIMPublicKeyHashValid(
|
||||
domainName,
|
||||
publicKeyHash
|
||||
),
|
||||
"Invalid public key hash"
|
||||
assertFalse(
|
||||
registryWithContract.isKeyHashValid(domainNameHash, publicKeyHash)
|
||||
);
|
||||
vm.stopPrank();
|
||||
}
|
||||
@@ -950,35 +864,25 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterRevokedByMainAuthorizer()
|
||||
public
|
||||
{
|
||||
function testIsKeyHashValidByUser1AfterRevokedByMainAuthorizer() public {
|
||||
testRevokeDKIMPublicKeyHashByMainAuthorizer();
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterRevokedByUser1()
|
||||
public
|
||||
{
|
||||
function testIsKeyHashValidByUser1AfterRevokedByUser1() public {
|
||||
testRevokeDKIMPublicKeyHashByUser1();
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterSetByUser1RevokedByMainAuthorizer()
|
||||
function testIsKeyHashValidByUser1AfterSetByUser1RevokedByMainAuthorizer()
|
||||
public
|
||||
{
|
||||
testSetDKIMPublicKeyHashByUser1();
|
||||
@@ -986,14 +890,11 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterSetByMainAuthorizerBeforeEnabledRevokedByMainAuthorizer()
|
||||
function testIsKeyHashValidByUser1AfterSetByMainAuthorizerBeforeEnabledRevokedByMainAuthorizer()
|
||||
public
|
||||
{
|
||||
testSetDKIMPublicKeyHashByMainAuthorizerBeforeEnabled();
|
||||
@@ -1001,14 +902,11 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterSetByMainAuthorizerAfterEnabledRevokedByMainAuthorizer()
|
||||
function testIsKeyHashValidByUser1AfterSetByMainAuthorizerAfterEnabledRevokedByMainAuthorizer()
|
||||
public
|
||||
{
|
||||
testSetDKIMPublicKeyHashByMainAuthorizerAfterEnabled();
|
||||
@@ -1016,29 +914,21 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 1
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterSetByUser1RevokedByUser1()
|
||||
public
|
||||
{
|
||||
function testIsKeyHashValidByUser1AfterSetByUser1RevokedByUser1() public {
|
||||
testSetDKIMPublicKeyHashByUser1();
|
||||
testRevokeDKIMPublicKeyHashByUser1();
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterSetByMainAuthorizerBeforeEnabledRevokedByUser1()
|
||||
function testIsKeyHashValidByUser1AfterSetByMainAuthorizerBeforeEnabledRevokedByUser1()
|
||||
public
|
||||
{
|
||||
testSetDKIMPublicKeyHashByMainAuthorizerBeforeEnabled();
|
||||
@@ -1046,14 +936,11 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
function testFailIsDKIMPublicKeyHashValidByUser1AfterSetByMainAuthorizerAfterEnabledRevokedByUser1()
|
||||
function testIsKeyHashValidByUser1AfterSetByMainAuthorizerAfterEnabledRevokedByUser1()
|
||||
public
|
||||
{
|
||||
testSetDKIMPublicKeyHashByMainAuthorizerAfterEnabled();
|
||||
@@ -1061,10 +948,7 @@ contract UserOverrideableDKIMRegistryTest is Test {
|
||||
|
||||
vm.startPrank(address(exampleOwnable1));
|
||||
// revokeThreshold = 2
|
||||
require(
|
||||
registry.isDKIMPublicKeyHashValid(domainName, publicKeyHash),
|
||||
"Invalid public key hash"
|
||||
);
|
||||
assertFalse(registry.isKeyHashValid(domainNameHash, publicKeyHash));
|
||||
vm.stopPrank();
|
||||
}
|
||||
|
||||
|
||||
File diff suppressed because one or more lines are too long
Reference in New Issue
Block a user