secure dkg without stage 4
							parent
							
								
									a233f2f713
								
							
						
					
					
						commit
						210cc327ac
					
				|  | @ -0,0 +1,43 @@ | |||
| package Communication; | ||||
| 
 | ||||
| import com.google.protobuf.InvalidProtocolBufferException; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/14/2016. | ||||
|  */ | ||||
| public class MailHandler { | ||||
| 
 | ||||
|     private MessageHandler messageHandler; | ||||
| 
 | ||||
|     public MailHandler(MessageHandler messageHandler){ | ||||
|         this.messageHandler = messageHandler; | ||||
|     } | ||||
| 
 | ||||
|     public MessageHandler getMessageHandler(){ | ||||
|         return messageHandler; | ||||
|     } | ||||
| 
 | ||||
|     public void handel(DKGMessages.Mail mail) throws InvalidProtocolBufferException { | ||||
|         switch (mail.getType()){ | ||||
|             case SECRET: | ||||
|                 DKGMessages.SecretMessage secretMessage = DKGMessages.SecretMessage.parseFrom(mail.getMessage()); | ||||
|                 messageHandler.handelSecretMessage(mail.getSender(),mail.getDestination()== Network.BROADCAST,secretMessage); | ||||
|                 break; | ||||
|             case COMMITMENT: | ||||
|                 DKGMessages.CommitmentMessage commitmentMessage = DKGMessages.CommitmentMessage.parseFrom(mail.getMessage()); | ||||
|                 messageHandler.handelCommitmentMessage(mail.getSender(),mail.getDestination()== Network.BROADCAST,commitmentMessage); | ||||
|                 break; | ||||
|             case DONE: | ||||
|                 DKGMessages.DoneMessage doneMessage = DKGMessages.DoneMessage.parseFrom(mail.getMessage()); | ||||
|                 messageHandler.handelDoneMessage(mail.getSender(),mail.getDestination()== Network.BROADCAST,doneMessage); | ||||
|                 break; | ||||
|             case COMPLAINT: | ||||
|                 DKGMessages.ComplaintMessage complaintMessage = DKGMessages.ComplaintMessage.parseFrom(mail.getMessage()); | ||||
|                 messageHandler.handelComplaintMessage(mail.getSender(),mail.getDestination()== Network.BROADCAST,complaintMessage); | ||||
|                 break; | ||||
|             default: | ||||
|                 break; | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  | @ -0,0 +1,14 @@ | |||
| package Communication; | ||||
| 
 | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/14/2016. | ||||
|  */ | ||||
| public interface MessageHandler { | ||||
|     void handelComplaintMessage(int sender, boolean isBroadcast,DKGMessages.ComplaintMessage complaintMessage); | ||||
|     void handelDoneMessage(int sender,  boolean isBroadcast, DKGMessages.DoneMessage doneMessage); | ||||
|     void handelCommitmentMessage(int sender,  boolean isBroadcast,DKGMessages.CommitmentMessage commitmentMessage); | ||||
|     void handelSecretMessage(int sender,  boolean isBroadcast,DKGMessages.SecretMessage secretMessage); | ||||
|     void handelDoubleSecretMessage(int sender,  boolean isBroadcast,DKGMessages.DoubleSecretMessage doubleSecretMessage); | ||||
| } | ||||
|  | @ -0,0 +1,70 @@ | |||
| package Communication; | ||||
| 
 | ||||
| import com.google.protobuf.InvalidProtocolBufferException; | ||||
| import com.google.protobuf.Message; | ||||
| import meerkat.protobuf.DKGMessages.*; | ||||
| import java.util.Queue; | ||||
| import java.util.concurrent.ArrayBlockingQueue; | ||||
| /** | ||||
|  * Created by Tzlil on 2/7/2016. | ||||
|  * JointFeldamn protocol assumes all parties can communicate throw broadcast chanel | ||||
|  * and private chanel (for each pair) | ||||
|  * this class simulates it | ||||
|  */ | ||||
| public class Network { | ||||
| 
 | ||||
|     protected final User[] users; | ||||
|     protected final int n; | ||||
|     protected final Queue<Integer> availableIDs; | ||||
|     public static final int BROADCAST = 0; | ||||
| 
 | ||||
| 
 | ||||
|     public Network(int n) { | ||||
|         this.n = n; | ||||
|         this.users = new User[n]; | ||||
|         this.availableIDs = new ArrayBlockingQueue<Integer>(n); | ||||
|         for (int id = 1; id <= n; id++){ | ||||
|             availableIDs.add(id); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     public User connect(MessageHandler messageHandler){ | ||||
|         Integer id = availableIDs.poll(); | ||||
|         if (id == null) | ||||
|             return null; | ||||
|         users[id - 1] = new User(id,this,new MailHandler(messageHandler)); | ||||
|         return users[id - 1]; | ||||
|     } | ||||
| 
 | ||||
|     protected boolean sendMessage(User sender,int destination,Mail.Type type,Message message){ | ||||
|         if(destination < 1 || destination > n) | ||||
|             return false; | ||||
|         User user = users[destination - 1]; | ||||
|         if (user == null) | ||||
|             return false; | ||||
|         Mail mail = Mail.newBuilder() | ||||
|                 .setSender(sender.getID()) | ||||
|                 .setDestination(destination) | ||||
|                 .setIsPrivate(true) | ||||
|                 .setType(type) | ||||
|                 .setMessage(message.toByteString()) | ||||
|                 .build(); | ||||
|         return user.mailbox.add(mail); | ||||
|     } | ||||
| 
 | ||||
|     protected void sendBroadcast(User sender,Mail.Type type,Message message){ | ||||
|         User user; | ||||
|         Mail mail = Mail.newBuilder() | ||||
|                 .setSender(sender.getID()) | ||||
|                 .setDestination(BROADCAST) | ||||
|                 .setIsPrivate(false) | ||||
|                 .setType(type) | ||||
|                 .setMessage(message.toByteString()) | ||||
|                 .build(); | ||||
|         for (int i = 0 ; i < n ; i++){ | ||||
|             user = users[i]; | ||||
|             user.mailbox.add(mail); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
| } | ||||
|  | @ -0,0 +1,68 @@ | |||
| package Communication; | ||||
| 
 | ||||
| import com.google.protobuf.InvalidProtocolBufferException; | ||||
| import com.google.protobuf.Message; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| 
 | ||||
| import java.util.Queue; | ||||
| import java.util.concurrent.ArrayBlockingQueue; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/14/2016. | ||||
|  */ | ||||
| public class User{ | ||||
|     protected final MailHandler mailHandler; | ||||
|     protected final Queue<DKGMessages.Mail> mailbox; | ||||
|     protected final int ID; | ||||
|     protected final Thread receiverThread; | ||||
|     private final Network network; | ||||
| 
 | ||||
|     protected User(int ID, Network network, MailHandler mailHandler) { | ||||
|         this.mailbox = new ArrayBlockingQueue<DKGMessages.Mail>(2 * network.n * network.n); | ||||
|         this.ID = ID; | ||||
|         this.mailHandler = mailHandler; | ||||
|         this.receiverThread = new Thread(new Receiver()); | ||||
|         this.network = network; | ||||
|     } | ||||
| 
 | ||||
|     public boolean send(int id, DKGMessages.Mail.Type type, Message message){ | ||||
|         return network.sendMessage(this,id,type,message); | ||||
|     } | ||||
| 
 | ||||
|     public void broadcast(DKGMessages.Mail.Type type, Message message){ | ||||
|         network.sendBroadcast(this,type,message); | ||||
|     } | ||||
| 
 | ||||
|     public MessageHandler getMessageHandler(){ | ||||
|         return mailHandler.getMessageHandler(); | ||||
|     } | ||||
| 
 | ||||
|     public int getID() { | ||||
|         return ID; | ||||
|     } | ||||
|     public Thread getReceiverThread(){ | ||||
|         return receiverThread; | ||||
|     } | ||||
|     private class Receiver implements Runnable{ | ||||
|         @Override | ||||
|         public void run() { | ||||
|             while (true){ | ||||
|                 if (!mailbox.isEmpty()){ | ||||
|                     try { | ||||
|                         mailHandler.handel(mailbox.poll()); | ||||
|                     } catch (InvalidProtocolBufferException e) { | ||||
|                         e.printStackTrace(); | ||||
|                     } | ||||
|                 }else{ | ||||
|                     try { | ||||
|                         Thread.sleep(30); | ||||
|                     } catch (InterruptedException e) { | ||||
|                         // do nothing
 | ||||
|                     } | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
| } | ||||
|  | @ -1,9 +1,12 @@ | |||
| package FeldmanVerifiableSecretSharing; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.SecretSharing; | ||||
| import org.bouncycastle.util.Arrays; | ||||
| import org.factcenter.qilin.primitives.CyclicGroup; | ||||
| import Communication.Network; | ||||
| import Communication.User; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.SecretSharing; | ||||
| import com.google.protobuf.ByteString; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| import java.util.Arrays; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
|  | @ -21,8 +24,7 @@ public class VerifiableSecretSharing extends SecretSharing { | |||
|     protected final Zpstar zpstar; | ||||
|     protected final BigInteger g; // public generator of group
 | ||||
|     private final BigInteger y; // y = g ^ x
 | ||||
|     private final BigInteger[] commitments; | ||||
| 
 | ||||
|     protected final BigInteger[] commitments; | ||||
|     /** | ||||
|      * @param p a large prime | ||||
|      * @param q a large prime dividing p - 1. | ||||
|  | @ -30,8 +32,9 @@ public class VerifiableSecretSharing extends SecretSharing { | |||
|      *          the generated group is a subgroup of Zp*. | ||||
|      *          it must be chosen such that computing discrete logarithms is hard in this group. | ||||
|      */ | ||||
|     public VerifiableSecretSharing(int t, int n, BigInteger x, Random random,BigInteger p,BigInteger q,BigInteger g) { | ||||
|         super(t, n, x, random,q); | ||||
|     public VerifiableSecretSharing(int t, int n, BigInteger x, Random random, BigInteger p, BigInteger q, BigInteger g | ||||
|             , User user) { | ||||
|         super(t, n, x, random,q,user); | ||||
|         this.g = g; | ||||
|         this.zpstar = new Zpstar(p); | ||||
|         assert (zpstar.contains(g)); | ||||
|  | @ -40,6 +43,11 @@ public class VerifiableSecretSharing extends SecretSharing { | |||
|         this.y = zpstar.multiply(g,x); | ||||
|     } | ||||
| 
 | ||||
|     public VerifiableSecretSharing(int t, int n, BigInteger x, Random random, BigInteger p, BigInteger q, BigInteger g | ||||
|             , Network network) { | ||||
|         this(t,n,x,random,p,q,g,network.connect(new VerifiableSecretSharingMessageHandler(t))); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @return commitments[i] = g ^ polynomial.coefficients[i] | ||||
|      */ | ||||
|  | @ -102,6 +110,30 @@ public class VerifiableSecretSharing extends SecretSharing { | |||
|      * @return copy of commitments | ||||
|      */ | ||||
|     public BigInteger[] getCommitments() { | ||||
|         return Arrays.clone(commitments); | ||||
|         return Arrays.copyOf(commitments,commitments.length); | ||||
|     } | ||||
| 
 | ||||
|     public DKGMessages.CommitmentMessage[] prepareCommitmentMessages(){ | ||||
|         DKGMessages.CommitmentMessage[] commitmentMessages = new DKGMessages.CommitmentMessage[t + 1]; | ||||
|         for (int k = 0; k <= t ; k ++) { | ||||
|             commitmentMessages[k] = DKGMessages.CommitmentMessage.newBuilder() | ||||
|                     .setK(k) | ||||
|                     .setCommitment(ByteString.copyFrom(commitments[k].toByteArray())) | ||||
|                     .build(); | ||||
|         } | ||||
|         return commitmentMessages; | ||||
|     } | ||||
| 
 | ||||
|     protected void computeAndSendCommitments(){ | ||||
|         DKGMessages.CommitmentMessage[] commitmentMessages = prepareCommitmentMessages(); | ||||
|         for (int k = 0; k <= t ; k ++){ | ||||
|             user.broadcast(DKGMessages.Mail.Type.COMMITMENT,commitmentMessages[k]); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void run() { | ||||
|         super.run(); | ||||
|         computeAndSendCommitments(); | ||||
|     } | ||||
| } | ||||
|  |  | |||
|  | @ -0,0 +1,40 @@ | |||
| package FeldmanVerifiableSecretSharing; | ||||
| 
 | ||||
| import Communication.Network; | ||||
| import ShamirSecretSharing.SecretSharingMessageHandler; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| 
 | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.Arrays; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/16/2016. | ||||
|  */ | ||||
| public class VerifiableSecretSharingMessageHandler extends SecretSharingMessageHandler { | ||||
| 
 | ||||
|     private final BigInteger[] commitments; | ||||
| 
 | ||||
|     public VerifiableSecretSharingMessageHandler(int t) { | ||||
|         this.commitments = new BigInteger[t + 1]; | ||||
|     } | ||||
| 
 | ||||
|     public static BigInteger extractCommitment(DKGMessages.CommitmentMessage commitmentMessage){ | ||||
|         return new BigInteger(commitmentMessage.getCommitment().toByteArray()); | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelCommitmentMessage(int sender,  boolean isBroadcast, DKGMessages.CommitmentMessage commitmentMessage) { | ||||
|         if(isBroadcast) { // receive in broadcast only
 | ||||
|             commitments[commitmentMessage.getK()] = extractCommitment(commitmentMessage); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     public BigInteger[] getCommitments() { | ||||
|         return commitments; | ||||
|     } | ||||
| 
 | ||||
|     public BigInteger getY(){ | ||||
|         return commitments[0]; | ||||
|     } | ||||
| } | ||||
|  | @ -1,362 +0,0 @@ | |||
| package JointFeldmanProtocol; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharing; | ||||
| import com.google.protobuf.ByteString; | ||||
| import com.google.protobuf.InvalidProtocolBufferException; | ||||
| import org.bouncycastle.util.Arrays; | ||||
| import meerkat.protobuf.DKGMessages.*; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.HashSet; | ||||
| import java.util.Random; | ||||
| import java.util.Set; | ||||
| import java.util.concurrent.Callable; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/5/2016. | ||||
|  * | ||||
|  * an implementation of a version of Pedersen's distributed key generation protocol | ||||
|  */ | ||||
| public class DKG extends VerifiableSecretSharing implements Runnable{ | ||||
| 
 | ||||
|     private final int id; | ||||
|     private final Network.User user; // send and receive messages throw network
 | ||||
| 
 | ||||
|     private final BigInteger[] ys; // container for y values that
 | ||||
|     private final Polynomial.Point[] shares; // shares[i] equivalent to Si,id in terms of the protocol
 | ||||
|     private final BigInteger[][] commitmentsArray; // commitmentsArray[i] equivalent to Ai in terms of the protocol
 | ||||
|     private final ComplainState[][] complainStates; // complainStates[i][j] == state of Pj's complaint against Pi
 | ||||
| 
 | ||||
|     private final Set<Integer> QUAL; // set of all non-disqualified parties
 | ||||
|     private final BigInteger[] commitments; // public verification values
 | ||||
|     private Polynomial.Point share; // final share of the secrete
 | ||||
|     private BigInteger y; // final public value
 | ||||
| 
 | ||||
| 
 | ||||
|     public DKG(int t, int n, BigInteger x, Random random, BigInteger p, BigInteger q, BigInteger g,Network network) { | ||||
|         super(t, n, x, random, p, q, g); | ||||
| 
 | ||||
|         this.commitmentsArray = new BigInteger[n][t + 1]; | ||||
|         this.shares = new Polynomial.Point[n]; | ||||
|         this.user = network.connect(new Handler()); | ||||
|         this.id = user.getID(); | ||||
|         this.complainStates = new ComplainState[n][n]; | ||||
|         this.QUAL = new HashSet<Integer>(); | ||||
|         this.ys = new BigInteger[n]; | ||||
|         this.commitments = new BigInteger[t + 1]; | ||||
| 
 | ||||
|         for (int i = 0; i < n; i ++){ | ||||
|             for (int j = 0 ; j < n ; j ++) | ||||
|                 complainStates[i][j] = ComplainState.Non; | ||||
|         } | ||||
| 
 | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * use for simulate real distributed protocol | ||||
|      */ | ||||
|     @Override | ||||
|     public void run() { | ||||
|         user.getReceiverThread().start(); | ||||
|         stage1(); | ||||
|         stage2(); | ||||
|         stage3(); | ||||
|         stage4(); | ||||
|         user.getReceiverThread().interrupt(); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * stage1 according to the protocol | ||||
|      *  1. Pi broadcasts Aik for k = 0,...,t. | ||||
|      *  2. Pi computes the shares Sij for j = 1,...,n and sends Sij secretly to Pj. | ||||
|      */ | ||||
|     private void stage1(){ | ||||
|         // for avoiding edge cases, sets commitmentsArray[id - 1]
 | ||||
|         BigInteger[] commitments = super.getCommitments(); | ||||
|         System.arraycopy(commitments, 0, commitmentsArray[id - 1], 0, commitmentsArray[id - 1].length); | ||||
| 
 | ||||
|         // broadcasts commitments
 | ||||
|         CommitmentMessage commitment; | ||||
|         for (int k = 0; k <= t ; k ++){ | ||||
|             commitment = CommitmentMessage.newBuilder() | ||||
|                             .setK(k) | ||||
|                             .setCommitment(ByteString.copyFrom(commitmentsArray[id - 1][k].toByteArray())) | ||||
|                             .build(); | ||||
|             user.broadcast(Mail.Type.COMMITMENT,commitment); | ||||
|         } | ||||
| 
 | ||||
|         // computes and sends shares
 | ||||
|         SecretMessage secret; | ||||
|         for (int j = 1; j <= n ; j++ ){ | ||||
|             if(j != id){ | ||||
|                 secret = SecretMessage.newBuilder() | ||||
|                             .setSecret(getShare(j).asMessage()) | ||||
|                             .build(); | ||||
|                 user.send(j, Mail.Type.SECRET,secret); | ||||
|             } | ||||
|             else{ | ||||
|                 shares[id - 1] = super.getShare(id); | ||||
|             } | ||||
|         } | ||||
|         while (!isStage1Complete()){ | ||||
|             try { | ||||
|                 Thread.sleep(300); | ||||
|             } catch (InterruptedException e) { | ||||
|                 // do nothing
 | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @return true iff all shares and commitments were received | ||||
|      */ | ||||
|     private boolean isStage1Complete(){ | ||||
|         for (int i = 1 ; i <= n ; i++){ | ||||
|             if(shares[i - 1] == null) | ||||
|                 return false; | ||||
|         } | ||||
| 
 | ||||
|         for (int i = 0; i < commitmentsArray.length; i++){ | ||||
|             for (int j = 0; j < commitmentsArray[i].length; j++){ | ||||
|                 if(commitmentsArray[i][j] == null) | ||||
|                     return false; | ||||
|             } | ||||
|         } | ||||
|         return true; | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @param secret | ||||
|      * @param i | ||||
|      * @return g ^ Sij == verify(j,Ai,zpstar) (mod p) | ||||
|      */ | ||||
|     private boolean isValidSecret(Polynomial.Point secret, int i){ | ||||
|         int j = secret.x.intValue(); | ||||
|         return zpstar.multiply(g,secret.y).equals(verify(j,commitmentsArray[i - 1],zpstar)); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * stage2 according to the protocol | ||||
|      *  Pj verifies all the shares he received (using isValidSecret) | ||||
|      *  if check fails for an index i, Pj broadcasts a complaint against Pi. | ||||
|      *  Pj broadcasts yj value at the end of this stage | ||||
|      */ | ||||
|     private void stage2(){ | ||||
|         ys[id - 1] = super.getY(); | ||||
|         ComplaintMessage complaint; | ||||
|         for (int i = 1; i <= n ; i++ ){ | ||||
|             if(id != i && !isValidSecret(shares[i - 1],i)) { | ||||
|                 //message = new Message(Type.Complaint, j)
 | ||||
|                 complaint = ComplaintMessage.newBuilder() | ||||
|                                 .setId(i) | ||||
|                                 .build(); | ||||
|                 user.broadcast(Mail.Type.COMPLAINT,complaint); | ||||
|                 complainStates[i - 1][id - 1] = ComplainState.Waiting; | ||||
|             } | ||||
|         } | ||||
|         //broadcast y after all complaints
 | ||||
|         YMessage yMessage = YMessage.newBuilder() | ||||
|                 .setY(ByteString.copyFrom(super.getY().toByteArray())) | ||||
|                 .build(); | ||||
|         user.broadcast(Mail.Type.Y,yMessage); | ||||
| 
 | ||||
|         while (!isStage2Complete()){ | ||||
|             try { | ||||
|                 Thread.sleep(300); | ||||
|             } catch (InterruptedException e) { | ||||
|                 // do nothing
 | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @return true iff all yi received for i = 1,...,n . | ||||
|      */ | ||||
|     private boolean isStage2Complete() { | ||||
|         for (int j = 1; j <= n ; j++) { | ||||
|             if (j != id && ys[j - 1] == null) | ||||
|                 return false; | ||||
|         } | ||||
|         return true; | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
|     /** | ||||
|      * stage3 according to the protocol | ||||
|      *  1. if more than t players complain against a player Pi he is disqualified. | ||||
|      *  2. Pi broadcasts the share Sij for each complaining player Pj. | ||||
|      *  3. if any of the revealed shares fails the verification test, player Pi is disqualified. | ||||
|      *  4. set QUAL to be the set of non-disqualified players. | ||||
|      */ | ||||
|     private void stage3(){ | ||||
| 
 | ||||
|         // broadcasts Sij for each complaint against Pid
 | ||||
|         for (int j = 1 ; j <= complainStates[id - 1].length;j++) { | ||||
|             switch (complainStates[id - 1][j - 1]) { | ||||
|                 case Waiting: | ||||
|                     user.broadcast(Mail.Type.SECRET, SecretMessage.newBuilder() | ||||
|                             .setSecret(getShare(j).asMessage()) | ||||
|                             .build()); | ||||
|                     complainStates[id - 1][j - 1] = ComplainState.NonDisqualified; | ||||
|                     break; | ||||
|                 default: | ||||
|                     break; | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         // wait until there is no complaint waiting for answer
 | ||||
|         for (int i = 0; i < complainStates.length;i++){ | ||||
|             for (int j = 0 ; j < complainStates[i].length;j++){ | ||||
|                 while (complainStates[i][j].equals(ComplainState.Waiting)){ | ||||
|                     try { | ||||
|                         Thread.sleep(300); | ||||
|                     } catch (InterruptedException e) { | ||||
|                         // do nothing
 | ||||
|                     } | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         // add each non-disqualified player to QUAL
 | ||||
|         boolean nonDisqualified; | ||||
|         for (int i = 1; i <= complainStates.length;i++){ | ||||
|             nonDisqualified = true; | ||||
|             for (int j = 1 ; j <= complainStates[i - 1].length;j++){ | ||||
|                 nonDisqualified &= complainStates[i - 1][j - 1].equals(ComplainState.Disqualified); | ||||
|             } | ||||
|             if(nonDisqualified){ | ||||
|                 QUAL.add(i); | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * stage4 according to the protocol | ||||
|      *  1. public value y is computed as y = multiplication of yi mod p for i in QUAL | ||||
|      *  2. public verification values are computed as Ak = multiplication of Aik mod p for i in QUAL for k = 0,...,t | ||||
|      *  3. Pj sets is share of the secret as xj = sum of Sij mod q for i in QUAL | ||||
|      */ | ||||
|     private void stage4(){ | ||||
|         this.y = zpstar.zero(); | ||||
|         for (int i : QUAL) { | ||||
|             this.y = zpstar.add(this.y , ys[i - 1]); | ||||
|         } | ||||
|         BigInteger commitment; | ||||
|         for (int k = 0; k <= t ; k++){ | ||||
|             commitment = zpstar.zero(); | ||||
|             for (int i : QUAL) { | ||||
|                 commitment = zpstar.add(commitment,commitmentsArray[i - 1][k]); | ||||
|             } | ||||
|             commitments[k] = commitment; | ||||
|         } | ||||
| 
 | ||||
|         BigInteger xj = BigInteger.ZERO; | ||||
|         for (int i : QUAL) { | ||||
|             xj = xj.add(shares[i - 1].y); | ||||
|         } | ||||
|         this.share = new Polynomial.Point(BigInteger.valueOf(id) , xj.mod(q)); | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public BigInteger getY() { | ||||
|         return y; | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public BigInteger[] getCommitments() { | ||||
|         return Arrays.clone(commitments); | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
|     private enum ComplainState{ | ||||
|         Non, Waiting,Disqualified,NonDisqualified | ||||
|     } | ||||
| 
 | ||||
|     private class Handler implements Network.MailHandler { | ||||
| 
 | ||||
|         private Handler() {} | ||||
| 
 | ||||
|         void handelSecretMessage(Mail mail) throws InvalidProtocolBufferException { | ||||
|             if(shares[mail.getSender() - 1] == null) { | ||||
|                 SecretMessage secretMessage = SecretMessage.parseFrom(mail.getMessage()); | ||||
|                 Polynomial.Point secret = new Polynomial.Point(secretMessage.getSecret()); | ||||
|                 if(mail.getIsPrivate()){ | ||||
|                     shares[mail.getSender() - 1] = secret; | ||||
|                 }else{ | ||||
|                     int i = mail.getSender(); | ||||
|                     int j = secret.x.intValue(); | ||||
|                     switch (complainStates[i - 1][j - 1]){ | ||||
|                         case Waiting: | ||||
|                             if(isValidSecret(secret,i)){ | ||||
|                                 complainStates[i - 1][j - 1] = ComplainState.NonDisqualified; | ||||
|                             }else{ | ||||
|                                 complainStates[i - 1][j - 1] = ComplainState.Disqualified; | ||||
|                             } | ||||
|                             break; | ||||
|                         default: | ||||
|                             break; | ||||
|                     } | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         void handelCommitmentMessage(Mail mail) throws InvalidProtocolBufferException { | ||||
|             if(!mail.getIsPrivate()) { //broadcast only
 | ||||
|                 CommitmentMessage commitmentMessage = CommitmentMessage.parseFrom(mail.getMessage()); | ||||
|                 if (commitmentsArray[mail.getSender() - 1][commitmentMessage.getK()] == null) { | ||||
|                     BigInteger commitment = new BigInteger(commitmentMessage.getCommitment().toByteArray()); | ||||
|                     commitmentsArray[mail.getSender() - 1][commitmentMessage.getK()] = commitment; | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         void handelYMessage(Mail mail) throws InvalidProtocolBufferException { | ||||
|             if(!mail.getIsPrivate()) { //broadcast only
 | ||||
|                 if (ys[mail.getSender() - 1] == null) { | ||||
|                     YMessage yMessage = YMessage.parseFrom(mail.getMessage()); | ||||
|                     BigInteger y = new BigInteger(yMessage.getY().toByteArray()); | ||||
|                     ys[mail.getSender() - 1] = y; | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         void handelComplaintMessage(Mail mail) throws InvalidProtocolBufferException { | ||||
|             int id = user.getID(); | ||||
|             if(!mail.getIsPrivate()) { //broadcast only
 | ||||
|                 ComplaintMessage complaintMessage = ComplaintMessage.parseFrom(mail.getMessage()); | ||||
|                 int i = complaintMessage.getId(); | ||||
|                 int j = mail.getSender(); | ||||
|                 switch (complainStates[i - 1][j - 1]){ | ||||
|                     case Non: | ||||
|                         complainStates[i - 1][j - 1] = ComplainState.Waiting; | ||||
|                         break; | ||||
|                     default: | ||||
|                         break; | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         @Override | ||||
|         public void handel(Mail mail) throws InvalidProtocolBufferException { | ||||
|            switch (mail.getType()){ | ||||
|                case SECRET: | ||||
|                    handelSecretMessage(mail); | ||||
|                    break; | ||||
|                case COMMITMENT: | ||||
|                    handelCommitmentMessage(mail); | ||||
|                    break; | ||||
|                case Y: | ||||
|                    handelYMessage(mail); | ||||
|                    break; | ||||
|                case COMPLAINT: | ||||
|                    handelComplaintMessage(mail); | ||||
|                    break; | ||||
|                default: | ||||
|                    break; | ||||
|            } | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  | @ -0,0 +1,216 @@ | |||
| package JointFeldmanProtocol; | ||||
| 
 | ||||
| import Communication.Network; | ||||
| import Communication.User; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharing; | ||||
| import meerkat.protobuf.DKGMessages.*; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.HashSet; | ||||
| import java.util.Random; | ||||
| import java.util.Set; | ||||
| import java.util.Arrays; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/5/2016. | ||||
|  * | ||||
|  * an implementation of a version of Pedersen's distributed key generation protocol | ||||
|  */ | ||||
| public class DistributedKeyGeneration extends VerifiableSecretSharing implements Runnable{ | ||||
| 
 | ||||
|     private final int id; | ||||
| 
 | ||||
|     private final Set<Integer> QUAL; // set of all non-disqualified parties
 | ||||
|     private final BigInteger[] finalCommitments; // public verification values
 | ||||
| 
 | ||||
|     private Polynomial.Point share; // final share of the secrete
 | ||||
|     private BigInteger y; // final public value
 | ||||
| 
 | ||||
|     private final DistributedKeyGenerationMessageHandler handler; | ||||
| 
 | ||||
|     public DistributedKeyGeneration(int t, int n, BigInteger zi, Random random, BigInteger p, BigInteger q, BigInteger g | ||||
|             , User user) { | ||||
|         super(t, n, zi, random, p, q, g,user); | ||||
|         this.handler = (DistributedKeyGenerationMessageHandler) user.getMessageHandler(); | ||||
|         this.id = user.getID(); | ||||
|         this.QUAL = new HashSet<Integer>(); | ||||
|         this.finalCommitments = new BigInteger[t + 1]; | ||||
|         Arrays.fill(this.finalCommitments,zpstar.zero()); | ||||
|     } | ||||
|     public DistributedKeyGeneration(int t, int n, BigInteger zi, Random random, BigInteger p, BigInteger q, BigInteger g | ||||
|             , Network network) { | ||||
|         this(t,n,zi,random,p,q,g,network.connect(new DistributedKeyGenerationMessageHandler(t,n,g,new Zpstar(p)))); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * use for simulate real distributed protocol | ||||
|      */ | ||||
|     @Override | ||||
|     public void run() { | ||||
|         user.getReceiverThread().start(); | ||||
|         stage1(); | ||||
|         stage2(); | ||||
|         stage3(); | ||||
|         stage4(); | ||||
|         user.getReceiverThread().interrupt(); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * stage1 according to the protocol | ||||
|      *  1. Pi broadcasts Aik for k = 0,...,t. | ||||
|      *  2. Pi computes the shares Sij for j = 1,...,n and sends Sij secretly to Pj. | ||||
|      */ | ||||
|     protected void stage1(){ | ||||
|         super.run(); | ||||
|         while (!handler.isStage1Complete()){ | ||||
|             try { | ||||
|                 Thread.sleep(300); | ||||
|             } catch (InterruptedException e) { | ||||
|                 // do nothing
 | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * stage2 according to the protocol | ||||
|      *  Pj verifies all the shares he received (using isValidSecret) | ||||
|      *  if check fails for an index i, Pj broadcasts a complaint against Pi. | ||||
|      *  Pj broadcasts yj value at the end of this stage | ||||
|      */ | ||||
|     private void stage2(){ | ||||
|         ComplaintMessage complaint; | ||||
|         for (int i = 1; i <= n ; i++ ){ | ||||
|             if(id != i && !handler.isValidSecret(i)) { | ||||
|                 //message = new Message(Type.Complaint, j)
 | ||||
|                 complaint = ComplaintMessage.newBuilder() | ||||
|                                 .setId(i) | ||||
|                                 .build(); | ||||
|                 user.broadcast(Mail.Type.COMPLAINT,complaint); | ||||
|             } | ||||
|         } | ||||
|         //broadcast done message after all complaints
 | ||||
|         DoneMessage doneMessage = DoneMessage.newBuilder().build(); | ||||
|         user.broadcast(Mail.Type.DONE,doneMessage); | ||||
| 
 | ||||
|         while (!handler.isStage2Complete()){ | ||||
|             try { | ||||
|                 Thread.sleep(300); | ||||
|             } catch (InterruptedException e) { | ||||
|                 // do nothing
 | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
|     protected void answerComplaint(int j){ | ||||
|         user.broadcast(Mail.Type.SECRET, SecretMessage.newBuilder() | ||||
|                 .setSecret(getShare(j).asMessage()) | ||||
|                 .build()); | ||||
|     } | ||||
|     /** | ||||
|      * stage3 according to the protocol | ||||
|      *  1. if more than t players complain against a player Pi he is disqualified. | ||||
|      *  2. Pi broadcasts the share Sij for each complaining player Pj. | ||||
|      *  3. if any of the revealed shares fails the verification test, player Pi is disqualified. | ||||
|      *  4. set QUAL to be the set of non-disqualified players. | ||||
|      */ | ||||
|     private void stage3(){ | ||||
|         DistributedKeyGenerationMessageHandler.ComplainState[][] complainStates = handler.getComplainStates(); | ||||
|         // broadcasts Sij for each complaint against Pid
 | ||||
|         for (int j = 1; j <= complainStates[id - 1].length; j++) { | ||||
|             switch (complainStates[id - 1][j - 1]) { | ||||
|                 case Waiting: | ||||
|                     answerComplaint(j); | ||||
|                     break; | ||||
|                 default: | ||||
|                     break; | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         // wait until there is no complaint waiting for answer
 | ||||
|         for (int i = 0; i < complainStates.length; i++){ | ||||
|             for (int j = 0; j < complainStates[i].length; j++){ | ||||
|                 while (complainStates[i][j].equals(DistributedKeyGenerationMessageHandler.ComplainState.Waiting)){ | ||||
|                     try { | ||||
|                         Thread.sleep(300); | ||||
|                     } catch (InterruptedException e) { | ||||
|                         // do nothing
 | ||||
|                     } | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         // add each non-disqualified player to QUAL
 | ||||
|         boolean nonDisqualified; | ||||
|         int counter; | ||||
|         for (int i = 1; i <= complainStates.length; i++){ | ||||
|             nonDisqualified = true; | ||||
|             counter = 0; | ||||
|             for (int j = 1; j <= complainStates[i - 1].length; j++){ | ||||
|                 switch (complainStates[i - 1][j - 1]) { | ||||
|                     case Non: | ||||
|                         break; | ||||
|                     case NonDisqualified: | ||||
|                         counter++; | ||||
|                     default: | ||||
|                         nonDisqualified = false; | ||||
|                 } | ||||
|                 if(!nonDisqualified) | ||||
|                     break; | ||||
|             } | ||||
|             if(nonDisqualified && counter <= t){ | ||||
|                 QUAL.add(i); | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * stage4 according to the protocol | ||||
|      *  1. public value y is computed as y = multiplication of yi mod p for i in QUAL | ||||
|      *  2. public verification values are computed as Ak = multiplication of Aik mod p for i in QUAL for k = 0,...,t | ||||
|      *  3. Pj sets is share of the secret as xj = sum of Sij mod q for i in QUAL | ||||
|      */ | ||||
|     private void stage4(){ | ||||
|         this.y = zpstar.zero(); | ||||
|         for (int i : QUAL) { | ||||
|             this.y = zpstar.add(this.y , handler.getY(i)); | ||||
|         } | ||||
| 
 | ||||
|         BigInteger[] commitments; | ||||
| 
 | ||||
|         for (int i : QUAL) { | ||||
|             commitments = handler.getCommitments(i); | ||||
|             for (int k = 0; k <= t; k++){ | ||||
|                 this.finalCommitments[k] = zpstar.add(this.finalCommitments[k],commitments[k]); | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         BigInteger xj = BigInteger.ZERO; | ||||
|         for (int i : QUAL) { | ||||
|             if( i == id){ | ||||
|                 xj = xj.add(super.getShare(i).y); | ||||
|             }else{ | ||||
|                 xj = xj.add(handler.getShare(i).y); | ||||
|             } | ||||
|         } | ||||
|         this.share = new Polynomial.Point(BigInteger.valueOf(id) , xj.mod(q)); | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public BigInteger getY() { | ||||
|         return y; | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public BigInteger[] getCommitments() { | ||||
|         return Arrays.copyOf(finalCommitments, finalCommitments.length); | ||||
|     } | ||||
| 
 | ||||
|     public Polynomial.Point getShare() { | ||||
|         return share; | ||||
|     } | ||||
| 
 | ||||
| } | ||||
|  | @ -0,0 +1,161 @@ | |||
| package JointFeldmanProtocol; | ||||
| 
 | ||||
| import Communication.MessageHandler; | ||||
| import Communication.Network; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharing; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharingMessageHandler; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.SecretSharingMessageHandler; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/16/2016. | ||||
|  */ | ||||
| public class DistributedKeyGenerationMessageHandler implements MessageHandler { | ||||
| 
 | ||||
|     protected enum ComplainState{ | ||||
|         Non, Waiting,Disqualified,NonDisqualified | ||||
|     } | ||||
| 
 | ||||
|     protected final VerifiableSecretSharingMessageHandler[] vssHandlers; | ||||
|     protected final ComplainState[][] complainStates; // complainStates[i][j] == state of Pj's complaint against Pi
 | ||||
|     protected final BigInteger g; | ||||
|     protected final Zpstar zpstar; | ||||
|     protected final int n; | ||||
|     private final boolean[] doneFlags; | ||||
| 
 | ||||
|     public DistributedKeyGenerationMessageHandler(int t, int n, BigInteger g, Zpstar zpstar) { | ||||
|         this.g = g; | ||||
|         this.zpstar = zpstar; | ||||
|         this.n = n; | ||||
|         this.doneFlags = new boolean[n]; | ||||
|         this.vssHandlers = new VerifiableSecretSharingMessageHandler[n]; | ||||
|         for (int i = 1; i <= n ; i++){ | ||||
|             vssHandlers[i - 1] = new VerifiableSecretSharingMessageHandler(t); | ||||
|         } | ||||
|         this.complainStates = new ComplainState[n][n]; | ||||
|         for (int i = 0; i < n; i ++){ | ||||
|             for (int j = 0 ; j < n ; j ++) | ||||
|                 this.complainStates[i][j] = ComplainState.Non; | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @return true iff all shares and commitments were received | ||||
|      */ | ||||
|     protected boolean isStage1Complete(){ | ||||
|         for (int i = 1 ; i <= n ; i++){ | ||||
|             if(vssHandlers[i - 1].getShare() == null) | ||||
|                 return false; | ||||
|         } | ||||
| 
 | ||||
|         BigInteger[] commitments; | ||||
|         for (int i = 0; i < vssHandlers.length; i++){ | ||||
|             commitments = vssHandlers[i].getCommitments(); | ||||
|             for (int j = 0; j < commitments.length; j++){ | ||||
|                 if(commitments[j] == null) | ||||
|                     return false; | ||||
|             } | ||||
|         } | ||||
|         return true; | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @return true iff all flags in doneFlags are true | ||||
|      */ | ||||
|     protected boolean isStage2Complete() { | ||||
|         for (int j = 0; j < n ; j++) { | ||||
|             if(!doneFlags[j]) | ||||
|                 return false; | ||||
|         } | ||||
|         return true; | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelComplaintMessage(int sender,  boolean isBroadcast, DKGMessages.ComplaintMessage complaintMessage) { | ||||
|         if(isBroadcast){ | ||||
|             int i = complaintMessage.getId(); | ||||
|             int j = sender; | ||||
|             switch (complainStates[i - 1][j - 1]){ | ||||
|                 case Non: | ||||
|                     complainStates[i - 1][j - 1] = ComplainState.Waiting; | ||||
|                     break; | ||||
|                 default: | ||||
|                     break; | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelDoneMessage(int sender,  boolean isBroadcast, DKGMessages.DoneMessage doneMessage) { | ||||
|         if(isBroadcast) | ||||
|             this.doneFlags[sender - 1] = true; | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelCommitmentMessage(int sender,  boolean isBroadcast, DKGMessages.CommitmentMessage commitmentMessage) { | ||||
|         vssHandlers[sender - 1].handelCommitmentMessage(sender, isBroadcast, commitmentMessage); | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
|     /** | ||||
|      * @param secret | ||||
|      * @param i | ||||
|      * @return g ^ Sij == verify(j,Ai,zpstar) (mod p) | ||||
|      */ | ||||
|     private boolean isValidSecret(Polynomial.Point secret, int i){ | ||||
|         int j = secret.x.intValue(); | ||||
|         BigInteger[] commitments = vssHandlers[i - 1].getCommitments(); | ||||
|         return zpstar.multiply(g,secret.y).equals(VerifiableSecretSharing.verify(j,commitments,zpstar)); | ||||
|     } | ||||
| 
 | ||||
|     protected boolean isValidSecret(int i){ | ||||
|         return isValidSecret(getShare(i),i); | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelSecretMessage(int sender,  boolean isBroadcast, DKGMessages.SecretMessage secretMessage) { | ||||
|         vssHandlers[sender - 1].handelSecretMessage(sender, isBroadcast, secretMessage); | ||||
|         if(isBroadcast){ | ||||
|             Polynomial.Point secret = SecretSharingMessageHandler.extractSecret(secretMessage); | ||||
|             int i = sender; | ||||
|             int j = secret.x.intValue(); | ||||
|             switch (complainStates[i - 1][j - 1]){ | ||||
|                 case Waiting: | ||||
|                     if(isValidSecret(secret,i)){ | ||||
|                         complainStates[i - 1][j - 1] = ComplainState.NonDisqualified; | ||||
|                     }else{ | ||||
|                         complainStates[i - 1][j - 1] = ComplainState.Disqualified; | ||||
|                     } | ||||
|                     break; | ||||
|                 default: | ||||
|                     break; | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelDoubleSecretMessage(int sender, boolean isBroadcast, DKGMessages.DoubleSecretMessage doubleSecretMessage) { | ||||
|         // ignore
 | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
|     protected ComplainState[][] getComplainStates() { | ||||
|         return complainStates; | ||||
|     } | ||||
| 
 | ||||
|     protected BigInteger getY(int i){ | ||||
|         return vssHandlers[i - 1].getY(); | ||||
|     } | ||||
| 
 | ||||
|     protected BigInteger[] getCommitments(int i){ | ||||
|         return vssHandlers[i -1].getCommitments(); | ||||
|     } | ||||
| 
 | ||||
|     protected Polynomial.Point getShare(int i){ | ||||
|         return vssHandlers[i-1].getShare(); | ||||
|     } | ||||
| } | ||||
|  | @ -1,124 +0,0 @@ | |||
| package JointFeldmanProtocol; | ||||
| 
 | ||||
| import com.google.protobuf.InvalidProtocolBufferException; | ||||
| import com.google.protobuf.Message; | ||||
| import meerkat.protobuf.DKGMessages.*; | ||||
| import java.util.Queue; | ||||
| import java.util.concurrent.ArrayBlockingQueue; | ||||
| /** | ||||
|  * Created by Tzlil on 2/7/2016. | ||||
|  * JointFeldamn protocol assumes all parties can communicate throw broadcast chanel | ||||
|  * and private chanel (for each pair) | ||||
|  * this class simulates it | ||||
|  */ | ||||
| public class Network { | ||||
| 
 | ||||
|     private final User[] users; | ||||
|     private final int n; | ||||
|     private final Queue<Integer> availableIDs; | ||||
| 
 | ||||
| 
 | ||||
|     public Network(int n) { | ||||
|         this.n = n; | ||||
|         this.users = new User[n]; | ||||
|         this.availableIDs = new ArrayBlockingQueue<Integer>(n); | ||||
|         for (int id = 1; id <= n; id++){ | ||||
|             availableIDs.add(id); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     public User connect(MailHandler messageHandler){ | ||||
|         Integer id = availableIDs.poll(); | ||||
|         if (id == null) | ||||
|             return null; | ||||
|         users[id - 1] = new User(id,messageHandler); | ||||
|         return users[id - 1]; | ||||
|     } | ||||
| 
 | ||||
|     private boolean sendMessage(User sender,int destination,Mail.Type type,Message message){ | ||||
|         if(destination < 1 || destination > n) | ||||
|             return false; | ||||
|         User user = users[destination - 1]; | ||||
|         if (user == null) | ||||
|             return false; | ||||
|         Mail mail = Mail.newBuilder() | ||||
|                 .setSender(sender.getID()) | ||||
|                 .setDestination(destination) | ||||
|                 .setIsPrivate(true) | ||||
|                 .setType(type) | ||||
|                 .setMessage(message.toByteString()) | ||||
|                 .build(); | ||||
|         return user.mailbox.add(mail); | ||||
|     } | ||||
| 
 | ||||
|     private void sendBroadcast(User sender,Mail.Type type,Message message){ | ||||
|         User user; | ||||
|         int ID = sender.ID; | ||||
|         Mail mail = Mail.newBuilder() | ||||
|                 .setSender(sender.getID()) | ||||
|                 .setDestination(0) | ||||
|                 .setIsPrivate(false) | ||||
|                 .setType(type) | ||||
|                 .setMessage(message.toByteString()) | ||||
|                 .build(); | ||||
|         for (int i = 0 ; i < n ; i++){ | ||||
|             if (i + 1 == ID) { | ||||
|                 continue; | ||||
|             } | ||||
|             user = users[i]; | ||||
|             user.mailbox.add(mail); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     public class User{ | ||||
|         private final MailHandler messageHandler; | ||||
|         private final Queue<Mail> mailbox; | ||||
|         private final int ID; | ||||
|         private final Thread receiverThread; | ||||
|         public User(int ID, MailHandler messageHandler) { | ||||
|             this.mailbox = new ArrayBlockingQueue<Mail>(1 << n); | ||||
|             this.ID = ID; | ||||
|             this.messageHandler = messageHandler; | ||||
|             this.receiverThread = new Thread(new Receiver()); | ||||
|         } | ||||
| 
 | ||||
|         public boolean send(int id, Mail.Type type,Message message){ | ||||
|             return sendMessage(this,id,type,message); | ||||
|         } | ||||
|         public void broadcast(Mail.Type type,Message message){ | ||||
|             sendBroadcast(this,type,message); | ||||
|         } | ||||
|         public int getID() { | ||||
|             return ID; | ||||
|         } | ||||
|         public Thread getReceiverThread(){ | ||||
|             return receiverThread; | ||||
|         } | ||||
|         private class Receiver implements Runnable{ | ||||
|             @Override | ||||
|             public void run() { | ||||
|                 while (true){ | ||||
|                     if (!mailbox.isEmpty()){ | ||||
|                         try { | ||||
|                             messageHandler.handel(mailbox.poll()); | ||||
|                         } catch (InvalidProtocolBufferException e) { | ||||
|                             e.printStackTrace(); | ||||
|                         } | ||||
|                     }else{ | ||||
|                         try { | ||||
|                             Thread.sleep(30); | ||||
|                         } catch (InterruptedException e) { | ||||
|                             // do nothing
 | ||||
|                         } | ||||
|                     } | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
| 
 | ||||
|     } | ||||
| 
 | ||||
|     public interface MailHandler { | ||||
|         public void handel(Mail mail) throws InvalidProtocolBufferException; | ||||
|     } | ||||
| } | ||||
|  | @ -0,0 +1,68 @@ | |||
| package SecureDistributedKeyGeneration; | ||||
| 
 | ||||
| import Communication.Network; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharing; | ||||
| import JointFeldmanProtocol.DistributedKeyGeneration; | ||||
| import com.google.protobuf.ByteString; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.Random; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/17/2016. | ||||
|  */ | ||||
| public class SecureDistributedKeyGeneration extends DistributedKeyGeneration { | ||||
| 
 | ||||
|     VerifiableSecretSharing verifiableSecretSharing; | ||||
| 
 | ||||
|     public SecureDistributedKeyGeneration(int t, int n, BigInteger zi, Random random, BigInteger p, BigInteger q, BigInteger g | ||||
|             ,BigInteger h, Network network) { | ||||
|         super(t, n, zi, random, p, q, g, network.connect(new SecureDistributedKeyGenerationMessageHandler(t,n,g,new Zpstar(p)))); | ||||
|         this.verifiableSecretSharing = new VerifiableSecretSharing(t,n,new BigInteger(q.bitLength(), random).mod(q),random,p,q,h,user); | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     protected void computeAndSendSecrets() { | ||||
|         DKGMessages.SecretMessage[] secretMessages1 = prepareSecretMessages(); | ||||
|         DKGMessages.SecretMessage[] secretMessages2 = verifiableSecretSharing.prepareSecretMessages(); | ||||
|         DKGMessages.DoubleSecretMessage doubleSecretMessage; | ||||
| 
 | ||||
|         for (int j = 1; j <= n ; j++ ){ | ||||
|             doubleSecretMessage = DKGMessages.DoubleSecretMessage.newBuilder() | ||||
|                     .setS1(secretMessages1[j - 1]) | ||||
|                     .setS1(secretMessages2[j - 1]) | ||||
|                     .build(); | ||||
|             user.send(j, DKGMessages.Mail.Type.SECRET,doubleSecretMessage); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public DKGMessages.CommitmentMessage[] prepareCommitmentMessages() { | ||||
|         DKGMessages.CommitmentMessage[] commitmentMessages = new DKGMessages.CommitmentMessage[t + 1]; | ||||
|         BigInteger[] commitments2 = verifiableSecretSharing.getCommitments(); | ||||
|         for (int k = 0; k <= t ; k ++) { | ||||
|             commitmentMessages[k] = DKGMessages.CommitmentMessage.newBuilder() | ||||
|                     .setK(k) | ||||
|                     .setCommitment(ByteString.copyFrom(zpstar.add(commitments[k],commitments2[k]).toByteArray())) | ||||
|                     .build(); | ||||
|         } | ||||
|         return commitmentMessages; | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     protected void answerComplaint(int j) { | ||||
|         DKGMessages.SecretMessage secretMessage1 = DKGMessages.SecretMessage.newBuilder() | ||||
|                 .setSecret(getShare(j).asMessage()) | ||||
|                 .build(); | ||||
|         DKGMessages.SecretMessage secretMessage2 = DKGMessages.SecretMessage.newBuilder() | ||||
|                 .setSecret(verifiableSecretSharing.getShare(j).asMessage()) | ||||
|                 .build(); | ||||
| 
 | ||||
|         user.broadcast(DKGMessages.Mail.Type.SECRET, DKGMessages.DoubleSecretMessage.newBuilder() | ||||
|                 .setS1(secretMessage1) | ||||
|                 .setS2(secretMessage2) | ||||
|                 .build()); | ||||
|     } | ||||
| } | ||||
|  | @ -0,0 +1,61 @@ | |||
| package SecureDistributedKeyGeneration; | ||||
| 
 | ||||
| import Communication.Network; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharing; | ||||
| import JointFeldmanProtocol.DistributedKeyGenerationMessageHandler; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.SecretSharingMessageHandler; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/17/2016. | ||||
|  */ | ||||
| public class SecureDistributedKeyGenerationMessageHandler extends DistributedKeyGenerationMessageHandler { | ||||
| 
 | ||||
|     private final SecretSharingMessageHandler[] ssHandlers; | ||||
|     public SecureDistributedKeyGenerationMessageHandler(int t, int n, BigInteger g, Zpstar zpstar) { | ||||
|         super(t, n, g, zpstar); | ||||
|         this.ssHandlers = new SecretSharingMessageHandler[n]; | ||||
|     } | ||||
| 
 | ||||
|     private boolean isValidSecret(Polynomial.Point secret1,Polynomial.Point secret2,int i){ | ||||
|         int j = secret1.x.intValue(); | ||||
|         BigInteger[] commitments = vssHandlers[i - 1].getCommitments(); | ||||
|         return zpstar.multiply(g,zpstar.add(secret1.y,secret2.y)).equals(VerifiableSecretSharing.verify(j,commitments,zpstar)); | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     protected boolean isValidSecret(int i) { | ||||
|         return isValidSecret(getShare(i),ssHandlers[i - 1].getShare(),i); | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelDoubleSecretMessage(int sender,  boolean isBroadcast, DKGMessages.DoubleSecretMessage doubleSecretMessage) { | ||||
|         if(!isBroadcast){ | ||||
|             this.handelSecretMessage(sender,isBroadcast,doubleSecretMessage.getS1()); | ||||
|             ssHandlers[sender - 1].handelSecretMessage(sender,isBroadcast,doubleSecretMessage.getS2()); | ||||
|         }else{ | ||||
|             Polynomial.Point secret1 = SecretSharingMessageHandler.extractSecret(doubleSecretMessage.getS1()); | ||||
|             Polynomial.Point secret2 = SecretSharingMessageHandler.extractSecret(doubleSecretMessage.getS2()); | ||||
|             int i = sender; | ||||
|             int j = secret1.x.intValue(); | ||||
|             switch (complainStates[i - 1][j - 1]){ | ||||
|                 case Waiting: | ||||
|                     if(isValidSecret(secret1,secret2,i)){ | ||||
|                         complainStates[i - 1][j - 1] = ComplainState.NonDisqualified; | ||||
|                     }else{ | ||||
|                         complainStates[i - 1][j - 1] = ComplainState.Disqualified; | ||||
|                     } | ||||
|                     break; | ||||
|                 default: | ||||
|                     break; | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
| } | ||||
|  | @ -1,4 +1,4 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing; | ||||
| package ShamirSecretSharing; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| 
 | ||||
|  | @ -1,4 +1,4 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing; | ||||
| package ShamirSecretSharing; | ||||
| 
 | ||||
| import com.google.protobuf.ByteString; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
|  | @ -9,8 +9,8 @@ import java.math.BigInteger; | |||
|  * Created by Tzlil on 1/27/2016. | ||||
|  */ | ||||
| public class Polynomial implements Comparable<Polynomial> { | ||||
|     protected static final Polynomial ZERO = new Polynomial(new BigInteger[]{BigInteger.ZERO}); // neutral for add
 | ||||
|     protected static final Polynomial ONE = new Polynomial(new BigInteger[]{BigInteger.ONE});   // neutral for mul
 | ||||
|     public static final Polynomial ZERO = new Polynomial(new BigInteger[]{BigInteger.ZERO}); // neutral for add
 | ||||
|     public static final Polynomial ONE = new Polynomial(new BigInteger[]{BigInteger.ONE});   // neutral for mul
 | ||||
|     private final int degree; | ||||
|     private final BigInteger[] coefficients; | ||||
| 
 | ||||
|  | @ -45,7 +45,7 @@ public class Polynomial implements Comparable<Polynomial> { | |||
| 
 | ||||
|     @Override | ||||
|     public String toString() { | ||||
|         return "FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests{" + | ||||
|         return "ShamirSecretSharing.PolynomialTests{" + | ||||
|                 "degree=" + degree + | ||||
|                 ", coefficients=" + java.util.Arrays.toString(coefficients) + | ||||
|                 '}'; | ||||
|  | @ -101,7 +101,7 @@ public class Polynomial implements Comparable<Polynomial> { | |||
| 
 | ||||
|     /** | ||||
|      * @param other | ||||
|      * @return new FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests of degree max(this degree,other degree) s.t for all x in Z | ||||
|      * @return new ShamirSecretSharing.PolynomialTests of degree max(this degree,other degree) s.t for all x in Z | ||||
|      *         new.image(x) = this.image(x) + other.image(x) | ||||
|      */ | ||||
|     public Polynomial add(Polynomial other){ | ||||
|  | @ -123,7 +123,7 @@ public class Polynomial implements Comparable<Polynomial> { | |||
| 
 | ||||
|     /** | ||||
|      * @param constant | ||||
|      * @return new FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests of degree this.degree s.t for all x in Z | ||||
|      * @return new ShamirSecretSharing.PolynomialTests of degree this.degree s.t for all x in Z | ||||
|      *         new.image(x) = constant * this.image(x) | ||||
|      */ | ||||
|     public Polynomial mul(BigInteger constant){ | ||||
|  | @ -138,7 +138,7 @@ public class Polynomial implements Comparable<Polynomial> { | |||
| 
 | ||||
|     /** | ||||
|      * @param other | ||||
|      * @return new FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests of degree this degree + other degree + 1 s.t for all x in Z | ||||
|      * @return new ShamirSecretSharing.PolynomialTests of degree this degree + other degree + 1 s.t for all x in Z | ||||
|      *         new.image(x) = this.image(x) * other.image(x) | ||||
|      */ | ||||
|     public Polynomial mul(Polynomial other){ | ||||
|  | @ -1,6 +1,10 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing; | ||||
| package ShamirSecretSharing; | ||||
| 
 | ||||
| 
 | ||||
| import Communication.Network; | ||||
| import Communication.User; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.Random; | ||||
| 
 | ||||
|  | @ -8,11 +12,12 @@ import java.util.Random; | |||
|  * Created by Tzlil on 1/27/2016. | ||||
|  * an implementation of Shamire's secret sharing scheme | ||||
|  */ | ||||
| public class SecretSharing { | ||||
| public class SecretSharing implements Runnable{ | ||||
|     protected final int t; | ||||
|     protected final int n; | ||||
|     protected final BigInteger q; | ||||
| 
 | ||||
|     protected final User user; // send and receive messages throw network
 | ||||
|     private final Polynomial polynomial; | ||||
| 
 | ||||
|     /** | ||||
|  | @ -24,11 +29,16 @@ public class SecretSharing { | |||
|      * @param x      secret, chosen from Zq | ||||
|      * @param random use for generate random polynomial | ||||
|      */ | ||||
|     public SecretSharing(int t, int n, BigInteger x, Random random,BigInteger q) { | ||||
|     public SecretSharing(int t, int n, BigInteger x, Random random, BigInteger q, Network network) { | ||||
|         this(t,n,x,random,q,network.connect(new SecretSharingMessageHandler())); | ||||
|     } | ||||
| 
 | ||||
|     public SecretSharing(int t, int n, BigInteger x, Random random, BigInteger q, User user) { | ||||
|         this.q = q; | ||||
|         this.t = t; | ||||
|         this.n = n; | ||||
|         this.polynomial = generateRandomPolynomial(x,random); | ||||
|         this.user = user; | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|  | @ -53,18 +63,11 @@ public class SecretSharing { | |||
|      * | ||||
|      * @return polynomial.image(i)%q | ||||
|      */ | ||||
|     protected final Polynomial.Point getShare(int i){ | ||||
|     public Polynomial.Point getShare(int i){ | ||||
|         assert (i > 0 && i <= n); | ||||
|         return new Polynomial.Point(BigInteger.valueOf(i), polynomial, q); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * use for test only | ||||
|      */ | ||||
|     public Polynomial.Point getShareForTest(int i){ | ||||
|         return  getShare(i); | ||||
|     } | ||||
| 
 | ||||
|     /** | ||||
|      * @param shares - subset of the original shares | ||||
|      * | ||||
|  | @ -99,8 +102,31 @@ public class SecretSharing { | |||
|         return q; | ||||
|     } | ||||
| 
 | ||||
|     protected Polynomial getPolynomial() { | ||||
|     public Polynomial getPolynomial() { | ||||
| 
 | ||||
|         return polynomial; | ||||
|     } | ||||
| 
 | ||||
|     public DKGMessages.SecretMessage[] prepareSecretMessages(){ | ||||
|         DKGMessages.SecretMessage[] secretMessages = new DKGMessages.SecretMessage[n]; | ||||
|         for (int j = 1; j <= n ; j++ ){ | ||||
|             secretMessages[j - 1] = DKGMessages.SecretMessage.newBuilder() | ||||
|                     .setSecret(getShare(j).asMessage()) | ||||
|                     .build(); | ||||
|         } | ||||
|         return secretMessages; | ||||
|     } | ||||
| 
 | ||||
|     protected void computeAndSendSecrets(){ | ||||
|         DKGMessages.SecretMessage[] secretMessages = prepareSecretMessages(); | ||||
|         for (int j = 1; j <= n ; j++ ){ | ||||
|             user.send(j, DKGMessages.Mail.Type.SECRET,secretMessages[j - 1]); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void run() { | ||||
|         // computes and sends shares
 | ||||
|         computeAndSendSecrets(); | ||||
|     } | ||||
| } | ||||
|  | @ -0,0 +1,47 @@ | |||
| package ShamirSecretSharing; | ||||
| 
 | ||||
| import Communication.MessageHandler; | ||||
| import Communication.Network; | ||||
| import meerkat.protobuf.DKGMessages; | ||||
| 
 | ||||
| /** | ||||
|  * Created by Tzlil on 2/16/2016. | ||||
|  */ | ||||
| public class SecretSharingMessageHandler implements MessageHandler{ | ||||
| 
 | ||||
|     private Polynomial.Point share; | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelComplaintMessage(int sender,  boolean isBroadcast, DKGMessages.ComplaintMessage complaintMessage) { | ||||
|         // ignore
 | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelDoneMessage(int sender,  boolean isBroadcast, DKGMessages.DoneMessage doneMessage) { | ||||
|         // ignore
 | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelCommitmentMessage(int sender,  boolean isBroadcast, DKGMessages.CommitmentMessage commitmentMessage) { | ||||
|         // ignore
 | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelDoubleSecretMessage(int sender,  boolean isBroadcast, DKGMessages.DoubleSecretMessage doubleSecretMessage) { | ||||
|         // ignore
 | ||||
|     } | ||||
| 
 | ||||
|     @Override | ||||
|     public void handelSecretMessage(int sender,  boolean isBroadcast, DKGMessages.SecretMessage secretMessage) { | ||||
|         if(!isBroadcast) | ||||
|             this.share = extractSecret(secretMessage); | ||||
|     } | ||||
| 
 | ||||
|     public static Polynomial.Point extractSecret(DKGMessages.SecretMessage secretMessage){ | ||||
|         return new Polynomial.Point(secretMessage.getSecret()); | ||||
|     } | ||||
| 
 | ||||
|     public Polynomial.Point getShare() { | ||||
|         return share; | ||||
|     } | ||||
| } | ||||
|  | @ -1,6 +1,7 @@ | |||
| package FeldmanVerifiableSecretSharing; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import Communication.Network; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| import org.junit.Before; | ||||
| import org.junit.Test; | ||||
|  | @ -31,11 +32,12 @@ public class VerifiableSecretSharingTest { | |||
|         }while (!g.equals(ZERO) && !zpstar.multiply(g,q).equals(ZERO));// sample from QRZp*
 | ||||
|         int t = 8; | ||||
|         int n = 20; | ||||
| 
 | ||||
|         Network network; | ||||
|         verifiableSecretSharingArray = new VerifiableSecretSharing[tests]; | ||||
|         for (int i = 0; i < verifiableSecretSharingArray.length; i++){ | ||||
|             network = new Network(n); | ||||
|             verifiableSecretSharingArray[i] = new VerifiableSecretSharing(t,n | ||||
|                     ,new BigInteger(q.bitLength(),random).mod(q),random,p,q,g); | ||||
|                     ,new BigInteger(q.bitLength(),random).mod(q),random,p,q,g,network); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|  | @ -47,7 +49,7 @@ public class VerifiableSecretSharingTest { | |||
|         BigInteger[] commitments = verifiableSecretSharing.getCommitments(); | ||||
|         BigInteger[] verifications = new BigInteger[n]; | ||||
|         for (int i = 1 ; i <= shares.length; i ++){ | ||||
|             shares[i - 1] = verifiableSecretSharing.getShareForTest(i); | ||||
|             shares[i - 1] = verifiableSecretSharing.getShare(i); | ||||
|             verifications[i - 1] = VerifiableSecretSharing.verify(i,commitments,zpstar); | ||||
|         } | ||||
|         BigInteger expected; | ||||
|  |  | |||
|  | @ -1,10 +1,16 @@ | |||
| package JointFeldmanProtocol; | ||||
| 
 | ||||
| import Communication.Network; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.SecretSharing; | ||||
| import FeldmanVerifiableSecretSharing.VerifiableSecretSharing; | ||||
| import org.factcenter.qilin.primitives.concrete.Zpstar; | ||||
| import org.junit.Before; | ||||
| import org.junit.Test; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.ArrayList; | ||||
| import java.util.List; | ||||
| import java.util.Random; | ||||
| 
 | ||||
| /** | ||||
|  | @ -13,45 +19,98 @@ import java.util.Random; | |||
| public class DKGTest { | ||||
| 
 | ||||
| 
 | ||||
|     DKG[] dkgs; | ||||
|     Thread[] threads; | ||||
|     int tests = 1 << 10; | ||||
|     Random random; | ||||
| 
 | ||||
|     DistributedKeyGeneration[][] dkgsArrays; | ||||
|     Thread[][] threadsArrays; | ||||
|     int tests = 10; | ||||
|     BigInteger p = BigInteger.valueOf(2903); | ||||
|     BigInteger q = p.subtract(BigInteger.ONE).divide(BigInteger.valueOf(2)); | ||||
|     BigInteger[] secrets; | ||||
|     @Before | ||||
|     public void settings(){ | ||||
|         BigInteger p = BigInteger.valueOf(2903); | ||||
|         BigInteger q = p.subtract(BigInteger.ONE).divide(BigInteger.valueOf(2)); | ||||
|         Zpstar zpstar = new Zpstar(p); | ||||
|         random = new Random(); | ||||
|         Random random = new Random(); | ||||
|         BigInteger g; | ||||
|         int t = 9; | ||||
|         int n = 20; | ||||
|         BigInteger ZERO = zpstar.zero(); | ||||
|         do{ | ||||
|             g = zpstar.sample(random); | ||||
|         }while (!g.equals(ZERO) && !zpstar.multiply(g,q).equals(ZERO));// sample from QRZp*
 | ||||
|         int t = 8; | ||||
|         int n = 20 | ||||
|                 ; | ||||
|         Network network = new Network(n); | ||||
|         dkgs = new DKG[n]; | ||||
|         threads = new Thread[n]; | ||||
|         for (int i = 0 ; i < n ; i++) { | ||||
|             dkgs[i] = new DKG(t, n, new BigInteger(q.bitLength(), random).mod(q), random, p, q, g, network); | ||||
|             threads[i] = new Thread(dkgs[i]); | ||||
|         dkgsArrays = new DistributedKeyGeneration[tests][n]; | ||||
|         threadsArrays = new Thread[tests][n]; | ||||
|         secrets = new BigInteger[tests]; | ||||
|         for (int test = 0; test < tests; test++) { | ||||
|             do { | ||||
|                 g = zpstar.sample(random); | ||||
|             } while (!g.equals(ZERO) && !zpstar.multiply(g, q).equals(ZERO));// sample from QRZp*
 | ||||
|             secrets[test] = BigInteger.ZERO; | ||||
|             Network network = new Network(n); | ||||
|             for (int i = 0; i < n; i++) { | ||||
|                 BigInteger secret = new BigInteger(q.bitLength(), random).mod(q); | ||||
|                 secrets[test] = secrets[test].add(secret).mod(q); | ||||
|                 dkgsArrays[test][i] = new DistributedKeyGeneration(t, n,secret, random, p, q, g, network); | ||||
|                 threadsArrays[test][i] = new Thread(dkgsArrays[test][i]); | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     @Test | ||||
|     public void DKGTest() throws Exception { | ||||
|         for (int i = 0 ; i < threads.length ; i++){ | ||||
|     public void oneTest(Thread[] threads, DistributedKeyGeneration[] dkgs,BigInteger secret) throws Exception { | ||||
|         for (int i = 0; i < threads.length ; i++){ | ||||
|             threads[i].start(); | ||||
|         } | ||||
|         for (int i = 0 ; i < threads.length ; i++){ | ||||
|         for (int i = 0; i < threads.length ; i++){ | ||||
|             threads[i].join(); | ||||
|         } | ||||
|         int t = dkgs[0].getT(); | ||||
|         int n = dkgs[0].getN(); | ||||
| 
 | ||||
|         Zpstar zpstar = dkgs[0].getZpstar(); | ||||
|         BigInteger g = dkgs[0].getGenerator(); | ||||
| 
 | ||||
|         // got the right public value
 | ||||
|         assert(zpstar.multiply(g,secret).equals(dkgs[0].getY())); | ||||
| 
 | ||||
|         // assert all players agreed on the same public value
 | ||||
|         for (int i = 0; i < dkgs.length - 1 ; i++){ | ||||
|             assert (dkgs[i].getY().equals(dkgs[i+1].getY())); | ||||
|         } | ||||
| 
 | ||||
|         // assert valid verification values
 | ||||
|         BigInteger expected,verification; | ||||
|         for (int j = 1; j <= dkgs.length ; j++){ | ||||
|             expected = zpstar.multiply(g, dkgs[j - 1].getShare().y); | ||||
|             verification = VerifiableSecretSharing.verify(j, dkgs[j - 1].getCommitments(),zpstar); | ||||
|             assert (expected.equals(verification)); | ||||
|         } | ||||
| 
 | ||||
| 
 | ||||
|         // restore the secret from t + 1 random shares
 | ||||
|         Polynomial.Point[] shares = new Polynomial.Point[t + 1]; | ||||
|         for (int i = 0 ; i < shares.length; i++){ | ||||
|             shares[i] = dkgs[i].getShare(); | ||||
|         } | ||||
|         //List<Integer> indexes = new ArrayList<Integer>(n);
 | ||||
|         //for (int i = 1 ; i <= n; i ++){
 | ||||
|         //    indexes.add(i);
 | ||||
|         //}
 | ||||
|         //Random random = new Random();
 | ||||
|         //int index;
 | ||||
|         //for (int i = 0 ; i < shares.length ; i++){
 | ||||
|         //    index = indexes.remove(random.nextInt(indexes.size()));
 | ||||
|         //    shares[i] = dkgs[index - 1].getShare();
 | ||||
|         //}
 | ||||
|         BigInteger calculatedSecret = SecretSharing.getSecrete(shares).mod(q); | ||||
| 
 | ||||
|         Polynomial polynomial = Polynomial.ZERO; | ||||
|         for (int i = 0 ; i < dkgs.length ; i++){ | ||||
|             polynomial  = polynomial.add(dkgs[i].getPolynomial()); | ||||
|         } | ||||
| 
 | ||||
|         assert (calculatedSecret.equals(secret)); | ||||
| 
 | ||||
|     } | ||||
| 
 | ||||
|     @Test | ||||
|     public void secretSharingTest() throws Exception { | ||||
|         for (int i = 0 ; i < dkgsArrays.length; i ++){ | ||||
|             oneTest(threadsArrays[i],dkgsArrays[i],secrets[i]); | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  |  | |||
|  | @ -1,5 +1,5 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests; | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| package ShamirSecretSharing.PolynomialTests; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import org.junit.Before; | ||||
| import org.junit.Test; | ||||
| 
 | ||||
|  | @ -1,6 +1,6 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests; | ||||
| package ShamirSecretSharing.PolynomialTests; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import org.junit.Before; | ||||
| import org.junit.Test; | ||||
| 
 | ||||
|  | @ -1,6 +1,6 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests; | ||||
| package ShamirSecretSharing.PolynomialTests; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import org.junit.Before; | ||||
| import org.junit.Test; | ||||
| 
 | ||||
|  | @ -1,6 +1,6 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests; | ||||
| package ShamirSecretSharing.PolynomialTests; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| import org.junit.Before; | ||||
| import org.junit.Test; | ||||
| 
 | ||||
|  | @ -1,6 +1,6 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests; | ||||
| package ShamirSecretSharing.PolynomialTests; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.Polynomial; | ||||
| import ShamirSecretSharing.Polynomial; | ||||
| 
 | ||||
| import java.math.BigInteger; | ||||
| import java.util.Random; | ||||
|  | @ -1,6 +1,7 @@ | |||
| package FeldmanVerifiableSecretSharing.ShamirSecretSharing; | ||||
| package ShamirSecretSharing; | ||||
| 
 | ||||
| import FeldmanVerifiableSecretSharing.ShamirSecretSharing.PolynomialTests.Utils; | ||||
| import Communication.Network; | ||||
| import Communication.User; | ||||
| import org.factcenter.qilin.primitives.CyclicGroup; | ||||
| import org.factcenter.qilin.primitives.concrete.Zn; | ||||
| import org.junit.Before; | ||||
|  | @ -26,14 +27,17 @@ public class SecretSharingTest { | |||
|     public void settings(){ | ||||
|         BigInteger p = BigInteger.valueOf(2903); | ||||
|         group = new Zn(p); | ||||
|         int t = 10; | ||||
|         int t = 9; | ||||
|         int n = 20; | ||||
|         random = new Random(); | ||||
|         secretSharingArray = new SecretSharing[tests]; | ||||
|         secrets = new BigInteger[tests]; | ||||
|         Network network; | ||||
| 
 | ||||
|         for (int i = 0; i < secretSharingArray.length; i++){ | ||||
|             secrets[i] = group.sample(random); | ||||
|             secretSharingArray[i] = new SecretSharing(t,n,secrets[i],random,p); | ||||
|             network = new Network(n); | ||||
|             secretSharingArray[i] = new SecretSharing(t,n,secrets[i],random,p,network); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|  | @ -8,7 +8,7 @@ message Mail{ | |||
|     enum Type { | ||||
|         SECRET = 0; | ||||
|         COMMITMENT = 1; | ||||
|         Y = 2; | ||||
|         DONE = 2; | ||||
|         COMPLAINT = 3; | ||||
|     } | ||||
|     int32 sender = 1; | ||||
|  | @ -26,14 +26,17 @@ message SecretMessage { | |||
|     Point secret = 1; | ||||
| } | ||||
| 
 | ||||
| message DoubleSecretMessage{ | ||||
|     SecretMessage s1 = 1; | ||||
|     SecretMessage s2 = 2; | ||||
| } | ||||
| 
 | ||||
| message CommitmentMessage{ | ||||
|     int32 k = 1; | ||||
|     bytes commitment = 2; | ||||
| } | ||||
| 
 | ||||
| message YMessage{ | ||||
|     bytes y = 1; | ||||
| } | ||||
| message DoneMessage{} | ||||
| 
 | ||||
| message ComplaintMessage{ | ||||
|     int32 id = 1; | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue