aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMITSUNARI Shigeo <herumi@nifty.com>2018-09-17 21:26:05 +0800
committerMITSUNARI Shigeo <herumi@nifty.com>2018-09-17 21:26:05 +0800
commit48a73206e83cb0901deaab594340b2711a4430b5 (patch)
tree075bb29de07276c4033f4da4c4e16411e4f780ae
parentaf2e557d9eb824a0c8d5c42a8cf1c8f09c8d16a7 (diff)
downloaddexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.tar
dexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.tar.gz
dexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.tar.bz2
dexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.tar.lz
dexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.tar.xz
dexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.tar.zst
dexon-bls-48a73206e83cb0901deaab594340b2711a4430b5.zip
add verifyAggregatedHashes
-rw-r--r--include/bls/bls.h11
-rw-r--r--include/bls/bls.hpp12
-rw-r--r--src/bls_c_impl.hpp24
-rw-r--r--test/bls_test.hpp38
4 files changed, 85 insertions, 0 deletions
diff --git a/include/bls/bls.h b/include/bls/bls.h
index b2b8604..71e3d02 100644
--- a/include/bls/bls.h
+++ b/include/bls/bls.h
@@ -124,6 +124,11 @@ BLS_DLL_API int blsPublicKeyIsValidOrder(const blsPublicKey *pub);
#ifndef BLS_MINIMUM_API
/*
+ set h to a point of G1
+ return 0 if success else -1
+*/
+BLS_DLL_API int blsG1SetHash(mclBnG1 *g1, const void *h, mclSize size);
+/*
sign the hash
use the low (bitSize of r) - 1 bit of h
return 0 if success else -1
@@ -132,6 +137,12 @@ BLS_DLL_API int blsPublicKeyIsValidOrder(const blsPublicKey *pub);
BLS_DLL_API int blsSignHash(blsSignature *sig, const blsSecretKey *sec, const void *h, mclSize size);
// return 1 if valid
BLS_DLL_API int blsVerifyHash(const blsSignature *sig, const blsPublicKey *pub, const void *h, mclSize size);
+/*
+ verify aggSig with pubVec[0, n) and g1Vec[0, n)
+ e(aggSig, Q) = prod_i e(g1Vec[i], pubVec[i])
+ return 1 if valid
+*/
+BLS_DLL_API int blsVerifyAggregation(const blsSignature *aggSig, const blsPublicKey *pubVec, const mclBnG1 *g1Vec, mclSize n);
// sub
BLS_DLL_API void blsSecretKeySub(blsSecretKey *sec, const blsSecretKey *rhs);
diff --git a/include/bls/bls.hpp b/include/bls/bls.hpp
index 3dbacd7..868e574 100644
--- a/include/bls/bls.hpp
+++ b/include/bls/bls.hpp
@@ -419,6 +419,18 @@ public:
{
return verifyHash(pub, h.c_str(), h.size());
}
+ bool verifyAggregation(const PublicKey *pubVec, const mclBnG1 *g1Vec, size_t n) const
+ {
+ return blsVerifyAggregation(&self_, &pubVec[0].self_, g1Vec, n) == 1;
+ }
+ bool verifyAggregatedHashes(const PublicKey *pubVec, const void *hVec, size_t sizeofHash, size_t n) const
+ {
+ std::vector<mclBnG1> g1Vec(n);
+ for (size_t i = 0; i < n; i++) {
+ if (blsG1SetHash(&g1Vec[i], (const char*)hVec + sizeofHash * i, sizeofHash) != 0) throw std::runtime_error("blsG1SetHash");
+ }
+ return verifyAggregation(pubVec, g1Vec.data(), n);
+ }
/*
verify self(pop) with pub
*/
diff --git a/src/bls_c_impl.hpp b/src/bls_c_impl.hpp
index 768c206..ad52cf7 100644
--- a/src/bls_c_impl.hpp
+++ b/src/bls_c_impl.hpp
@@ -275,6 +275,30 @@ inline bool toG1(G1& Hm, const void *h, mclSize size)
BN::mapToG1(&b, Hm, t);
return b;
}
+int blsG1SetHash(mclBnG1 *g1, const void *h, mclSize size)
+{
+ return toG1(*cast(g1), h, size) ? 0 : -1;
+}
+
+int blsVerifyAggregation(const blsSignature *aggSig, const blsPublicKey *pubVec, const mclBnG1 *g1Vec, mclSize n)
+{
+ if (n == 0) return 0;
+ /*
+ e(aggSig, Q) = prod_i e(g1Vec[i], pubVec[i])
+ <=> finalExp(ML(-aggSig, Q) * prod_i ML(g1Vec[i], pubVec[i])) == 1
+ */
+ GT e1, e2;
+ BN::precomputedMillerLoop(e1, -*cast(&aggSig->v), g_Qcoeff.data());
+ BN::millerLoop(e2, *cast(&g1Vec[0]), *cast(&pubVec[0].v));
+ e1 *= e2;
+ for (size_t i = 1; i < n; i++) {
+ BN::millerLoop(e2, *cast(&g1Vec[i]), *cast(&pubVec[i].v));
+ e1 *= e2;
+ }
+ BN::finalExp(e1, e1);
+ return e1.isOne();
+}
+
int blsSignHash(blsSignature *sig, const blsSecretKey *sec, const void *h, mclSize size)
{
G1 Hm;
diff --git a/test/bls_test.hpp b/test/bls_test.hpp
index d713118..bb58ad2 100644
--- a/test/bls_test.hpp
+++ b/test/bls_test.hpp
@@ -4,6 +4,11 @@
#include <iostream>
#include <sstream>
#include <cybozu/benchmark.hpp>
+#ifdef MCL_DONT_USE_OPENSSL
+#include <cybozu/sha2.hpp>
+#else
+#include <cybozu/crypto.hpp>
+#endif
template<class T>
void streamTest(const T& t)
@@ -421,6 +426,38 @@ void dataTest()
}
}
+void verifyAggregateTest()
+{
+ const size_t n = 10;
+ bls::SecretKey secs[n];
+ bls::PublicKey pubs[n];
+ bls::Signature sigs[n], sig;
+ const size_t sizeofHash = 32;
+ std::vector<char[sizeofHash]> h(n);
+ for (size_t i = 0; i < n; i++) {
+ char msg[128];
+ CYBOZU_SNPRINTF(msg, sizeof(msg), "abc-%d", (int)i);
+ const size_t msgSize = strlen(msg);
+#ifdef MCL_DONT_USE_OPENSSL
+ cybozu::Sha256(msg, msgSize).get(h[i]);
+#else
+ cybozu::crypto::Hash::digest(h[i], cybozu::crypto::Hash::N_SHA256, msg, msgSize);
+#endif
+ secs[i].init();
+ secs[i].getPublicKey(pubs[i]);
+ secs[i].signHash(sigs[i], h[i], sizeofHash);
+ }
+ sig = sigs[0];
+ for (size_t i = 1; i < n; i++) {
+ sig.add(sigs[i]);
+ }
+ CYBOZU_TEST_ASSERT(sig.verifyAggregatedHashes(pubs, h.data(), sizeofHash, n));
+ bls::Signature invalidSig = sigs[0] + sigs[1];
+ CYBOZU_TEST_ASSERT(!invalidSig.verifyAggregatedHashes(pubs, h.data(), sizeofHash, n));
+ h[0][0]++;
+ CYBOZU_TEST_ASSERT(!sig.verifyAggregatedHashes(pubs, h.data(), sizeofHash, n));
+}
+
void testAll()
{
blsTest();
@@ -429,6 +466,7 @@ void testAll()
addTest();
dataTest();
aggregateTest();
+ verifyAggregateTest();
}
CYBOZU_TEST_AUTO(all)
{