mirror of
https://github.com/tornadocash/tornado-core.git
synced 2024-12-29 16:17:55 +01:00
revert verifier code to deployed one
This commit is contained in:
parent
8580c5e427
commit
f5d8f6d971
@ -1,4 +1,8 @@
|
|||||||
// https://tornado.cash
|
/**
|
||||||
|
*Submitted for verification at Etherscan.io on 2020-05-12
|
||||||
|
*/
|
||||||
|
|
||||||
|
// https://tornado.cash Verifier.sol generated by trusted setup ceremony.
|
||||||
/*
|
/*
|
||||||
* d888888P dP a88888b. dP
|
* d888888P dP a88888b. dP
|
||||||
* 88 88 d8' `88 88
|
* 88 88 d8' `88 88
|
||||||
@ -8,8 +12,26 @@
|
|||||||
* dP `88888P' dP dP dP `88888P8 `88888P8 `88888P' 88 Y88888P' `88888P8 `88888P' dP dP
|
* dP `88888P' dP dP dP `88888P8 `88888P8 `88888P' 88 Y88888P' `88888P8 `88888P' dP dP
|
||||||
* ooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo
|
* ooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// SPDX-License-Identifier: MIT
|
// SPDX-License-Identifier: MIT
|
||||||
|
// Copyright 2017 Christian Reitwiessner
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to
|
||||||
|
// deal in the Software without restriction, including without limitation the
|
||||||
|
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
||||||
|
// sell copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
// The above copyright notice and this permission notice shall be included in
|
||||||
|
// all copies or substantial portions of the Software.
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||||
|
// IN THE SOFTWARE.
|
||||||
|
|
||||||
|
// 2019 OKIMS
|
||||||
|
|
||||||
pragma solidity ^0.6.0;
|
pragma solidity ^0.6.0;
|
||||||
|
|
||||||
library Pairing {
|
library Pairing {
|
||||||
@ -27,7 +49,7 @@ library Pairing {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* @return The negation of p, i.e. p.plus(p.negate()) should be zero
|
* @return The negation of p, i.e. p.plus(p.negate()) should be zero.
|
||||||
*/
|
*/
|
||||||
function negate(G1Point memory p) internal pure returns (G1Point memory) {
|
function negate(G1Point memory p) internal pure returns (G1Point memory) {
|
||||||
// The prime q in the base field F_q for G1
|
// The prime q in the base field F_q for G1
|
||||||
@ -45,10 +67,11 @@ library Pairing {
|
|||||||
G1Point memory p1,
|
G1Point memory p1,
|
||||||
G1Point memory p2
|
G1Point memory p2
|
||||||
) internal view returns (G1Point memory r) {
|
) internal view returns (G1Point memory r) {
|
||||||
uint256[4] memory input = [
|
uint256[4] memory input;
|
||||||
p1.X, p1.Y,
|
input[0] = p1.X;
|
||||||
p2.X, p2.Y
|
input[1] = p1.Y;
|
||||||
];
|
input[2] = p2.X;
|
||||||
|
input[3] = p2.Y;
|
||||||
bool success;
|
bool success;
|
||||||
|
|
||||||
// solium-disable-next-line security/no-inline-assembly
|
// solium-disable-next-line security/no-inline-assembly
|
||||||
@ -63,20 +86,21 @@ library Pairing {
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* @return r the product of a point on G1 and a scalar, i.e.
|
* @return r the product of a point on G1 and a scalar, i.e.
|
||||||
* p == p.scalarMul(1) and p.plus(p) == p.scalarMul(2) for all
|
* p == p.scalar_mul(1) and p.plus(p) == p.scalar_mul(2) for all
|
||||||
* points p.
|
* points p.
|
||||||
*/
|
*/
|
||||||
function scalarMul(G1Point memory p, uint256 s) internal view returns (G1Point memory r) {
|
function scalar_mul(G1Point memory p, uint256 s) internal view returns (G1Point memory r) {
|
||||||
uint256[3] memory input = [p.X, p.Y, s];
|
uint256[3] memory input;
|
||||||
|
input[0] = p.X;
|
||||||
|
input[1] = p.Y;
|
||||||
|
input[2] = s;
|
||||||
bool success;
|
bool success;
|
||||||
|
|
||||||
// solium-disable-next-line security/no-inline-assembly
|
// solium-disable-next-line security/no-inline-assembly
|
||||||
assembly {
|
assembly {
|
||||||
success := staticcall(sub(gas(), 2000), 7, input, 0x80, r, 0x60)
|
success := staticcall(sub(gas(), 2000), 7, input, 0x80, r, 0x60)
|
||||||
// Use "invalid" to make gas estimation work
|
// Use "invalid" to make gas estimation work
|
||||||
switch success case 0 { invalid() }
|
switch success case 0 { invalid() }
|
||||||
}
|
}
|
||||||
|
|
||||||
require(success, "pairing-mul-failed");
|
require(success, "pairing-mul-failed");
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -95,23 +119,34 @@ library Pairing {
|
|||||||
G1Point memory d1,
|
G1Point memory d1,
|
||||||
G2Point memory d2
|
G2Point memory d2
|
||||||
) internal view returns (bool) {
|
) internal view returns (bool) {
|
||||||
uint256[24] memory input = [
|
G1Point[4] memory p1 = [a1, b1, c1, d1];
|
||||||
a1.X, a1.Y, a2.X[0], a2.X[1], a2.Y[0], a2.Y[1],
|
G2Point[4] memory p2 = [a2, b2, c2, d2];
|
||||||
b1.X, b1.Y, b2.X[0], b2.X[1], b2.Y[0], b2.Y[1],
|
|
||||||
c1.X, c1.Y, c2.X[0], c2.X[1], c2.Y[0], c2.Y[1],
|
uint256 inputSize = 24;
|
||||||
d1.X, d1.Y, d2.X[0], d2.X[1], d2.Y[0], d2.Y[1]
|
uint256[] memory input = new uint256[](inputSize);
|
||||||
];
|
|
||||||
|
for (uint256 i = 0; i < 4; i++) {
|
||||||
|
uint256 j = i * 6;
|
||||||
|
input[j + 0] = p1[i].X;
|
||||||
|
input[j + 1] = p1[i].Y;
|
||||||
|
input[j + 2] = p2[i].X[0];
|
||||||
|
input[j + 3] = p2[i].X[1];
|
||||||
|
input[j + 4] = p2[i].Y[0];
|
||||||
|
input[j + 5] = p2[i].Y[1];
|
||||||
|
}
|
||||||
|
|
||||||
uint256[1] memory out;
|
uint256[1] memory out;
|
||||||
bool success;
|
bool success;
|
||||||
|
|
||||||
// solium-disable-next-line security/no-inline-assembly
|
// solium-disable-next-line security/no-inline-assembly
|
||||||
assembly {
|
assembly {
|
||||||
success := staticcall(sub(gas(), 2000), 8, input, mul(24, 0x20), out, 0x20)
|
success := staticcall(sub(gas(), 2000), 8, add(input, 0x20), mul(inputSize, 0x20), out, 0x20)
|
||||||
// Use "invalid" to make gas estimation work
|
// Use "invalid" to make gas estimation work
|
||||||
switch success case 0 { invalid() }
|
switch success case 0 { invalid() }
|
||||||
}
|
}
|
||||||
|
|
||||||
require(success, "pairing-opcode-failed");
|
require(success, "pairing-opcode-failed");
|
||||||
|
|
||||||
return out[0] != 0;
|
return out[0] != 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -129,6 +164,12 @@ contract Verifier {
|
|||||||
Pairing.G1Point[7] IC;
|
Pairing.G1Point[7] IC;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct Proof {
|
||||||
|
Pairing.G1Point A;
|
||||||
|
Pairing.G2Point B;
|
||||||
|
Pairing.G1Point C;
|
||||||
|
}
|
||||||
|
|
||||||
function verifyingKey() internal pure returns (VerifyingKey memory vk) {
|
function verifyingKey() internal pure returns (VerifyingKey memory vk) {
|
||||||
vk.alfa1 = Pairing.G1Point(uint256(20692898189092739278193869274495556617788530808486270118371701516666252877969), uint256(11713062878292653967971378194351968039596396853904572879488166084231740557279));
|
vk.alfa1 = Pairing.G1Point(uint256(20692898189092739278193869274495556617788530808486270118371701516666252877969), uint256(11713062878292653967971378194351968039596396853904572879488166084231740557279));
|
||||||
vk.beta2 = Pairing.G2Point([uint256(12168528810181263706895252315640534818222943348193302139358377162645029937006), uint256(281120578337195720357474965979947690431622127986816839208576358024608803542)], [uint256(16129176515713072042442734839012966563817890688785805090011011570989315559913), uint256(9011703453772030375124466642203641636825223906145908770308724549646909480510)]);
|
vk.beta2 = Pairing.G2Point([uint256(12168528810181263706895252315640534818222943348193302139358377162645029937006), uint256(281120578337195720357474965979947690431622127986816839208576358024608803542)], [uint256(16129176515713072042442734839012966563817890688785805090011011570989315559913), uint256(9011703453772030375124466642203641636825223906145908770308724549646909480510)]);
|
||||||
@ -153,31 +194,37 @@ contract Verifier {
|
|||||||
uint256[6] memory input
|
uint256[6] memory input
|
||||||
) public view returns (bool) {
|
) public view returns (bool) {
|
||||||
uint256[8] memory p = abi.decode(proof, (uint256[8]));
|
uint256[8] memory p = abi.decode(proof, (uint256[8]));
|
||||||
for (uint8 i = 0; i < p.length; i++) {
|
|
||||||
// Make sure that each element in the proof is less than the prime q
|
// Make sure that each element in the proof is less than the prime q
|
||||||
|
for (uint8 i = 0; i < p.length; i++) {
|
||||||
require(p[i] < PRIME_Q, "verifier-proof-element-gte-prime-q");
|
require(p[i] < PRIME_Q, "verifier-proof-element-gte-prime-q");
|
||||||
}
|
}
|
||||||
Pairing.G1Point memory proofA = Pairing.G1Point(p[0], p[1]);
|
|
||||||
Pairing.G2Point memory proofB = Pairing.G2Point([p[2], p[3]], [p[4], p[5]]);
|
Proof memory _proof;
|
||||||
Pairing.G1Point memory proofC = Pairing.G1Point(p[6], p[7]);
|
_proof.A = Pairing.G1Point(p[0], p[1]);
|
||||||
|
_proof.B = Pairing.G2Point([p[2], p[3]], [p[4], p[5]]);
|
||||||
|
_proof.C = Pairing.G1Point(p[6], p[7]);
|
||||||
|
|
||||||
VerifyingKey memory vk = verifyingKey();
|
VerifyingKey memory vk = verifyingKey();
|
||||||
// Compute the linear combination vkX
|
|
||||||
Pairing.G1Point memory vkX = vk.IC[0];
|
// Compute the linear combination vk_x
|
||||||
for (uint256 i = 0; i < input.length; i++) {
|
Pairing.G1Point memory vk_x = Pairing.G1Point(0, 0);
|
||||||
|
vk_x = Pairing.plus(vk_x, vk.IC[0]);
|
||||||
|
|
||||||
// Make sure that every input is less than the snark scalar field
|
// Make sure that every input is less than the snark scalar field
|
||||||
require(input[i] < SNARK_SCALAR_FIELD, "verifier-input-gte-snark-scalar-field");
|
for (uint256 i = 0; i < input.length; i++) {
|
||||||
vkX = Pairing.plus(vkX, Pairing.scalarMul(vk.IC[i + 1], input[i]));
|
require(input[i] < SNARK_SCALAR_FIELD, "verifier-gte-snark-scalar-field");
|
||||||
|
vk_x = Pairing.plus(vk_x, Pairing.scalar_mul(vk.IC[i + 1], input[i]));
|
||||||
}
|
}
|
||||||
|
|
||||||
return Pairing.pairing(
|
return Pairing.pairing(
|
||||||
Pairing.negate(proofA),
|
Pairing.negate(_proof.A),
|
||||||
proofB,
|
_proof.B,
|
||||||
vk.alfa1,
|
vk.alfa1,
|
||||||
vk.beta2,
|
vk.beta2,
|
||||||
vkX,
|
vk_x,
|
||||||
vk.gamma2,
|
vk.gamma2,
|
||||||
proofC,
|
_proof.C,
|
||||||
vk.delta2
|
vk.delta2
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user