mirror of
https://github.com/getwax/bls-wallet.git
synced 2026-01-10 08:07:54 -05:00
Initial BLS stub
This commit is contained in:
48
contracts/BLSWallet.sol
Normal file
48
contracts/BLSWallet.sol
Normal file
@@ -0,0 +1,48 @@
|
||||
//SPDX-License-Identifier: Unlicense
|
||||
pragma solidity ^0.8.0;
|
||||
pragma abicoder v2;
|
||||
|
||||
import "./lib/BLS.sol";
|
||||
import "./lib/IERC20.sol";
|
||||
import "hardhat/console.sol";
|
||||
|
||||
|
||||
contract BLSWallet //is IERC20 //(to consider?)
|
||||
{
|
||||
IERC20 baseToken;
|
||||
|
||||
mapping (address => uint256[4])public blsKeys;
|
||||
mapping (address => uint256) balances;
|
||||
|
||||
constructor(IERC20 token) {
|
||||
baseToken = token;
|
||||
}
|
||||
|
||||
/**
|
||||
@dev Called from token holder's address
|
||||
*/
|
||||
function deposit(
|
||||
uint256[4] memory blsPubKey,
|
||||
uint256 amount
|
||||
) public {
|
||||
// TODO: check existing key
|
||||
baseToken.transferFrom(msg.sender, address(this), amount);
|
||||
blsKeys[msg.sender] = blsPubKey;
|
||||
balances[msg.sender] += amount;
|
||||
}
|
||||
|
||||
function withdraw() public {
|
||||
uint256 amount = balances[msg.sender];
|
||||
blsKeys[msg.sender] = [0,0,0,0];
|
||||
balances[msg.sender] = 0;
|
||||
baseToken.transfer(msg.sender, amount);
|
||||
}
|
||||
|
||||
// //TODO: verifyMultiple
|
||||
// function transferBatch() {}
|
||||
|
||||
function balanceOf(address account) public view returns (uint256) {
|
||||
return balances[account];
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,23 +0,0 @@
|
||||
//SPDX-License-Identifier: Unlicense
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "hardhat/console.sol";
|
||||
|
||||
|
||||
contract Greeter {
|
||||
string greeting;
|
||||
|
||||
constructor(string memory _greeting) {
|
||||
console.log("Deploying a Greeter with greeting:", _greeting);
|
||||
greeting = _greeting;
|
||||
}
|
||||
|
||||
function greet() public view returns (string memory) {
|
||||
return greeting;
|
||||
}
|
||||
|
||||
function setGreeting(string memory _greeting) public {
|
||||
console.log("Changing greeting from '%s' to '%s'", greeting, _greeting);
|
||||
greeting = _greeting;
|
||||
}
|
||||
}
|
||||
437
contracts/lib/BLS.sol
Normal file
437
contracts/lib/BLS.sol
Normal file
@@ -0,0 +1,437 @@
|
||||
//SPDX-License-Identifier: Unlicense
|
||||
pragma solidity ^0.8.0;
|
||||
|
||||
import { ModexpInverse, ModexpSqrt } from "./ModExp.sol";
|
||||
|
||||
/**
|
||||
@title Boneh–Lynn–Shacham (BLS) signature scheme on Barreto-Naehrig 254 bit curve (BN-254)
|
||||
@notice We use BLS signature aggregation to reduce the size of signature data to store on chain.
|
||||
@dev We use G1 points for signatures and messages, and G2 points for public keys
|
||||
*/
|
||||
library BLS {
|
||||
// Field order
|
||||
// prettier-ignore
|
||||
uint256 private constant N = 21888242871839275222246405745257275088696311157297823662689037894645226208583;
|
||||
|
||||
// Negated genarator of G2
|
||||
// prettier-ignore
|
||||
uint256 private constant N_G2_X1 = 11559732032986387107991004021392285783925812861821192530917403151452391805634;
|
||||
// prettier-ignore
|
||||
uint256 private constant N_G2_X0 = 10857046999023057135944570762232829481370756359578518086990519993285655852781;
|
||||
// prettier-ignore
|
||||
uint256 private constant N_G2_Y1 = 17805874995975841540914202342111839520379459829704422454583296818431106115052;
|
||||
// prettier-ignore
|
||||
uint256 private constant N_G2_Y0 = 13392588948715843804641432497768002650278120570034223513918757245338268106653;
|
||||
|
||||
// sqrt(-3)
|
||||
// prettier-ignore
|
||||
uint256 private constant Z0 = 0x0000000000000000b3c4d79d41a91759a9e4c7e359b6b89eaec68e62effffffd;
|
||||
// (sqrt(-3) - 1) / 2
|
||||
// prettier-ignore
|
||||
uint256 private constant Z1 = 0x000000000000000059e26bcea0d48bacd4f263f1acdb5c4f5763473177fffffe;
|
||||
|
||||
// prettier-ignore
|
||||
uint256 private constant T24 = 0x1000000000000000000000000000000000000000000000000;
|
||||
// prettier-ignore
|
||||
uint256 private constant MASK24 = 0xffffffffffffffffffffffffffffffffffffffffffffffff;
|
||||
|
||||
function verifySingle(
|
||||
uint256[2] memory signature,
|
||||
uint256[4] memory pubkey,
|
||||
uint256[2] memory message
|
||||
) internal view returns (bool, bool) {
|
||||
uint256[12] memory input = [
|
||||
signature[0],
|
||||
signature[1],
|
||||
N_G2_X1,
|
||||
N_G2_X0,
|
||||
N_G2_Y1,
|
||||
N_G2_Y0,
|
||||
message[0],
|
||||
message[1],
|
||||
pubkey[1],
|
||||
pubkey[0],
|
||||
pubkey[3],
|
||||
pubkey[2]
|
||||
];
|
||||
uint256[1] memory out;
|
||||
uint256 precompileGasCost = pairingPrecompileCallGasCost(2);
|
||||
bool callSuccess;
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
callSuccess := staticcall(
|
||||
precompileGasCost,
|
||||
8,
|
||||
input,
|
||||
384,
|
||||
out,
|
||||
0x20
|
||||
)
|
||||
}
|
||||
if (!callSuccess) {
|
||||
return (false, false);
|
||||
}
|
||||
return (out[0] != 0, true);
|
||||
}
|
||||
|
||||
function verifyMultiple(
|
||||
uint256[2] memory signature,
|
||||
uint256[4][] memory pubkeys,
|
||||
uint256[2][] memory messages
|
||||
) internal view returns (bool checkResult, bool callSuccess) {
|
||||
uint256 size = pubkeys.length;
|
||||
require(size > 0, "BLS: number of public key is zero");
|
||||
require(
|
||||
size == messages.length,
|
||||
"BLS: number of public keys and messages must be equal"
|
||||
);
|
||||
uint256 inputSize = (size + 1) * 6;
|
||||
uint256[] memory input = new uint256[](inputSize);
|
||||
input[0] = signature[0];
|
||||
input[1] = signature[1];
|
||||
input[2] = N_G2_X1;
|
||||
input[3] = N_G2_X0;
|
||||
input[4] = N_G2_Y1;
|
||||
input[5] = N_G2_Y0;
|
||||
for (uint256 i = 0; i < size; i++) {
|
||||
input[i * 6 + 6] = messages[i][0];
|
||||
input[i * 6 + 7] = messages[i][1];
|
||||
input[i * 6 + 8] = pubkeys[i][1];
|
||||
input[i * 6 + 9] = pubkeys[i][0];
|
||||
input[i * 6 + 10] = pubkeys[i][3];
|
||||
input[i * 6 + 11] = pubkeys[i][2];
|
||||
}
|
||||
uint256[1] memory out;
|
||||
uint256 precompileGasCost = pairingPrecompileCallGasCost(size);
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
callSuccess := staticcall(
|
||||
precompileGasCost,
|
||||
8,
|
||||
add(input, 0x20),
|
||||
mul(inputSize, 0x20),
|
||||
out,
|
||||
0x20
|
||||
)
|
||||
}
|
||||
if (!callSuccess) {
|
||||
return (false, false);
|
||||
}
|
||||
return (out[0] != 0, true);
|
||||
}
|
||||
|
||||
function pairingPrecompileCallGasCost(uint256 pubkeyLen)
|
||||
internal
|
||||
pure
|
||||
returns (uint256)
|
||||
{
|
||||
uint256 base = 34000;
|
||||
uint256 pair = 45000;
|
||||
return base + pair * pubkeyLen;
|
||||
}
|
||||
|
||||
/**
|
||||
@notice Fouque-Tibouchi Hash to Curve
|
||||
*/
|
||||
function hashToPoint(bytes32 domain, bytes memory message)
|
||||
internal
|
||||
view
|
||||
returns (uint256[2] memory)
|
||||
{
|
||||
uint256[2] memory u = hashToField(domain, message);
|
||||
uint256[2] memory p0 = mapToPoint(u[0]);
|
||||
uint256[2] memory p1 = mapToPoint(u[1]);
|
||||
uint256[4] memory bnAddInput;
|
||||
bnAddInput[0] = p0[0];
|
||||
bnAddInput[1] = p0[1];
|
||||
bnAddInput[2] = p1[0];
|
||||
bnAddInput[3] = p1[1];
|
||||
bool success;
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
success := staticcall(sub(gas(), 2000), 6, bnAddInput, 128, p0, 64)
|
||||
switch success
|
||||
case 0 {
|
||||
invalid()
|
||||
}
|
||||
}
|
||||
require(success, "BLS: bn add call failed");
|
||||
return p0;
|
||||
}
|
||||
|
||||
function mapToPoint(uint256 _x)
|
||||
internal
|
||||
pure
|
||||
returns (uint256[2] memory p)
|
||||
{
|
||||
require(_x < N, "mapToPointFT: invalid field element");
|
||||
uint256 x = _x;
|
||||
|
||||
(, bool decision) = sqrt(x);
|
||||
|
||||
uint256 a0 = mulmod(x, x, N);
|
||||
a0 = addmod(a0, 4, N);
|
||||
uint256 a1 = mulmod(x, Z0, N);
|
||||
uint256 a2 = mulmod(a1, a0, N);
|
||||
a2 = inverse(a2);
|
||||
a1 = mulmod(a1, a1, N);
|
||||
a1 = mulmod(a1, a2, N);
|
||||
|
||||
// x1
|
||||
a1 = mulmod(x, a1, N);
|
||||
x = addmod(Z1, N - a1, N);
|
||||
// check curve
|
||||
a1 = mulmod(x, x, N);
|
||||
a1 = mulmod(a1, x, N);
|
||||
a1 = addmod(a1, 3, N);
|
||||
bool found;
|
||||
(a1, found) = sqrt(a1);
|
||||
if (found) {
|
||||
if (!decision) {
|
||||
a1 = N - a1;
|
||||
}
|
||||
return [x, a1];
|
||||
}
|
||||
|
||||
// x2
|
||||
x = N - addmod(x, 1, N);
|
||||
// check curve
|
||||
a1 = mulmod(x, x, N);
|
||||
a1 = mulmod(a1, x, N);
|
||||
a1 = addmod(a1, 3, N);
|
||||
(a1, found) = sqrt(a1);
|
||||
if (found) {
|
||||
if (!decision) {
|
||||
a1 = N - a1;
|
||||
}
|
||||
return [x, a1];
|
||||
}
|
||||
|
||||
// x3
|
||||
x = mulmod(a0, a0, N);
|
||||
x = mulmod(x, x, N);
|
||||
x = mulmod(x, a2, N);
|
||||
x = mulmod(x, a2, N);
|
||||
x = addmod(x, 1, N);
|
||||
// must be on curve
|
||||
a1 = mulmod(x, x, N);
|
||||
a1 = mulmod(a1, x, N);
|
||||
a1 = addmod(a1, 3, N);
|
||||
(a1, found) = sqrt(a1);
|
||||
require(found, "BLS: bad ft mapping implementation");
|
||||
if (!decision) {
|
||||
a1 = N - a1;
|
||||
}
|
||||
return [x, a1];
|
||||
}
|
||||
|
||||
function isValidSignature(uint256[2] memory signature)
|
||||
internal
|
||||
pure
|
||||
returns (bool)
|
||||
{
|
||||
if ((signature[0] >= N) || (signature[1] >= N)) {
|
||||
return false;
|
||||
} else {
|
||||
return isOnCurveG1(signature);
|
||||
}
|
||||
}
|
||||
|
||||
function isOnCurveG1(uint256[2] memory point)
|
||||
internal
|
||||
pure
|
||||
returns (bool _isOnCurve)
|
||||
{
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let t0 := mload(point)
|
||||
let t1 := mload(add(point, 32))
|
||||
let t2 := mulmod(t0, t0, N)
|
||||
t2 := mulmod(t2, t0, N)
|
||||
t2 := addmod(t2, 3, N)
|
||||
t1 := mulmod(t1, t1, N)
|
||||
_isOnCurve := eq(t1, t2)
|
||||
}
|
||||
}
|
||||
|
||||
function isOnCurveG2(uint256[4] memory point)
|
||||
internal
|
||||
pure
|
||||
returns (bool _isOnCurve)
|
||||
{
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
// x0, x1
|
||||
let t0 := mload(point)
|
||||
let t1 := mload(add(point, 32))
|
||||
// x0 ^ 2
|
||||
let t2 := mulmod(t0, t0, N)
|
||||
// x1 ^ 2
|
||||
let t3 := mulmod(t1, t1, N)
|
||||
// 3 * x0 ^ 2
|
||||
let t4 := add(add(t2, t2), t2)
|
||||
// 3 * x1 ^ 2
|
||||
let t5 := addmod(add(t3, t3), t3, N)
|
||||
// x0 * (x0 ^ 2 - 3 * x1 ^ 2)
|
||||
t2 := mulmod(add(t2, sub(N, t5)), t0, N)
|
||||
// x1 * (3 * x0 ^ 2 - x1 ^ 2)
|
||||
t3 := mulmod(add(t4, sub(N, t3)), t1, N)
|
||||
|
||||
// x ^ 3 + b
|
||||
t0 := addmod(
|
||||
t2,
|
||||
0x2b149d40ceb8aaae81be18991be06ac3b5b4c5e559dbefa33267e6dc24a138e5,
|
||||
N
|
||||
)
|
||||
t1 := addmod(
|
||||
t3,
|
||||
0x009713b03af0fed4cd2cafadeed8fdf4a74fa084e52d1852e4a2bd0685c315d2,
|
||||
N
|
||||
)
|
||||
|
||||
// y0, y1
|
||||
t2 := mload(add(point, 64))
|
||||
t3 := mload(add(point, 96))
|
||||
// y ^ 2
|
||||
t4 := mulmod(addmod(t2, t3, N), addmod(t2, sub(N, t3), N), N)
|
||||
t3 := mulmod(shl(1, t2), t3, N)
|
||||
|
||||
// y ^ 2 == x ^ 3 + b
|
||||
_isOnCurve := and(eq(t0, t4), eq(t1, t3))
|
||||
}
|
||||
}
|
||||
|
||||
function sqrt(uint256 xx) internal pure returns (uint256 x, bool hasRoot) {
|
||||
x = ModexpSqrt.run(xx);
|
||||
hasRoot = mulmod(x, x, N) == xx;
|
||||
}
|
||||
|
||||
function inverse(uint256 a) internal pure returns (uint256) {
|
||||
return ModexpInverse.run(a);
|
||||
}
|
||||
|
||||
function hashToField(bytes32 domain, bytes memory messages)
|
||||
internal
|
||||
pure
|
||||
returns (uint256[2] memory)
|
||||
{
|
||||
bytes memory _msg = expandMsgTo96(domain, messages);
|
||||
uint256 u0;
|
||||
uint256 u1;
|
||||
uint256 a0;
|
||||
uint256 a1;
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let p := add(_msg, 24)
|
||||
u1 := and(mload(p), MASK24)
|
||||
p := add(_msg, 48)
|
||||
u0 := and(mload(p), MASK24)
|
||||
a0 := addmod(mulmod(u1, T24, N), u0, N)
|
||||
p := add(_msg, 72)
|
||||
u1 := and(mload(p), MASK24)
|
||||
p := add(_msg, 96)
|
||||
u0 := and(mload(p), MASK24)
|
||||
a1 := addmod(mulmod(u1, T24, N), u0, N)
|
||||
}
|
||||
return [a0, a1];
|
||||
}
|
||||
|
||||
function expandMsgTo96(bytes32 domain, bytes memory message)
|
||||
internal
|
||||
pure
|
||||
returns (bytes memory)
|
||||
{
|
||||
// zero<64>|msg<var>|lib_str<2>|I2OSP(0, 1)<1>|dst<var>|dst_len<1>
|
||||
uint256 t0 = message.length;
|
||||
bytes memory msg0 = new bytes(32 + t0 + 64 + 4);
|
||||
bytes memory out = new bytes(96);
|
||||
// b0
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let p := add(msg0, 96)
|
||||
for {
|
||||
let z := 0
|
||||
} lt(z, t0) {
|
||||
z := add(z, 32)
|
||||
} {
|
||||
mstore(add(p, z), mload(add(message, add(z, 32))))
|
||||
}
|
||||
p := add(p, t0)
|
||||
|
||||
mstore8(p, 0)
|
||||
p := add(p, 1)
|
||||
mstore8(p, 96)
|
||||
p := add(p, 1)
|
||||
mstore8(p, 0)
|
||||
p := add(p, 1)
|
||||
|
||||
mstore(p, domain)
|
||||
p := add(p, 32)
|
||||
mstore8(p, 32)
|
||||
}
|
||||
bytes32 b0 = sha256(msg0);
|
||||
bytes32 bi;
|
||||
t0 = 32 + 34;
|
||||
|
||||
// resize intermediate message
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
mstore(msg0, t0)
|
||||
}
|
||||
|
||||
// b1
|
||||
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
mstore(add(msg0, 32), b0)
|
||||
mstore8(add(msg0, 64), 1)
|
||||
mstore(add(msg0, 65), domain)
|
||||
mstore8(add(msg0, add(32, 65)), 32)
|
||||
}
|
||||
|
||||
bi = sha256(msg0);
|
||||
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
mstore(add(out, 32), bi)
|
||||
}
|
||||
|
||||
// b2
|
||||
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let t := xor(b0, bi)
|
||||
mstore(add(msg0, 32), t)
|
||||
mstore8(add(msg0, 64), 2)
|
||||
mstore(add(msg0, 65), domain)
|
||||
mstore8(add(msg0, add(32, 65)), 32)
|
||||
}
|
||||
|
||||
bi = sha256(msg0);
|
||||
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
mstore(add(out, 64), bi)
|
||||
}
|
||||
|
||||
// b3
|
||||
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let t := xor(b0, bi)
|
||||
mstore(add(msg0, 32), t)
|
||||
mstore8(add(msg0, 64), 3)
|
||||
mstore(add(msg0, 65), domain)
|
||||
mstore8(add(msg0, add(32, 65)), 32)
|
||||
}
|
||||
|
||||
bi = sha256(msg0);
|
||||
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
mstore(add(out, 96), bi)
|
||||
}
|
||||
|
||||
return out;
|
||||
}
|
||||
}
|
||||
73
contracts/lib/IERC20.sol
Normal file
73
contracts/lib/IERC20.sol
Normal file
@@ -0,0 +1,73 @@
|
||||
//SPDX-License-Identifier: Unlicense
|
||||
pragma solidity ^0.8.0;
|
||||
|
||||
interface IERC20 {
|
||||
/**
|
||||
* @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);
|
||||
}
|
||||
652
contracts/lib/ModExp.sol
Normal file
652
contracts/lib/ModExp.sol
Normal file
@@ -0,0 +1,652 @@
|
||||
//SPDX-License-Identifier: Unlicense
|
||||
pragma solidity ^0.8.0;
|
||||
|
||||
/**
|
||||
@title Compute Inverse by Modular Exponentiation
|
||||
@notice Compute $input^(N - 2) mod N$ using Addition Chain method.
|
||||
Where N = 0x30644e72e131a029b85045b68181585d97816a916871ca8d3c208c16d87cfd47
|
||||
and N - 2 = 0x30644e72e131a029b85045b68181585d97816a916871ca8d3c208c16d87cfd45
|
||||
@dev the function body is generated with the modified addchain script
|
||||
see https://github.com/kobigurk/addchain/commit/2c37a2ace567a9bdc680b4e929c94aaaa3ec700f
|
||||
*/
|
||||
library ModexpInverse {
|
||||
function run(uint256 t2) internal pure returns (uint256 t0) {
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let
|
||||
n
|
||||
:= 0x30644e72e131a029b85045b68181585d97816a916871ca8d3c208c16d87cfd47
|
||||
t0 := mulmod(t2, t2, n)
|
||||
let t5 := mulmod(t0, t2, n)
|
||||
let t1 := mulmod(t5, t0, n)
|
||||
let t3 := mulmod(t5, t5, n)
|
||||
let t8 := mulmod(t1, t0, n)
|
||||
let t4 := mulmod(t3, t5, n)
|
||||
let t6 := mulmod(t3, t1, n)
|
||||
t0 := mulmod(t3, t3, n)
|
||||
let t7 := mulmod(t8, t3, n)
|
||||
t3 := mulmod(t4, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t7, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t7, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t7, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@title Compute Squre Root by Modular Exponentiation
|
||||
@notice Compute $input^{(N + 1) / 4} mod N$ using Addition Chain method.
|
||||
Where N = 0x30644e72e131a029b85045b68181585d97816a916871ca8d3c208c16d87cfd47
|
||||
and (N + 1) / 4 = 0xc19139cb84c680a6e14116da060561765e05aa45a1c72a34f082305b61f3f52
|
||||
*/
|
||||
library ModexpSqrt {
|
||||
function run(uint256 t6) internal pure returns (uint256 t0) {
|
||||
// solium-disable-next-line security/no-inline-assembly
|
||||
assembly {
|
||||
let
|
||||
n
|
||||
:= 0x30644e72e131a029b85045b68181585d97816a916871ca8d3c208c16d87cfd47
|
||||
|
||||
t0 := mulmod(t6, t6, n)
|
||||
let t4 := mulmod(t0, t6, n)
|
||||
let t2 := mulmod(t4, t0, n)
|
||||
let t3 := mulmod(t4, t4, n)
|
||||
let t8 := mulmod(t2, t0, n)
|
||||
let t1 := mulmod(t3, t4, n)
|
||||
let t5 := mulmod(t3, t2, n)
|
||||
t0 := mulmod(t3, t3, n)
|
||||
let t7 := mulmod(t8, t3, n)
|
||||
t3 := mulmod(t1, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t7, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t7, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t8, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t7, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t6, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t5, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t4, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t3, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t2, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
t0 := mulmod(t0, t1, n)
|
||||
t0 := mulmod(t0, t0, n)
|
||||
}
|
||||
}
|
||||
}
|
||||
18
contracts/mock/MockERC20.sol
Normal file
18
contracts/mock/MockERC20.sol
Normal file
@@ -0,0 +1,18 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "@openzeppelin/contracts/token/ERC20/ERC20.sol";
|
||||
|
||||
contract MockERC20 is ERC20 {
|
||||
constructor(
|
||||
string memory name,
|
||||
string memory symbol,
|
||||
uint256 supply
|
||||
) public ERC20(name, symbol) {
|
||||
_mint(msg.sender, supply);
|
||||
}
|
||||
|
||||
function mint(address _to, uint256 _amount) public {
|
||||
_mint(_to, _amount);
|
||||
}
|
||||
}
|
||||
@@ -17,6 +17,15 @@ task("accounts", "Prints the list of accounts", async () => {
|
||||
* @type import('hardhat/config').HardhatUserConfig
|
||||
*/
|
||||
module.exports = {
|
||||
solidity: "0.7.3",
|
||||
solidity: {
|
||||
compilers: [
|
||||
{
|
||||
version: "0.8.0"
|
||||
},
|
||||
{
|
||||
version: "0.7.0"
|
||||
}
|
||||
]
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -6,5 +6,8 @@
|
||||
"ethereum-waffle": "^3.0.0",
|
||||
"ethers": "^5.0.0",
|
||||
"hardhat": "^2.0.7"
|
||||
},
|
||||
"dependencies": {
|
||||
"@openzeppelin/contracts": "^3.3.0"
|
||||
}
|
||||
}
|
||||
|
||||
22
test/blsWallet-test.js
Normal file
22
test/blsWallet-test.js
Normal file
@@ -0,0 +1,22 @@
|
||||
const { expect } = require("chai");
|
||||
const { ethers } = require("hardhat");
|
||||
|
||||
const acc1BLSPubKey = [0xAA, 0xBB, 0xCC, 0xDD];
|
||||
const acc2BLSPubKey = [0xEE, 0xFF, 0x00, 0x11];
|
||||
const initialSupply = ethers.utils.parseUnits("1000000")
|
||||
|
||||
describe('BLSWallet', async function () {
|
||||
beforeEach(async function () {
|
||||
[admin, account1, account2] = await ethers.getSigners();
|
||||
|
||||
const MockERC20 = await ethers.getContractFactory("MockERC20");
|
||||
this.baseToken = await MockERC20.deploy("AnyToken","TOK", initialSupply);
|
||||
|
||||
const BLSWallet = await ethers.getContractFactory("BLSWallet");
|
||||
this.blsWallet = await BLSWallet.deploy(this.baseToken.address);
|
||||
});
|
||||
|
||||
it('should ', async function () {
|
||||
await this.blsWallet.connect(account1).deposit(acc1BLSPubKey, 0);
|
||||
});
|
||||
});
|
||||
@@ -1,14 +0,0 @@
|
||||
const { expect } = require("chai");
|
||||
|
||||
describe("Greeter", function() {
|
||||
it("Should return the new greeting once it's changed", async function() {
|
||||
const Greeter = await ethers.getContractFactory("Greeter");
|
||||
const greeter = await Greeter.deploy("Hello, world!");
|
||||
|
||||
await greeter.deployed();
|
||||
expect(await greeter.greet()).to.equal("Hello, world!");
|
||||
|
||||
await greeter.setGreeting("Hola, mundo!");
|
||||
expect(await greeter.greet()).to.equal("Hola, mundo!");
|
||||
});
|
||||
});
|
||||
@@ -453,6 +453,11 @@
|
||||
"@types/sinon-chai" "^3.2.3"
|
||||
"@types/web3" "1.0.19"
|
||||
|
||||
"@openzeppelin/contracts@^3.3.0":
|
||||
version "3.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@openzeppelin/contracts/-/contracts-3.3.0.tgz#ffdb693c5c349fc33bba420248dd3ac0a2d7c408"
|
||||
integrity sha512-AemZEsQYtUp1WRkcmZm1div5ORfTpLquLaziCIrSagjxyKdmObxuaY1yjQ5SHFMctR8rLwp706NXTbiIRJg7pw==
|
||||
|
||||
"@resolver-engine/core@^0.3.3":
|
||||
version "0.3.3"
|
||||
resolved "https://registry.yarnpkg.com/@resolver-engine/core/-/core-0.3.3.tgz#590f77d85d45bc7ecc4e06c654f41345db6ca967"
|
||||
|
||||
Reference in New Issue
Block a user