zkp speedup
parent
9bb2f47b50
commit
ae2b7c51f0
|
@ -11,6 +11,6 @@ import java.util.List;
|
||||||
* Created by talm on 25/10/15.
|
* Created by talm on 25/10/15.
|
||||||
*/
|
*/
|
||||||
public interface Mixer {
|
public interface Mixer {
|
||||||
public Pair<Mixing.ZeroKnowledgeProof[][],Crypto.RerandomizableEncryptedMessage[][]>
|
public MixerOutput mix(List<Crypto.RerandomizableEncryptedMessage> ciphertexts)
|
||||||
mix(List<Crypto.RerandomizableEncryptedMessage> ciphertexts) throws InvalidProtocolBufferException;
|
throws InvalidProtocolBufferException;
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,13 @@
|
||||||
|
package meerkat.crypto.mixnet;
|
||||||
|
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import meerkat.protobuf.Mixing;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/18/2016.
|
||||||
|
*/
|
||||||
|
public interface MixerOutput {
|
||||||
|
public Mixing.ZeroKnowledgeProof[][] gerProofs();
|
||||||
|
public Crypto.RerandomizableEncryptedMessage[][] getEncryptedMessages();
|
||||||
|
public int getN();
|
||||||
|
}
|
|
@ -1,6 +1,7 @@
|
||||||
package main;
|
package main;
|
||||||
|
|
||||||
import com.google.protobuf.ByteString;
|
import com.google.protobuf.ByteString;
|
||||||
|
import meerkat.crypto.mixnet.MixerOutput;
|
||||||
import meerkat.protobuf.BulletinBoardAPI;
|
import meerkat.protobuf.BulletinBoardAPI;
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
|
@ -29,8 +30,7 @@ public class BatchConverter {
|
||||||
return Integer.valueOf(bs.toString());
|
return Integer.valueOf(bs.toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<BulletinBoardAPI.BatchData> mixerOutput2BatchData
|
public List<BulletinBoardAPI.BatchData> mixerOutput2BatchData(MixerOutput mixerOutput) {
|
||||||
(Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]> mixerOutput) {
|
|
||||||
|
|
||||||
List<BulletinBoardAPI.BatchData> result = new ArrayList<BulletinBoardAPI.BatchData>();
|
List<BulletinBoardAPI.BatchData> result = new ArrayList<BulletinBoardAPI.BatchData>();
|
||||||
|
|
||||||
|
@ -38,14 +38,14 @@ public class BatchConverter {
|
||||||
.setData(IntegerToByteString(n))
|
.setData(IntegerToByteString(n))
|
||||||
.build());
|
.build());
|
||||||
|
|
||||||
for (Mixing.ZeroKnowledgeProof[] zkpLayer : mixerOutput.a) {
|
for (Mixing.ZeroKnowledgeProof[] zkpLayer : mixerOutput.gerProofs()) {
|
||||||
for (Mixing.ZeroKnowledgeProof zkp : zkpLayer) {
|
for (Mixing.ZeroKnowledgeProof zkp : zkpLayer) {
|
||||||
result.add(BulletinBoardAPI.BatchData.newBuilder()
|
result.add(BulletinBoardAPI.BatchData.newBuilder()
|
||||||
.setData(zkp.toByteString())
|
.setData(zkp.toByteString())
|
||||||
.build());
|
.build());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (Crypto.RerandomizableEncryptedMessage[] encryptionLayer : mixerOutput.b) {
|
for (Crypto.RerandomizableEncryptedMessage[] encryptionLayer : mixerOutput.getEncryptedMessages()) {
|
||||||
for (Crypto.RerandomizableEncryptedMessage encryption : encryptionLayer) {
|
for (Crypto.RerandomizableEncryptedMessage encryption : encryptionLayer) {
|
||||||
result.add(BulletinBoardAPI.BatchData.newBuilder()
|
result.add(BulletinBoardAPI.BatchData.newBuilder()
|
||||||
.setData(encryption.toByteString())
|
.setData(encryption.toByteString())
|
||||||
|
@ -55,7 +55,7 @@ public class BatchConverter {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]> batchDataList2MixerOutput
|
public MixerOutput batchDataList2MixerOutput
|
||||||
(List<BulletinBoardAPI.BatchData> batchDataList) throws Exception {
|
(List<BulletinBoardAPI.BatchData> batchDataList) throws Exception {
|
||||||
|
|
||||||
if (n != ByteString2Integer(batchDataList.remove(0).getData())){
|
if (n != ByteString2Integer(batchDataList.remove(0).getData())){
|
||||||
|
@ -83,7 +83,7 @@ public class BatchConverter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return new Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]>(proofs,encryptions);
|
return new mixer.MixerOutput(n,layers,proofs,encryptions);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package main;
|
package main;
|
||||||
|
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
|
import meerkat.crypto.mixnet.MixerOutput;
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
import necessary.AsyncBulletinBoardClient;
|
import necessary.AsyncBulletinBoardClient;
|
||||||
|
@ -17,7 +18,7 @@ import java.util.List;
|
||||||
*/
|
*/
|
||||||
public class BatchHandler implements AsyncBulletinBoardClient.ClientCallback<CompleteBatch> {
|
public class BatchHandler implements AsyncBulletinBoardClient.ClientCallback<CompleteBatch> {
|
||||||
|
|
||||||
private Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]> mixerOutput;
|
private MixerOutput mixerOutput;
|
||||||
private boolean msgReceived;
|
private boolean msgReceived;
|
||||||
private Throwable t;
|
private Throwable t;
|
||||||
private CompleteBatch msg;
|
private CompleteBatch msg;
|
||||||
|
@ -73,7 +74,7 @@ public class BatchHandler implements AsyncBulletinBoardClient.ClientCallback<Com
|
||||||
throw new Exception("in valid table");
|
throw new Exception("in valid table");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return Arrays.asList(mixerOutput.b[mixerOutput.b.length - 1]);
|
return Arrays.asList(mixerOutput.getEncryptedMessages()[layers]);//there are layers + 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ package main;
|
||||||
|
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
import meerkat.crypto.mixnet.Mixer;
|
import meerkat.crypto.mixnet.Mixer;
|
||||||
|
import meerkat.crypto.mixnet.MixerOutput;
|
||||||
import meerkat.protobuf.BulletinBoardAPI;
|
import meerkat.protobuf.BulletinBoardAPI;
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
|
@ -84,14 +85,13 @@ public class MainMixing {
|
||||||
mixerInput = null;
|
mixerInput = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]> mixerOutput
|
MixerOutput mixerOutput = mixer.mix(mixerInput);
|
||||||
= mixer.mix(mixerInput);
|
|
||||||
updateBB(mixerOutput, batchId, callback);
|
updateBB(mixerOutput, batchId, callback);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void updateBB(Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]> mixerOutput
|
private void updateBB(MixerOutput mixerOutput
|
||||||
, int batchId, AsyncBulletinBoardClient.ClientCallback<?> callback) {
|
, int batchId, AsyncBulletinBoardClient.ClientCallback<?> callback) {
|
||||||
|
|
||||||
BatchConverter batchConverter = new BatchConverter(n,layers);
|
BatchConverter batchConverter = new BatchConverter(n,layers);
|
||||||
|
|
|
@ -1,9 +1,13 @@
|
||||||
package mixer;
|
package mixer;
|
||||||
|
|
||||||
|
import java.math.*;
|
||||||
|
import java.math.BigInteger;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
|
import meerkat.crypto.mixnet.MixerOutput;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
import qilin.util.Pair;
|
import qilin.util.Pair;
|
||||||
import java.util.Random;
|
import java.util.Random;
|
||||||
|
|
||||||
|
@ -30,8 +34,14 @@ public class Mixer implements meerkat.crypto.mixnet.Mixer {
|
||||||
this.verifier = null;
|
this.verifier = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Mixer(Random rand, Mix2ZeroKnowledgeProver prov, Encryption enc,Mix2ZeroKnowledgeVerifier verifier) {
|
||||||
|
this.random = rand;
|
||||||
|
this.prover = prov;
|
||||||
|
this.encryptor = enc;
|
||||||
|
this.verifier = verifier;
|
||||||
|
}
|
||||||
|
|
||||||
public Pair<ZeroKnowledgeProof[][], RerandomizableEncryptedMessage[][]> mix(List<RerandomizableEncryptedMessage> ciphertexts) throws InvalidProtocolBufferException {
|
public MixerOutput mix(List<RerandomizableEncryptedMessage> ciphertexts) throws InvalidProtocolBufferException {
|
||||||
|
|
||||||
int n = ciphertexts.size();
|
int n = ciphertexts.size();
|
||||||
int nDiv2 = n >> 1;
|
int nDiv2 = n >> 1;
|
||||||
|
@ -42,7 +52,7 @@ public class Mixer implements meerkat.crypto.mixnet.Mixer {
|
||||||
//initialization
|
//initialization
|
||||||
int layers = (int) (2 * Math.log(n) / Math.log(2)) - 1; // layers = 2logn -1
|
int layers = (int) (2 * Math.log(n) / Math.log(2)) - 1; // layers = 2logn -1
|
||||||
RerandomizableEncryptedMessage[][] encryptionTable = new RerandomizableEncryptedMessage[layers + 1][n];
|
RerandomizableEncryptedMessage[][] encryptionTable = new RerandomizableEncryptedMessage[layers + 1][n];
|
||||||
ZeroKnowledgeProof[][] proofsTable = new ZeroKnowledgeProof[layers][nDiv2];
|
ZeroKnowledgeProof[][] proofsTable = new ZeroKnowledgeProof[layers][n];
|
||||||
int index1, index2, switchIndex = 0;
|
int index1, index2, switchIndex = 0;
|
||||||
EncryptionRandomness r1, r2;
|
EncryptionRandomness r1, r2;
|
||||||
RerandomizableEncryptedMessage e1, e2;
|
RerandomizableEncryptedMessage e1, e2;
|
||||||
|
@ -50,12 +60,14 @@ public class Mixer implements meerkat.crypto.mixnet.Mixer {
|
||||||
MixNetwork mixNetwork = new MixNetwork(new RandomPermutation(n,random));
|
MixNetwork mixNetwork = new MixNetwork(new RandomPermutation(n,random));
|
||||||
Switch[] switchesLayer;
|
Switch[] switchesLayer;
|
||||||
|
|
||||||
|
EncryptionRandomness[][] randomnesses = new EncryptionRandomness[layers][n];
|
||||||
// set first level of encryption
|
// set first level of encryption
|
||||||
for (int j = 0; j < n; j++) {
|
for (int j = 0; j < n; j++) {
|
||||||
encryptionTable[0][j] = ciphertexts.get(j);
|
encryptionTable[0][j] = ciphertexts.get(j);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BigInteger time = BigInteger.valueOf(System.currentTimeMillis());
|
||||||
// main loop
|
// main loop
|
||||||
for (int layer = 0; layer < layers; layer++)
|
for (int layer = 0; layer < layers; layer++)
|
||||||
{
|
{
|
||||||
|
@ -65,6 +77,7 @@ public class Mixer implements meerkat.crypto.mixnet.Mixer {
|
||||||
index2 = sw.j;
|
index2 = sw.j;
|
||||||
e1 = encryptionTable[layer][index1];
|
e1 = encryptionTable[layer][index1];
|
||||||
e2 = encryptionTable[layer][index2];
|
e2 = encryptionTable[layer][index2];
|
||||||
|
|
||||||
r1 = encryptor.generateRandomness(random);
|
r1 = encryptor.generateRandomness(random);
|
||||||
r2 = encryptor.generateRandomness(random);
|
r2 = encryptor.generateRandomness(random);
|
||||||
if (!sw.value) {
|
if (!sw.value) {
|
||||||
|
@ -75,15 +88,34 @@ public class Mixer implements meerkat.crypto.mixnet.Mixer {
|
||||||
encryptionTable[layer + 1][index1] = encryptor.rerandomize(e2, r2);
|
encryptionTable[layer + 1][index1] = encryptor.rerandomize(e2, r2);
|
||||||
encryptionTable[layer + 1][index2] = encryptor.rerandomize(e1, r1);
|
encryptionTable[layer + 1][index2] = encryptor.rerandomize(e1, r1);
|
||||||
}
|
}
|
||||||
|
randomnesses[layer][index1] = r1;
|
||||||
|
randomnesses[layer][index2] = r2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
System.out.println("re enc time : " + BigInteger.valueOf(System.currentTimeMillis()).subtract(time));
|
||||||
|
time = BigInteger.valueOf(System.currentTimeMillis());
|
||||||
|
// main loop
|
||||||
|
for (int layer = 0; layer < layers; layer++)
|
||||||
|
{
|
||||||
|
switchesLayer = mixNetwork.getSwitchesByLayer(layer);
|
||||||
|
for (Switch sw : switchesLayer) {
|
||||||
|
index1 = sw.i;
|
||||||
|
index2 = sw.j;
|
||||||
|
e1 = encryptionTable[layer][index1];
|
||||||
|
e2 = encryptionTable[layer][index2];
|
||||||
|
r1 = randomnesses[layer][index1];
|
||||||
|
r2 = randomnesses[layer][index2];
|
||||||
|
|
||||||
proofsTable[layer][switchIndex] =
|
proofsTable[layer][switchIndex] =
|
||||||
prover.prove(e1, e2, encryptionTable[layer + 1][index1],
|
prover.prove(e1, e2, encryptionTable[layer + 1][index1],
|
||||||
encryptionTable[layer + 1][index2],
|
encryptionTable[layer + 1][index2],
|
||||||
sw.value, sw.i,sw.j,sw.layer, r1, r2);
|
sw.value, sw.i, sw.j, sw.layer, r1, r2);
|
||||||
|
|
||||||
switchIndex = (switchIndex + 1) % nDiv2;
|
switchIndex = (switchIndex + 1) % nDiv2;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return new Pair<ZeroKnowledgeProof[][], RerandomizableEncryptedMessage[][]>(proofsTable, encryptionTable);
|
System.out.println("zkp time : " + BigInteger.valueOf(System.currentTimeMillis()).subtract(time));
|
||||||
|
return new mixer.MixerOutput(n,layers,proofsTable, encryptionTable);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
|
@ -0,0 +1,109 @@
|
||||||
|
package mixer;
|
||||||
|
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import meerkat.protobuf.Mixing;
|
||||||
|
|
||||||
|
import java.awt.*;
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.FileOutputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.file.Files;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/18/2016.
|
||||||
|
*/
|
||||||
|
public class MixerOutput implements meerkat.crypto.mixnet.MixerOutput{
|
||||||
|
private final Mixing.ZeroKnowledgeProof[][] proofs;
|
||||||
|
private final Crypto.RerandomizableEncryptedMessage[][] encryptedMessages;
|
||||||
|
private final int n;
|
||||||
|
private final int layers;
|
||||||
|
|
||||||
|
public MixerOutput(int n,int layers,Mixing.ZeroKnowledgeProof[][] proofs, Crypto.RerandomizableEncryptedMessage[][] encryptedMessages) {
|
||||||
|
this.proofs = proofs;
|
||||||
|
this.encryptedMessages = encryptedMessages;
|
||||||
|
this.n = n;
|
||||||
|
this.layers = layers;
|
||||||
|
}
|
||||||
|
|
||||||
|
public MixerOutput(meerkat.crypto.mixnet.MixerOutput mixerOutput) {
|
||||||
|
this.proofs = mixerOutput.gerProofs();
|
||||||
|
this.encryptedMessages = mixerOutput.getEncryptedMessages();
|
||||||
|
this.n = mixerOutput.getN();
|
||||||
|
this.layers = (int) (2 * Math.log(n) / Math.log(2)) - 1; // layers = 2logn -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Mixing.ZeroKnowledgeProof[][] gerProofs() {
|
||||||
|
return proofs;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Crypto.RerandomizableEncryptedMessage[][] getEncryptedMessages() {
|
||||||
|
return encryptedMessages;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getN() {
|
||||||
|
return n;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void outToFile(String dir) throws IOException {
|
||||||
|
|
||||||
|
(new File(dir)).mkdirs();
|
||||||
|
//create files
|
||||||
|
String proofsDir = dir + "/Proofs";
|
||||||
|
String encDir = dir + "/EncryptedMessages";
|
||||||
|
(new File(proofsDir)).mkdir();
|
||||||
|
(new File(encDir)).mkdir();
|
||||||
|
for (int layer = 0; layer < layers; layer++){
|
||||||
|
(new File(proofsDir +"/layer" + layer )).mkdir();
|
||||||
|
(new File(encDir +"/layer" + layer )).mkdir();
|
||||||
|
}
|
||||||
|
(new File(encDir +"/input")).mkdir();
|
||||||
|
|
||||||
|
|
||||||
|
for (int layer = 0; layer < layers; layer++){
|
||||||
|
for(int i = 0; i < proofs[layer].length; i ++){
|
||||||
|
writeProofToFile(proofsDir,proofs[layer][i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int layer = 0; layer <= layers; layer++){
|
||||||
|
for(int i = 0; i < encryptedMessages[layer].length; i ++){
|
||||||
|
writeEncToFile(encDir,layer - 1, i,encryptedMessages[layer][i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void writeProofToFile(String proofsDir, Mixing.ZeroKnowledgeProof proof) throws IOException {
|
||||||
|
Mixing.ZeroKnowledgeProof.Location location = proof.getLocation();
|
||||||
|
int layer = location.getLayer();
|
||||||
|
int i = location.getI();
|
||||||
|
int j = location.getJ();
|
||||||
|
String fileName = proofsDir+"/layer" + layer +"/" + i +"_" + j;
|
||||||
|
|
||||||
|
File file = new File(fileName);
|
||||||
|
file.createNewFile();
|
||||||
|
FileOutputStream fos = new FileOutputStream(file);
|
||||||
|
fos.write(proof.toByteArray());
|
||||||
|
fos.close();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void writeEncToFile(String encDir,int layer,int i, Crypto.RerandomizableEncryptedMessage enc) throws IOException {
|
||||||
|
|
||||||
|
String fileName;
|
||||||
|
if(layer >= 0)
|
||||||
|
fileName = encDir+"/layer" + layer +"/" + i;
|
||||||
|
else
|
||||||
|
fileName = encDir+"/input/" + i;
|
||||||
|
|
||||||
|
File file = new File(fileName);
|
||||||
|
file.createNewFile();
|
||||||
|
FileOutputStream fos = new FileOutputStream(file);
|
||||||
|
fos.write(enc.toByteArray());
|
||||||
|
fos.close();
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,239 @@
|
||||||
|
package prover;
|
||||||
|
|
||||||
|
import com.google.protobuf.ByteString;
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import meerkat.protobuf.ConcreteCrypto;
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 12/30/2015.
|
||||||
|
*/
|
||||||
|
public class ElGamalProofOrganizer {
|
||||||
|
|
||||||
|
private final ECGroup group;
|
||||||
|
private final ECPoint g;
|
||||||
|
private final ECPoint h;
|
||||||
|
private final byte[] gEncoded;
|
||||||
|
private final byte[] hEncoded;
|
||||||
|
|
||||||
|
public ElGamalProofOrganizer(ECGroup group, ECPoint g, ECPoint h){
|
||||||
|
this.group = group;
|
||||||
|
this.g = g;
|
||||||
|
this.h = h;
|
||||||
|
this.gEncoded = group.encode(g);
|
||||||
|
this.hEncoded = group.encode(h);
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum OrProofOrder {
|
||||||
|
first, second, third, fourth
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum TrueCouple {
|
||||||
|
left, right, unknown
|
||||||
|
}
|
||||||
|
|
||||||
|
//used by prover only
|
||||||
|
protected ElGamalProofInput createProofInput(Crypto.RerandomizableEncryptedMessage e1, Crypto.RerandomizableEncryptedMessage e2
|
||||||
|
, Crypto.RerandomizableEncryptedMessage e1New, Crypto.RerandomizableEncryptedMessage e2New
|
||||||
|
, Crypto.EncryptionRandomness r1, Crypto.EncryptionRandomness r2, boolean switched) throws InvalidProtocolBufferException {
|
||||||
|
|
||||||
|
//convert RerandomizableEncryptedMessage to ElGamalCiphertext
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e1ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e1);
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e2ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e2);
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e1NewElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e1New);
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e2NewElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e2New);
|
||||||
|
|
||||||
|
return new ElGamalProofInput(e1ElGamal,e2ElGamal,e1NewElGamal,e2NewElGamal,r1,r2,switched);
|
||||||
|
}
|
||||||
|
|
||||||
|
// can be used by anyone, e.g Verifier
|
||||||
|
public ElGamalProofInput createProofInput(Crypto.RerandomizableEncryptedMessage e1, Crypto.RerandomizableEncryptedMessage e2
|
||||||
|
, Crypto.RerandomizableEncryptedMessage e1New, Crypto.RerandomizableEncryptedMessage e2New) throws InvalidProtocolBufferException {
|
||||||
|
|
||||||
|
//convert RerandomizableEncryptedMessage to ElGamalCiphertext
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e1ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e1);
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e2ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e2);
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e1NewElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e1New);
|
||||||
|
ConcreteCrypto.ElGamalCiphertext e2NewElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(e2New);
|
||||||
|
|
||||||
|
return new ElGamalProofInput(e1ElGamal,e2ElGamal,e1NewElGamal,e2NewElGamal);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public class ElGamalProofInput {
|
||||||
|
|
||||||
|
|
||||||
|
private final OrProofInput first;
|
||||||
|
private final OrProofInput second;
|
||||||
|
private final OrProofInput third;
|
||||||
|
private final OrProofInput fourth;
|
||||||
|
|
||||||
|
private ECPoint convert2ECPoint(ByteString bs){
|
||||||
|
return group.decode(bs.toByteArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
private ElGamalProofInput(ConcreteCrypto.ElGamalCiphertext e1, ConcreteCrypto.ElGamalCiphertext e2
|
||||||
|
, ConcreteCrypto.ElGamalCiphertext e1New, ConcreteCrypto.ElGamalCiphertext e2New
|
||||||
|
, Crypto.EncryptionRandomness r1, Crypto.EncryptionRandomness r2, boolean switched){
|
||||||
|
|
||||||
|
ECPoint e1c1 = convert2ECPoint(e1.getC1());
|
||||||
|
ECPoint e1c2 = convert2ECPoint(e1.getC2());
|
||||||
|
ECPoint e2c1 = convert2ECPoint(e2.getC1());
|
||||||
|
ECPoint e2c2 = convert2ECPoint(e2.getC2());
|
||||||
|
ECPoint e1Nc1 = convert2ECPoint(e1New.getC1());
|
||||||
|
ECPoint e1Nc2 = convert2ECPoint(e1New.getC2());
|
||||||
|
ECPoint e2Nc1 = convert2ECPoint(e2New.getC1());
|
||||||
|
ECPoint e2Nc2 = convert2ECPoint(e2New.getC2());
|
||||||
|
|
||||||
|
ECPoint c1_e1NDive1 = group.add(e1Nc1, group.negate(e1c1));
|
||||||
|
ECPoint c1_e2NDive1 = group.add(e2Nc1, group.negate(e1c1));
|
||||||
|
ECPoint c1_e1NDive2 = group.add(e1Nc1, group.negate(e2c1));
|
||||||
|
ECPoint c1_e2NDive2 = group.add(e2Nc1, group.negate(e2c1));
|
||||||
|
|
||||||
|
ECPoint c2_e1NDive1 = group.add(e1Nc2, group.negate(e1c2));
|
||||||
|
ECPoint c2_e2NDive1 = group.add(e2Nc2, group.negate(e1c2));
|
||||||
|
ECPoint c2_e1NDive2 = group.add(e1Nc2, group.negate(e2c2));
|
||||||
|
ECPoint c2_e2NDive2 = group.add(e2Nc2, group.negate(e2c2));
|
||||||
|
|
||||||
|
byte[] c1_e1NDive1Encoded = group.encode(c1_e1NDive1);
|
||||||
|
byte[] c1_e2NDive1Encoded = group.encode(c1_e2NDive1);
|
||||||
|
byte[] c1_e1NDive2Encoded = group.encode(c1_e1NDive2);
|
||||||
|
byte[] c1_e2NDive2Encoded = group.encode(c1_e2NDive2);
|
||||||
|
byte[] c2_e1NDive1Encoded = group.encode(c2_e1NDive1);
|
||||||
|
byte[] c2_e2NDive1Encoded = group.encode(c2_e2NDive1);
|
||||||
|
byte[] c2_e1NDive2Encoded = group.encode(c2_e1NDive2);
|
||||||
|
byte[] c2_e2NDive2Encoded = group.encode(c2_e2NDive2);
|
||||||
|
|
||||||
|
|
||||||
|
if (!switched) {
|
||||||
|
this.first = new OrProofInput(c1_e1NDive1,c2_e1NDive1,c1_e1NDive2,c2_e1NDive2
|
||||||
|
,c1_e1NDive1Encoded,c2_e1NDive1Encoded,c1_e1NDive2Encoded,c2_e1NDive2Encoded
|
||||||
|
,r1,TrueCouple.left);
|
||||||
|
this.second = new OrProofInput(c1_e1NDive1,c2_e1NDive1,c1_e2NDive1,c2_e2NDive1
|
||||||
|
,c1_e1NDive1Encoded,c2_e1NDive1Encoded,c1_e2NDive1Encoded,c2_e2NDive1Encoded
|
||||||
|
,r1,TrueCouple.left);
|
||||||
|
this.third = new OrProofInput(c1_e1NDive2,c2_e1NDive2,c1_e2NDive2,c2_e2NDive2
|
||||||
|
,c1_e1NDive2Encoded,c2_e1NDive2Encoded,c1_e2NDive2Encoded,c2_e2NDive2Encoded
|
||||||
|
,r2,TrueCouple.right);
|
||||||
|
this.fourth = new OrProofInput(c1_e2NDive1,c2_e2NDive1,c1_e2NDive2,c2_e2NDive2
|
||||||
|
,c1_e2NDive1Encoded,c2_e2NDive1Encoded,c1_e2NDive2Encoded,c2_e2NDive2Encoded
|
||||||
|
,r2,TrueCouple.right);
|
||||||
|
} else {
|
||||||
|
this.first = new OrProofInput(c1_e1NDive1,c2_e1NDive1,c1_e1NDive2,c2_e1NDive2
|
||||||
|
,c1_e1NDive1Encoded,c2_e1NDive1Encoded,c1_e1NDive2Encoded,c2_e1NDive2Encoded
|
||||||
|
,r2,TrueCouple.right);
|
||||||
|
this.second = new OrProofInput(c1_e1NDive1,c2_e1NDive1,c1_e2NDive1,c2_e2NDive1
|
||||||
|
,c1_e1NDive1Encoded,c2_e1NDive1Encoded,c1_e2NDive1Encoded,c2_e2NDive1Encoded
|
||||||
|
,r1,TrueCouple.right);
|
||||||
|
this.third = new OrProofInput(c1_e1NDive2,c2_e1NDive2,c1_e2NDive2,c2_e2NDive2
|
||||||
|
,c1_e1NDive2Encoded,c2_e1NDive2Encoded,c1_e2NDive2Encoded,c2_e2NDive2Encoded
|
||||||
|
,r2,TrueCouple.left);
|
||||||
|
this.fourth = new OrProofInput(c1_e2NDive1,c2_e2NDive1,c1_e2NDive2,c2_e2NDive2
|
||||||
|
,c1_e2NDive1Encoded,c2_e2NDive1Encoded,c1_e2NDive2Encoded,c2_e2NDive2Encoded
|
||||||
|
,r1,TrueCouple.left);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private ElGamalProofInput(ConcreteCrypto.ElGamalCiphertext e1, ConcreteCrypto.ElGamalCiphertext e2
|
||||||
|
, ConcreteCrypto.ElGamalCiphertext e1New, ConcreteCrypto.ElGamalCiphertext e2New){
|
||||||
|
|
||||||
|
ECPoint e1c1 = convert2ECPoint(e1.getC1());
|
||||||
|
ECPoint e1c2 = convert2ECPoint(e1.getC2());
|
||||||
|
ECPoint e2c1 = convert2ECPoint(e2.getC1());
|
||||||
|
ECPoint e2c2 = convert2ECPoint(e2.getC2());
|
||||||
|
ECPoint e1Nc1 = convert2ECPoint(e1New.getC1());
|
||||||
|
ECPoint e1Nc2 = convert2ECPoint(e1New.getC2());
|
||||||
|
ECPoint e2Nc1 = convert2ECPoint(e2New.getC1());
|
||||||
|
ECPoint e2Nc2 = convert2ECPoint(e2New.getC2());
|
||||||
|
|
||||||
|
ECPoint c1_e1NDive1 = group.add(e1Nc1, group.negate(e1c1));
|
||||||
|
ECPoint c1_e2NDive1 = group.add(e2Nc1, group.negate(e1c1));
|
||||||
|
ECPoint c1_e1NDive2 = group.add(e1Nc1, group.negate(e2c1));
|
||||||
|
ECPoint c1_e2NDive2 = group.add(e2Nc1, group.negate(e2c1));
|
||||||
|
|
||||||
|
ECPoint c2_e1NDive1 = group.add(e1Nc2, group.negate(e1c2));
|
||||||
|
ECPoint c2_e2NDive1 = group.add(e2Nc2, group.negate(e1c2));
|
||||||
|
ECPoint c2_e1NDive2 = group.add(e1Nc2, group.negate(e2c2));
|
||||||
|
ECPoint c2_e2NDive2 = group.add(e2Nc2, group.negate(e2c2));
|
||||||
|
|
||||||
|
this.first = new OrProofInput(c1_e1NDive1,c2_e1NDive1,c1_e1NDive2,c2_e1NDive2);
|
||||||
|
this.second = new OrProofInput(c1_e1NDive1,c2_e1NDive1,c1_e2NDive1,c2_e2NDive1);
|
||||||
|
this.third = new OrProofInput(c1_e1NDive2,c2_e1NDive2,c1_e2NDive2,c2_e2NDive2);
|
||||||
|
this.fourth = new OrProofInput(c1_e2NDive1,c2_e2NDive1,c1_e2NDive2,c2_e2NDive2);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
public OrProofInput getOrProofInput(OrProofOrder orProofOrder) {
|
||||||
|
switch (orProofOrder) {
|
||||||
|
|
||||||
|
case first:
|
||||||
|
return this.first;
|
||||||
|
case second:
|
||||||
|
return this.second;
|
||||||
|
case third:
|
||||||
|
return this.third;
|
||||||
|
case fourth:
|
||||||
|
return this.fourth;
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public class OrProofInput{
|
||||||
|
|
||||||
|
public final ECPoint g1;
|
||||||
|
public final ECPoint h1;
|
||||||
|
public final ECPoint g2;
|
||||||
|
public final ECPoint h2;
|
||||||
|
public final ECPoint g1Tag;
|
||||||
|
public final ECPoint h1Tag;
|
||||||
|
public final ECPoint g2Tag;
|
||||||
|
public final ECPoint h2Tag;
|
||||||
|
|
||||||
|
protected final byte[] g1Encoded;
|
||||||
|
protected final byte[] h1Encoded;
|
||||||
|
protected final byte[] g2Encoded;
|
||||||
|
protected final byte[] h2Encoded;
|
||||||
|
protected final byte[] g1TagEncoded;
|
||||||
|
protected final byte[] h1TagEncoded;
|
||||||
|
protected final byte[] g2TagEncoded;
|
||||||
|
protected final byte[] h2TagEncoded;
|
||||||
|
|
||||||
|
protected final Crypto.EncryptionRandomness x;
|
||||||
|
protected final TrueCouple flag;
|
||||||
|
|
||||||
|
private OrProofInput(ECPoint h1, ECPoint h2, ECPoint h1Tag, ECPoint h2Tag
|
||||||
|
,byte[] h1Encoded, byte[] h2Encoded, byte[] h1TagEncoded, byte[] h2TagEncoded
|
||||||
|
, Crypto.EncryptionRandomness x, TrueCouple flag) {
|
||||||
|
this.g1 = g;
|
||||||
|
this.h1 = h1;
|
||||||
|
this.g2 = h;
|
||||||
|
this.h2 = h2;
|
||||||
|
this.g1Tag = g;
|
||||||
|
this.h1Tag = h1Tag;
|
||||||
|
this.g2Tag = h;
|
||||||
|
this.h2Tag = h2Tag;
|
||||||
|
|
||||||
|
this.g1Encoded = gEncoded;
|
||||||
|
this.h1Encoded = h1Encoded;
|
||||||
|
this.g2Encoded = hEncoded;
|
||||||
|
this.h2Encoded = h2Encoded;
|
||||||
|
this.g1TagEncoded = gEncoded;
|
||||||
|
this.h1TagEncoded = h1TagEncoded;
|
||||||
|
this.g2TagEncoded = hEncoded;
|
||||||
|
this.h2TagEncoded = h2TagEncoded;
|
||||||
|
|
||||||
|
this.x = x;
|
||||||
|
this.flag = flag;
|
||||||
|
|
||||||
|
}
|
||||||
|
private OrProofInput(ECPoint h1, ECPoint h2, ECPoint h1Tag, ECPoint h2Tag) {
|
||||||
|
this(h1,h2,h1Tag,h2Tag,null,null,null,null,null,TrueCouple.unknown);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,85 +0,0 @@
|
||||||
package prover;
|
|
||||||
|
|
||||||
import meerkat.protobuf.Crypto;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Created by Tzlil on 12/30/2015.
|
|
||||||
*/
|
|
||||||
public class ProofOrganizer {
|
|
||||||
|
|
||||||
private final OrProofInput first;
|
|
||||||
private final OrProofInput second;
|
|
||||||
private final OrProofInput third;
|
|
||||||
private final OrProofInput fourth;
|
|
||||||
|
|
||||||
protected ProofOrganizer(Crypto.RerandomizableEncryptedMessage e1,Crypto.RerandomizableEncryptedMessage e2
|
|
||||||
,Crypto.RerandomizableEncryptedMessage e1New,Crypto.RerandomizableEncryptedMessage e2New
|
|
||||||
,Crypto.EncryptionRandomness r1,Crypto.EncryptionRandomness r2,boolean switched) {
|
|
||||||
if(!switched) {
|
|
||||||
this.first = new OrProofInput(e1, e1New, e2, e1New, r1,TrueCouple.left);
|
|
||||||
this.second = new OrProofInput(e1, e1New, e1, e2New,r1,TrueCouple.left);
|
|
||||||
this.third = new OrProofInput(e2, e1New, e2, e2New,r2,TrueCouple.right);
|
|
||||||
this.fourth = new OrProofInput(e1, e2New, e2, e2New,r2,TrueCouple.right);
|
|
||||||
}else{
|
|
||||||
this.first = new OrProofInput(e1, e1New, e2, e1New, r2,TrueCouple.right);
|
|
||||||
this.second = new OrProofInput(e1, e1New, e1, e2New,r1,TrueCouple.right);
|
|
||||||
this.third = new OrProofInput(e2, e1New, e2, e2New,r2,TrueCouple.left);
|
|
||||||
this.fourth = new OrProofInput(e1, e2New, e2, e2New,r1,TrueCouple.left);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public ProofOrganizer(Crypto.RerandomizableEncryptedMessage e1,Crypto.RerandomizableEncryptedMessage e2
|
|
||||||
,Crypto.RerandomizableEncryptedMessage e1New,Crypto.RerandomizableEncryptedMessage e2New) {
|
|
||||||
this.first = new OrProofInput(e1, e1New, e2, e1New, null,TrueCouple.unknown);
|
|
||||||
this.second = new OrProofInput(e1, e1New, e1, e2New,null,TrueCouple.unknown);
|
|
||||||
this.third = new OrProofInput(e2, e1New, e2, e2New,null,TrueCouple.unknown);
|
|
||||||
this.fourth = new OrProofInput(e1, e2New, e2, e2New,null,TrueCouple.unknown);
|
|
||||||
}
|
|
||||||
|
|
||||||
public enum OrProofOrder{
|
|
||||||
first,second,third,fourth
|
|
||||||
}
|
|
||||||
|
|
||||||
public enum TrueCouple{
|
|
||||||
left,right,unknown
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public OrProofInput getOrProofInput(OrProofOrder orProofOrder){
|
|
||||||
switch (orProofOrder){
|
|
||||||
|
|
||||||
case first:
|
|
||||||
return this.first;
|
|
||||||
case second:
|
|
||||||
return this.second;
|
|
||||||
case third:
|
|
||||||
return this.third;
|
|
||||||
case fourth:
|
|
||||||
return this.fourth;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public class OrProofInput{
|
|
||||||
|
|
||||||
|
|
||||||
public final Crypto.RerandomizableEncryptedMessage e1;
|
|
||||||
public final Crypto.RerandomizableEncryptedMessage e1New;
|
|
||||||
public final Crypto.RerandomizableEncryptedMessage e2;
|
|
||||||
public final Crypto.RerandomizableEncryptedMessage e2New;
|
|
||||||
protected final Crypto.EncryptionRandomness x;
|
|
||||||
protected final TrueCouple flag;
|
|
||||||
|
|
||||||
private OrProofInput(Crypto.RerandomizableEncryptedMessage e1, Crypto.RerandomizableEncryptedMessage e1New,
|
|
||||||
Crypto.RerandomizableEncryptedMessage e2, Crypto.RerandomizableEncryptedMessage e2New,
|
|
||||||
Crypto.EncryptionRandomness x, TrueCouple flag) {
|
|
||||||
this.e1 = e1;
|
|
||||||
this.e1New = e1New;
|
|
||||||
this.e2 = e2;
|
|
||||||
this.e2New = e2New;
|
|
||||||
this.x = x;
|
|
||||||
this.flag = flag;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -4,8 +4,6 @@ import com.google.protobuf.ByteString;
|
||||||
import com.google.protobuf.InvalidProtocolBufferException;
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
import meerkat.crypto.concrete.ECElGamalEncryption;
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeProver;
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeProver;
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
|
||||||
import meerkat.protobuf.ConcreteCrypto;
|
|
||||||
import meerkat.protobuf.ConcreteCrypto.ElGamalCiphertext;
|
import meerkat.protobuf.ConcreteCrypto.ElGamalCiphertext;
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
|
@ -14,7 +12,6 @@ import qilin.primitives.RandomOracle;
|
||||||
import qilin.primitives.concrete.ECGroup;
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
import java.math.BigInteger;
|
import java.math.BigInteger;
|
||||||
import java.util.List;
|
|
||||||
import java.util.Random;
|
import java.util.Random;
|
||||||
|
|
||||||
public class Prover implements Mix2ZeroKnowledgeProver {
|
public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
|
@ -24,6 +21,7 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
Random rand;
|
Random rand;
|
||||||
ECElGamalEncryption ecElGamalEncryption;
|
ECElGamalEncryption ecElGamalEncryption;
|
||||||
ECPoint g,h;
|
ECPoint g,h;
|
||||||
|
ElGamalProofOrganizer organizer;
|
||||||
|
|
||||||
public Prover(Random rand,ECElGamalEncryption encryptor,RandomOracle randomOracle) {
|
public Prover(Random rand,ECElGamalEncryption encryptor,RandomOracle randomOracle) {
|
||||||
|
|
||||||
|
@ -33,10 +31,9 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
this.group = ecElGamalEncryption.getGroup();
|
this.group = ecElGamalEncryption.getGroup();
|
||||||
this.g = group.getGenerator();
|
this.g = group.getGenerator();
|
||||||
this.h = ecElGamalEncryption.getElGamalPK().getPK();
|
this.h = ecElGamalEncryption.getElGamalPK().getPK();
|
||||||
|
this.organizer = new ElGamalProofOrganizer(group,g,h);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public Mixing.ZeroKnowledgeProof prove(Crypto.RerandomizableEncryptedMessage in1,
|
public Mixing.ZeroKnowledgeProof prove(Crypto.RerandomizableEncryptedMessage in1,
|
||||||
Crypto.RerandomizableEncryptedMessage in2,
|
Crypto.RerandomizableEncryptedMessage in2,
|
||||||
Crypto.RerandomizableEncryptedMessage out1,
|
Crypto.RerandomizableEncryptedMessage out1,
|
||||||
|
@ -44,18 +41,14 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
boolean sw,int i,int j, int layer,
|
boolean sw,int i,int j, int layer,
|
||||||
Crypto.EncryptionRandomness r1,
|
Crypto.EncryptionRandomness r1,
|
||||||
Crypto.EncryptionRandomness r2) throws InvalidProtocolBufferException {
|
Crypto.EncryptionRandomness r2) throws InvalidProtocolBufferException {
|
||||||
|
|
||||||
Mixing.ZeroKnowledgeProof.OrProof first,second,third,fourth;
|
Mixing.ZeroKnowledgeProof.OrProof first,second,third,fourth;
|
||||||
ProofOrganizer organizer = new ProofOrganizer(in1,in2,out1,out2,r1,r2,sw);
|
|
||||||
|
|
||||||
System.out.println("first");
|
ElGamalProofOrganizer.ElGamalProofInput input = organizer.createProofInput(in1,in2,out1,out2,r1,r2,sw);
|
||||||
first = createOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.first));
|
|
||||||
System.out.println("second");
|
first = createOrProofElGamal(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.first));
|
||||||
second = createOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.second));
|
second = createOrProofElGamal(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.second));
|
||||||
System.out.println("third");
|
third = createOrProofElGamal(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.third));
|
||||||
third = createOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.third));
|
fourth = createOrProofElGamal(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.fourth));
|
||||||
System.out.println("fourth");
|
|
||||||
fourth = createOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.fourth));
|
|
||||||
|
|
||||||
Mixing.ZeroKnowledgeProof.Location location = Mixing.ZeroKnowledgeProof.Location.newBuilder()
|
Mixing.ZeroKnowledgeProof.Location location = Mixing.ZeroKnowledgeProof.Location.newBuilder()
|
||||||
.setI(i)
|
.setI(i)
|
||||||
|
@ -70,25 +63,9 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
.setFourth(fourth)
|
.setFourth(fourth)
|
||||||
.setLocation(location)
|
.setLocation(location)
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
private Mixing.ZeroKnowledgeProof.OrProof createOrProof(ProofOrganizer.OrProofInput orProofInput)
|
|
||||||
throws InvalidProtocolBufferException {
|
|
||||||
|
|
||||||
ElGamalCiphertext e1ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e1);
|
|
||||||
ElGamalCiphertext e2ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e2);
|
|
||||||
ElGamalCiphertext e1TagElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e1New);
|
|
||||||
ElGamalCiphertext e2TagElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e2New);
|
|
||||||
|
|
||||||
return createOrProofElGamal(e1ElGamal,e2ElGamal,e1TagElGamal,e2TagElGamal,orProofInput.x,orProofInput.flag);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
private ECPoint convert2ECPoint(ByteString bs){
|
|
||||||
return group.decode(bs.toByteArray());
|
|
||||||
}
|
|
||||||
|
|
||||||
public BigInteger hash(Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle input) {
|
public BigInteger hash(Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle input) {
|
||||||
byte[] arr = input.toByteArray();
|
byte[] arr = input.toByteArray();
|
||||||
|
@ -96,28 +73,25 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private Mixing.ZeroKnowledgeProof.OrProof createOrProofElGamal(ElGamalCiphertext e1,
|
private Mixing.ZeroKnowledgeProof.OrProof createOrProofElGamal(ElGamalProofOrganizer.OrProofInput orProofInput) {
|
||||||
ElGamalCiphertext e2,
|
|
||||||
ElGamalCiphertext e1New,
|
|
||||||
ElGamalCiphertext e2New,
|
|
||||||
Crypto.EncryptionRandomness x,
|
|
||||||
ProofOrganizer.TrueCouple flag) {
|
|
||||||
|
|
||||||
ECPoint g1 = g;
|
ECPoint g1 = orProofInput.g1;
|
||||||
ECPoint h1 = group.add(convert2ECPoint(e1New.getC1()),group.negate(convert2ECPoint(e1.getC1())));
|
ECPoint h1 = orProofInput.h1;
|
||||||
ECPoint g2 = h;
|
ECPoint g2 = orProofInput.g2;
|
||||||
ECPoint h2 = group.add(convert2ECPoint(e1New.getC2()),group.negate(convert2ECPoint(e1.getC2())));
|
ECPoint h2 = orProofInput.h2;
|
||||||
|
|
||||||
ECPoint g1Tag = g;
|
ECPoint g1Tag = orProofInput.g1Tag;
|
||||||
ECPoint h1Tag = group.add(convert2ECPoint(e2New.getC1()),group.negate(convert2ECPoint(e2.getC1())));
|
ECPoint h1Tag = orProofInput.h1Tag;
|
||||||
ECPoint g2Tag = h;
|
ECPoint g2Tag = orProofInput.g2Tag;
|
||||||
ECPoint h2Tag = group.add(convert2ECPoint(e2New.getC2()),group.negate(convert2ECPoint(e2.getC2())));
|
ECPoint h2Tag = orProofInput.h2Tag;
|
||||||
|
|
||||||
BigInteger r = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
BigInteger r = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
||||||
BigInteger c1,c2,z,zTag;
|
BigInteger c1,c2,z,zTag;
|
||||||
ECPoint u,v,uTag,vTag;
|
ECPoint u,v,uTag,vTag;
|
||||||
Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle forRandomOracle;
|
Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle forRandomOracle;
|
||||||
switch (flag) {
|
|
||||||
|
|
||||||
|
switch (orProofInput.flag) {
|
||||||
case left:
|
case left:
|
||||||
c2 = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
c2 = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
||||||
zTag = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
zTag = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
||||||
|
@ -130,14 +104,14 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
// c1 = (hash(input + step1) + group size - c2)% group size
|
// c1 = (hash(input + step1) + group size - c2)% group size
|
||||||
forRandomOracle =
|
forRandomOracle =
|
||||||
Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle.newBuilder()
|
Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle.newBuilder()
|
||||||
.setG1(ByteString.copyFrom(group.encode(g1)))
|
.setG1(ByteString.copyFrom(orProofInput.g1Encoded))
|
||||||
.setH1(ByteString.copyFrom(group.encode(h1)))
|
.setH1(ByteString.copyFrom(orProofInput.h1Encoded))
|
||||||
.setG2(ByteString.copyFrom(group.encode(g2)))
|
.setG2(ByteString.copyFrom(orProofInput.g2Encoded))
|
||||||
.setH2(ByteString.copyFrom(group.encode(h2)))
|
.setH2(ByteString.copyFrom(orProofInput.h2Encoded))
|
||||||
.setG1Tag(ByteString.copyFrom(group.encode(g1Tag)))
|
.setG1Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setH1Tag(ByteString.copyFrom(group.encode(h1Tag)))
|
.setH1Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setG2Tag(ByteString.copyFrom(group.encode(g2Tag)))
|
.setG2Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setH2Tag(ByteString.copyFrom(group.encode(h2Tag)))
|
.setH2Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setU(ByteString.copyFrom(group.encode(u)))
|
.setU(ByteString.copyFrom(group.encode(u)))
|
||||||
.setV(ByteString.copyFrom(group.encode(v)))
|
.setV(ByteString.copyFrom(group.encode(v)))
|
||||||
.setUTag(ByteString.copyFrom(group.encode(uTag)))
|
.setUTag(ByteString.copyFrom(group.encode(uTag)))
|
||||||
|
@ -146,7 +120,7 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
c1 = hash(forRandomOracle).add(group.orderUpperBound().subtract(c2)).mod(group.orderUpperBound());
|
c1 = hash(forRandomOracle).add(group.orderUpperBound().subtract(c2)).mod(group.orderUpperBound());
|
||||||
//step 3
|
//step 3
|
||||||
//z = (r + c1 * x) % group size;
|
//z = (r + c1 * x) % group size;
|
||||||
z = r.add(c1.multiply(new BigInteger(x.getData().toByteArray()))).mod(group.orderUpperBound());
|
z = r.add(c1.multiply(new BigInteger(orProofInput.x.getData().toByteArray()))).mod(group.orderUpperBound());
|
||||||
break;
|
break;
|
||||||
case right:
|
case right:
|
||||||
c1 = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
c1 = new BigInteger(ecElGamalEncryption.generateRandomness(rand).getData().toByteArray()).mod(group.orderUpperBound());
|
||||||
|
@ -160,14 +134,14 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
// c1 = (hash(input + step1) + group size - c1)% group size
|
// c1 = (hash(input + step1) + group size - c1)% group size
|
||||||
forRandomOracle =
|
forRandomOracle =
|
||||||
Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle.newBuilder()
|
Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle.newBuilder()
|
||||||
.setG1(ByteString.copyFrom(group.encode(g1)))
|
.setG1(ByteString.copyFrom(orProofInput.g1Encoded))
|
||||||
.setH1(ByteString.copyFrom(group.encode(h1)))
|
.setH1(ByteString.copyFrom(orProofInput.h1Encoded))
|
||||||
.setG2(ByteString.copyFrom(group.encode(g2)))
|
.setG2(ByteString.copyFrom(orProofInput.g2Encoded))
|
||||||
.setH2(ByteString.copyFrom(group.encode(h2)))
|
.setH2(ByteString.copyFrom(orProofInput.h2Encoded))
|
||||||
.setG1Tag(ByteString.copyFrom(group.encode(g1Tag)))
|
.setG1Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setH1Tag(ByteString.copyFrom(group.encode(h1Tag)))
|
.setH1Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setG2Tag(ByteString.copyFrom(group.encode(g2Tag)))
|
.setG2Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setH2Tag(ByteString.copyFrom(group.encode(h2Tag)))
|
.setH2Tag(ByteString.copyFrom(orProofInput.g1TagEncoded))
|
||||||
.setU(ByteString.copyFrom(group.encode(u)))
|
.setU(ByteString.copyFrom(group.encode(u)))
|
||||||
.setV(ByteString.copyFrom(group.encode(v)))
|
.setV(ByteString.copyFrom(group.encode(v)))
|
||||||
.setUTag(ByteString.copyFrom(group.encode(uTag)))
|
.setUTag(ByteString.copyFrom(group.encode(uTag)))
|
||||||
|
@ -176,39 +150,37 @@ public class Prover implements Mix2ZeroKnowledgeProver {
|
||||||
c2 = hash(forRandomOracle).add(group.orderUpperBound().subtract(c1)).mod(group.orderUpperBound());
|
c2 = hash(forRandomOracle).add(group.orderUpperBound().subtract(c1)).mod(group.orderUpperBound());
|
||||||
//step 3
|
//step 3
|
||||||
//zTag = (r + c2 * x) % group size;
|
//zTag = (r + c2 * x) % group size;
|
||||||
zTag = r.add(c2.multiply(new BigInteger(x.getData().toByteArray()))).mod(group.orderUpperBound());
|
zTag = r.add(c2.multiply(new BigInteger(orProofInput.x.getData().toByteArray()))).mod(group.orderUpperBound());
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
//debugging
|
//debugging
|
||||||
assert (group.multiply(g1, z).equals(group.add(u, group.multiply(h1,c1))));
|
//assert (group.multiply(g1, z).equals(group.add(u, group.multiply(h1,c1))));
|
||||||
assert (group.multiply(g2, z).equals(group.add(v, group.multiply(h2,c1))));
|
//assert (group.multiply(g2, z).equals(group.add(v, group.multiply(h2,c1))));
|
||||||
assert (group.multiply(g1Tag, zTag).equals(group.add(uTag, group.multiply(h1Tag,c2))));
|
//assert (group.multiply(g1Tag, zTag).equals(group.add(uTag, group.multiply(h1Tag,c2))));
|
||||||
assert (group.multiply(g2Tag, zTag).equals(group.add(vTag, group.multiply(h2Tag,c2))));
|
//assert (group.multiply(g2Tag, zTag).equals(group.add(vTag, group.multiply(h2Tag,c2))));
|
||||||
|
|
||||||
|
|
||||||
return Mixing.ZeroKnowledgeProof.OrProof.newBuilder()
|
return Mixing.ZeroKnowledgeProof.OrProof.newBuilder()
|
||||||
.setG1(ByteString.copyFrom(group.encode(g1)))
|
.setG1(forRandomOracle.getG1())
|
||||||
.setH1(ByteString.copyFrom(group.encode(h1)))
|
.setH1(forRandomOracle.getH1())
|
||||||
.setG2(ByteString.copyFrom(group.encode(g2)))
|
.setG2(forRandomOracle.getG2())
|
||||||
.setH2(ByteString.copyFrom(group.encode(h2)))
|
.setH2(forRandomOracle.getH2())
|
||||||
.setG1Tag(ByteString.copyFrom(group.encode(g1Tag)))
|
.setG1Tag(forRandomOracle.getG1())
|
||||||
.setH1Tag(ByteString.copyFrom(group.encode(h1Tag)))
|
.setH1Tag(forRandomOracle.getH1Tag())
|
||||||
.setG2Tag(ByteString.copyFrom(group.encode(g2Tag)))
|
.setG2Tag(forRandomOracle.getG2Tag())
|
||||||
.setH2Tag(ByteString.copyFrom(group.encode(h2Tag)))
|
.setH2Tag(forRandomOracle.getH2Tag())
|
||||||
.setU(ByteString.copyFrom(group.encode(u)))
|
.setU(forRandomOracle.getU())
|
||||||
.setV(ByteString.copyFrom(group.encode(v)))
|
.setV(forRandomOracle.getV())
|
||||||
.setUTag(ByteString.copyFrom(group.encode(uTag)))
|
.setUTag(forRandomOracle.getUTag())
|
||||||
.setVTag(ByteString.copyFrom(group.encode(vTag)))
|
.setVTag(forRandomOracle.getVTag())
|
||||||
.setC1(ByteString.copyFrom(c1.toByteArray()))
|
.setC1(ByteString.copyFrom(c1.toByteArray()))
|
||||||
.setC2(ByteString.copyFrom(c2.toByteArray()))
|
.setC2(ByteString.copyFrom(c2.toByteArray()))
|
||||||
.setZ(ByteString.copyFrom(z.toByteArray()))
|
.setZ(ByteString.copyFrom(z.toByteArray()))
|
||||||
.setZTag(ByteString.copyFrom(zTag.toByteArray()))
|
.setZTag(ByteString.copyFrom(zTag.toByteArray()))
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -8,7 +8,7 @@ import meerkat.protobuf.ConcreteCrypto.ElGamalCiphertext;
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
import org.bouncycastle.math.ec.ECPoint;
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
import prover.ProofOrganizer;
|
import prover.ElGamalProofOrganizer;
|
||||||
import qilin.primitives.RandomOracle;
|
import qilin.primitives.RandomOracle;
|
||||||
import qilin.primitives.concrete.ECGroup;
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
@ -33,6 +33,7 @@ public class Verifier implements Mix2ZeroKnowledgeVerifier {
|
||||||
RandomOracle randomOracle;
|
RandomOracle randomOracle;
|
||||||
ECElGamalEncryption encryptor;
|
ECElGamalEncryption encryptor;
|
||||||
ECPoint g,h;
|
ECPoint g,h;
|
||||||
|
ElGamalProofOrganizer organizer;
|
||||||
|
|
||||||
public Verifier(ECElGamalEncryption encryptor, RandomOracle randomOracle) {
|
public Verifier(ECElGamalEncryption encryptor, RandomOracle randomOracle) {
|
||||||
this.encryptor = encryptor;
|
this.encryptor = encryptor;
|
||||||
|
@ -40,6 +41,7 @@ public class Verifier implements Mix2ZeroKnowledgeVerifier {
|
||||||
this.g = group.getGenerator();
|
this.g = group.getGenerator();
|
||||||
this.h = encryptor.getElGamalPK().getPK();
|
this.h = encryptor.getElGamalPK().getPK();
|
||||||
this.randomOracle = randomOracle;
|
this.randomOracle = randomOracle;
|
||||||
|
this.organizer = new ElGamalProofOrganizer(group,g,h);
|
||||||
}
|
}
|
||||||
|
|
||||||
public BigInteger hash(Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle input) {
|
public BigInteger hash(Mixing.ZeroKnowledgeProof.OrProof.ForRandomOracle input) {
|
||||||
|
@ -57,26 +59,14 @@ public class Verifier implements Mix2ZeroKnowledgeVerifier {
|
||||||
Crypto.RerandomizableEncryptedMessage out1,
|
Crypto.RerandomizableEncryptedMessage out1,
|
||||||
Crypto.RerandomizableEncryptedMessage out2,
|
Crypto.RerandomizableEncryptedMessage out2,
|
||||||
Mixing.ZeroKnowledgeProof proof) throws InvalidProtocolBufferException {
|
Mixing.ZeroKnowledgeProof proof) throws InvalidProtocolBufferException {
|
||||||
|
ElGamalProofOrganizer.ElGamalProofInput input = organizer.createProofInput(in1,in2,out1,out2);
|
||||||
ProofOrganizer organizer = new ProofOrganizer(in1,in2,out1,out2);
|
return verifyElGamaOrProof(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.first), proof.getFirst())&&
|
||||||
return verifyOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.first), proof.getFirst())&&
|
verifyElGamaOrProof(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.second), proof.getSecond())&&
|
||||||
verifyOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.second), proof.getSecond())&&
|
verifyElGamaOrProof(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.third), proof.getThird())&&
|
||||||
verifyOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.third), proof.getThird())&&
|
verifyElGamaOrProof(input.getOrProofInput(ElGamalProofOrganizer.OrProofOrder.fourth), proof.getFourth());
|
||||||
verifyOrProof(organizer.getOrProofInput(ProofOrganizer.OrProofOrder.fourth), proof.getFourth());
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean verifyOrProof(ProofOrganizer.OrProofInput orProofInput, Mixing.ZeroKnowledgeProof.OrProof orProof)
|
|
||||||
throws InvalidProtocolBufferException {
|
|
||||||
ElGamalCiphertext e1ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e1);
|
|
||||||
ElGamalCiphertext e2ElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e2);
|
|
||||||
ElGamalCiphertext e1TagElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e1New);
|
|
||||||
ElGamalCiphertext e2TagElGamal = ECElGamalEncryption.rerandomizableEncryptedMessage2ElGamalCiphertext(orProofInput.e2New);
|
|
||||||
return verifyElGamaOrProof(e1ElGamal,e2ElGamal,e1TagElGamal,e2TagElGamal,orProof);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
private ECPoint g1,g2,h1,h2;
|
private ECPoint g1,g2,h1,h2;
|
||||||
private ECPoint g1Tag,g2Tag,h1Tag,h2Tag;
|
private ECPoint g1Tag,g2Tag,h1Tag,h2Tag;
|
||||||
private ECPoint u,v,uTag,vTag;
|
private ECPoint u,v,uTag,vTag;
|
||||||
|
@ -117,23 +107,16 @@ public class Verifier implements Mix2ZeroKnowledgeVerifier {
|
||||||
zTag = new BigInteger(orProof.getZTag().toByteArray());
|
zTag = new BigInteger(orProof.getZTag().toByteArray());
|
||||||
}
|
}
|
||||||
|
|
||||||
private List<Condition> createConditionsList(ElGamalCiphertext e1,
|
private List<Condition> createConditionsList(ElGamalProofOrganizer.OrProofInput orProofInput){
|
||||||
ElGamalCiphertext e2,
|
|
||||||
ElGamalCiphertext e1New,
|
|
||||||
ElGamalCiphertext e2New){
|
|
||||||
List<Condition> conditions = new ArrayList<Condition>();
|
List<Condition> conditions = new ArrayList<Condition>();
|
||||||
conditions.add(new Condition<ECPoint>( g1,g,"g1 != g"));
|
conditions.add(new Condition<ECPoint>( g1,orProofInput.g1,"g1 != g"));
|
||||||
conditions.add(new Condition<ECPoint>( h1,group.add(convert2ECPoint(e1New.getC1()),
|
conditions.add(new Condition<ECPoint>( h1,orProofInput.h1,"h1 != e1New.c1/e1.c1"));
|
||||||
group.negate(convert2ECPoint(e1.getC1()))),"h1 != e1New.c1/e1.c1"));
|
conditions.add(new Condition<ECPoint>( g2,orProofInput.g2,"g2 != h"));
|
||||||
conditions.add(new Condition<ECPoint>( g2,h,"g2 != h"));
|
conditions.add(new Condition<ECPoint>( h2,orProofInput.h2,"h2 != e1New.c2/e1.c2"));
|
||||||
conditions.add(new Condition<ECPoint>( h2,group.add(convert2ECPoint(e1New.getC2()),
|
conditions.add(new Condition<ECPoint>( g1Tag,orProofInput.g1Tag,"g1Tag != g"));
|
||||||
group.negate(convert2ECPoint(e1.getC2()))),"h2 != e1New.c2/e1.c2"));
|
conditions.add(new Condition<ECPoint>( h1Tag,orProofInput.h1Tag,"h1Tag != e2New.c1/e2.c1"));
|
||||||
conditions.add(new Condition<ECPoint>( g1Tag,g,"g1Tag != g"));
|
conditions.add(new Condition<ECPoint>( g2Tag,orProofInput.g2,"g2Tag != h"));
|
||||||
conditions.add(new Condition<ECPoint>( h1Tag,group.add(convert2ECPoint(e2New.getC1()),
|
conditions.add(new Condition<ECPoint>( h2Tag,orProofInput.h2,"h2Tag != e2New.c2/e2.c2"));
|
||||||
group.negate(convert2ECPoint(e2.getC1()))),"h1Tag != e2New.c1/e2.c1"));
|
|
||||||
conditions.add(new Condition<ECPoint>( g2Tag,h,"g2Tag != h"));
|
|
||||||
conditions.add(new Condition<ECPoint>( h2Tag,group.add(convert2ECPoint(e2New.getC2()),
|
|
||||||
group.negate(convert2ECPoint(e2.getC2()))),"h2Tag != e2New.c2/e2.c2"));
|
|
||||||
conditions.add(new Condition<BigInteger>(c1.add(c2).mod(group.orderUpperBound()),
|
conditions.add(new Condition<BigInteger>(c1.add(c2).mod(group.orderUpperBound()),
|
||||||
hash(forRandomOracle).mod(group.orderUpperBound()).mod(group.orderUpperBound()),
|
hash(forRandomOracle).mod(group.orderUpperBound()).mod(group.orderUpperBound()),
|
||||||
"(c1 + c2 ) % group size == hash (imput + step1) % group size"));
|
"(c1 + c2 ) % group size == hash (imput + step1) % group size"));
|
||||||
|
@ -148,14 +131,11 @@ public class Verifier implements Mix2ZeroKnowledgeVerifier {
|
||||||
return conditions;
|
return conditions;
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean verifyElGamaOrProof(ElGamalCiphertext e1,
|
public boolean verifyElGamaOrProof(ElGamalProofOrganizer.OrProofInput orProofInput, Mixing.ZeroKnowledgeProof.OrProof orProof)
|
||||||
ElGamalCiphertext e2,
|
|
||||||
ElGamalCiphertext e1New,
|
|
||||||
ElGamalCiphertext e2New,
|
|
||||||
Mixing.ZeroKnowledgeProof.OrProof orProof)
|
|
||||||
{
|
{
|
||||||
parseOrProof(orProof);
|
parseOrProof(orProof);
|
||||||
List<Condition> conditions = createConditionsList(e1,e2,e1New,e2New);
|
List<Condition> conditions = createConditionsList(orProofInput);
|
||||||
|
|
||||||
boolean result = true;
|
boolean result = true;
|
||||||
for (Condition condition: conditions) {
|
for (Condition condition: conditions) {
|
||||||
|
|
|
@ -2,6 +2,7 @@ package verifier;
|
||||||
|
|
||||||
import com.google.protobuf.InvalidProtocolBufferException;
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
|
import meerkat.crypto.mixnet.MixerOutput;
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
import qilin.util.Pair;
|
import qilin.util.Pair;
|
||||||
|
@ -13,8 +14,8 @@ import java.util.Arrays;
|
||||||
*/
|
*/
|
||||||
public final class VerifyTable {
|
public final class VerifyTable {
|
||||||
|
|
||||||
public static boolean verifyTable(Mix2ZeroKnowledgeVerifier verifier,int n,Pair<Mixing.ZeroKnowledgeProof[][]
|
public static boolean verifyTable(Mix2ZeroKnowledgeVerifier verifier,int n,MixerOutput mixerOutput)
|
||||||
,Crypto.RerandomizableEncryptedMessage[][]> mixerOutput) throws InvalidProtocolBufferException {
|
throws InvalidProtocolBufferException {
|
||||||
int index1,index2,layer;
|
int index1,index2,layer;
|
||||||
|
|
||||||
//assert n = 2^k
|
//assert n = 2^k
|
||||||
|
@ -29,8 +30,8 @@ public final class VerifyTable {
|
||||||
Arrays.fill(locationChecksumLayer,false);
|
Arrays.fill(locationChecksumLayer,false);
|
||||||
}
|
}
|
||||||
|
|
||||||
Mixing.ZeroKnowledgeProof[][] zeroKnowledgeProofs = mixerOutput.a;
|
Mixing.ZeroKnowledgeProof[][] zeroKnowledgeProofs = mixerOutput.gerProofs();
|
||||||
Crypto.RerandomizableEncryptedMessage[][] rerandomizableEncryptedMessages = mixerOutput.b;
|
Crypto.RerandomizableEncryptedMessage[][] rerandomizableEncryptedMessages = mixerOutput.getEncryptedMessages();
|
||||||
|
|
||||||
for (Mixing.ZeroKnowledgeProof[] zkpLayer: zeroKnowledgeProofs) {
|
for (Mixing.ZeroKnowledgeProof[] zkpLayer: zeroKnowledgeProofs) {
|
||||||
for (Mixing.ZeroKnowledgeProof zkp: zkpLayer) {
|
for (Mixing.ZeroKnowledgeProof zkp: zkpLayer) {
|
||||||
|
|
|
@ -0,0 +1,100 @@
|
||||||
|
package mixer;
|
||||||
|
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeProver;
|
||||||
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import meerkat.protobuf.Voting;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import prover.Prover;
|
||||||
|
import qilin.primitives.RandomOracle;
|
||||||
|
import qilin.primitives.concrete.DigestOracle;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
import verifier.Verifier;
|
||||||
|
import verifier.VerifyTable;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.security.spec.InvalidKeySpecException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/19/2016.
|
||||||
|
*/
|
||||||
|
public class CreateTestVector {
|
||||||
|
|
||||||
|
|
||||||
|
ECElGamalEncryption encryptor;
|
||||||
|
ECGroup group;
|
||||||
|
Random random,randomMixer,randomProver;
|
||||||
|
RandomOracle randomOracle;
|
||||||
|
Mix2ZeroKnowledgeVerifier verifier;
|
||||||
|
Mix2ZeroKnowledgeProver prover;
|
||||||
|
meerkat.crypto.mixnet.Mixer mixer;
|
||||||
|
private int layers;
|
||||||
|
private int n;
|
||||||
|
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void setup() throws InvalidKeySpecException {
|
||||||
|
// initialization
|
||||||
|
random = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
encryptor = new ECElGamalEncryption();
|
||||||
|
encryptor.init(Utiles.serializePk(group, new ECElGamal.SK(group, ECElGamal.generateSecretKey(group, random))));
|
||||||
|
randomMixer = new Random();
|
||||||
|
randomProver = new Random();
|
||||||
|
randomOracle = new DigestOracle();
|
||||||
|
verifier = new Verifier(encryptor,randomOracle);
|
||||||
|
prover = new Prover(randomProver,encryptor,randomOracle);
|
||||||
|
mixer = new Mixer(randomMixer,prover,encryptor,verifier);
|
||||||
|
|
||||||
|
// generate n
|
||||||
|
int logN = 10; // + random.nextInt(8)
|
||||||
|
layers = 2*logN - 1;
|
||||||
|
n = 1 << logN;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Crypto.RerandomizableEncryptedMessage> generateMixerInput(){
|
||||||
|
List<Crypto.RerandomizableEncryptedMessage> result = new ArrayList<Crypto.RerandomizableEncryptedMessage>();
|
||||||
|
Voting.PlaintextBallot msg;
|
||||||
|
for (int i = 0; i < n ; i++){
|
||||||
|
msg = Utiles.genRandomBallot(2,3,16);
|
||||||
|
result.add(encryptor.encrypt(msg, encryptor.generateRandomness(random)));
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
//@Test
|
||||||
|
public void createValidTest() throws IOException {
|
||||||
|
|
||||||
|
List<Crypto.RerandomizableEncryptedMessage> mixerInput = generateMixerInput();
|
||||||
|
System.out.println("start mixing");
|
||||||
|
MixerOutput mixerOutput = new MixerOutput(mixer.mix(mixerInput));
|
||||||
|
System.out.println("mixing ended, start verification");
|
||||||
|
assert (VerifyTable.verifyTable(verifier,n,mixerOutput));
|
||||||
|
System.out.println("verification ended, start printing");
|
||||||
|
mixerOutput.outToFile("C:\\Users\\Tzlil\\Desktop\\TestVector\\Test3");
|
||||||
|
System.out.println("all done");
|
||||||
|
}
|
||||||
|
|
||||||
|
//@Test
|
||||||
|
public void createInvalidTest() throws IOException {
|
||||||
|
|
||||||
|
//Mix2ZeroKnowledgeVerifier corruptedVerifier = new Verifier(encryptor,randomOracle,true);
|
||||||
|
//Mix2ZeroKnowledgeProver corruptedProver = new Prover(randomProver,encryptor,randomOracle,true);
|
||||||
|
//mixer = new Mixer(randomMixer,corruptedProver,encryptor,corruptedVerifier);
|
||||||
|
|
||||||
|
List<Crypto.RerandomizableEncryptedMessage> mixerInput = generateMixerInput();
|
||||||
|
System.out.println("start mixing");
|
||||||
|
MixerOutput mixerOutput = new MixerOutput(mixer.mix(mixerInput));
|
||||||
|
System.out.println("mixing ended, start negative verification");
|
||||||
|
assert (!VerifyTable.verifyTable(verifier,n,mixerOutput));
|
||||||
|
System.out.println("verification ended, start printing");
|
||||||
|
mixerOutput.outToFile("C:\\Users\\Tzlil\\Desktop\\TestVector\\Test5");
|
||||||
|
System.out.println("all done");
|
||||||
|
}
|
||||||
|
}
|
|
@ -6,8 +6,7 @@ package mixer;
|
||||||
|
|
||||||
import com.google.protobuf.InvalidProtocolBufferException;
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
import meerkat.crypto.concrete.ECElGamalEncryption;
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeProver;
|
import meerkat.crypto.mixnet.*;
|
||||||
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
|
||||||
import meerkat.protobuf.Crypto;
|
import meerkat.protobuf.Crypto;
|
||||||
import meerkat.protobuf.Mixing;
|
import meerkat.protobuf.Mixing;
|
||||||
import meerkat.protobuf.Voting;
|
import meerkat.protobuf.Voting;
|
||||||
|
@ -33,7 +32,7 @@ public class MixingText {
|
||||||
Random random,randomMixer,randomProver;
|
Random random,randomMixer,randomProver;
|
||||||
RandomOracle randomOracle;
|
RandomOracle randomOracle;
|
||||||
Mix2ZeroKnowledgeVerifier verifier;
|
Mix2ZeroKnowledgeVerifier verifier;
|
||||||
Mix2ZeroKnowledgeProver prover;
|
Prover prover;
|
||||||
meerkat.crypto.mixnet.Mixer mixer;
|
meerkat.crypto.mixnet.Mixer mixer;
|
||||||
private int layers;
|
private int layers;
|
||||||
private int n;
|
private int n;
|
||||||
|
@ -54,7 +53,7 @@ public class MixingText {
|
||||||
mixer = new Mixer(randomMixer,prover,encryptor);
|
mixer = new Mixer(randomMixer,prover,encryptor);
|
||||||
|
|
||||||
// generate n
|
// generate n
|
||||||
int logN = 8; // + random.nextInt(8)
|
int logN = 10; // + random.nextInt(8)
|
||||||
layers = 2*logN - 1;
|
layers = 2*logN - 1;
|
||||||
n = 1 << logN;
|
n = 1 << logN;
|
||||||
}
|
}
|
||||||
|
@ -71,7 +70,23 @@ public class MixingText {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void mixingTest() throws InvalidProtocolBufferException {
|
public void mixingTest() throws InvalidProtocolBufferException {
|
||||||
Pair<Mixing.ZeroKnowledgeProof[][], Crypto.RerandomizableEncryptedMessage[][]> mixerOutput = mixer.mix(generateMixerInput());
|
System.out.println("n is : " + n);
|
||||||
|
System.out.println(" generating input");
|
||||||
|
List<Crypto.RerandomizableEncryptedMessage> mixerInput = generateMixerInput();
|
||||||
|
System.out.println(" start mixing");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
|
||||||
|
meerkat.crypto.mixnet.MixerOutput mixerOutput = mixer.mix(mixerInput);
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
|
||||||
|
System.out.println("start verification");
|
||||||
|
startTime = System.currentTimeMillis();
|
||||||
|
|
||||||
assert (VerifyTable.verifyTable(verifier,n,mixerOutput));
|
assert (VerifyTable.verifyTable(verifier,n,mixerOutput));
|
||||||
|
|
||||||
|
finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -68,7 +68,7 @@ public class RerandomizeTest {
|
||||||
|
|
||||||
assert (g.multiply(new BigInteger(r.getData().toByteArray())).equals(
|
assert (g.multiply(new BigInteger(r.getData().toByteArray())).equals(
|
||||||
group.add(convert2ECPoint(eNewElGamal.getC1()),group.negate(convert2ECPoint(eElGamal.getC1())))));
|
group.add(convert2ECPoint(eNewElGamal.getC1()),group.negate(convert2ECPoint(eElGamal.getC1())))));
|
||||||
assert (h.multiply(new BigInteger(r.getData().toByteArray())).equals(
|
assert(h.multiply(new BigInteger(r.getData().toByteArray())).equals(
|
||||||
group.add(convert2ECPoint(eNewElGamal.getC2()), group.negate(convert2ECPoint(eElGamal.getC2())))));
|
group.add(convert2ECPoint(eNewElGamal.getC2()), group.negate(convert2ECPoint(eElGamal.getC2())))));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,65 @@
|
||||||
|
package profiling.ECGroupProfiling;
|
||||||
|
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import mixer.Utiles;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
import java.security.spec.InvalidKeySpecException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/20/2016.
|
||||||
|
*/
|
||||||
|
public class AddProfiling {
|
||||||
|
|
||||||
|
ECElGamalEncryption encryptor;
|
||||||
|
ECGroup group;
|
||||||
|
Random random;
|
||||||
|
private int n;
|
||||||
|
List<ECPoint> members1;
|
||||||
|
List<ECPoint> members2;
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void setup() throws InvalidKeySpecException {
|
||||||
|
// initialization
|
||||||
|
random = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
encryptor = new ECElGamalEncryption();
|
||||||
|
encryptor.init(Utiles.serializePk(group, new ECElGamal.SK(group, ECElGamal.generateSecretKey(group, random))));
|
||||||
|
// generate n;
|
||||||
|
int sqrtn = 128;
|
||||||
|
n = sqrtn*sqrtn;
|
||||||
|
|
||||||
|
members1 = new ArrayList<ECPoint>(sqrtn);
|
||||||
|
members2 = new ArrayList<ECPoint>(sqrtn);
|
||||||
|
|
||||||
|
for (int i = 0 ; i < sqrtn; i ++){
|
||||||
|
members1.add(group.sample(random));
|
||||||
|
members2.add(group.sample(random));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void addProfiling() throws InvalidProtocolBufferException {
|
||||||
|
System.out.println("Add");
|
||||||
|
System.out.println("n is : " + n);
|
||||||
|
System.out.println("start n operations");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
for (ECPoint member1: members1) {
|
||||||
|
for (ECPoint member2: members2) {
|
||||||
|
group.add(member1,member2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
System.out.println(" avg of"+((double)(finishTime-startTime))/(n * n)+ " ms");
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,59 @@
|
||||||
|
package profiling.ECGroupProfiling;
|
||||||
|
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import mixer.Utiles;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
import java.security.spec.InvalidKeySpecException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/20/2016.
|
||||||
|
*/
|
||||||
|
public class EncodeProfiling {
|
||||||
|
|
||||||
|
ECElGamalEncryption encryptor;
|
||||||
|
ECGroup group;
|
||||||
|
Random random;
|
||||||
|
private int n;
|
||||||
|
List<ECPoint> members;
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void setup() throws InvalidKeySpecException {
|
||||||
|
// initialization
|
||||||
|
random = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
encryptor = new ECElGamalEncryption();
|
||||||
|
encryptor.init(Utiles.serializePk(group, new ECElGamal.SK(group, ECElGamal.generateSecretKey(group, random))));
|
||||||
|
// generate n;
|
||||||
|
int sqrtn = 128;
|
||||||
|
n = sqrtn*sqrtn;
|
||||||
|
|
||||||
|
members = new ArrayList<ECPoint>(n);
|
||||||
|
for (int i = 0 ; i < n; i ++){
|
||||||
|
members.add(group.sample(random));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@Test
|
||||||
|
public void encodeProfiling() throws InvalidProtocolBufferException {
|
||||||
|
System.out.println("Encode");
|
||||||
|
System.out.println("n is : " + n);
|
||||||
|
|
||||||
|
System.out.println("start n operations");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
for (ECPoint member: members) {
|
||||||
|
group.encode(member);
|
||||||
|
}
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
System.out.println(" avg of"+((double)(finishTime-startTime))/(n * n)+ " ms");
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,81 @@
|
||||||
|
package profiling.ECGroupProfiling;
|
||||||
|
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import meerkat.protobuf.Voting;
|
||||||
|
import mixer.Mixer;
|
||||||
|
import mixer.Utiles;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import prover.Prover;
|
||||||
|
import qilin.primitives.RandomOracle;
|
||||||
|
import qilin.primitives.concrete.DigestOracle;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
import verifier.Verifier;
|
||||||
|
import verifier.VerifyTable;
|
||||||
|
|
||||||
|
import java.math.BigInteger;
|
||||||
|
import java.security.spec.InvalidKeySpecException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/19/2016.
|
||||||
|
*/
|
||||||
|
public class MulProfiling {
|
||||||
|
|
||||||
|
ECElGamalEncryption encryptor;
|
||||||
|
ECGroup group;
|
||||||
|
Random random;
|
||||||
|
private int n;
|
||||||
|
List<ECPoint> members;
|
||||||
|
List<BigInteger> randomnesses;
|
||||||
|
@Before
|
||||||
|
public void setup() throws InvalidKeySpecException {
|
||||||
|
// initialization
|
||||||
|
random = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
encryptor = new ECElGamalEncryption();
|
||||||
|
encryptor.init(Utiles.serializePk(group, new ECElGamal.SK(group, ECElGamal.generateSecretKey(group, random))));
|
||||||
|
// generate n
|
||||||
|
int sqrtn = 128;
|
||||||
|
n = sqrtn*sqrtn;
|
||||||
|
|
||||||
|
members = new ArrayList<ECPoint>(sqrtn);
|
||||||
|
randomnesses = new ArrayList<BigInteger>(sqrtn);
|
||||||
|
|
||||||
|
byte[] arr = new byte[256];
|
||||||
|
for (int i = 0 ; i < sqrtn; i ++){
|
||||||
|
members.add(group.sample(random));
|
||||||
|
random.nextBytes(arr);
|
||||||
|
randomnesses.add(new BigInteger(arr));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void mulProfiling() throws InvalidProtocolBufferException {
|
||||||
|
System.out.println("Multiply");
|
||||||
|
System.out.println("n is : " + n);
|
||||||
|
|
||||||
|
System.out.println("start n operations");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
for(ECPoint member:members) {
|
||||||
|
for (BigInteger rand : randomnesses) {
|
||||||
|
group.multiply(member, rand);
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
System.out.println(" avg of"+((double)(finishTime-startTime))/(n*n)+ " ms");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,59 @@
|
||||||
|
package profiling.ECGroupProfiling;
|
||||||
|
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import mixer.Utiles;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
import java.security.spec.InvalidKeySpecException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/20/2016.
|
||||||
|
*/
|
||||||
|
public class NegateProfiling {
|
||||||
|
|
||||||
|
ECElGamalEncryption encryptor;
|
||||||
|
ECGroup group;
|
||||||
|
Random random;
|
||||||
|
private int n;
|
||||||
|
List<ECPoint> members;
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void setup() throws InvalidKeySpecException {
|
||||||
|
// initialization
|
||||||
|
random = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
encryptor = new ECElGamalEncryption();
|
||||||
|
encryptor.init(Utiles.serializePk(group, new ECElGamal.SK(group, ECElGamal.generateSecretKey(group, random))));
|
||||||
|
// generate n;
|
||||||
|
int sqrtn = 128;
|
||||||
|
n = sqrtn*sqrtn;
|
||||||
|
|
||||||
|
members = new ArrayList<ECPoint>(n);
|
||||||
|
for (int i = 0 ; i < n; i ++){
|
||||||
|
members.add(group.sample(random));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@Test
|
||||||
|
public void negProfiling() throws InvalidProtocolBufferException {
|
||||||
|
System.out.println("Neg");
|
||||||
|
System.out.println("n is : " + n);
|
||||||
|
|
||||||
|
System.out.println("start n operations");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
for (ECPoint member: members) {
|
||||||
|
group.negate(member);
|
||||||
|
}
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
System.out.println(" avg of"+((double)(finishTime-startTime))/(n * n)+ " ms");
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,79 @@
|
||||||
|
package profiling;
|
||||||
|
|
||||||
|
import com.google.protobuf.ByteString;
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeProver;
|
||||||
|
import meerkat.protobuf.ConcreteCrypto;
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import meerkat.protobuf.Voting;
|
||||||
|
import mixer.Utiles;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import prover.Prover;
|
||||||
|
import qilin.primitives.RandomOracle;
|
||||||
|
import qilin.primitives.concrete.DigestOracle;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
import java.math.BigInteger;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/20/2016.
|
||||||
|
*/
|
||||||
|
public class RerandomizeProfiling {
|
||||||
|
|
||||||
|
Random rand;
|
||||||
|
ECElGamal.SK key;
|
||||||
|
ECGroup group;
|
||||||
|
ECElGamalEncryption enc;
|
||||||
|
ConcreteCrypto.ElGamalPublicKey serializedPk;
|
||||||
|
int n;
|
||||||
|
Crypto.EncryptionRandomness[] randomnesses;
|
||||||
|
Crypto.RerandomizableEncryptedMessage[] encryptedMessage;
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void setup() throws Exception {
|
||||||
|
rand = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
BigInteger sk = ECElGamal.generateSecretKey(group, rand);
|
||||||
|
key = new ECElGamal.SK(group, sk);
|
||||||
|
serializedPk = Utiles.serializePk(group, key);
|
||||||
|
enc = new ECElGamalEncryption();
|
||||||
|
enc.init(serializedPk);
|
||||||
|
n = 1024 * 18;
|
||||||
|
randomnesses = new Crypto.EncryptionRandomness[n];
|
||||||
|
encryptedMessage = new Crypto.RerandomizableEncryptedMessage[n];
|
||||||
|
|
||||||
|
Voting.PlaintextBallot msg;
|
||||||
|
|
||||||
|
for (int i = 0; i < n ; i ++){
|
||||||
|
msg = Utiles.genRandomBallot(2,3,16);
|
||||||
|
randomnesses[i] = enc.generateRandomness(rand);
|
||||||
|
encryptedMessage[i] = enc.encrypt(msg, enc.generateRandomness(rand));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private ECPoint convert2ECPoint(ByteString bs){
|
||||||
|
return group.decode(bs.toByteArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void RerandomizeProfiling() throws InvalidProtocolBufferException {
|
||||||
|
|
||||||
|
System.out.println("Rerandomiz");
|
||||||
|
System.out.println("n is : " + n);
|
||||||
|
System.out.println("start n operations");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
|
||||||
|
for (int i = 0; i < n ; i ++){
|
||||||
|
enc.rerandomize(encryptedMessage[i],randomnesses[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
System.out.println(" avg of"+((double)(finishTime-startTime))/n + " ms");
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,87 @@
|
||||||
|
package profiling;
|
||||||
|
|
||||||
|
import com.google.protobuf.ByteString;
|
||||||
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
|
import meerkat.crypto.concrete.ECElGamalEncryption;
|
||||||
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeProver;
|
||||||
|
import meerkat.crypto.mixnet.Mix2ZeroKnowledgeVerifier;
|
||||||
|
import meerkat.protobuf.ConcreteCrypto;
|
||||||
|
import meerkat.protobuf.Crypto;
|
||||||
|
import meerkat.protobuf.Voting;
|
||||||
|
import mixer.Utiles;
|
||||||
|
import org.bouncycastle.math.ec.ECPoint;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
import prover.Prover;
|
||||||
|
import qilin.primitives.RandomOracle;
|
||||||
|
import qilin.primitives.concrete.DigestOracle;
|
||||||
|
import qilin.primitives.concrete.ECElGamal;
|
||||||
|
import qilin.primitives.concrete.ECGroup;
|
||||||
|
|
||||||
|
|
||||||
|
import java.math.BigInteger;
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by Tzlil on 1/20/2016.
|
||||||
|
*/
|
||||||
|
public class ZeroKnowledgeProofProfiling {
|
||||||
|
|
||||||
|
Random rand;
|
||||||
|
ECElGamal.SK key;
|
||||||
|
ECGroup group;
|
||||||
|
ECElGamalEncryption enc;
|
||||||
|
ConcreteCrypto.ElGamalPublicKey serializedPk;
|
||||||
|
Mix2ZeroKnowledgeProver prover ;
|
||||||
|
int n;
|
||||||
|
Crypto.EncryptionRandomness[] randomnesses;
|
||||||
|
Crypto.RerandomizableEncryptedMessage[] encryptedMessage;
|
||||||
|
Crypto.RerandomizableEncryptedMessage[] reencryptedMessage;
|
||||||
|
@Before
|
||||||
|
public void setup() throws Exception {
|
||||||
|
rand = new Random();
|
||||||
|
group = new ECGroup("secp256k1");
|
||||||
|
BigInteger sk = ECElGamal.generateSecretKey(group, rand);
|
||||||
|
key = new ECElGamal.SK(group, sk);
|
||||||
|
serializedPk = Utiles.serializePk(group, key);
|
||||||
|
enc = new ECElGamalEncryption();
|
||||||
|
enc.init(serializedPk);
|
||||||
|
RandomOracle randomOracle = new DigestOracle();
|
||||||
|
prover = new Prover(new Random(),enc,randomOracle);
|
||||||
|
n = 512 * 18;
|
||||||
|
randomnesses = new Crypto.EncryptionRandomness[n*2];
|
||||||
|
encryptedMessage = new Crypto.RerandomizableEncryptedMessage[n*2];
|
||||||
|
reencryptedMessage = new Crypto.RerandomizableEncryptedMessage[n*2];
|
||||||
|
|
||||||
|
Voting.PlaintextBallot msg;
|
||||||
|
|
||||||
|
for (int i = 0; i < n*2 ; i ++){
|
||||||
|
msg = Utiles.genRandomBallot(2,3,16);
|
||||||
|
randomnesses[i] = enc.generateRandomness(rand);
|
||||||
|
encryptedMessage[i] = enc.encrypt(msg, enc.generateRandomness(rand));
|
||||||
|
reencryptedMessage[i] = enc.rerandomize(encryptedMessage[i], randomnesses[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private ECPoint convert2ECPoint(ByteString bs){
|
||||||
|
return group.decode(bs.toByteArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void zeroKnowledgeProofTest() throws InvalidProtocolBufferException {
|
||||||
|
|
||||||
|
System.out.println("Prove");
|
||||||
|
System.out.println("n is : " + n);
|
||||||
|
System.out.println("start n proves");
|
||||||
|
long startTime = System.currentTimeMillis();
|
||||||
|
|
||||||
|
for (int i = 0; i < n*2 ; i +=2){
|
||||||
|
prover.prove(encryptedMessage[i],encryptedMessage[i+1],reencryptedMessage[i],reencryptedMessage[i+1],
|
||||||
|
false,0,0,0,randomnesses[i],randomnesses[i+1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
long finishTime = System.currentTimeMillis();
|
||||||
|
System.out.println(" that took: "+(finishTime-startTime)+ " ms");
|
||||||
|
System.out.println(" avg of"+((double)(finishTime-startTime))/n + " ms");
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue