aboutsummaryrefslogtreecommitdiff
path: root/src/main/java
diff options
context:
space:
mode:
authorFlorian Dold <florian.dold@gmail.com>2013-10-15 10:49:30 +0000
committerFlorian Dold <florian.dold@gmail.com>2013-10-15 10:49:30 +0000
commit4cbf5731c126695bbd964552b92e7ae9151561e1 (patch)
tree5c7bbdd7ddf08dad3a67e29190e246055db01775 /src/main/java
parent3b0a0f129a4e78671d6ccfaf7cb1b74295846375 (diff)
downloadgnunet-java-4cbf5731c126695bbd964552b92e7ae9151561e1.tar.gz
gnunet-java-4cbf5731c126695bbd964552b92e7ae9151561e1.zip
- started implementing new crypto
- $-expansion and XDG in config
Diffstat (limited to 'src/main/java')
-rw-r--r--src/main/java/org/gnunet/construct/MessageLoader.java2
-rw-r--r--src/main/java/org/gnunet/identity/Identity.java22
-rw-r--r--src/main/java/org/gnunet/identity/messages/CreateRequestMessage.java4
-rw-r--r--src/main/java/org/gnunet/identity/messages/GetDefaultMessage.java2
-rw-r--r--src/main/java/org/gnunet/identity/messages/ResultCodeMessage.java1
-rw-r--r--src/main/java/org/gnunet/identity/messages/SetDefaultMessage.java4
-rw-r--r--src/main/java/org/gnunet/identity/messages/StartMessage.java4
-rw-r--r--src/main/java/org/gnunet/identity/messages/UpdateListMessage.java4
-rw-r--r--src/main/java/org/gnunet/util/Configuration.java114
-rw-r--r--src/main/java/org/gnunet/util/CryptoECC.java513
-rw-r--r--src/main/java/org/gnunet/util/HashCode.java2
-rw-r--r--src/main/java/org/gnunet/util/crypto/Curve25519.java69
-rw-r--r--src/main/java/org/gnunet/util/crypto/DsaPrng.java86
-rw-r--r--src/main/java/org/gnunet/util/crypto/EcdhePrivateKey.java4
-rw-r--r--src/main/java/org/gnunet/util/crypto/EcdhePublicKey.java20
-rw-r--r--src/main/java/org/gnunet/util/crypto/EcdsaPrivateKey.java35
-rw-r--r--src/main/java/org/gnunet/util/crypto/EcdsaPublicKey.java27
-rw-r--r--src/main/java/org/gnunet/util/crypto/EcdsaSignature.java (renamed from src/main/java/org/gnunet/voting/messages/CertificateDenyMessage.java)18
-rw-r--r--src/main/java/org/gnunet/util/crypto/Ed25519.java133
-rw-r--r--src/main/java/org/gnunet/util/crypto/EddsaPrivateKey.java83
-rw-r--r--src/main/java/org/gnunet/util/crypto/EddsaPublicKey.java29
-rw-r--r--src/main/java/org/gnunet/util/crypto/EddsaSignature.java94
-rw-r--r--src/main/java/org/gnunet/voting/Ballot.java74
-rw-r--r--src/main/java/org/gnunet/voting/BallotTool.java84
-rw-r--r--src/main/java/org/gnunet/voting/CertificateAuthorityDaemon.java70
-rw-r--r--src/main/java/org/gnunet/voting/CertifyGroupCommand.java129
-rw-r--r--src/main/java/org/gnunet/voting/CertifyGroupTool.java25
-rw-r--r--src/main/java/org/gnunet/voting/SubmitCommand.java6
-rw-r--r--src/main/java/org/gnunet/voting/TallyAuthorityDaemon.java8
-rw-r--r--src/main/java/org/gnunet/voting/messages/BallotRegisterFailureMessage.java2
-rw-r--r--src/main/java/org/gnunet/voting/messages/BallotRegisterSuccessMessage.java4
-rw-r--r--src/main/java/org/gnunet/voting/messages/CertificateGrantMessage.java19
-rw-r--r--src/main/java/org/gnunet/voting/messages/CertificateRequestMessage.java23
-rw-r--r--src/main/java/org/gnunet/voting/messages/SubmitMessage.java6
-rw-r--r--src/main/java/org/gnunet/voting/messages/SubmitSuccessMessage.java4
35 files changed, 795 insertions, 929 deletions
diff --git a/src/main/java/org/gnunet/construct/MessageLoader.java b/src/main/java/org/gnunet/construct/MessageLoader.java
index 71e2719..aa4b98a 100644
--- a/src/main/java/org/gnunet/construct/MessageLoader.java
+++ b/src/main/java/org/gnunet/construct/MessageLoader.java
@@ -46,7 +46,7 @@ public class MessageLoader {
46 46
47 47
48 /** 48 /**
49 * Thrown when a trying to serialize an object that is not registered as a union type. 49 * Thrown when trying to serialize an object that is not registered as a union type.
50 */ 50 */
51 public static class UnknownUnionException extends RuntimeException { 51 public static class UnknownUnionException extends RuntimeException {
52 public UnknownUnionException(String msg) { 52 public UnknownUnionException(String msg) {
diff --git a/src/main/java/org/gnunet/identity/Identity.java b/src/main/java/org/gnunet/identity/Identity.java
index 657a0b9..1450031 100644
--- a/src/main/java/org/gnunet/identity/Identity.java
+++ b/src/main/java/org/gnunet/identity/Identity.java
@@ -27,6 +27,8 @@ import org.gnunet.mq.Envelope;
27import org.gnunet.requests.RequestContainer; 27import org.gnunet.requests.RequestContainer;
28import org.gnunet.requests.SequentialRequestContainer; 28import org.gnunet.requests.SequentialRequestContainer;
29import org.gnunet.util.*; 29import org.gnunet.util.*;
30import org.gnunet.util.crypto.EcdsaPrivateKey;
31import org.gnunet.util.crypto.EcdsaPublicKey;
30import org.slf4j.Logger; 32import org.slf4j.Logger;
31import org.slf4j.LoggerFactory; 33import org.slf4j.LoggerFactory;
32 34
@@ -45,17 +47,17 @@ public class Identity {
45 47
46 public static class Ego { 48 public static class Ego {
47 private String name; 49 private String name;
48 private CryptoECC.PrivateKey privateKey; 50 private EcdsaPrivateKey privateKey;
49 51
50 public Ego(String egoName, CryptoECC.PrivateKey privateKey) { 52 public Ego(String egoName, EcdsaPrivateKey privateKey) {
51 this.name = egoName; 53 this.name = egoName;
52 this.privateKey = privateKey; 54 this.privateKey = privateKey;
53 } 55 }
54 public CryptoECC.PrivateKey getPrivateKey() { 56 public EcdsaPrivateKey getPrivateKey() {
55 return privateKey; 57 return privateKey;
56 } 58 }
57 public CryptoECC.PublicSignKey getPublicKey() { 59 public EcdsaPublicKey getPublicKey() {
58 return CryptoECC.computePublicKey(privateKey); 60 return privateKey.getPublicKey();
59 } 61 }
60 public String getName() { 62 public String getName() {
61 return name; 63 return name;
@@ -171,10 +173,10 @@ public class Identity {
171 } 173 }
172 174
173 public class CreateRequest extends IdentityRequest { 175 public class CreateRequest extends IdentityRequest {
174 final CryptoECC.PrivateKey privateKey; 176 final EcdsaPrivateKey privateKey;
175 IdentityContinuation cont; 177 IdentityContinuation cont;
176 String name; 178 String name;
177 CreateRequest(String name, CryptoECC.PrivateKey privateKey, IdentityContinuation cont) { 179 CreateRequest(String name, EcdsaPrivateKey privateKey, IdentityContinuation cont) {
178 this.cont = cont; 180 this.cont = cont;
179 this.privateKey = privateKey; 181 this.privateKey = privateKey;
180 this.name = name; 182 this.name = name;
@@ -200,7 +202,7 @@ public class Identity {
200 202
201 public static Ego getAnonymousEgo() { 203 public static Ego getAnonymousEgo() {
202 if (anonymousEgo == null) { 204 if (anonymousEgo == null) {
203 anonymousEgo = new Ego(null, CryptoECC.getAnonymous()); 205 anonymousEgo = new Ego(null, EcdsaPrivateKey.getAnonymous());
204 } 206 }
205 return anonymousEgo; 207 return anonymousEgo;
206 } 208 }
@@ -248,7 +250,7 @@ public class Identity {
248 * @return object for cancellation 250 * @return object for cancellation
249 */ 251 */
250 public Cancelable create(String name, IdentityContinuation cont) { 252 public Cancelable create(String name, IdentityContinuation cont) {
251 CryptoECC.PrivateKey privateKey = CryptoECC.PrivateKey.createRandom(); 253 EcdsaPrivateKey privateKey = EcdsaPrivateKey.createRandom();
252 return requests.addRequest(new CreateRequest(name, privateKey, cont)); 254 return requests.addRequest(new CreateRequest(name, privateKey, cont));
253 } 255 }
254 256
@@ -273,7 +275,7 @@ public class Identity {
273 return requests.addRequest(new DeleteRequest(name)); 275 return requests.addRequest(new DeleteRequest(name));
274 } 276 }
275 277
276 private Ego getEgoForKey(CryptoECC.PrivateKey privateKey) { 278 private Ego getEgoForKey(EcdsaPrivateKey privateKey) {
277 for (Ego ex : knownEgos) { 279 for (Ego ex : knownEgos) {
278 if (ex.privateKey.equals(privateKey)) { 280 if (ex.privateKey.equals(privateKey)) {
279 return ex; 281 return ex;
diff --git a/src/main/java/org/gnunet/identity/messages/CreateRequestMessage.java b/src/main/java/org/gnunet/identity/messages/CreateRequestMessage.java
index 475100c..dd67fa1 100644
--- a/src/main/java/org/gnunet/identity/messages/CreateRequestMessage.java
+++ b/src/main/java/org/gnunet/identity/messages/CreateRequestMessage.java
@@ -44,8 +44,8 @@ import org.gnunet.construct.NestedMessage;
44import org.gnunet.construct.UInt16; 44import org.gnunet.construct.UInt16;
45import org.gnunet.construct.UnionCase; 45import org.gnunet.construct.UnionCase;
46import org.gnunet.construct.ZeroTerminatedString; 46import org.gnunet.construct.ZeroTerminatedString;
47import org.gnunet.util.CryptoECC;
48import org.gnunet.util.GnunetMessage; 47import org.gnunet.util.GnunetMessage;
48import org.gnunet.util.crypto.EcdsaPrivateKey;
49 49
50@UnionCase(629) 50@UnionCase(629)
51public class CreateRequestMessage implements GnunetMessage.Body { 51public class CreateRequestMessage implements GnunetMessage.Body {
@@ -57,7 +57,7 @@ public class CreateRequestMessage implements GnunetMessage.Body {
57 @UInt16 57 @UInt16
58 public int reserved; 58 public int reserved;
59 @NestedMessage 59 @NestedMessage
60 public CryptoECC.PrivateKey privateKey; 60 public EcdsaPrivateKey privateKey;
61 @ZeroTerminatedString 61 @ZeroTerminatedString
62 public String name; 62 public String name;
63} 63}
diff --git a/src/main/java/org/gnunet/identity/messages/GetDefaultMessage.java b/src/main/java/org/gnunet/identity/messages/GetDefaultMessage.java
index fab5f33..eb44eba 100644
--- a/src/main/java/org/gnunet/identity/messages/GetDefaultMessage.java
+++ b/src/main/java/org/gnunet/identity/messages/GetDefaultMessage.java
@@ -80,11 +80,9 @@
80 80
81package org.gnunet.identity.messages; 81package org.gnunet.identity.messages;
82 82
83import org.gnunet.construct.NestedMessage;
84import org.gnunet.construct.UInt16; 83import org.gnunet.construct.UInt16;
85import org.gnunet.construct.UnionCase; 84import org.gnunet.construct.UnionCase;
86import org.gnunet.construct.ZeroTerminatedString; 85import org.gnunet.construct.ZeroTerminatedString;
87import org.gnunet.util.CryptoECC;
88import org.gnunet.util.GnunetMessage; 86import org.gnunet.util.GnunetMessage;
89 87
90@UnionCase(627) 88@UnionCase(627)
diff --git a/src/main/java/org/gnunet/identity/messages/ResultCodeMessage.java b/src/main/java/org/gnunet/identity/messages/ResultCodeMessage.java
index c761603..12bd55b 100644
--- a/src/main/java/org/gnunet/identity/messages/ResultCodeMessage.java
+++ b/src/main/java/org/gnunet/identity/messages/ResultCodeMessage.java
@@ -101,7 +101,6 @@
101package org.gnunet.identity.messages; 101package org.gnunet.identity.messages;
102 102
103import org.gnunet.construct.*; 103import org.gnunet.construct.*;
104import org.gnunet.util.CryptoECC;
105import org.gnunet.util.GnunetMessage; 104import org.gnunet.util.GnunetMessage;
106 105
107/** 106/**
diff --git a/src/main/java/org/gnunet/identity/messages/SetDefaultMessage.java b/src/main/java/org/gnunet/identity/messages/SetDefaultMessage.java
index bcdb233..484bde7 100644
--- a/src/main/java/org/gnunet/identity/messages/SetDefaultMessage.java
+++ b/src/main/java/org/gnunet/identity/messages/SetDefaultMessage.java
@@ -64,8 +64,8 @@ import org.gnunet.construct.NestedMessage;
64import org.gnunet.construct.UInt16; 64import org.gnunet.construct.UInt16;
65import org.gnunet.construct.UnionCase; 65import org.gnunet.construct.UnionCase;
66import org.gnunet.construct.ZeroTerminatedString; 66import org.gnunet.construct.ZeroTerminatedString;
67import org.gnunet.util.CryptoECC;
68import org.gnunet.util.GnunetMessage; 67import org.gnunet.util.GnunetMessage;
68import org.gnunet.util.crypto.EcdsaPrivateKey;
69 69
70 70
71/** 71/**
@@ -79,7 +79,7 @@ public class SetDefaultMessage implements GnunetMessage.Body {
79 @UInt16 79 @UInt16
80 public int reserved; 80 public int reserved;
81 @NestedMessage 81 @NestedMessage
82 public CryptoECC.PrivateKey privateKey; 82 public EcdsaPrivateKey privateKey;
83 @ZeroTerminatedString 83 @ZeroTerminatedString
84 public String serviceName; 84 public String serviceName;
85} 85}
diff --git a/src/main/java/org/gnunet/identity/messages/StartMessage.java b/src/main/java/org/gnunet/identity/messages/StartMessage.java
index b8fbbee..ffc0a08 100644
--- a/src/main/java/org/gnunet/identity/messages/StartMessage.java
+++ b/src/main/java/org/gnunet/identity/messages/StartMessage.java
@@ -60,11 +60,7 @@
60 60
61package org.gnunet.identity.messages; 61package org.gnunet.identity.messages;
62 62
63import org.gnunet.construct.NestedMessage;
64import org.gnunet.construct.UInt16;
65import org.gnunet.construct.UnionCase; 63import org.gnunet.construct.UnionCase;
66import org.gnunet.construct.ZeroTerminatedString;
67import org.gnunet.util.CryptoECC;
68import org.gnunet.util.GnunetMessage; 64import org.gnunet.util.GnunetMessage;
69 65
70@UnionCase(624) 66@UnionCase(624)
diff --git a/src/main/java/org/gnunet/identity/messages/UpdateListMessage.java b/src/main/java/org/gnunet/identity/messages/UpdateListMessage.java
index f1fb8ab..f30d18a 100644
--- a/src/main/java/org/gnunet/identity/messages/UpdateListMessage.java
+++ b/src/main/java/org/gnunet/identity/messages/UpdateListMessage.java
@@ -84,8 +84,8 @@ import org.gnunet.construct.NestedMessage;
84import org.gnunet.construct.UInt16; 84import org.gnunet.construct.UInt16;
85import org.gnunet.construct.UnionCase; 85import org.gnunet.construct.UnionCase;
86import org.gnunet.construct.ZeroTerminatedString; 86import org.gnunet.construct.ZeroTerminatedString;
87import org.gnunet.util.CryptoECC;
88import org.gnunet.util.GnunetMessage; 87import org.gnunet.util.GnunetMessage;
88import org.gnunet.util.crypto.EcdsaPrivateKey;
89 89
90 90
91/** 91/**
@@ -98,7 +98,7 @@ public class UpdateListMessage implements GnunetMessage.Body{
98 @UInt16 98 @UInt16
99 public int endOfList; 99 public int endOfList;
100 @NestedMessage 100 @NestedMessage
101 public CryptoECC.PrivateKey privateKey; 101 public EcdsaPrivateKey privateKey;
102 @ZeroTerminatedString 102 @ZeroTerminatedString
103 public String egoName; 103 public String egoName;
104} 104}
diff --git a/src/main/java/org/gnunet/util/Configuration.java b/src/main/java/org/gnunet/util/Configuration.java
index 43290d0..2ea2d0e 100644
--- a/src/main/java/org/gnunet/util/Configuration.java
+++ b/src/main/java/org/gnunet/util/Configuration.java
@@ -21,6 +21,7 @@
21package org.gnunet.util; 21package org.gnunet.util;
22 22
23import com.google.common.base.Charsets; 23import com.google.common.base.Charsets;
24import com.google.common.base.Joiner;
24import com.google.common.base.Optional; 25import com.google.common.base.Optional;
25import com.google.common.collect.HashBasedTable; 26import com.google.common.collect.HashBasedTable;
26import com.google.common.collect.Table; 27import com.google.common.collect.Table;
@@ -33,6 +34,7 @@ import java.io.File;
33import java.io.FileWriter; 34import java.io.FileWriter;
34import java.io.IOException; 35import java.io.IOException;
35import java.nio.charset.Charset; 36import java.nio.charset.Charset;
37import java.nio.file.Path;
36import java.util.*; 38import java.util.*;
37import java.util.regex.Matcher; 39import java.util.regex.Matcher;
38import java.util.regex.Pattern; 40import java.util.regex.Pattern;
@@ -73,23 +75,95 @@ public class Configuration {
73 75
74 76
75 /** 77 /**
76 * Expand an expression of the form "$FOO/BAR" to "DIRECTORY/BAR" where 78 * Expand an expression of the form "$FOO/BAR" to "DIRECTORY/BAR"
77 * either in the "PATHS" section or the environment "FOO" is set to 79 * where either in the "PATHS" section or the environtment "FOO" is
78 * "DIRECTORY". 80 * set to "DIRECTORY". We also support default expansion,
81 * i.e. ${VARIABLE:-default} will expand to $VARIABLE if VARIABLE is
82 * set in PATHS or the environment, and otherwise to "default". Note
83 * that "default" itself can also be a $-expression, thus
84 * "${VAR1:-{$VAR2}}" will expand to VAR1 and if that is not defined
85 * to VAR2.
79 * 86 *
80 * @param orig string to $-expand 87 * @param orig string to $-expand
81 * @return $-expanded string 88 * @return $-expanded string
82 */ 89 */
83 public String expandDollar(String orig) { 90 public String expandDollar(String orig) {
84 Map<String, String> env = System.getenv(); 91
85 for (final Map.Entry<String, String> e : env.entrySet()) { 92 if (orig.length() < 2 || !orig.startsWith("$"))
86 orig = orig.replace("$" + e.getKey(), e.getValue()); 93 return orig;
94 String defaultVal;
95 String substVal;
96 String outside;
97
98 if (orig.charAt(1) == '{')
99 {
100 int open = 1;
101 int p = 2;
102 while (open != 0) {
103 if (orig.length() == p) {
104 logger.debug("unclosed '{'");
105 break;
106 }
107 if (orig.charAt(p) == '{') {
108 open++;
109 } else if (orig.charAt(p) == '}') {
110 open--;
111 }
112 p++;
113 }
114 if (p != 2) {
115 String inside = orig.substring(2, p-1);
116 String[] parts = inside.split(Pattern.quote(":-"), 2);
117 if (parts.length == 1) {
118 substVal = orig.substring(2, p-1);
119 defaultVal = "";
120 } else {
121 substVal = parts[0];
122 defaultVal = parts[1];
123 }
124 if (orig.length() > p) {
125 outside = orig.substring(p, orig.length());
126 } else {
127 outside = "";
128 }
129 } else {
130 outside = "";
131 substVal = "";
132 defaultVal = "";
133 }
134 } else {
135 defaultVal = "";
136 int p = 1;
137 for (; p < orig.length(); p++) {
138 if (orig.charAt(p) == '\\' || orig.charAt(p) == '/') {
139 break;
140 }
141 }
142 if (p != orig.length()) {
143 substVal = orig.substring(1, p);
144 outside = orig.substring(p, orig.length());
145 } else {
146 substVal = orig.substring(1, orig.length());
147 outside = "";
148 }
87 } 149 }
88 150
89 for (final Map.Entry<String, String> e : sections.row("PATHS").entrySet()) { 151 String result;
90 orig = orig.replace("$" + e.getKey(), e.getValue()); 152
153 Map<String, String> env = System.getenv();
154 if (env.containsKey(substVal)) {
155 result = env.get(substVal);
156 } else {
157 Optional<String> path = getValueString("PATHS", substVal);
158 if (path.isPresent()) {
159 result = path.get();
160 } else {
161 result = expandDollar(defaultVal);
162 }
91 } 163 }
92 return orig; 164
165 return result + outside;
166
93 } 167 }
94 168
95 /** 169 /**
@@ -382,9 +456,7 @@ public class Configuration {
382 456
383 457
384 public void loadDefaults() { 458 public void loadDefaults() {
385 Collection<File> dirs = new ArrayList<File>(5); 459 Collection<File> dirs = new ArrayList<File>();
386 dirs.add(new File("/usr/share/gnunet/config.d/"));
387 dirs.add(new File("/usr/local/share/gnunet/config.d/"));
388 String pfx = System.getenv("GNUNET_PREFIX"); 460 String pfx = System.getenv("GNUNET_PREFIX");
389 if (pfx != null) { 461 if (pfx != null) {
390 dirs.add(new File(pfx, "share/gnunet/config.d/")); 462 dirs.add(new File(pfx, "share/gnunet/config.d/"));
@@ -402,6 +474,24 @@ public class Configuration {
402 } 474 }
403 } 475 }
404 } 476 }
477 Collection<File> files = new ArrayList<File>();
478 String xdg = System.getenv("XDG_CONFIG_HOME");
479 if (xdg != null && !xdg.isEmpty()) {
480 File f = new File(xdg + "/gnunet.conf");
481 if (f.exists()) {
482 parse(f.getAbsolutePath());
483 }
484 }
485 }
486
487 /**
488 * Read a filename from the section.
489 * @param section
490 * @param option
491 * @return
492 */
493 public Optional<String> getValueFilename(String section, String option) {
494 return null;
405 } 495 }
406 496
407 public void deserialize(String str) { 497 public void deserialize(String str) {
diff --git a/src/main/java/org/gnunet/util/CryptoECC.java b/src/main/java/org/gnunet/util/CryptoECC.java
deleted file mode 100644
index a02cf70..0000000
--- a/src/main/java/org/gnunet/util/CryptoECC.java
+++ /dev/null
@@ -1,513 +0,0 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20
21package org.gnunet.util;
22
23import org.gnunet.construct.FixedSizeIntegerArray;
24import org.gnunet.construct.Message;
25
26import java.io.File;
27import java.io.IOError;
28import java.io.IOException;
29import java.math.BigInteger;
30import java.nio.ByteBuffer;
31import java.nio.file.Files;
32import java.nio.file.StandardOpenOption;
33import java.security.MessageDigest;
34import java.security.NoSuchAlgorithmException;
35import java.security.SecureRandom;
36import java.util.Arrays;
37import java.util.Random;
38
39/**
40 * Implementation of the Ed25519 public-key signature system. See http://ed25519.cr.yp.to/.
41 * Original Java version written and placed into the public domain by k3d3 (https://github.com/k3d3/ed25519-java).
42 */
43public class CryptoECC {
44 /**
45 * Private ECC key.
46 */
47 public static final class PrivateKey implements Message {
48 /**
49 * Value of the private key, represents a number modulo q.
50 * The number is stored as little endian.
51 */
52 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
53 public byte[] d;
54
55 /**
56 * Load a private key from the given file.
57 *
58 * @param privKeyFilename the private key file name
59 * @return the private key from the file
60 */
61 public static PrivateKey fromFile(String privKeyFilename) {
62 byte[] data;
63 try {
64 data = Files.readAllBytes(new File(privKeyFilename).toPath());
65 } catch (IOException e) {
66 throw new IOError(e);
67 }
68 if (data.length != 32)
69 return null;
70 PrivateKey privateKey = new PrivateKey();
71 privateKey.d = data;
72 return privateKey;
73 }
74
75 public static PrivateKey createRandom() {
76 PrivateKey privateKey = new PrivateKey();
77 privateKey.d = new byte[32];
78 SecureRandom r = new SecureRandom();
79 r.nextBytes(privateKey.d);
80 return privateKey;
81 }
82
83 public void write(String privKeyFilename) throws IOException {
84 File f = new File(privKeyFilename);
85 Files.write(f.toPath(), d, StandardOpenOption.CREATE_NEW);
86 }
87 }
88
89 /**
90 * Public ECC key.
91 */
92 public static final class PublicSignKey implements Message {
93 /**
94 * x-coordinate of the point on the curve.
95 * The number is stored as little endian.
96 */
97 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
98 public byte[] x;
99
100 /**
101 * y-coordinate of the point on the curve.
102 * The number is stored as little endian.
103 */
104 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
105 public byte[] y;
106
107 @Override
108 public String toString() {
109 byte[] data = encodepoint(asPoint());
110 return Strings.dataToString(data);
111 }
112
113 public BigInteger[] asPoint() {
114 return new BigInteger[]{decodeint(x), decodeint(y)};
115 }
116
117 public static PublicSignKey fromString(String s) {
118 PublicSignKey pk = new PublicSignKey();
119 byte[] data = Strings.stringToData(s, 32);
120 if (null == data)
121 return null;
122 BigInteger[] point = decodepoint(data);
123 pk.x = encodeint(point[0]);
124 pk.y = encodeint(point[1]);
125 return pk;
126 }
127
128 @Override
129 public boolean equals(Object o) {
130 if (this == o) return true;
131 if (o == null || getClass() != o.getClass()) return false;
132
133 PublicSignKey that = (PublicSignKey) o;
134
135 if (!Arrays.equals(x, that.x)) return false;
136 if (!Arrays.equals(y, that.y)) return false;
137
138 return true;
139 }
140
141 @Override
142 public int hashCode() {
143 int result = Arrays.hashCode(x);
144 result = 31 * result + Arrays.hashCode(y);
145 return result;
146 }
147 }
148
149 /**
150 * ECC Signature.
151 */
152 public static final class Signature implements Message {
153 /**
154 * R value of the signature in compressed form.
155 * The number is stored as little endian.
156 */
157 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
158 public byte[] r;
159
160 /**
161 * S-value of the signature.
162 * The number is stored as little endian.
163 */
164 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
165 public byte[] s;
166
167 @Override
168 public String toString() {
169 byte[] data = new byte[r.length + s.length];
170 System.arraycopy(r, 0, data, 0, r.length);
171 System.arraycopy(s, 0, data, r.length, s.length);
172 return Strings.dataToString(data);
173 }
174
175 public static Signature fromString(String s) {
176 Signature sig = new Signature();
177 sig.r = new byte[32];
178 sig.s = new byte[32];
179 byte[] data = Strings.stringToData(s, 64);
180 if (null == data) {
181 return null;
182 }
183 System.arraycopy(data, 0, sig.r, 0, 32);
184 System.arraycopy(data, 32, sig.s, 0, 32);
185 return sig;
186 }
187
188 /**
189 * Create a random signature that is invalid with
190 * very high probability.
191 *
192 * @return random signature, most probably invalid
193 */
194 public static Signature randomSignature() {
195 Random r = new Random();
196 Signature sig = new Signature();
197 sig.r = new byte[32];
198 sig.s = new byte[32];
199 r.nextBytes(sig.r);
200 r.nextBytes(sig.s);
201 return sig;
202 }
203 }
204
205 // curve parameter b
206 private static final int b = 256;
207 // curve parameter q
208 private static final BigInteger q = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819949");
209 // q-3
210 private static final BigInteger qm2 = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819947");
211 // q-3
212 private static final BigInteger qp3 = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819952");
213 private static final BigInteger l = new BigInteger("7237005577332262213973186563042994240857116359379907606001950938285454250989");
214 private static final BigInteger d = new BigInteger("-4513249062541557337682894930092624173785641285191125241628941591882900924598840740");
215 private static final BigInteger I = new BigInteger("19681161376707505956807079304988542015446066515923890162744021073123829784752");
216 private static final BigInteger By = new BigInteger("46316835694926478169428394003475163141307993866256225615783033603165251855960");
217 private static final BigInteger Bx = new BigInteger("15112221349535400772501151409588531511454012693041857206046113283949847762202");
218 private static final BigInteger[] B = {Bx.mod(q),By.mod(q)};
219 // 2^255
220 private static final BigInteger un = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819967");
221
222 static final private MessageDigest sha512;
223 static {
224 try {
225 sha512 = MessageDigest.getInstance("SHA-512");
226 } catch (NoSuchAlgorithmException e) {
227 throw new RuntimeException("SHA-512 not available");
228 }
229 }
230
231 /**
232 * Computes the multiplicative inverse of x modulo q using Euler's theorem.
233 *
234 * @param x the group element to invert
235 * @return the inverse of x modulo q
236 */
237 private static BigInteger inv(BigInteger x) {
238 return x.modPow(qm2, q);
239 }
240
241 /**
242 * Compute the x-component of a point on our curve from
243 * the y-coordinate.
244 *
245 * @param y the y-coordinate of a point
246 * @return the x-coordinate of the point (x,y) on the curve
247 */
248 private static BigInteger xrecover(BigInteger y) {
249 BigInteger y2 = y.multiply(y);
250 BigInteger xx = (y2.subtract(BigInteger.ONE)).multiply(inv(d.multiply(y2).add(BigInteger.ONE)));
251 BigInteger x = xx.modPow(qp3.divide(BigInteger.valueOf(8)), q);
252 if (!x.multiply(x).subtract(xx).mod(q).equals(BigInteger.ZERO)) x = (x.multiply(I).mod(q));
253 if (!x.mod(BigInteger.valueOf(2)).equals(BigInteger.ZERO)) x = q.subtract(x);
254 return x;
255 }
256
257 /**
258 * Implements the group operation (twisted Edwards addition) on our curve.
259 *
260 * @param P a point on the curve
261 * @param Q another point on the curve
262 * @return P+Q
263 */
264 private static BigInteger[] edwards(BigInteger[] P, BigInteger[] Q) {
265 BigInteger x1 = P[0];
266 BigInteger y1 = P[1];
267 BigInteger x2 = Q[0];
268 BigInteger y2 = Q[1];
269 BigInteger dtemp = d.multiply(x1).multiply(x2).multiply(y1).multiply(y2);
270 BigInteger x3 = ((x1.multiply(y2)).add((x2.multiply(y1)))).multiply(inv(BigInteger.ONE.add(dtemp)));
271 BigInteger y3 = ((y1.multiply(y2)).add((x1.multiply(x2)))).multiply(inv(BigInteger.ONE.subtract(dtemp)));
272 return new BigInteger[]{x3.mod(q), y3.mod(q)};
273 }
274
275 /**
276 * Multiply a point on the curve with a constant.
277 *
278 * @param P point on the curve
279 * @param e constant
280 * @return eP
281 */
282 private static BigInteger[] scalarmult(BigInteger[] P, BigInteger e) {
283 if (e.equals(BigInteger.ZERO)) {
284 return new BigInteger[]{BigInteger.ZERO, BigInteger.ONE};
285 }
286 BigInteger[] Q = scalarmult(P, e.shiftRight(1));
287 Q = edwards(Q, Q);
288 if (e.testBit(0)) Q = edwards(Q, P);
289 return Q;
290 }
291
292 /**
293 * Encode an integer to binary format.
294 *
295 * @param y integer to encode
296 * @return encoded integer as byte array
297 */
298 private static byte[] encodeint(BigInteger y) {
299 byte[] in = y.toByteArray();
300 // reverse the array
301 for (int i = 0; i < in.length / 2; i++) {
302 byte tmp = in[i];
303 in[i] = in[in.length - i - 1];
304 in[in.length - i - 1] = tmp;
305 }
306 return in;
307 }
308
309 /**
310 * Encode a point to binary format.
311 *
312 * @param P point to encode
313 * @return encoded point as byte array
314 */
315 private static byte[] encodepoint(BigInteger[] P) {
316 BigInteger x = P[0];
317 BigInteger y = P[1];
318 byte[] out = encodeint(y);
319 out[out.length-1] |= (x.testBit(0) ? 0x80 : 0);
320 return out;
321 }
322
323 /**
324 * Get return the i-th bit in the given array of bytes h.
325 *
326 * @param h array of bytes
327 * @param i bit index
328 * @return i-th bit in h
329 */
330 private static int bit(byte[] h, int i) {
331 return h[i/8] >> (i%8) & 1;
332 }
333
334 /**
335 * Compute from a private key the scalar value that yields the public key when
336 * multiplied with the generator point.
337 *
338 * @param sk private key
339 * @return public key coefficient
340 */
341 static private BigInteger computePublicKeyCoefficient(PrivateKey sk) {
342 byte[] h = sha512.digest(sk.d);
343 BigInteger a = BigInteger.valueOf(2).pow(b-2);
344 for (int i=3; i < (b - 2); i++) {
345 BigInteger apart = BigInteger.valueOf(2).pow(i).multiply(BigInteger.valueOf(bit(h,i)));
346 a = a.add(apart);
347 }
348 return a;
349 }
350
351 /**
352 * Derive the public key from the private key 'sk'.
353 *
354 * @param sk private key
355 * @return public key derived from 'sk'
356 */
357 static public PublicSignKey computePublicKey(PrivateKey sk) {
358 BigInteger a = computePublicKeyCoefficient(sk);
359 BigInteger[] A = scalarmult(B, a);
360 PublicSignKey publicKey = new PublicSignKey();
361 publicKey.x = encodeint(A[0]);
362 publicKey.y = encodeint(A[1]);
363 return publicKey;
364 }
365
366 /**
367 * Hash the data in m and return 2^h(m)
368 *
369 * @param m data to hash
370 * @return 2^h(m)
371 */
372 static private BigInteger Hint(byte[] m) {
373 final byte[] h = sha512.digest(m);
374 for (int i = 0; i < 32; i++) {
375 byte tmp = h[i];
376 h[i] = h[63 - i];
377 h[63 - i] = tmp;
378 }
379 return new BigInteger(1, h);
380 }
381
382 /**
383 * Sign a message.
384 *
385 * @param m the message to sign
386 * @param sk the private (secret) key
387 * @param pk the public key, derived from 'sk', but passed as a
388 * parameter for performance reasons
389 * @return a signature on m
390 */
391 public static Signature sign(byte[] m, PrivateKey sk, PublicSignKey pk) {
392 byte[] compressed_pk = encodepoint(new BigInteger[]{decodeint(pk.x), decodeint(pk.y)});
393 byte[] h = sha512.digest(sk.d);
394 BigInteger a = BigInteger.valueOf(2).pow(b-2);
395 for (int i = 3; i < (b - 2); i++) {
396 a = a.add(BigInteger.valueOf(2).pow(i).multiply(BigInteger.valueOf(bit(h,i))));
397 }
398 ByteBuffer rsub = ByteBuffer.allocate((b/8)+m.length);
399 rsub.put(h, b/8, b/4-b/8).put(m);
400 BigInteger r = Hint(rsub.array());
401 BigInteger[] R = scalarmult(B,r);
402
403 Signature sig = new Signature();
404 sig.r = encodepoint(R);
405
406 ByteBuffer buf = ByteBuffer.allocate(32 + compressed_pk.length + m.length);
407 buf.put(encodepoint(R)).put(compressed_pk).put(m);
408
409 BigInteger S = r.add(Hint(buf.array()).multiply(a)).mod(l);
410 sig.s = encodeint(S);
411
412 return sig;
413 }
414
415 /**
416 * Check if a point is on the curve.
417 *
418 * @param P point to check
419 * @return whether the point P is on the curve
420 */
421 private static boolean isoncurve(BigInteger[] P) {
422 BigInteger x = P[0];
423 BigInteger y = P[1];
424 BigInteger xx = x.multiply(x);
425 BigInteger yy = y.multiply(y);
426 BigInteger dxxyy = d.multiply(yy).multiply(xx);
427 return xx.negate().add(yy).subtract(BigInteger.ONE).subtract(dxxyy).mod(q).equals(BigInteger.ZERO);
428 }
429
430 /**
431 * Decode an integer from its binary form.
432 *
433 * @param s the binary form if the integer
434 * @return the decoded integer
435 */
436 private static BigInteger decodeint(byte[] s) {
437 byte[] out = new byte[s.length];
438 for (int i=0;i<s.length;i++) {
439 out[i] = s[s.length-1-i];
440 }
441 return new BigInteger(out).and(un);
442 }
443
444 /**
445 * Decode a curve point from its compressed form.
446 *
447 * @param s the compressed point data
448 * @return the uncompressed point, null if not a valid point
449 */
450 private static BigInteger[] decodepoint(byte[] s) {
451 byte[] ybyte = new byte[s.length];
452 for (int i=0;i<s.length;i++) {
453 ybyte[i] = s[s.length-1-i];
454 }
455 BigInteger y = new BigInteger(ybyte).and(un);
456 BigInteger x = xrecover(y);
457 if ((x.testBit(0)?1:0) != bit(s, b-1)) {
458 x = q.subtract(x);
459 }
460 BigInteger[] P = {x,y};
461 if (!isoncurve(P))
462 return null;
463 return P;
464 }
465
466 /**
467 * Verify the validity of a signature on a message.
468 *
469 * @param sig signature
470 * @param m message
471 * @param pk public key of the signature creator
472 * @return whether the signature is valid
473 */
474 public static boolean verify(Signature sig, byte[] m, PublicSignKey pk) {
475 BigInteger[] R = decodepoint(sig.r);
476 BigInteger[] A = new BigInteger[]{decodeint(pk.x), decodeint(pk.y)};
477 BigInteger S = decodeint(sig.s);
478 ByteBuffer Stemp = ByteBuffer.allocate(32 + 32 + m.length);
479 Stemp.put(encodepoint(R)).put(encodepoint(A)).put(m);
480 BigInteger h = Hint(Stemp.array());
481 BigInteger[] ra = scalarmult(B,S);
482 BigInteger[] rb = edwards(R,scalarmult(A,h));
483 return ra[0].equals(rb[0]) && ra[1].equals(rb[1]);
484 }
485
486 /**
487 * Derive key material from a public and a private ECC key.
488 *
489 * @param privateKey private key to use for the ECDH (x)
490 * @param publicKey public key to use for the ECDH (yG)
491 * @return key material (xyG)
492 */
493 public static HashCode ecdh(PrivateKey privateKey, PublicSignKey publicKey) {
494 BigInteger[] publicPoint = new BigInteger[]{decodeint(publicKey.x), decodeint(publicKey.y)};
495 BigInteger coeff = computePublicKeyCoefficient(privateKey);
496 BigInteger[] R = scalarmult(publicPoint, coeff);
497 // FIXME: this is *not* equivalent to the GNUnet C implementation, which hashes an s-expr
498 sha512.update(R[0].toByteArray());
499 return new HashCode(sha512.digest(R[1].toByteArray()));
500 }
501
502 /**
503 * Get the shared private key we use for anonymous users.
504 *
505 * @return "anonymous" private key
506 */
507 public static PrivateKey getAnonymous() {
508 PrivateKey privateKey = new PrivateKey();
509 privateKey.d = encodeint(BigInteger.ONE);
510 return privateKey;
511 }
512
513}
diff --git a/src/main/java/org/gnunet/util/HashCode.java b/src/main/java/org/gnunet/util/HashCode.java
index 2ae127d..63ab11d 100644
--- a/src/main/java/org/gnunet/util/HashCode.java
+++ b/src/main/java/org/gnunet/util/HashCode.java
@@ -96,4 +96,6 @@ public class HashCode implements Message {
96 public String toString() { 96 public String toString() {
97 return Strings.dataToString(data); 97 return Strings.dataToString(data);
98 } 98 }
99
100
99} \ No newline at end of file 101} \ No newline at end of file
diff --git a/src/main/java/org/gnunet/util/crypto/Curve25519.java b/src/main/java/org/gnunet/util/crypto/Curve25519.java
new file mode 100644
index 0000000..86e6949
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/Curve25519.java
@@ -0,0 +1,69 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20
21package org.gnunet.util.crypto;
22
23
24import java.math.BigInteger;
25
26/**
27 * Java-only implementation of arithmetic on DJBs Curve25519.
28 * The curve is a Montgomery curve, and we use coordinates in
29 * Montgomery form.
30 * Very, very slow.
31 */
32public class Curve25519 {
33 private BigInteger X;
34 private BigInteger Z;
35
36 private BigInteger B = new BigInteger("486662");
37
38 // curve parameter q = 255^(-19)
39 private static final BigInteger q = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819949");
40
41
42 public Curve25519(BigInteger X, BigInteger Z) {
43 this.X = X;
44 this.Z = Z;
45 }
46
47 public Curve25519 scalarmult(BigInteger e) {
48 if (e.equals(BigInteger.ZERO)) {
49 return new Curve25519(BigInteger.ZERO, BigInteger.ONE);
50 }
51 Curve25519 Q = scalarmult(e.shiftRight(1));
52 Q = Q.add(Q);
53 if (e.testBit(0)) Q = Q.add(this);
54 return Q;
55 }
56
57 /**
58 * Addition law for montgomery curve in montgomery coordinates.
59 *
60 * @param other
61 * @return
62 */
63 public Curve25519 add(Curve25519 other) {
64 return null;
65 }
66
67
68
69}
diff --git a/src/main/java/org/gnunet/util/crypto/DsaPrng.java b/src/main/java/org/gnunet/util/crypto/DsaPrng.java
new file mode 100644
index 0000000..c26848e
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/DsaPrng.java
@@ -0,0 +1,86 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20
21package org.gnunet.util.crypto;
22
23import com.google.common.primitives.Bytes;
24
25import javax.crypto.Mac;
26import javax.crypto.spec.SecretKeySpec;
27import java.math.BigInteger;
28import java.security.InvalidKeyException;
29import java.security.MessageDigest;
30import java.security.NoSuchAlgorithmException;
31import java.util.Arrays;
32
33/**
34 * Deterministic generator for the 'k'-value of DSA, conforming to RFC 6979.
35 * SHA-1 is used as H.
36 */
37public class DsaPrng {
38 private static final int qlen = 32;
39 private Mac mac;
40 private byte[] V = new byte[64];
41 private byte[] K = new byte[64];
42
43 public byte[] hmacK(byte[]... args) {
44 try {
45 mac.init(new SecretKeySpec(K, "HmacSHA1"));
46 } catch (InvalidKeyException e) {
47 throw new RuntimeException("invalid key: " + e.getMessage());
48 }
49 for (byte[] bytes : args) {
50 mac.update(bytes);
51 }
52 return mac.doFinal();
53 }
54
55 public DsaPrng(byte[] key, byte[] message) {
56 try {
57 mac = Mac.getInstance("HmacSHA1");
58 } catch (NoSuchAlgorithmException e) {
59 throw new RuntimeException("crypto algorithm 'HmacSHA1' required but not provided");
60 }
61 MessageDigest digest;
62 try {
63 digest = MessageDigest.getInstance("SHA-512");
64 } catch (NoSuchAlgorithmException e) {
65 throw new RuntimeException("crypto algorithm 'SHA-512' required but not provided");
66 }
67 byte[] h1 = digest.digest(message);
68
69 Arrays.fill(V, (byte) 1);
70 K = hmacK(V, new byte[]{0}, key, h1);
71 V = hmacK(V);
72 K = hmacK(V, new byte[]{1}, key, h1);
73 V = hmacK(V);
74 }
75
76 public BigInteger nextK() {
77 byte[] T = new byte[0];
78 while (T.length < qlen) {
79 V = hmacK(V);
80 T = Bytes.concat(T, V);
81 }
82 K = hmacK(V, new byte[]{0});
83 V = hmacK(V);
84 return new BigInteger(1, T);
85 }
86}
diff --git a/src/main/java/org/gnunet/util/crypto/EcdhePrivateKey.java b/src/main/java/org/gnunet/util/crypto/EcdhePrivateKey.java
new file mode 100644
index 0000000..e3cd861
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EcdhePrivateKey.java
@@ -0,0 +1,4 @@
1package org.gnunet.util.crypto;
2
3public class EcdhePrivateKey {
4}
diff --git a/src/main/java/org/gnunet/util/crypto/EcdhePublicKey.java b/src/main/java/org/gnunet/util/crypto/EcdhePublicKey.java
new file mode 100644
index 0000000..3943137
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EcdhePublicKey.java
@@ -0,0 +1,20 @@
1package org.gnunet.util.crypto;
2
3import org.gnunet.construct.FixedSizeIntegerArray;
4
5public class EcdhePublicKey {
6 /**
7 * x-coordinate of the point on the curve.
8 * The number is stored as little endian.
9 */
10 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
11 public byte[] x;
12
13 /**
14 * y-coordinate of the point on the curve.
15 * The number is stored as little endian.
16 */
17 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
18 public byte[] y;
19
20}
diff --git a/src/main/java/org/gnunet/util/crypto/EcdsaPrivateKey.java b/src/main/java/org/gnunet/util/crypto/EcdsaPrivateKey.java
new file mode 100644
index 0000000..284c88c
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EcdsaPrivateKey.java
@@ -0,0 +1,35 @@
1package org.gnunet.util.crypto;
2
3import org.gnunet.construct.FixedSizeIntegerArray;
4import org.gnunet.construct.Message;
5
6import java.security.SecureRandom;
7
8public class EcdsaPrivateKey implements Message {
9 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
10 public byte[] d;
11
12 public static EcdsaPrivateKey getAnonymous() {
13 return null;
14 }
15
16 public EcdsaSignature sign(int purpose, byte[] data) {
17 return null;
18 }
19
20 public static EcdsaPrivateKey fromFile(String privKeyFilename) {
21 return null;
22 }
23
24 public EcdsaPublicKey getPublicKey() {
25 return null;
26 }
27
28 public static EcdsaPrivateKey createRandom() {
29 SecureRandom sr = new SecureRandom();
30 EcdsaPrivateKey privateKey = new EcdsaPrivateKey();
31 privateKey.d = new byte[32];
32 sr.nextBytes(privateKey.d);
33 return privateKey;
34 }
35}
diff --git a/src/main/java/org/gnunet/util/crypto/EcdsaPublicKey.java b/src/main/java/org/gnunet/util/crypto/EcdsaPublicKey.java
new file mode 100644
index 0000000..9642e1a
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EcdsaPublicKey.java
@@ -0,0 +1,27 @@
1package org.gnunet.util.crypto;
2
3import org.gnunet.construct.FixedSizeIntegerArray;
4
5public class EcdsaPublicKey {
6 /**
7 * x-coordinate of the point on the curve.
8 * The number is stored as little endian.
9 */
10 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
11 public byte[] x;
12
13 /**
14 * y-coordinate of the point on the curve.
15 * The number is stored as little endian.
16 */
17 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
18 public byte[] y;
19
20 public EcdsaPublicKey(Ed25519 a) {
21
22 }
23
24 public static EcdsaPublicKey fromString(String s) {
25 return null;
26 }
27}
diff --git a/src/main/java/org/gnunet/voting/messages/CertificateDenyMessage.java b/src/main/java/org/gnunet/util/crypto/EcdsaSignature.java
index aefd6ab..fcb2ba5 100644
--- a/src/main/java/org/gnunet/voting/messages/CertificateDenyMessage.java
+++ b/src/main/java/org/gnunet/util/crypto/EcdsaSignature.java
@@ -18,17 +18,15 @@
18 Boston, MA 02111-1307, USA. 18 Boston, MA 02111-1307, USA.
19 */ 19 */
20 20
21package org.gnunet.voting.messages; 21package org.gnunet.util.crypto;
22 22
23 23
24import org.gnunet.construct.NestedMessage; 24public class EcdsaSignature {
25import org.gnunet.construct.UnionCase; 25 boolean verify() {
26import org.gnunet.construct.ZeroTerminatedString; 26 return false;
27import org.gnunet.util.CryptoECC; 27 }
28import org.gnunet.util.GnunetMessage;
29 28
30@UnionCase(42011) 29 public static EcdsaSignature fromString(String s) {
31public class CertificateDenyMessage implements GnunetMessage.Body { 30 return null; //To change body of created methods use File | Settings | File Templates.
32 @ZeroTerminatedString 31 }
33 public String reason;
34} 32}
diff --git a/src/main/java/org/gnunet/util/crypto/Ed25519.java b/src/main/java/org/gnunet/util/crypto/Ed25519.java
new file mode 100644
index 0000000..0947de4
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/Ed25519.java
@@ -0,0 +1,133 @@
1package org.gnunet.util.crypto;
2
3
4import java.math.BigInteger;
5import java.security.MessageDigest;
6import java.security.NoSuchAlgorithmException;
7
8/**
9 * Java-only implementation of arithmetic on DJBs Ed25519.
10 * Very, very slow.
11 */
12public class Ed25519 {
13 // curve parameter b
14 static final int b = 256;
15 // curve parameter q = 255^(-19)
16 private static final BigInteger q = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819949");
17 // q-3
18 private static final BigInteger qm2 = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819947");
19 // q-3
20 private static final BigInteger qp3 = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819952");
21 static final BigInteger l = new BigInteger("7237005577332262213973186563042994240857116359379907606001950938285454250989");
22 private static final BigInteger d = new BigInteger("-4513249062541557337682894930092624173785641285191125241628941591882900924598840740");
23 private static final BigInteger I = new BigInteger("19681161376707505956807079304988542015446066515923890162744021073123829784752");
24 private static final BigInteger By = new BigInteger("46316835694926478169428394003475163141307993866256225615783033603165251855960");
25 private static final BigInteger Bx = new BigInteger("15112221349535400772501151409588531511454012693041857206046113283949847762202");
26 static final Ed25519 B = new Ed25519(Bx.mod(q),By.mod(q));
27 // 2^255
28 private static final BigInteger un = new BigInteger("57896044618658097711785492504343953926634992332820282019728792003956564819967");
29
30
31 BigInteger P0;
32 BigInteger P1;
33
34 public Ed25519(BigInteger P0, BigInteger P1) {
35 this.P0 = P0;
36 this.P1 = P1;
37 }
38
39 public static Ed25519 decompress(BigInteger y) {
40 BigInteger y2 = y.multiply(y);
41 BigInteger xx = (y2.subtract(BigInteger.ONE)).multiply(inv(d.multiply(y2).add(BigInteger.ONE)));
42 BigInteger x = xx.modPow(qp3.divide(BigInteger.valueOf(8)), q);
43 if (!x.multiply(x).subtract(xx).mod(q).equals(BigInteger.ZERO)) x = (x.multiply(I).mod(q));
44 if (!x.mod(BigInteger.valueOf(2)).equals(BigInteger.ZERO)) x = q.subtract(x);
45 return new Ed25519(x, y);
46 }
47
48 /**
49 * Computes the multiplicative inverse of x modulo q using Euler's theorem.
50 *
51 * @param x the group element to invert
52 * @return the inverse of x modulo q
53 */
54 private static BigInteger inv(BigInteger x) {
55 return x.modPow(qm2, q);
56 }
57
58 /**
59 * Twisted edwards curve addition law.
60 *
61 * @param other other point
62 * @return this + other
63 */
64 public Ed25519 add(Ed25519 other) {
65 BigInteger x1 = this.P0;
66 BigInteger y1 = this.P1;
67 BigInteger x2 = other.P0;
68 BigInteger y2 = other.P1;
69 BigInteger dtemp = d.multiply(x1).multiply(x2).multiply(y1).multiply(y2);
70 BigInteger x3 = ((x1.multiply(y2)).add((x2.multiply(y1)))).multiply(inv(BigInteger.ONE.add(dtemp)));
71 BigInteger y3 = ((y1.multiply(y2)).add((x1.multiply(x2)))).multiply(inv(BigInteger.ONE.subtract(dtemp)));
72 return new Ed25519(x3.mod(q), y3.mod(q));
73 }
74
75 public Ed25519 scalarmult(BigInteger e) {
76 if (e.equals(BigInteger.ZERO)) {
77 return new Ed25519(BigInteger.ZERO, BigInteger.ONE);
78 }
79 Ed25519 Q = scalarmult(e.shiftRight(1));
80 Q = Q.add(Q);
81 if (e.testBit(0)) Q = Q.add(this);
82 return Q;
83 }
84
85 public static BigInteger decodeScalar(byte[] s) {
86 byte[] out = new byte[s.length];
87 for (int i=0; i < s.length;i++) {
88 out[i] = s[s.length-1-i];
89 }
90 return new BigInteger(out).and(un);
91 }
92
93 public static byte[] encodeScalar(BigInteger n) {
94 byte[] in = n.toByteArray();
95 // reverse the array
96 for (int i = 0; i < in.length / 2; i++) {
97 byte tmp = in[i];
98 in[i] = in[in.length - i - 1];
99 in[in.length - i - 1] = tmp;
100 }
101 return in;
102 }
103
104 public byte[] encode() {
105 byte[] out = encodeScalar(P1);
106 out[out.length-1] |= (P0.testBit(0) ? 0x80 : 0);
107 return out;
108 }
109
110
111 /**
112 * Hash the data in m and return 2^h(m)
113 *
114 * @param m data to hash
115 * @return 2^h(m)
116 */
117 static BigInteger Hint(byte[] m) {
118 MessageDigest sha512;
119 try {
120 sha512 = MessageDigest.getInstance("SHA-512");
121 } catch (NoSuchAlgorithmException e) {
122 throw new RuntimeException("crypto algorithm required but not provided");
123 }
124 final byte[] h = sha512.digest(m);
125 for (int i = 0; i < 32; i++) {
126 byte tmp = h[i];
127 h[i] = h[63 - i];
128 h[63 - i] = tmp;
129 }
130 return new BigInteger(1, h);
131 }
132
133}
diff --git a/src/main/java/org/gnunet/util/crypto/EddsaPrivateKey.java b/src/main/java/org/gnunet/util/crypto/EddsaPrivateKey.java
new file mode 100644
index 0000000..973706f
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EddsaPrivateKey.java
@@ -0,0 +1,83 @@
1package org.gnunet.util.crypto;
2
3import org.gnunet.construct.FixedSizeIntegerArray;
4import org.gnunet.construct.Message;
5
6import java.math.BigInteger;
7import java.nio.ByteBuffer;
8import java.security.MessageDigest;
9import java.security.NoSuchAlgorithmException;
10import java.security.SecureRandom;
11
12public class EddsaPrivateKey implements Message {
13 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
14 public byte[] d;
15
16 public EddsaSignature sign(EddsaPublicKey publicKey, int purpose, byte[] m) {
17 MessageDigest sha512;
18 try {
19 sha512 = MessageDigest.getInstance("SHA-512");
20 } catch (NoSuchAlgorithmException e) {
21 throw new RuntimeException("crypto algorithm required but not provided");
22 }
23 byte[] h = sha512.digest(d);
24 BigInteger a = BigInteger.valueOf(2).pow(Ed25519.b-2);
25 for (int i = 3; i < (Ed25519.b - 2); i++) {
26 a = a.add(BigInteger.valueOf(2).pow(i).multiply(BigInteger.valueOf(bit(h,i))));
27 }
28 ByteBuffer rsub = ByteBuffer.allocate((Ed25519.b/8)+m.length);
29 rsub.put(h, Ed25519.b/8, Ed25519.b/4-Ed25519.b/8).put(m);
30 BigInteger r = Ed25519.Hint(rsub.array());
31 Ed25519 R = Ed25519.B.scalarmult(r);
32
33 byte[] encodedPublicKey = publicKey.asPoint().encode();
34 ByteBuffer buf = ByteBuffer.allocate(32 + encodedPublicKey.length + m.length);
35 buf.put(R.encode()).put(encodedPublicKey).put(m);
36
37 BigInteger S = r.add(Ed25519.Hint(buf.array()).multiply(a)).mod(Ed25519.l);
38
39 return new EddsaSignature(R, S);
40 }
41
42 /**
43 * Get return the i-th bit in the given array of bytes h.
44 *
45 * @param h array of bytes
46 * @param i bit index
47 * @return i-th bit in h
48 */
49 private static int bit(byte[] h, int i) {
50 return h[i/8] >> (i%8) & 1;
51 }
52
53
54 private BigInteger computePublicKeyCoefficient() {
55 MessageDigest sha512;
56 try {
57 sha512 = MessageDigest.getInstance("SHA-512");
58 } catch (NoSuchAlgorithmException e) {
59 throw new RuntimeException("crypto algorithm required but not provided");
60 }
61 byte[] h = sha512.digest(d);
62 BigInteger a = BigInteger.valueOf(2).pow(Ed25519.b - 2);
63 for (int i=3; i < (Ed25519.b - 2); i++) {
64 BigInteger apart = BigInteger.valueOf(2).pow(i).multiply(BigInteger.valueOf(bit(h,i)));
65 a = a.add(apart);
66 }
67 return a;
68 }
69
70 public EddsaPublicKey getPublicKey() {
71 BigInteger a = computePublicKeyCoefficient();
72 Ed25519 A = Ed25519.B.scalarmult(a);
73 return new EddsaPublicKey(A);
74 }
75
76 public static EddsaPrivateKey createRandom() {
77 SecureRandom sr = new SecureRandom();
78 EddsaPrivateKey privateKey = new EddsaPrivateKey();
79 privateKey.d = new byte[32];
80 sr.nextBytes(privateKey.d);
81 return privateKey;
82 }
83}
diff --git a/src/main/java/org/gnunet/util/crypto/EddsaPublicKey.java b/src/main/java/org/gnunet/util/crypto/EddsaPublicKey.java
new file mode 100644
index 0000000..725208f
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EddsaPublicKey.java
@@ -0,0 +1,29 @@
1package org.gnunet.util.crypto;
2
3import org.gnunet.construct.FixedSizeIntegerArray;
4import org.gnunet.construct.Message;
5
6public class EddsaPublicKey implements Message {
7 /**
8 * x-coordinate of the point on the curve.
9 * The number is stored as little endian.
10 */
11 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
12 public byte[] x;
13
14 /**
15 * y-coordinate of the point on the curve.
16 * The number is stored as little endian.
17 */
18 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
19 public byte[] y;
20
21 public EddsaPublicKey(Ed25519 a) {
22 x = Ed25519.encodeScalar(a.P0);
23 y = Ed25519.encodeScalar(a.P1);
24 }
25
26 public Ed25519 asPoint() {
27 return new Ed25519(Ed25519.decodeScalar(x), Ed25519.decodeScalar(y));
28 }
29}
diff --git a/src/main/java/org/gnunet/util/crypto/EddsaSignature.java b/src/main/java/org/gnunet/util/crypto/EddsaSignature.java
new file mode 100644
index 0000000..d0ee328
--- /dev/null
+++ b/src/main/java/org/gnunet/util/crypto/EddsaSignature.java
@@ -0,0 +1,94 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20
21/*
22 This file is part of GNUnet.
23 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
24
25 GNUnet is free software; you can redistribute it and/or modify
26 it under the terms of the GNU General Public License as published
27 by the Free Software Foundation; either version 3, or (at your
28 option) any later version.
29
30 GNUnet is distributed in the hope that it will be useful, but
31 WITHOUT ANY WARRANTY; without even the implied warranty of
32 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
33 General Public License for more details.
34
35 You should have received a copy of the GNU General Public License
36 along with GNUnet; see the file COPYING. If not, write to the
37 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
38 Boston, MA 02111-1307, USA.
39 */
40
41package org.gnunet.util.crypto;
42
43
44import org.gnunet.construct.FixedSizeIntegerArray;
45import org.gnunet.construct.Message;
46
47import java.math.BigInteger;
48import java.nio.ByteBuffer;
49
50public class EddsaSignature implements Message {
51 /**
52 * R value of the signature in compressed form.
53 * The number is stored as little endian.
54 */
55 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
56 public byte[] r;
57
58 /**
59 * S-value of the signature.
60 * The number is stored as little endian.
61 */
62 @FixedSizeIntegerArray(bitSize = 8, signed = false, length = 32)
63 public byte[] s;
64
65 public EddsaSignature(Ed25519 r, BigInteger s) {
66 this.r = r.encode();
67 this.s = Ed25519.encodeScalar(s);
68 }
69
70 public boolean verify(byte[] m, int purpose, EddsaPublicKey publicKey) {
71 Ed25519 R = Ed25519.decompress(Ed25519.decodeScalar(r));
72 Ed25519 A = publicKey.asPoint();
73 BigInteger S = Ed25519.decodeScalar(s);
74 ByteBuffer Stemp = ByteBuffer.allocate(32 + 32 + m.length);
75 Stemp.put(R.encode()).put(A.encode()).put(m);
76 BigInteger h = Ed25519.Hint(Stemp.array());
77 Ed25519 ra = Ed25519.B.scalarmult(S);
78 Ed25519 rb = R.add(A.scalarmult(h));
79 return rb.equals(rb);
80 }
81
82 public static EddsaSignature fromString(String value) {
83 return null;
84 }
85
86 /**
87 * Return a signature that is invalid with very, very high probability.
88 *
89 * @return
90 */
91 public static EddsaSignature randomGarbage() {
92 return null;
93 }
94}
diff --git a/src/main/java/org/gnunet/voting/Ballot.java b/src/main/java/org/gnunet/voting/Ballot.java
index 0d8de27..531b662 100644
--- a/src/main/java/org/gnunet/voting/Ballot.java
+++ b/src/main/java/org/gnunet/voting/Ballot.java
@@ -26,6 +26,10 @@ import com.google.common.collect.BiMap;
26import com.google.common.collect.HashBiMap; 26import com.google.common.collect.HashBiMap;
27import com.google.common.primitives.Longs; 27import com.google.common.primitives.Longs;
28import org.gnunet.util.*; 28import org.gnunet.util.*;
29import org.gnunet.util.crypto.EcdsaPrivateKey;
30import org.gnunet.util.crypto.EcdsaPublicKey;
31import org.gnunet.util.crypto.EcdsaSignature;
32import org.gnunet.util.crypto.EddsaSignature;
29 33
30import java.security.MessageDigest; 34import java.security.MessageDigest;
31import java.security.NoSuchAlgorithmException; 35import java.security.NoSuchAlgorithmException;
@@ -45,15 +49,15 @@ public class Ballot {
45 AbsoluteTime queryTime; 49 AbsoluteTime queryTime;
46 AbsoluteTime endTime; 50 AbsoluteTime endTime;
47 BiMap<String,PeerIdentity> authorities; 51 BiMap<String,PeerIdentity> authorities;
48 SortedMap<String,CryptoECC.Signature> registrationSigs; 52 SortedMap<String,EddsaSignature> registrationSigs;
49 CryptoECC.PublicSignKey caPub; 53 EcdsaPublicKey caPub;
50 CryptoECC.PublicSignKey issuerPub; 54 EcdsaPublicKey issuerPub;
51 CryptoECC.Signature issuerSig; 55 EcdsaSignature issuerSig;
52 CryptoECC.PublicSignKey voterPub; 56 EcdsaPublicKey voterPub;
53 CryptoECC.Signature voterGroupCert; 57 EcdsaSignature voterGroupCert;
54 CryptoECC.Signature permission; 58 EcdsaSignature permission;
55 CryptoECC.PublicSignKey voterSig; 59 EcdsaPublicKey voterSig;
56 SortedMap<String,CryptoECC.Signature> voucherSigs; 60 SortedMap<String,EddsaSignature> confirmationSigs;
57 61
58 /** 62 /**
59 * Choice in plaintext. 63 * Choice in plaintext.
@@ -152,22 +156,22 @@ public class Ballot {
152 if (!optCaPub.isPresent()) { 156 if (!optCaPub.isPresent()) {
153 throw new InvalidBallotException("no CA pub key given"); 157 throw new InvalidBallotException("no CA pub key given");
154 } 158 }
155 caPub = CryptoECC.PublicSignKey.fromString(optCaPub.get()); 159 caPub = EcdsaPublicKey.fromString(optCaPub.get());
156 if (null == caPub) { 160 if (null == caPub) {
157 throw new InvalidBallotException("CA pub key invalid"); 161 throw new InvalidBallotException("CA pub key invalid");
158 } 162 }
159 Optional<String> optIssuerPub = cfg.getValueString("election", "ISSUER_PUB"); 163 Optional<String> optIssuerPub = cfg.getValueString("election", "ISSUER_PUB");
160 if (optIssuerPub.isPresent()) { 164 if (optIssuerPub.isPresent()) {
161 issuerPub = CryptoECC.PublicSignKey.fromString(optIssuerPub.get()); 165 issuerPub = EcdsaPublicKey.fromString(optIssuerPub.get());
162 Optional<String> optIssuerSig = cfg.getValueString("election", "ISSUER_SIG"); 166 Optional<String> optIssuerSig = cfg.getValueString("election", "ISSUER_SIG");
163 if (!optIssuerSig.isPresent()) { 167 if (!optIssuerSig.isPresent()) {
164 throw new InvalidBallotException("issuer public key present, but no signature"); 168 throw new InvalidBallotException("issuer public key present, but no signature");
165 } 169 }
166 issuerSig = CryptoECC.Signature.fromString(optIssuerSig.get()); 170 issuerSig = EcdsaSignature.fromString(optIssuerSig.get());
167 } 171 }
168 registrationSigs = new TreeMap<String, CryptoECC.Signature>(); 172 registrationSigs = new TreeMap<String, EddsaSignature>();
169 for (Map.Entry<String,String> e : cfg.getSection("registration-signatures").entrySet()) { 173 for (Map.Entry<String,String> e : cfg.getSection("registration-signatures").entrySet()) {
170 CryptoECC.Signature sig = CryptoECC.Signature.fromString(e.getValue()); 174 EddsaSignature sig = EddsaSignature.fromString(e.getValue());
171 if (null == sig) { 175 if (null == sig) {
172 throw new InvalidBallotException("registration signature has invalid format"); 176 throw new InvalidBallotException("registration signature has invalid format");
173 } 177 }
@@ -176,16 +180,16 @@ public class Ballot {
176 } 180 }
177 registrationSigs.put(e.getKey(), sig); 181 registrationSigs.put(e.getKey(), sig);
178 } 182 }
179 voucherSigs = new TreeMap<String, CryptoECC.Signature>(); 183 confirmationSigs = new TreeMap<String, EddsaSignature>();
180 for (Map.Entry<String,String> e : cfg.getSection("vouchers").entrySet()) { 184 for (Map.Entry<String,String> e : cfg.getSection("vouchers").entrySet()) {
181 CryptoECC.Signature sig = CryptoECC.Signature.fromString(e.getValue()); 185 EddsaSignature sig = EddsaSignature.fromString(e.getValue());
182 if (null == sig) { 186 if (null == sig) {
183 throw new InvalidBallotException("voucher signature has invalid format"); 187 throw new InvalidBallotException("voucher signature has invalid format");
184 } 188 }
185 if (!authorities.containsKey(e.getKey())) { 189 if (!authorities.containsKey(e.getKey())) {
186 throw new InvalidBallotException("ballot contains superfluous voucher signature"); 190 throw new InvalidBallotException("ballot contains superfluous voucher signature");
187 } 191 }
188 voucherSigs.put(e.getKey(), sig); 192 confirmationSigs.put(e.getKey(), sig);
189 } 193 }
190 Optional<String> optChoiceId = cfg.getValueString("vote", "CHOICE_ID"); 194 Optional<String> optChoiceId = cfg.getValueString("vote", "CHOICE_ID");
191 if (optChoiceId.isPresent()) { 195 if (optChoiceId.isPresent()) {
@@ -199,7 +203,7 @@ public class Ballot {
199 203
200 Optional<String> optVoterPub = cfg.getValueString("vote", "VOTER_PUB"); 204 Optional<String> optVoterPub = cfg.getValueString("vote", "VOTER_PUB");
201 if (optVoterPub.isPresent()) { 205 if (optVoterPub.isPresent()) {
202 voterPub = CryptoECC.PublicSignKey.fromString(optVoterPub.get()); 206 voterPub = EcdsaPublicKey.fromString(optVoterPub.get());
203 } 207 }
204 208
205 startTime = getTime(cfg, "START"); 209 startTime = getTime(cfg, "START");
@@ -250,7 +254,7 @@ public class Ballot {
250 * @param choice the choice to encode the ballot 254 * @param choice the choice to encode the ballot
251 * @param privateKey the private key to use for encoding 255 * @param privateKey the private key to use for encoding
252 */ 256 */
253 public void encodeChoice(String choice, CryptoECC.PrivateKey privateKey) { 257 public void encodeChoice(String choice, EcdsaPrivateKey privateKey) {
254 choiceId = -1; 258 choiceId = -1;
255 int i = 0; 259 int i = 0;
256 for (String possibleChoice : choices) { 260 for (String possibleChoice : choices) {
@@ -259,7 +263,7 @@ public class Ballot {
259 } 263 }
260 i++; 264 i++;
261 } 265 }
262 voterPub = CryptoECC.computePublicKey(privateKey); 266 voterPub = privateKey.getPublicKey();
263 if (choiceId == -1) { 267 if (choiceId == -1) {
264 throw new InvalidBallotException(String.format("choice '%s' not valid", choice)); 268 throw new InvalidBallotException(String.format("choice '%s' not valid", choice));
265 } 269 }
@@ -284,12 +288,12 @@ public class Ballot {
284 cfg.setValueString("authorities", e.getKey(), e.getValue().toString()); 288 cfg.setValueString("authorities", e.getKey(), e.getValue().toString());
285 } 289 }
286 if (null != registrationSigs) { 290 if (null != registrationSigs) {
287 for (Map.Entry<String, CryptoECC.Signature> e : registrationSigs.entrySet()) { 291 for (Map.Entry<String, EddsaSignature> e : registrationSigs.entrySet()) {
288 cfg.setValueString("registration-signatures", e.getKey(), e.getValue().toString()); 292 cfg.setValueString("registration-signatures", e.getKey(), e.getValue().toString());
289 } 293 }
290 } 294 }
291 if (null != voucherSigs) { 295 if (null != confirmationSigs) {
292 for (Map.Entry<String, CryptoECC.Signature> e : voucherSigs.entrySet()) { 296 for (Map.Entry<String, EddsaSignature> e : confirmationSigs.entrySet()) {
293 cfg.setValueString("vouchers", e.getKey(), e.getValue().toString()); 297 cfg.setValueString("vouchers", e.getKey(), e.getValue().toString());
294 } 298 }
295 } 299 }
@@ -370,15 +374,15 @@ public class Ballot {
370 } 374 }
371 if (!registrationSigs.isEmpty()) { 375 if (!registrationSigs.isEmpty()) {
372 buf.append("ballot is registered with the following authorities:\n"); 376 buf.append("ballot is registered with the following authorities:\n");
373 for (Map.Entry<String, CryptoECC.Signature> e : registrationSigs.entrySet()) { 377 for (Map.Entry<String, EddsaSignature> e : registrationSigs.entrySet()) {
374 buf.append(e.getKey()); 378 buf.append(e.getKey());
375 buf.append(" "); 379 buf.append(" ");
376 } 380 }
377 buf.append("\n"); 381 buf.append("\n");
378 } 382 }
379 if (!voucherSigs.isEmpty()) { 383 if (!confirmationSigs.isEmpty()) {
380 buf.append("ballot's vote has been submitted to with the following authorities:\n"); 384 buf.append("ballot's vote has been submitted to with the following authorities:\n");
381 for (Map.Entry<String, CryptoECC.Signature> e : voucherSigs.entrySet()) { 385 for (Map.Entry<String, EddsaSignature> e : confirmationSigs.entrySet()) {
382 buf.append(e.getKey()); 386 buf.append(e.getKey());
383 buf.append(" "); 387 buf.append(" ");
384 } 388 }
@@ -404,7 +408,7 @@ public class Ballot {
404 public List<PeerIdentity> getRemainingSubmitAuthorities() { 408 public List<PeerIdentity> getRemainingSubmitAuthorities() {
405 LinkedList<PeerIdentity> remaining = new LinkedList<PeerIdentity>(); 409 LinkedList<PeerIdentity> remaining = new LinkedList<PeerIdentity>();
406 for (SortedMap.Entry<String,PeerIdentity> x : authorities.entrySet()) { 410 for (SortedMap.Entry<String,PeerIdentity> x : authorities.entrySet()) {
407 if (!voucherSigs.containsKey(x.getKey())) 411 if (!confirmationSigs.containsKey(x.getKey()))
408 remaining.add(x.getValue()); 412 remaining.add(x.getValue());
409 } 413 }
410 return remaining; 414 return remaining;
@@ -430,9 +434,10 @@ public class Ballot {
430 * 434 *
431 * @param privateKey private key of the issuer 435 * @param privateKey private key of the issuer
432 */ 436 */
433 public void issue(CryptoECC.PrivateKey privateKey) { 437 public void issue(EcdsaPrivateKey privateKey) {
434 issuerPub = CryptoECC.computePublicKey(privateKey); 438 issuerPub = privateKey.getPublicKey();
435 issuerSig = CryptoECC.sign(getBallotGuid().data, privateKey, issuerPub); 439 // FIXME: purpose
440 issuerSig = privateKey.sign(0, getBallotGuid().data);
436 } 441 }
437 442
438 /** 443 /**
@@ -441,7 +446,8 @@ public class Ballot {
441 * @param currentAuthority authority we registered with 446 * @param currentAuthority authority we registered with
442 * @param registrationSignature signature over this ballot's GUID from the authority 447 * @param registrationSignature signature over this ballot's GUID from the authority
443 */ 448 */
444 public void addRegistrationSignature(PeerIdentity currentAuthority, CryptoECC.Signature registrationSignature) { 449 public void addRegistrationSignature(PeerIdentity currentAuthority,
450 EddsaSignature registrationSignature) {
445 String alias = authorities.inverse().get(currentAuthority); 451 String alias = authorities.inverse().get(currentAuthority);
446 registrationSigs.put(alias, registrationSignature); 452 registrationSigs.put(alias, registrationSignature);
447 } 453 }
@@ -451,11 +457,11 @@ public class Ballot {
451 * to the list of vouchers 457 * to the list of vouchers
452 * 458 *
453 * @param currentAuthority authority that received the vote 459 * @param currentAuthority authority that received the vote
454 * @param voucherSignature signature from the authority 460 * @param confirmationSignature signature from the authority
455 */ 461 */
456 public void addVoucher(PeerIdentity currentAuthority, CryptoECC.Signature voucherSignature) { 462 public void addConfirmation(PeerIdentity currentAuthority, EddsaSignature confirmationSignature) {
457 String alias = authorities.inverse().get(currentAuthority); 463 String alias = authorities.inverse().get(currentAuthority);
458 voucherSigs.put(alias, voucherSignature); 464 confirmationSigs.put(alias, confirmationSignature);
459 } 465 }
460 466
461 /** 467 /**
diff --git a/src/main/java/org/gnunet/voting/BallotTool.java b/src/main/java/org/gnunet/voting/BallotTool.java
index 1abf8fd..fe83789 100644
--- a/src/main/java/org/gnunet/voting/BallotTool.java
+++ b/src/main/java/org/gnunet/voting/BallotTool.java
@@ -25,8 +25,8 @@ import com.google.common.base.Charsets;
25import com.google.common.io.ByteStreams; 25import com.google.common.io.ByteStreams;
26import com.google.common.io.Files; 26import com.google.common.io.Files;
27import com.google.common.io.OutputSupplier; 27import com.google.common.io.OutputSupplier;
28import org.gnunet.util.CryptoECC;
29import org.gnunet.util.Program; 28import org.gnunet.util.Program;
29import org.gnunet.util.crypto.EcdsaPrivateKey;
30import org.gnunet.util.getopt.Argument; 30import org.gnunet.util.getopt.Argument;
31import org.gnunet.util.getopt.ArgumentAction; 31import org.gnunet.util.getopt.ArgumentAction;
32 32
@@ -78,13 +78,6 @@ public class BallotTool {
78 String select = null; 78 String select = null;
79 79
80 @Argument( 80 @Argument(
81 shortname = "G",
82 longname = "certify-group",
83 action = ArgumentAction.SET,
84 description = "request a certificate that the voter belongs to the ballot's group")
85 boolean certifyGroup = false;
86
87 @Argument(
88 shortname = "V", 81 shortname = "V",
89 longname = "verify", 82 longname = "verify",
90 action = ArgumentAction.SET, 83 action = ArgumentAction.SET,
@@ -98,21 +91,6 @@ public class BallotTool {
98 description = "write a template ballot to the give ballot file") 91 description = "write a template ballot to the give ballot file")
99 boolean template = false; 92 boolean template = false;
100 93
101 @Argument(
102 shortname = "g",
103 longname = "gen-key",
104 action = ArgumentAction.SET,
105 description = "generate a private key")
106 boolean genKey = false;
107
108 @Argument(
109 shortname = "P",
110 longname = "print-key",
111 action = ArgumentAction.SET,
112 description = "print the public key for the private key")
113 boolean printKey = false;
114
115
116 @Override 94 @Override
117 protected String makeHelpText() { 95 protected String makeHelpText() {
118 return "gnunet-ballot [OPTIONS]... BALLOT [PRIVKEYFILE]\n" + 96 return "gnunet-ballot [OPTIONS]... BALLOT [PRIVKEYFILE]\n" +
@@ -146,7 +124,7 @@ public class BallotTool {
146 return; 124 return;
147 } 125 }
148 Ballot b = new Ballot(ballotFilename); 126 Ballot b = new Ballot(ballotFilename);
149 CryptoECC.PrivateKey privateKey = CryptoECC.PrivateKey.fromFile(privKeyFilename); 127 EcdsaPrivateKey privateKey = EcdsaPrivateKey.fromFile(privKeyFilename);
150 if (privateKey == null) { 128 if (privateKey == null) {
151 System.err.println("keyfile invalid"); 129 System.err.println("keyfile invalid");
152 return; 130 return;
@@ -170,7 +148,7 @@ public class BallotTool {
170 System.err.println("private-key file does not exist"); 148 System.err.println("private-key file does not exist");
171 return; 149 return;
172 } 150 }
173 CryptoECC.PrivateKey privateKey = CryptoECC.PrivateKey.fromFile(privKeyFilename); 151 EcdsaPrivateKey privateKey = EcdsaPrivateKey.fromFile(privKeyFilename);
174 if (privateKey == null) { 152 if (privateKey == null) {
175 System.err.println("keyfile invalid"); 153 System.err.println("keyfile invalid");
176 return; 154 return;
@@ -186,38 +164,6 @@ public class BallotTool {
186 System.out.println("vote written to ballot file"); 164 System.out.println("vote written to ballot file");
187 } 165 }
188 166
189 public void runPermission(String ballotFilename, String privKeyFilename) {
190
191 }
192
193 public void runGenKey(String privKeyFilename) {
194 File kf = new File(privKeyFilename);
195 if (kf.exists()) {
196 System.err.println("private key file already exists, not overwriting");
197 return;
198 }
199 CryptoECC.PrivateKey privateKey = CryptoECC.PrivateKey.createRandom();
200 try {
201 privateKey.write(privKeyFilename);
202 } catch (IOException e) {
203 System.err.println("can't write to key file: " + e.getMessage());
204 }
205 }
206
207 public void runPrintKey(String privKeyFilename) {
208 File kf = new File(privKeyFilename);
209 if (!kf.exists()) {
210 System.err.println("key file does not exist");
211 return;
212 }
213 CryptoECC.PrivateKey privateKey = CryptoECC.PrivateKey.fromFile(privKeyFilename);
214 if (privateKey == null) {
215 System.err.println("key invalid");
216 return;
217 }
218 CryptoECC.PublicSignKey publicKey = CryptoECC.computePublicKey(privateKey);
219 System.out.println(publicKey.toString());
220 }
221 167
222 public void runVerify(String ballotFilename) { 168 public void runVerify(String ballotFilename) {
223 File bf = new File(ballotFilename); 169 File bf = new File(ballotFilename);
@@ -291,30 +237,6 @@ public class BallotTool {
291 c.run(); 237 c.run();
292 return; 238 return;
293 } 239 }
294 if (certifyGroup) {
295 if (this.unprocessedArgs.length != 2) {
296 System.err.println("-G/--certify-group requires exactly two positional arguments");
297 return;
298 }
299 CertifyGroupCommand c = new CertifyGroupCommand(getConfiguration(),
300 unprocessedArgs[0], unprocessedArgs[1]);
301 c.run();
302 return;
303 }
304 if (genKey) {
305 if (this.unprocessedArgs.length != 1) {
306 System.err.println("-g/--gen-key requires exactly one positional argument");
307 return;
308 }
309 runGenKey(unprocessedArgs[0]);
310 }
311 if (printKey) {
312 if (this.unprocessedArgs.length != 1) {
313 System.err.println("-P/--print-key requires exactly one positional argument");
314 return;
315 }
316 runPrintKey(unprocessedArgs[0]);
317 }
318 } 240 }
319 }.start(); 241 }.start();
320 242
diff --git a/src/main/java/org/gnunet/voting/CertificateAuthorityDaemon.java b/src/main/java/org/gnunet/voting/CertificateAuthorityDaemon.java
deleted file mode 100644
index fc54bbf..0000000
--- a/src/main/java/org/gnunet/voting/CertificateAuthorityDaemon.java
+++ /dev/null
@@ -1,70 +0,0 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20package org.gnunet.voting;
21
22import com.google.common.collect.Maps;
23import org.gnunet.mesh.Mesh;
24import org.gnunet.mesh.MeshRunabout;
25import org.gnunet.testbed.CompressedConfig;
26import org.gnunet.util.*;
27import org.gnunet.voting.messages.*;
28import org.slf4j.Logger;
29import org.slf4j.LoggerFactory;
30
31import java.util.HashMap;
32import java.util.HashSet;
33import java.util.Set;
34
35/**
36 * Gives a voter a certificate that acknowledges that he belongs to a certain group
37 * (e.g. all people from bavaria over 18 years old)
38 */
39public class CertificateAuthorityDaemon extends Program {
40 private static final Logger logger = LoggerFactory
41 .getLogger(CertificateAuthorityDaemon.class);
42
43 public static final int MESH_PORT = 1002;
44 private Mesh mesh;
45
46 public class CaMeshReceiver extends MeshRunabout {
47 public void visit(CertificateRequestMessage m) {
48 logger.info("granting group cert for '" + m.group + "'");
49 CertificateGrantMessage gm = new CertificateGrantMessage();
50 gm.expiration = AbsoluteTime.FOREVER.asMessage();
51 gm.groupCertificate = CryptoECC.Signature.randomSignature();
52 getSender().receiveDone();
53 }
54 }
55
56 public CertificateAuthorityDaemon(String[] args) {
57 super(args);
58 }
59
60 public static void main(String[] args) {
61 CertificateAuthorityDaemon daemon = new CertificateAuthorityDaemon(args);
62 daemon.start();
63 }
64
65 @Override
66 public void run() {
67 logger.info("running ca daemon");
68 mesh = new Mesh(getConfiguration(), null, null, new CaMeshReceiver(), MESH_PORT);
69 }
70}
diff --git a/src/main/java/org/gnunet/voting/CertifyGroupCommand.java b/src/main/java/org/gnunet/voting/CertifyGroupCommand.java
deleted file mode 100644
index e76ba1f..0000000
--- a/src/main/java/org/gnunet/voting/CertifyGroupCommand.java
+++ /dev/null
@@ -1,129 +0,0 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20
21/*
22 This file is part of GNUnet.
23 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
24
25 GNUnet is free software; you can redistribute it and/or modify
26 it under the terms of the GNU General Public License as published
27 by the Free Software Foundation; either version 3, or (at your
28 option) any later version.
29
30 GNUnet is distributed in the hope that it will be useful, but
31 WITHOUT ANY WARRANTY; without even the implied warranty of
32 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
33 General Public License for more details.
34
35 You should have received a copy of the GNU General Public License
36 along with GNUnet; see the file COPYING. If not, write to the
37 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
38 Boston, MA 02111-1307, USA.
39 */
40
41/*
42 This file is part of GNUnet.
43 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
44
45 GNUnet is free software; you can redistribute it and/or modify
46 it under the terms of the GNU General Public License as published
47 by the Free Software Foundation; either version 3, or (at your
48 option) any later version.
49
50 GNUnet is distributed in the hope that it will be useful, but
51 WITHOUT ANY WARRANTY; without even the implied warranty of
52 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
53 General Public License for more details.
54
55 You should have received a copy of the GNU General Public License
56 along with GNUnet; see the file COPYING. If not, write to the
57 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
58 Boston, MA 02111-1307, USA.
59 */
60
61package org.gnunet.voting;
62
63
64import org.gnunet.mesh.Mesh;
65import org.gnunet.mesh.MeshRunabout;
66import org.gnunet.mesh.TunnelEndHandler;
67import org.gnunet.util.Configuration;
68import org.gnunet.util.CryptoECC;
69import org.gnunet.voting.messages.CertificateGrantMessage;
70import org.gnunet.voting.messages.CertificateRequestMessage;
71import org.gnunet.voting.messages.QueryFailureMessage;
72
73import java.io.File;
74import java.util.Random;
75
76public class CertifyGroupCommand extends MeshRunabout implements TunnelEndHandler {
77 private final String ballotFilename;
78 private final String pubKeyString;
79 private Ballot ballot;
80 private final Configuration cfg;
81 private Mesh mesh;
82 private Mesh.Tunnel<Void> tunnel;
83 private boolean submitted = false;
84
85 @Override
86 public void onTunnelEnd(Mesh.Tunnel tunnel) {
87 if (!submitted)
88 throw new AssertionError();
89 }
90
91 public void visit(CertificateGrantMessage m) {
92 submitted = true;
93 System.out.println("certificate granted");
94
95 tunnel.destroy();
96 mesh.destroy();
97 }
98
99
100 public void visit(QueryFailureMessage m) {
101 submitted = true;
102 System.out.println("failure to query result: authority refused");
103 tunnel.destroy();
104 mesh.destroy();
105 }
106
107 public CertifyGroupCommand(Configuration cfg, String ballotFilename, String pubKeyString) {
108 this.cfg = cfg;
109 this.ballotFilename = ballotFilename;
110 this.pubKeyString = pubKeyString;
111 }
112
113 public void run() {
114 File bf = new File(ballotFilename);
115 if (!bf.exists()) {
116 System.err.println("ballot file does not exist");
117 return;
118 }
119 ballot = new Ballot(ballotFilename);
120
121 Random r = new Random();
122 mesh = new Mesh(cfg, this, this);
123 tunnel = mesh.createTunnel(null /* FIXME */, CertificateAuthorityDaemon.MESH_PORT, true, true, null);
124 CertificateRequestMessage m = new CertificateRequestMessage();
125 m.group = ballot.group;
126 m.publicKey = CryptoECC.PublicSignKey.fromString(pubKeyString);
127 tunnel.send(m);
128 }
129}
diff --git a/src/main/java/org/gnunet/voting/CertifyGroupTool.java b/src/main/java/org/gnunet/voting/CertifyGroupTool.java
new file mode 100644
index 0000000..0403c02
--- /dev/null
+++ b/src/main/java/org/gnunet/voting/CertifyGroupTool.java
@@ -0,0 +1,25 @@
1/*
2 This file is part of GNUnet.
3 (C) 2012, 2013 Christian Grothoff (and other contributing authors)
4
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
9
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
19 */
20
21package org.gnunet.voting;
22
23
24public class CertifyGroupTool {
25}
diff --git a/src/main/java/org/gnunet/voting/SubmitCommand.java b/src/main/java/org/gnunet/voting/SubmitCommand.java
index 43e10c9..b8e018a 100644
--- a/src/main/java/org/gnunet/voting/SubmitCommand.java
+++ b/src/main/java/org/gnunet/voting/SubmitCommand.java
@@ -28,8 +28,8 @@ import org.gnunet.mesh.MeshRunabout;
28import org.gnunet.mesh.TunnelEndHandler; 28import org.gnunet.mesh.TunnelEndHandler;
29import org.gnunet.util.AbsoluteTime; 29import org.gnunet.util.AbsoluteTime;
30import org.gnunet.util.Configuration; 30import org.gnunet.util.Configuration;
31import org.gnunet.util.CryptoECC;
32import org.gnunet.util.PeerIdentity; 31import org.gnunet.util.PeerIdentity;
32import org.gnunet.util.crypto.EddsaSignature;
33import org.gnunet.voting.messages.SubmitFailureMessage; 33import org.gnunet.voting.messages.SubmitFailureMessage;
34import org.gnunet.voting.messages.SubmitMessage; 34import org.gnunet.voting.messages.SubmitMessage;
35import org.gnunet.voting.messages.SubmitSuccessMessage; 35import org.gnunet.voting.messages.SubmitSuccessMessage;
@@ -60,7 +60,7 @@ public class SubmitCommand extends MeshRunabout implements TunnelEndHandler {
60 public void visit(SubmitSuccessMessage m) { 60 public void visit(SubmitSuccessMessage m) {
61 submitted = true; 61 submitted = true;
62 System.out.println("vote successfully submitted"); 62 System.out.println("vote successfully submitted");
63 ballot.addVoucher(currentAuthority, m.voucherSig); 63 ballot.addConfirmation(currentAuthority, m.confirmationSig);
64 try { 64 try {
65 Files.write(ballot.serialize(), new File(ballotFilename), Charsets.UTF_8); 65 Files.write(ballot.serialize(), new File(ballotFilename), Charsets.UTF_8);
66 } catch (IOException e) { 66 } catch (IOException e) {
@@ -108,7 +108,7 @@ public class SubmitCommand extends MeshRunabout implements TunnelEndHandler {
108 m.voterPub = ballot.voterPub; 108 m.voterPub = ballot.voterPub;
109 // FIXME: implement certs 109 // FIXME: implement certs
110 m.groupCertExpiration = AbsoluteTime.FOREVER.asMessage(); 110 m.groupCertExpiration = AbsoluteTime.FOREVER.asMessage();
111 m.groupCert = CryptoECC.Signature.randomSignature(); 111 m.groupCert = EddsaSignature.randomGarbage();
112 m.ballotGuid = ballot.getBallotGuid(); 112 m.ballotGuid = ballot.getBallotGuid();
113 m.choiceId = ballot.choiceId; 113 m.choiceId = ballot.choiceId;
114 tunnel.send(m); 114 tunnel.send(m);
diff --git a/src/main/java/org/gnunet/voting/TallyAuthorityDaemon.java b/src/main/java/org/gnunet/voting/TallyAuthorityDaemon.java
index aa27f9c..ace3f38 100644
--- a/src/main/java/org/gnunet/voting/TallyAuthorityDaemon.java
+++ b/src/main/java/org/gnunet/voting/TallyAuthorityDaemon.java
@@ -25,6 +25,8 @@ import org.gnunet.mesh.Mesh;
25import org.gnunet.mesh.MeshRunabout; 25import org.gnunet.mesh.MeshRunabout;
26import org.gnunet.testbed.CompressedConfig; 26import org.gnunet.testbed.CompressedConfig;
27import org.gnunet.util.*; 27import org.gnunet.util.*;
28import org.gnunet.util.crypto.EcdsaPublicKey;
29import org.gnunet.util.crypto.EddsaSignature;
28import org.gnunet.voting.messages.*; 30import org.gnunet.voting.messages.*;
29import org.slf4j.Logger; 31import org.slf4j.Logger;
30import org.slf4j.LoggerFactory; 32import org.slf4j.LoggerFactory;
@@ -58,7 +60,7 @@ public class TallyAuthorityDaemon extends Program {
58 /** 60 /**
59 * Set of voters that have submitted their ballot. 61 * Set of voters that have submitted their ballot.
60 */ 62 */
61 Set<CryptoECC.PublicSignKey> voters = new HashSet<CryptoECC.PublicSignKey>(); 63 Set<EcdsaPublicKey> voters = new HashSet<EcdsaPublicKey>();
62 64
63 /** 65 /**
64 * Maping from choice to number of votes for that choice. 66 * Maping from choice to number of votes for that choice.
@@ -98,7 +100,7 @@ public class TallyAuthorityDaemon extends Program {
98 electionState.voters.add(m.voterPub); 100 electionState.voters.add(m.voterPub);
99 electionState.tally[m.choiceId] += 1; 101 electionState.tally[m.choiceId] += 1;
100 SubmitSuccessMessage sm = new SubmitSuccessMessage(); 102 SubmitSuccessMessage sm = new SubmitSuccessMessage();
101 sm.voucherSig = CryptoECC.Signature.randomSignature(); 103 sm.confirmationSig = EddsaSignature.randomGarbage();
102 getSender().send(sm); 104 getSender().send(sm);
103 } 105 }
104 106
@@ -130,7 +132,7 @@ public class TallyAuthorityDaemon extends Program {
130 electionState.ballot = b; 132 electionState.ballot = b;
131 elections.put(guid, electionState); 133 elections.put(guid, electionState);
132 BallotRegisterSuccessMessage rm = new BallotRegisterSuccessMessage(); 134 BallotRegisterSuccessMessage rm = new BallotRegisterSuccessMessage();
133 rm.registrationSignature = CryptoECC.Signature.randomSignature(); 135 rm.registrationSignature = EddsaSignature.randomGarbage();
134 getSender().send(rm); 136 getSender().send(rm);
135 } 137 }
136 138
diff --git a/src/main/java/org/gnunet/voting/messages/BallotRegisterFailureMessage.java b/src/main/java/org/gnunet/voting/messages/BallotRegisterFailureMessage.java
index ecce92d..8986970 100644
--- a/src/main/java/org/gnunet/voting/messages/BallotRegisterFailureMessage.java
+++ b/src/main/java/org/gnunet/voting/messages/BallotRegisterFailureMessage.java
@@ -20,10 +20,8 @@
20 20
21package org.gnunet.voting.messages; 21package org.gnunet.voting.messages;
22 22
23import org.gnunet.construct.NestedMessage;
24import org.gnunet.construct.UnionCase; 23import org.gnunet.construct.UnionCase;
25import org.gnunet.construct.ZeroTerminatedString; 24import org.gnunet.construct.ZeroTerminatedString;
26import org.gnunet.util.CryptoECC;
27import org.gnunet.util.GnunetMessage; 25import org.gnunet.util.GnunetMessage;
28 26
29 27
diff --git a/src/main/java/org/gnunet/voting/messages/BallotRegisterSuccessMessage.java b/src/main/java/org/gnunet/voting/messages/BallotRegisterSuccessMessage.java
index 8ce007b..040c9b3 100644
--- a/src/main/java/org/gnunet/voting/messages/BallotRegisterSuccessMessage.java
+++ b/src/main/java/org/gnunet/voting/messages/BallotRegisterSuccessMessage.java
@@ -2,8 +2,8 @@ package org.gnunet.voting.messages;
2 2
3import org.gnunet.construct.NestedMessage; 3import org.gnunet.construct.NestedMessage;
4import org.gnunet.construct.UnionCase; 4import org.gnunet.construct.UnionCase;
5import org.gnunet.util.CryptoECC;
6import org.gnunet.util.GnunetMessage; 5import org.gnunet.util.GnunetMessage;
6import org.gnunet.util.crypto.EddsaSignature;
7 7
8 8
9/** 9/**
@@ -12,5 +12,5 @@ import org.gnunet.util.GnunetMessage;
12@UnionCase(42012) 12@UnionCase(42012)
13public class BallotRegisterSuccessMessage implements GnunetMessage.Body { 13public class BallotRegisterSuccessMessage implements GnunetMessage.Body {
14 @NestedMessage 14 @NestedMessage
15 public CryptoECC.Signature registrationSignature; 15 public EddsaSignature registrationSignature;
16} 16}
diff --git a/src/main/java/org/gnunet/voting/messages/CertificateGrantMessage.java b/src/main/java/org/gnunet/voting/messages/CertificateGrantMessage.java
deleted file mode 100644
index f209b7a..0000000
--- a/src/main/java/org/gnunet/voting/messages/CertificateGrantMessage.java
+++ /dev/null
@@ -1,19 +0,0 @@
1package org.gnunet.voting.messages;
2
3
4import org.gnunet.construct.NestedMessage;
5import org.gnunet.construct.UInt32;
6import org.gnunet.construct.UInt64;
7import org.gnunet.construct.UnionCase;
8import org.gnunet.util.AbsoluteTime;
9import org.gnunet.util.AbsoluteTimeMessage;
10import org.gnunet.util.CryptoECC;
11import org.gnunet.util.GnunetMessage;
12
13@UnionCase(42004)
14public class CertificateGrantMessage implements GnunetMessage.Body {
15 @NestedMessage
16 public CryptoECC.Signature groupCertificate;
17 @NestedMessage
18 public AbsoluteTimeMessage expiration;
19}
diff --git a/src/main/java/org/gnunet/voting/messages/CertificateRequestMessage.java b/src/main/java/org/gnunet/voting/messages/CertificateRequestMessage.java
deleted file mode 100644
index 1b4514e..0000000
--- a/src/main/java/org/gnunet/voting/messages/CertificateRequestMessage.java
+++ /dev/null
@@ -1,23 +0,0 @@
1package org.gnunet.voting.messages;
2
3import org.gnunet.construct.NestedMessage;
4import org.gnunet.construct.UnionCase;
5import org.gnunet.util.CryptoECC;
6import org.gnunet.util.GnunetMessage;
7
8/**
9 * Request a certificate that allows a voter to submit a ballot.
10 * Sent by the voter to the certificate authority.
11 */
12@UnionCase(42003)
13public class CertificateRequestMessage implements GnunetMessage.Body {
14 /**
15 * Public Key of the voter that requests group certification.
16 */
17 @NestedMessage
18 public CryptoECC.PublicSignKey publicKey;
19 /**
20 * Group that the voter wants to be certified for.
21 */
22 public String group;
23}
diff --git a/src/main/java/org/gnunet/voting/messages/SubmitMessage.java b/src/main/java/org/gnunet/voting/messages/SubmitMessage.java
index 1b71d3e..a47abfa 100644
--- a/src/main/java/org/gnunet/voting/messages/SubmitMessage.java
+++ b/src/main/java/org/gnunet/voting/messages/SubmitMessage.java
@@ -4,6 +4,8 @@ import org.gnunet.construct.NestedMessage;
4import org.gnunet.construct.UInt32; 4import org.gnunet.construct.UInt32;
5import org.gnunet.construct.UnionCase; 5import org.gnunet.construct.UnionCase;
6import org.gnunet.util.*; 6import org.gnunet.util.*;
7import org.gnunet.util.crypto.EcdsaPublicKey;
8import org.gnunet.util.crypto.EddsaSignature;
7 9
8/** 10/**
9 * Message send by the voter to the election authority to submit a vote. 11 * Message send by the voter to the election authority to submit a vote.
@@ -19,12 +21,12 @@ public class SubmitMessage implements GnunetMessage.Body {
19 * Public key of the voter. 21 * Public key of the voter.
20 */ 22 */
21 @NestedMessage 23 @NestedMessage
22 public CryptoECC.PublicSignKey voterPub; 24 public EcdsaPublicKey voterPub;
23 /** 25 /**
24 * Group certificate of the voter. 26 * Group certificate of the voter.
25 */ 27 */
26 @NestedMessage 28 @NestedMessage
27 public CryptoECC.Signature groupCert; 29 public EddsaSignature groupCert;
28 /** 30 /**
29 * Expiration time of the group certificate, checked by the authority. 31 * Expiration time of the group certificate, checked by the authority.
30 */ 32 */
diff --git a/src/main/java/org/gnunet/voting/messages/SubmitSuccessMessage.java b/src/main/java/org/gnunet/voting/messages/SubmitSuccessMessage.java
index 0c0e9e1..9e28b96 100644
--- a/src/main/java/org/gnunet/voting/messages/SubmitSuccessMessage.java
+++ b/src/main/java/org/gnunet/voting/messages/SubmitSuccessMessage.java
@@ -3,11 +3,11 @@ package org.gnunet.voting.messages;
3 3
4import org.gnunet.construct.NestedMessage; 4import org.gnunet.construct.NestedMessage;
5import org.gnunet.construct.UnionCase; 5import org.gnunet.construct.UnionCase;
6import org.gnunet.util.CryptoECC;
7import org.gnunet.util.GnunetMessage; 6import org.gnunet.util.GnunetMessage;
7import org.gnunet.util.crypto.EddsaSignature;
8 8
9@UnionCase(42008) 9@UnionCase(42008)
10public class SubmitSuccessMessage implements GnunetMessage.Body { 10public class SubmitSuccessMessage implements GnunetMessage.Body {
11 @NestedMessage 11 @NestedMessage
12 public CryptoECC.Signature voucherSig; 12 public EddsaSignature confirmationSig;
13} 13}