charm-crypto-framework 0.61.1__cp313-cp313-macosx_10_13_universal2.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- charm/__init__.py +5 -0
- charm/adapters/__init__.py +0 -0
- charm/adapters/abenc_adapt_hybrid.py +90 -0
- charm/adapters/dabenc_adapt_hybrid.py +145 -0
- charm/adapters/ibenc_adapt_hybrid.py +72 -0
- charm/adapters/ibenc_adapt_identityhash.py +80 -0
- charm/adapters/kpabenc_adapt_hybrid.py +91 -0
- charm/adapters/pkenc_adapt_bchk05.py +121 -0
- charm/adapters/pkenc_adapt_chk04.py +91 -0
- charm/adapters/pkenc_adapt_hybrid.py +98 -0
- charm/adapters/pksig_adapt_naor01.py +89 -0
- charm/config.py +7 -0
- charm/core/__init__.py +0 -0
- charm/core/benchmark/benchmark_util.c +353 -0
- charm/core/benchmark/benchmark_util.h +61 -0
- charm/core/benchmark/benchmarkmodule.c +476 -0
- charm/core/benchmark/benchmarkmodule.h +162 -0
- charm/core/benchmark.cpython-313-darwin.so +0 -0
- charm/core/crypto/AES/AES.c +1464 -0
- charm/core/crypto/AES.cpython-313-darwin.so +0 -0
- charm/core/crypto/DES/DES.c +113 -0
- charm/core/crypto/DES.cpython-313-darwin.so +0 -0
- charm/core/crypto/DES3/DES3.c +26 -0
- charm/core/crypto/DES3.cpython-313-darwin.so +0 -0
- charm/core/crypto/__init__.py +0 -0
- charm/core/crypto/cryptobase/XOR.c +80 -0
- charm/core/crypto/cryptobase/_counter.c +496 -0
- charm/core/crypto/cryptobase/_counter.h +54 -0
- charm/core/crypto/cryptobase/block_template.c +900 -0
- charm/core/crypto/cryptobase/block_template.h +69 -0
- charm/core/crypto/cryptobase/cryptobasemodule.c +220 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt.h +90 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_argchk.h +44 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_cfg.h +186 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_cipher.h +941 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_custom.h +556 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_des.c +1912 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_hash.h +407 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_mac.h +496 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_macros.h +435 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_math.h +534 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_misc.h +103 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_pk.h +653 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_pkcs.h +90 -0
- charm/core/crypto/cryptobase/libtom/tomcrypt_prng.h +199 -0
- charm/core/crypto/cryptobase/stream_template.c +271 -0
- charm/core/crypto/cryptobase/strxor.c +229 -0
- charm/core/crypto/cryptobase.cpython-313-darwin.so +0 -0
- charm/core/engine/__init__.py +5 -0
- charm/core/engine/protocol.py +293 -0
- charm/core/engine/util.py +174 -0
- charm/core/math/__init__.py +0 -0
- charm/core/math/elliptic_curve/ecmodule.c +1986 -0
- charm/core/math/elliptic_curve/ecmodule.h +230 -0
- charm/core/math/elliptic_curve.cpython-313-darwin.so +0 -0
- charm/core/math/elliptic_curve.pyi +63 -0
- charm/core/math/integer/integermodule.c +2539 -0
- charm/core/math/integer/integermodule.h +145 -0
- charm/core/math/integer.cpython-313-darwin.so +0 -0
- charm/core/math/integer.pyi +76 -0
- charm/core/math/pairing/miracl/miracl_config.h +37 -0
- charm/core/math/pairing/miracl/miracl_interface.h +118 -0
- charm/core/math/pairing/miracl/miracl_interface2.h +126 -0
- charm/core/math/pairing/miracl/pairingmodule2.c +2094 -0
- charm/core/math/pairing/miracl/pairingmodule2.h +307 -0
- charm/core/math/pairing/pairingmodule.c +2230 -0
- charm/core/math/pairing/pairingmodule.h +241 -0
- charm/core/math/pairing/relic/pairingmodule3.c +1853 -0
- charm/core/math/pairing/relic/pairingmodule3.h +233 -0
- charm/core/math/pairing/relic/relic_interface.c +1337 -0
- charm/core/math/pairing/relic/relic_interface.h +217 -0
- charm/core/math/pairing/relic/test_relic.c +171 -0
- charm/core/math/pairing.cpython-313-darwin.so +0 -0
- charm/core/math/pairing.pyi +69 -0
- charm/core/utilities/base64.c +248 -0
- charm/core/utilities/base64.h +15 -0
- charm/schemes/__init__.py +0 -0
- charm/schemes/abenc/__init__.py +0 -0
- charm/schemes/abenc/abenc_accountability_jyjxgd20.py +647 -0
- charm/schemes/abenc/abenc_bsw07.py +146 -0
- charm/schemes/abenc/abenc_ca_cpabe_ar17.py +684 -0
- charm/schemes/abenc/abenc_dacmacs_yj14.py +298 -0
- charm/schemes/abenc/abenc_lsw08.py +159 -0
- charm/schemes/abenc/abenc_maabe_rw15.py +236 -0
- charm/schemes/abenc/abenc_maabe_yj14.py +297 -0
- charm/schemes/abenc/abenc_tbpre_lww14.py +309 -0
- charm/schemes/abenc/abenc_unmcpabe_yahk14.py +223 -0
- charm/schemes/abenc/abenc_waters09.py +144 -0
- charm/schemes/abenc/abenc_yct14.py +208 -0
- charm/schemes/abenc/abenc_yllc15.py +178 -0
- charm/schemes/abenc/ac17.py +248 -0
- charm/schemes/abenc/bsw07.py +141 -0
- charm/schemes/abenc/cgw15.py +277 -0
- charm/schemes/abenc/dabe_aw11.py +204 -0
- charm/schemes/abenc/dfa_fe12.py +144 -0
- charm/schemes/abenc/pk_hve08.py +179 -0
- charm/schemes/abenc/waters11.py +143 -0
- charm/schemes/aggrsign_MuSig.py +150 -0
- charm/schemes/aggrsign_bls.py +267 -0
- charm/schemes/blindsig_ps16.py +654 -0
- charm/schemes/chamhash_adm05.py +113 -0
- charm/schemes/chamhash_rsa_hw09.py +100 -0
- charm/schemes/commit/__init__.py +0 -0
- charm/schemes/commit/commit_gs08.py +77 -0
- charm/schemes/commit/commit_pedersen92.py +53 -0
- charm/schemes/encap_bchk05.py +62 -0
- charm/schemes/grpsig/__init__.py +0 -0
- charm/schemes/grpsig/groupsig_bgls04.py +114 -0
- charm/schemes/grpsig/groupsig_bgls04_var.py +115 -0
- charm/schemes/hibenc/__init__.py +0 -0
- charm/schemes/hibenc/hibenc_bb04.py +105 -0
- charm/schemes/hibenc/hibenc_lew11.py +193 -0
- charm/schemes/ibenc/__init__.py +0 -0
- charm/schemes/ibenc/clpkc_rp03.py +119 -0
- charm/schemes/ibenc/ibenc_CW13_z.py +168 -0
- charm/schemes/ibenc/ibenc_bb03.py +94 -0
- charm/schemes/ibenc/ibenc_bf01.py +121 -0
- charm/schemes/ibenc/ibenc_ckrs09.py +120 -0
- charm/schemes/ibenc/ibenc_cllww12_z.py +172 -0
- charm/schemes/ibenc/ibenc_lsw08.py +120 -0
- charm/schemes/ibenc/ibenc_sw05.py +238 -0
- charm/schemes/ibenc/ibenc_waters05.py +144 -0
- charm/schemes/ibenc/ibenc_waters05_z.py +164 -0
- charm/schemes/ibenc/ibenc_waters09.py +107 -0
- charm/schemes/ibenc/ibenc_waters09_z.py +147 -0
- charm/schemes/joye_scheme.py +106 -0
- charm/schemes/lem_scheme.py +207 -0
- charm/schemes/pk_fre_ccv11.py +107 -0
- charm/schemes/pk_vrf.py +127 -0
- charm/schemes/pkenc/__init__.py +0 -0
- charm/schemes/pkenc/pkenc_cs98.py +108 -0
- charm/schemes/pkenc/pkenc_elgamal85.py +122 -0
- charm/schemes/pkenc/pkenc_gm82.py +98 -0
- charm/schemes/pkenc/pkenc_paillier99.py +118 -0
- charm/schemes/pkenc/pkenc_rabin.py +254 -0
- charm/schemes/pkenc/pkenc_rsa.py +186 -0
- charm/schemes/pksig/__init__.py +0 -0
- charm/schemes/pksig/pksig_CW13_z.py +135 -0
- charm/schemes/pksig/pksig_bls04.py +87 -0
- charm/schemes/pksig/pksig_boyen.py +156 -0
- charm/schemes/pksig/pksig_chch.py +97 -0
- charm/schemes/pksig/pksig_chp.py +70 -0
- charm/schemes/pksig/pksig_cl03.py +150 -0
- charm/schemes/pksig/pksig_cl04.py +87 -0
- charm/schemes/pksig/pksig_cllww12_z.py +142 -0
- charm/schemes/pksig/pksig_cyh.py +132 -0
- charm/schemes/pksig/pksig_dsa.py +76 -0
- charm/schemes/pksig/pksig_ecdsa.py +71 -0
- charm/schemes/pksig/pksig_hess.py +104 -0
- charm/schemes/pksig/pksig_hw.py +110 -0
- charm/schemes/pksig/pksig_lamport.py +63 -0
- charm/schemes/pksig/pksig_ps01.py +135 -0
- charm/schemes/pksig/pksig_ps02.py +124 -0
- charm/schemes/pksig/pksig_ps03.py +119 -0
- charm/schemes/pksig/pksig_rsa_hw09.py +206 -0
- charm/schemes/pksig/pksig_schnorr91.py +77 -0
- charm/schemes/pksig/pksig_waters.py +115 -0
- charm/schemes/pksig/pksig_waters05.py +121 -0
- charm/schemes/pksig/pksig_waters09.py +121 -0
- charm/schemes/pre_mg07.py +150 -0
- charm/schemes/prenc/pre_afgh06.py +126 -0
- charm/schemes/prenc/pre_bbs98.py +123 -0
- charm/schemes/prenc/pre_nal16.py +216 -0
- charm/schemes/protocol_a01.py +272 -0
- charm/schemes/protocol_ao00.py +215 -0
- charm/schemes/protocol_cns07.py +274 -0
- charm/schemes/protocol_schnorr91.py +125 -0
- charm/schemes/sigma1.py +64 -0
- charm/schemes/sigma2.py +129 -0
- charm/schemes/sigma3.py +126 -0
- charm/schemes/threshold/__init__.py +59 -0
- charm/schemes/threshold/dkls23_dkg.py +556 -0
- charm/schemes/threshold/dkls23_presign.py +1089 -0
- charm/schemes/threshold/dkls23_sign.py +761 -0
- charm/schemes/threshold/xrpl_wallet.py +967 -0
- charm/test/__init__.py +0 -0
- charm/test/adapters/__init__.py +0 -0
- charm/test/adapters/abenc_adapt_hybrid_test.py +29 -0
- charm/test/adapters/dabenc_adapt_hybrid_test.py +56 -0
- charm/test/adapters/ibenc_adapt_hybrid_test.py +36 -0
- charm/test/adapters/ibenc_adapt_identityhash_test.py +32 -0
- charm/test/adapters/kpabenc_adapt_hybrid_test.py +30 -0
- charm/test/benchmark/abenc_yllc15_bench.py +92 -0
- charm/test/benchmark/benchmark_test.py +148 -0
- charm/test/benchmark_threshold.py +260 -0
- charm/test/conftest.py +38 -0
- charm/test/fuzz/__init__.py +1 -0
- charm/test/fuzz/conftest.py +5 -0
- charm/test/fuzz/fuzz_policy_parser.py +76 -0
- charm/test/fuzz/fuzz_serialization.py +83 -0
- charm/test/schemes/__init__.py +0 -0
- charm/test/schemes/abenc/__init__.py +0 -0
- charm/test/schemes/abenc/abenc_bsw07_test.py +39 -0
- charm/test/schemes/abenc/abenc_dacmacs_yj14_test.py +16 -0
- charm/test/schemes/abenc/abenc_lsw08_test.py +33 -0
- charm/test/schemes/abenc/abenc_maabe_yj14_test.py +16 -0
- charm/test/schemes/abenc/abenc_tbpre_lww14_test.py +16 -0
- charm/test/schemes/abenc/abenc_waters09_test.py +38 -0
- charm/test/schemes/abenc/abenc_yllc15_test.py +74 -0
- charm/test/schemes/chamhash_adm05_test.py +31 -0
- charm/test/schemes/chamhash_rsa_hw09_test.py +29 -0
- charm/test/schemes/commit/__init__.py +0 -0
- charm/test/schemes/commit/commit_gs08_test.py +24 -0
- charm/test/schemes/commit/commit_pedersen92_test.py +26 -0
- charm/test/schemes/dabe_aw11_test.py +45 -0
- charm/test/schemes/encap_bchk05_test.py +21 -0
- charm/test/schemes/grpsig/__init__.py +0 -0
- charm/test/schemes/grpsig/groupsig_bgls04_test.py +35 -0
- charm/test/schemes/grpsig/groupsig_bgls04_var_test.py +39 -0
- charm/test/schemes/hibenc/__init__.py +0 -0
- charm/test/schemes/hibenc/hibenc_bb04_test.py +28 -0
- charm/test/schemes/ibenc/__init__.py +0 -0
- charm/test/schemes/ibenc/ibenc_bb03_test.py +26 -0
- charm/test/schemes/ibenc/ibenc_bf01_test.py +24 -0
- charm/test/schemes/ibenc/ibenc_ckrs09_test.py +25 -0
- charm/test/schemes/ibenc/ibenc_lsw08_test.py +31 -0
- charm/test/schemes/ibenc/ibenc_sw05_test.py +32 -0
- charm/test/schemes/ibenc/ibenc_waters05_test.py +31 -0
- charm/test/schemes/ibenc/ibenc_waters09_test.py +27 -0
- charm/test/schemes/pk_vrf_test.py +29 -0
- charm/test/schemes/pkenc/__init__.py +0 -0
- charm/test/schemes/pkenc_test.py +255 -0
- charm/test/schemes/pksig/__init__.py +0 -0
- charm/test/schemes/pksig_test.py +376 -0
- charm/test/schemes/rsa_alg_test.py +340 -0
- charm/test/schemes/threshold_test.py +1792 -0
- charm/test/serialize/__init__.py +0 -0
- charm/test/serialize/serialize_test.py +40 -0
- charm/test/toolbox/__init__.py +0 -0
- charm/test/toolbox/conversion_test.py +30 -0
- charm/test/toolbox/ecgroup_test.py +53 -0
- charm/test/toolbox/integer_arithmetic_test.py +441 -0
- charm/test/toolbox/paddingschemes_test.py +238 -0
- charm/test/toolbox/policy_parser_stress_test.py +969 -0
- charm/test/toolbox/secretshare_test.py +28 -0
- charm/test/toolbox/symcrypto_test.py +108 -0
- charm/test/toolbox/test_policy_expression.py +16 -0
- charm/test/vectors/__init__.py +1 -0
- charm/test/vectors/test_bls_vectors.py +289 -0
- charm/test/vectors/test_pedersen_vectors.py +315 -0
- charm/test/vectors/test_schnorr_vectors.py +368 -0
- charm/test/zkp_compiler/__init__.py +9 -0
- charm/test/zkp_compiler/benchmark_zkp.py +258 -0
- charm/test/zkp_compiler/test_and_proof.py +240 -0
- charm/test/zkp_compiler/test_batch_verify.py +248 -0
- charm/test/zkp_compiler/test_dleq_proof.py +264 -0
- charm/test/zkp_compiler/test_or_proof.py +231 -0
- charm/test/zkp_compiler/test_proof_serialization.py +121 -0
- charm/test/zkp_compiler/test_range_proof.py +241 -0
- charm/test/zkp_compiler/test_representation_proof.py +325 -0
- charm/test/zkp_compiler/test_schnorr_proof.py +221 -0
- charm/test/zkp_compiler/test_thread_safety.py +169 -0
- charm/test/zkp_compiler/test_zkp_parser.py +139 -0
- charm/toolbox/ABEnc.py +26 -0
- charm/toolbox/ABEncMultiAuth.py +66 -0
- charm/toolbox/ABEnumeric.py +800 -0
- charm/toolbox/Commit.py +24 -0
- charm/toolbox/DFA.py +89 -0
- charm/toolbox/FSA.py +1254 -0
- charm/toolbox/Hash.py +39 -0
- charm/toolbox/IBEnc.py +62 -0
- charm/toolbox/IBSig.py +64 -0
- charm/toolbox/PKEnc.py +66 -0
- charm/toolbox/PKSig.py +56 -0
- charm/toolbox/PREnc.py +32 -0
- charm/toolbox/ZKProof.py +289 -0
- charm/toolbox/__init__.py +0 -0
- charm/toolbox/bitstring.py +49 -0
- charm/toolbox/broadcast.py +220 -0
- charm/toolbox/conversion.py +100 -0
- charm/toolbox/eccurve.py +149 -0
- charm/toolbox/ecgroup.py +143 -0
- charm/toolbox/enum.py +60 -0
- charm/toolbox/hash_module.py +91 -0
- charm/toolbox/integergroup.py +323 -0
- charm/toolbox/iterate.py +22 -0
- charm/toolbox/matrixops.py +76 -0
- charm/toolbox/mpc_utils.py +296 -0
- charm/toolbox/msp.py +175 -0
- charm/toolbox/mta.py +985 -0
- charm/toolbox/node.py +120 -0
- charm/toolbox/ot/__init__.py +22 -0
- charm/toolbox/ot/base_ot.py +374 -0
- charm/toolbox/ot/dpf.py +642 -0
- charm/toolbox/ot/mpfss.py +228 -0
- charm/toolbox/ot/ot_extension.py +589 -0
- charm/toolbox/ot/silent_ot.py +378 -0
- charm/toolbox/paddingschemes.py +423 -0
- charm/toolbox/paddingschemes_test.py +238 -0
- charm/toolbox/pairingcurves.py +85 -0
- charm/toolbox/pairinggroup.py +186 -0
- charm/toolbox/policy_expression_spec.py +70 -0
- charm/toolbox/policytree.py +189 -0
- charm/toolbox/reCompiler.py +346 -0
- charm/toolbox/redundancyschemes.py +65 -0
- charm/toolbox/schemebase.py +188 -0
- charm/toolbox/secretshare.py +104 -0
- charm/toolbox/secretutil.py +174 -0
- charm/toolbox/securerandom.py +73 -0
- charm/toolbox/sigmaprotocol.py +46 -0
- charm/toolbox/specialprimes.py +45 -0
- charm/toolbox/symcrypto.py +279 -0
- charm/toolbox/threshold_sharing.py +553 -0
- charm/toolbox/xmlserialize.py +94 -0
- charm/toolbox/zknode.py +105 -0
- charm/zkp_compiler/__init__.py +89 -0
- charm/zkp_compiler/and_proof.py +460 -0
- charm/zkp_compiler/batch_verify.py +324 -0
- charm/zkp_compiler/dleq_proof.py +423 -0
- charm/zkp_compiler/or_proof.py +305 -0
- charm/zkp_compiler/range_proof.py +417 -0
- charm/zkp_compiler/representation_proof.py +466 -0
- charm/zkp_compiler/schnorr_proof.py +273 -0
- charm/zkp_compiler/thread_safe.py +150 -0
- charm/zkp_compiler/zk_demo.py +489 -0
- charm/zkp_compiler/zkp_factory.py +330 -0
- charm/zkp_compiler/zkp_generator.py +370 -0
- charm/zkp_compiler/zkparser.py +269 -0
- charm_crypto_framework-0.61.1.dist-info/METADATA +337 -0
- charm_crypto_framework-0.61.1.dist-info/RECORD +323 -0
- charm_crypto_framework-0.61.1.dist-info/WHEEL +5 -0
- charm_crypto_framework-0.61.1.dist-info/licenses/LICENSE.txt +165 -0
- charm_crypto_framework-0.61.1.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,654 @@
|
|
|
1
|
+
'''
|
|
2
|
+
**Pointcheval-Sanders Short Randomizable Signatures (PS16)**
|
|
3
|
+
|
|
4
|
+
*Authors:* David Pointcheval, Olivier Sanders
|
|
5
|
+
|
|
6
|
+
| **Title:** "Short Randomizable Signatures"
|
|
7
|
+
| **Published in:** RSA Conference on Topics in Cryptology, 2016
|
|
8
|
+
| **Available from:** https://dl.acm.org/doi/10.1007/978-3-319-29485-8_7
|
|
9
|
+
| **Notes:** Implements single/multi message signatures and blind signatures
|
|
10
|
+
|
|
11
|
+
.. rubric:: Scheme Properties
|
|
12
|
+
|
|
13
|
+
* **Type:** blind signature
|
|
14
|
+
* **Setting:** bilinear groups (asymmetric)
|
|
15
|
+
* **Assumption:** PS assumption
|
|
16
|
+
|
|
17
|
+
.. rubric:: Implementation
|
|
18
|
+
|
|
19
|
+
:Authors: Ahmed Bakr
|
|
20
|
+
:Date: 04/2023
|
|
21
|
+
'''
|
|
22
|
+
|
|
23
|
+
import sys
|
|
24
|
+
from charm.toolbox.pairinggroup import PairingGroup, ZR, G1, G2, pair
|
|
25
|
+
from charm.core.engine.util import objectToBytes
|
|
26
|
+
from charm.toolbox.PKSig import PKSig
|
|
27
|
+
|
|
28
|
+
|
|
29
|
+
def dump_to_zp_element(obj, group_obj):
|
|
30
|
+
serialized_message = objectToBytes(obj, group_obj)
|
|
31
|
+
return group_obj.hash(serialized_message) # convert the serialized message to object from Z_p
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
class ShnorrInteractiveZKP():
|
|
35
|
+
class Prover:
|
|
36
|
+
def __init__(self, secret_t, secret_messages, groupObj):
|
|
37
|
+
self.__r_t = None
|
|
38
|
+
self.__r_ms = None
|
|
39
|
+
self.group = groupObj
|
|
40
|
+
self.__ms = [dump_to_zp_element(secret_message, groupObj) for secret_message in secret_messages]
|
|
41
|
+
self.__t = secret_t # t is an element, so no need to transform it into an element
|
|
42
|
+
|
|
43
|
+
def create_prover_commitments(self, pk):
|
|
44
|
+
"""
|
|
45
|
+
1) This function is executed by the prover to send a random value to the verifier
|
|
46
|
+
"""
|
|
47
|
+
if 'Ys' not in pk:
|
|
48
|
+
pk['Ys'] = [pk['Y']] # Hack to convert it to an array because this method is general and used for both single and multiple messages
|
|
49
|
+
self.__r_ms = [self.group.random() for _ in range(len(self.__ms))]
|
|
50
|
+
self.__r_t = self.group.random()
|
|
51
|
+
Y_pow_m_prod = pk['Ys'][0] ** self.__r_ms[0]
|
|
52
|
+
for i in range(1, len(self.__ms)):
|
|
53
|
+
Y_pow_m_prod *= pk['Ys'][i] ** self.__r_ms[i]
|
|
54
|
+
Rc = (pk['g'] ** self.__r_t) * Y_pow_m_prod # Follow the same equation used to blind the message
|
|
55
|
+
return Rc
|
|
56
|
+
|
|
57
|
+
def create_proof(self, c):
|
|
58
|
+
"""
|
|
59
|
+
3) This function is executed by the prover after he received the challenge value (c) from the verifier
|
|
60
|
+
"""
|
|
61
|
+
s_t = self.__r_t + c * self.__t
|
|
62
|
+
s_ms = [r_m + c * m for (r_m, m) in zip(self.__r_ms, self.__ms)]
|
|
63
|
+
return (s_t, s_ms) # proof
|
|
64
|
+
|
|
65
|
+
class Verifier:
|
|
66
|
+
|
|
67
|
+
def __init__(self, groupObj):
|
|
68
|
+
self.group = groupObj
|
|
69
|
+
|
|
70
|
+
def create_verifier_challenge(self):
|
|
71
|
+
"""
|
|
72
|
+
2) This function is executed by the verifier after he had received the value u from the prover to send a challenge value to the prover.
|
|
73
|
+
"""
|
|
74
|
+
self.c = self.group.random()
|
|
75
|
+
return self.c
|
|
76
|
+
|
|
77
|
+
def is_proof_verified(self, s_t, s_ms, pk, blinded_message, commitment):
|
|
78
|
+
"""
|
|
79
|
+
4) This function is executed by the verifier to verify the authenticity of the proof sent by the prover
|
|
80
|
+
"""
|
|
81
|
+
if 'Ys' not in pk:
|
|
82
|
+
pk['Ys'] = [pk['Y']] # Hack to convert it to an array because this method is general and used for both single and multiple messages
|
|
83
|
+
Y_pow_m_prod = pk['Ys'][0] ** s_ms[0]
|
|
84
|
+
for i in range(1, len(s_ms)):
|
|
85
|
+
Y_pow_m_prod *= pk['Ys'][i] ** s_ms[i]
|
|
86
|
+
if (pk['g'] ** s_t) * Y_pow_m_prod == (blinded_message ** self.c) * commitment:
|
|
87
|
+
return True
|
|
88
|
+
return False
|
|
89
|
+
|
|
90
|
+
|
|
91
|
+
class PS_Sig(PKSig):
|
|
92
|
+
|
|
93
|
+
def __init__(self, groupObj):
|
|
94
|
+
PKSig.__init__(self)
|
|
95
|
+
self.group = groupObj
|
|
96
|
+
|
|
97
|
+
def _dump_to_zp_element(self, obj):
|
|
98
|
+
serialized_message = objectToBytes(obj, self.group)
|
|
99
|
+
return self.group.hash(serialized_message) # convert the serialized message to object from Z_p
|
|
100
|
+
|
|
101
|
+
def keygen(self):
|
|
102
|
+
"""
|
|
103
|
+
This function is used to generate the secret key and the public key of the signer
|
|
104
|
+
"""
|
|
105
|
+
print("This is a stub function. Implement it in the child class")
|
|
106
|
+
|
|
107
|
+
def sign(self, sk, message):
|
|
108
|
+
"""
|
|
109
|
+
This function is used for the signer to sign a message
|
|
110
|
+
Inputs:
|
|
111
|
+
- sk: Secret key of the signer
|
|
112
|
+
- message: message to be signed
|
|
113
|
+
Outputs:
|
|
114
|
+
- sigma: Signature on the message
|
|
115
|
+
"""
|
|
116
|
+
print("This is a stub function. Implement it in the child class")
|
|
117
|
+
|
|
118
|
+
def verify(self, message, pk, sig) -> bool:
|
|
119
|
+
"""
|
|
120
|
+
This function is used for the user to verify a signature on a specific message using the message and the public
|
|
121
|
+
key of the signer.
|
|
122
|
+
Inputs:
|
|
123
|
+
- message: The message
|
|
124
|
+
- pk: Public key
|
|
125
|
+
- sig: signature
|
|
126
|
+
Outputs:
|
|
127
|
+
- True if the signature is valid on the message by the user whose public key is pk
|
|
128
|
+
- False, otherwise
|
|
129
|
+
"""
|
|
130
|
+
print("This is a stub function. Implement it in the child class")
|
|
131
|
+
|
|
132
|
+
|
|
133
|
+
class PS_BlindSig(PS_Sig):
|
|
134
|
+
|
|
135
|
+
def __init__(self, groupObj):
|
|
136
|
+
PS_Sig.__init__(self, groupObj)
|
|
137
|
+
|
|
138
|
+
def keygen(self):
|
|
139
|
+
"""
|
|
140
|
+
This function is used to generate the secret key and the public key of the signer
|
|
141
|
+
"""
|
|
142
|
+
print("This is a stub function. Implement it in the child class")
|
|
143
|
+
|
|
144
|
+
def blind(self, message):
|
|
145
|
+
"""
|
|
146
|
+
This function takes a message and blinds it to return a blinded message.
|
|
147
|
+
Inputs:
|
|
148
|
+
- message: message to be blinded
|
|
149
|
+
Outputs:
|
|
150
|
+
- blinded_message: A blinded message
|
|
151
|
+
"""
|
|
152
|
+
print("This is a stub function. Implement it in the child class")
|
|
153
|
+
|
|
154
|
+
def sign(self, sk, blinded_message):
|
|
155
|
+
"""
|
|
156
|
+
This function is used for the signer to sign a message
|
|
157
|
+
Inputs:
|
|
158
|
+
- sk: Secret key of the signer
|
|
159
|
+
- blinded_message: A blinded message to be signed
|
|
160
|
+
Outputs:
|
|
161
|
+
- sigma_dash: Signature on the blinded message
|
|
162
|
+
"""
|
|
163
|
+
print("This is a stub function. Implement it in the child class")
|
|
164
|
+
|
|
165
|
+
def unblind(self, blinded_sig, t):
|
|
166
|
+
"""
|
|
167
|
+
This function takes a blinded signature and returns the unblinded signature
|
|
168
|
+
Inputs:
|
|
169
|
+
- blinded_sig: Blinded signature
|
|
170
|
+
- t: random number used to blind the original message
|
|
171
|
+
Outputs:
|
|
172
|
+
- sigma: unblinded signature
|
|
173
|
+
"""
|
|
174
|
+
print("This is a stub function. Implement it in the child class")
|
|
175
|
+
|
|
176
|
+
def proof_of_knowledge_of_commitment_secrets(self, t, messages, blinded_message, pk, group_obj, debug):
|
|
177
|
+
"""This function runs shnorr' interactive proof of knowledge"""
|
|
178
|
+
shnorr_interactive_zkp = ShnorrInteractiveZKP()
|
|
179
|
+
print("Prover wants to prove knowledge of the secret message to the signer (verifier) for him to agree to sign the message")
|
|
180
|
+
prover = shnorr_interactive_zkp.Prover(secret_t=t, secret_messages=messages, groupObj=group_obj)
|
|
181
|
+
verifier = shnorr_interactive_zkp.Verifier(groupObj=group_obj)
|
|
182
|
+
commitments = prover.create_prover_commitments(pk)
|
|
183
|
+
print("Prover sent commitments to the verifier")
|
|
184
|
+
if debug:
|
|
185
|
+
print("Rc = ", commitments)
|
|
186
|
+
challenge = verifier.create_verifier_challenge()
|
|
187
|
+
print("Verifier sends the challenge to the prover: ", challenge)
|
|
188
|
+
s_t, s_m = prover.create_proof(challenge)
|
|
189
|
+
print("Prover sends the proof of knowledge to the verifier: ")
|
|
190
|
+
if debug:
|
|
191
|
+
print("s_t: ", s_t)
|
|
192
|
+
print("s_m: ", s_m)
|
|
193
|
+
prover_knowledge_of_secret_message_status = verifier.is_proof_verified(s_t, s_m, pk, blinded_message, commitments)
|
|
194
|
+
return prover_knowledge_of_secret_message_status
|
|
195
|
+
|
|
196
|
+
|
|
197
|
+
def verify(self, message, pk, sig) -> bool:
|
|
198
|
+
"""
|
|
199
|
+
This function is used for the user to verify a signature on a specific message using the message and the public
|
|
200
|
+
key of the signer.
|
|
201
|
+
Inputs:
|
|
202
|
+
- message: The message
|
|
203
|
+
- pk: Public key
|
|
204
|
+
- sig: signature
|
|
205
|
+
Outputs:
|
|
206
|
+
- True if the signature is valid on the message by the user whose public key is pk
|
|
207
|
+
- False, otherwise
|
|
208
|
+
"""
|
|
209
|
+
print("This is a stub function. Implement it in the child class")
|
|
210
|
+
|
|
211
|
+
|
|
212
|
+
class PS_BlindSingleMessageSig(PS_BlindSig):
|
|
213
|
+
|
|
214
|
+
def __init__(self, groupObj):
|
|
215
|
+
PS_BlindSig.__init__(self, groupObj)
|
|
216
|
+
|
|
217
|
+
def keygen(self):
|
|
218
|
+
"""
|
|
219
|
+
This function is used to generate the secret key and the public key of the signer
|
|
220
|
+
Outputs:
|
|
221
|
+
- sk: Secret key
|
|
222
|
+
- pk: public key
|
|
223
|
+
"""
|
|
224
|
+
g = self.group.random(G1)
|
|
225
|
+
g_tilde = self.group.random(G2)
|
|
226
|
+
x = self.group.random()
|
|
227
|
+
y = self.group.random()
|
|
228
|
+
|
|
229
|
+
X = g ** x
|
|
230
|
+
Y = g ** y
|
|
231
|
+
X_tilde = g_tilde ** x
|
|
232
|
+
Y_tilde = g_tilde ** y
|
|
233
|
+
|
|
234
|
+
pk = {'g': g, 'Y': Y, 'g_tilde': g_tilde, 'X_tilde': X_tilde, 'Y_tilde': Y_tilde}
|
|
235
|
+
sk = {'X': X}
|
|
236
|
+
|
|
237
|
+
return sk, pk
|
|
238
|
+
|
|
239
|
+
def blind(self, message, pk):
|
|
240
|
+
"""
|
|
241
|
+
This function takes a message and blinds it to return a blinded message.
|
|
242
|
+
Inputs:
|
|
243
|
+
- message: message to be blinded
|
|
244
|
+
- pk: pk is needed to know some of the public parameters used in message blinding
|
|
245
|
+
Outputs:
|
|
246
|
+
- C: A blinded message
|
|
247
|
+
- t: Blind random value
|
|
248
|
+
"""
|
|
249
|
+
m = self._dump_to_zp_element(message) # serialize the message to an element
|
|
250
|
+
t = self.group.random()
|
|
251
|
+
C = (pk['g'] ** t) * (pk['Y'] ** m)
|
|
252
|
+
|
|
253
|
+
return C, t
|
|
254
|
+
|
|
255
|
+
def sign(self, sk, pk, blinded_message):
|
|
256
|
+
"""
|
|
257
|
+
This function is used for the signer to sign a message
|
|
258
|
+
Inputs:
|
|
259
|
+
- sk: Secret key of the signer
|
|
260
|
+
- pk: Public key of the signer
|
|
261
|
+
- blinded_message: A blinded message to be signed
|
|
262
|
+
Outputs:
|
|
263
|
+
- sigma_dash: Signature on the blinded message
|
|
264
|
+
"""
|
|
265
|
+
C = blinded_message
|
|
266
|
+
u = self.group.random()
|
|
267
|
+
sigma_dash_1 = pk['g'] ** u
|
|
268
|
+
sigma_dash_2 = (sk['X'] * C) ** u
|
|
269
|
+
sigma_dash = (sigma_dash_1, sigma_dash_2)
|
|
270
|
+
|
|
271
|
+
return sigma_dash
|
|
272
|
+
|
|
273
|
+
def unblind(self, blinded_sig, t):
|
|
274
|
+
"""
|
|
275
|
+
This function takes a blinded signature and returns the unblinded signature
|
|
276
|
+
Inputs:
|
|
277
|
+
- blinded_sig: Blinded signature
|
|
278
|
+
- t: random number used to blind the original message
|
|
279
|
+
Outputs:
|
|
280
|
+
- sigma: unblinded signature
|
|
281
|
+
"""
|
|
282
|
+
sigma_dash_1, sigma_dash_2 = blinded_sig
|
|
283
|
+
sigma_1 = sigma_dash_1
|
|
284
|
+
sigma_2 = sigma_dash_2 / (sigma_dash_1 ** t)
|
|
285
|
+
|
|
286
|
+
sigma = (sigma_1, sigma_2)
|
|
287
|
+
return sigma
|
|
288
|
+
|
|
289
|
+
def verify(self, message, pk, sig) -> bool:
|
|
290
|
+
"""
|
|
291
|
+
This function is used for the user to verify a signature on a specific message using the message and the public
|
|
292
|
+
key of the signer.
|
|
293
|
+
Inputs:
|
|
294
|
+
- message: The message
|
|
295
|
+
- pk: Public key
|
|
296
|
+
- sig: signature
|
|
297
|
+
Outputs:
|
|
298
|
+
- True if the signature is valid on the message by the user whose public key is pk
|
|
299
|
+
- False, otherwise
|
|
300
|
+
"""
|
|
301
|
+
sigma_1, sigma_2 = sig
|
|
302
|
+
m = self._dump_to_zp_element(message) # serialize the message to an element
|
|
303
|
+
if pair(sigma_1, pk['X_tilde'] * (pk['Y_tilde'] ** m)) == pair(sigma_2, pk['g_tilde']):
|
|
304
|
+
return True
|
|
305
|
+
return False
|
|
306
|
+
|
|
307
|
+
|
|
308
|
+
class PS_BlindMultiMessageSig(PS_BlindSig):
|
|
309
|
+
|
|
310
|
+
def __init__(self, groupObj):
|
|
311
|
+
PS_BlindSig.__init__(self, groupObj)
|
|
312
|
+
|
|
313
|
+
def keygen(self, num_messages):
|
|
314
|
+
"""
|
|
315
|
+
This function is used to generate the secret key and the public key of the signer
|
|
316
|
+
Outputs:
|
|
317
|
+
- sk: Secret key
|
|
318
|
+
- pk: public key
|
|
319
|
+
"""
|
|
320
|
+
g = self.group.random(G1)
|
|
321
|
+
g_tilde = self.group.random(G2)
|
|
322
|
+
x = self.group.random()
|
|
323
|
+
ys = [self.group.random() for i in range(num_messages)]
|
|
324
|
+
|
|
325
|
+
X = g ** x
|
|
326
|
+
Ys = [g ** y for y in ys]
|
|
327
|
+
X_tilde = g_tilde ** x
|
|
328
|
+
Ys_tilde = [g_tilde ** y for y in ys]
|
|
329
|
+
|
|
330
|
+
pk = {'g': g, 'Ys': Ys, 'g_tilde': g_tilde, 'X_tilde': X_tilde, 'Ys_tilde': Ys_tilde}
|
|
331
|
+
sk = {'X': X}
|
|
332
|
+
|
|
333
|
+
return sk, pk
|
|
334
|
+
|
|
335
|
+
def blind(self, messages, pk):
|
|
336
|
+
"""
|
|
337
|
+
This function takes a message and blinds it to return a blinded message.
|
|
338
|
+
Inputs:
|
|
339
|
+
- messages: List of messages to be blinded
|
|
340
|
+
- pk: pk is needed to know some of the public parameters used in message blinding
|
|
341
|
+
Outputs:
|
|
342
|
+
- C: A blinded message
|
|
343
|
+
- t: Blind random value
|
|
344
|
+
"""
|
|
345
|
+
ms = [self._dump_to_zp_element(message) for message in messages] # serialize the message to an element
|
|
346
|
+
t = self.group.random()
|
|
347
|
+
Y_pow_m_product = pk['Ys'][0] ** ms[0]
|
|
348
|
+
for i in range(1, len(ms)):
|
|
349
|
+
Y_pow_m_product *= pk['Ys'][i] ** ms[i]
|
|
350
|
+
C = (pk['g'] ** t) * Y_pow_m_product
|
|
351
|
+
|
|
352
|
+
return C, t
|
|
353
|
+
|
|
354
|
+
def sign(self, sk, pk, blinded_message):
|
|
355
|
+
"""
|
|
356
|
+
This function is used for the signer to sign a message
|
|
357
|
+
Inputs:
|
|
358
|
+
- sk: Secret key of the signer
|
|
359
|
+
- pk: Public key of the signer
|
|
360
|
+
- blinded_message: A blinded message to be signed
|
|
361
|
+
Outputs:
|
|
362
|
+
- sigma_dash: Signature on the blinded message
|
|
363
|
+
"""
|
|
364
|
+
C = blinded_message
|
|
365
|
+
u = self.group.random()
|
|
366
|
+
sigma_dash_1 = pk['g'] ** u
|
|
367
|
+
sigma_dash_2 = (sk['X'] * C) ** u
|
|
368
|
+
sigma_dash = (sigma_dash_1, sigma_dash_2)
|
|
369
|
+
|
|
370
|
+
return sigma_dash
|
|
371
|
+
|
|
372
|
+
def unblind(self, blinded_sig, t):
|
|
373
|
+
"""
|
|
374
|
+
This function takes a blinded signature and returns the unblinded signature
|
|
375
|
+
Inputs:
|
|
376
|
+
- blinded_sig: Blinded signature
|
|
377
|
+
- t: random number used to blind the original message
|
|
378
|
+
Outputs:
|
|
379
|
+
- sigma: unblinded signature
|
|
380
|
+
"""
|
|
381
|
+
sigma_dash_1, sigma_dash_2 = blinded_sig
|
|
382
|
+
sigma_1 = sigma_dash_1
|
|
383
|
+
sigma_2 = sigma_dash_2 / (sigma_dash_1 ** t)
|
|
384
|
+
|
|
385
|
+
sigma = (sigma_1, sigma_2)
|
|
386
|
+
return sigma
|
|
387
|
+
|
|
388
|
+
def verify(self, messages, pk, sig) -> bool:
|
|
389
|
+
"""
|
|
390
|
+
This function is used for the user to verify a signature on a specific message using the message and the public
|
|
391
|
+
key of the signer.
|
|
392
|
+
Inputs:
|
|
393
|
+
- messages: List of messages
|
|
394
|
+
- pk: Public key
|
|
395
|
+
- sig: signature
|
|
396
|
+
Outputs:
|
|
397
|
+
- True if the signature is valid on the message by the user whose public key is pk
|
|
398
|
+
- False, otherwise
|
|
399
|
+
"""
|
|
400
|
+
sigma_1, sigma_2 = sig
|
|
401
|
+
ms = [self._dump_to_zp_element(message) for message in messages] # serialize the message to an element
|
|
402
|
+
Y_pow_m_product = pk['Ys_tilde'][0] ** ms[0]
|
|
403
|
+
for i in range(1, len(ms)):
|
|
404
|
+
Y_pow_m_product *= pk['Ys_tilde'][i] ** ms[i]
|
|
405
|
+
if pair(sigma_1, pk['X_tilde'] * Y_pow_m_product) == pair(sigma_2, pk['g_tilde']):
|
|
406
|
+
return True
|
|
407
|
+
return False
|
|
408
|
+
|
|
409
|
+
|
|
410
|
+
class PS_SigSingleMessage(PS_Sig):
|
|
411
|
+
|
|
412
|
+
def __init__(self, groupObj):
|
|
413
|
+
PS_Sig.__init__(self, groupObj)
|
|
414
|
+
|
|
415
|
+
def keygen(self):
|
|
416
|
+
"""
|
|
417
|
+
This function is used to generate the secret key and the public key of the signer
|
|
418
|
+
"""
|
|
419
|
+
g_tilde = self.group.random(G2)
|
|
420
|
+
x = self.group.random()
|
|
421
|
+
y = self.group.random()
|
|
422
|
+
X_tilde = g_tilde ** x
|
|
423
|
+
Y_tilde = g_tilde ** y
|
|
424
|
+
|
|
425
|
+
pk = {'g_tilde': g_tilde, 'X_tilde': X_tilde, 'Y_tilde': Y_tilde}
|
|
426
|
+
sk = {'x': x, 'y': y}
|
|
427
|
+
|
|
428
|
+
return sk, pk
|
|
429
|
+
|
|
430
|
+
def sign(self, sk, message):
|
|
431
|
+
"""
|
|
432
|
+
This function is used for the signer to sign a message
|
|
433
|
+
Inputs:
|
|
434
|
+
- sk: Secret key of the signer
|
|
435
|
+
- message: message to be signed
|
|
436
|
+
Outputs:
|
|
437
|
+
- sigma: Signature on the message
|
|
438
|
+
"""
|
|
439
|
+
m = self._dump_to_zp_element(message) # serialize the message to an element
|
|
440
|
+
h = self.group.random(G1)
|
|
441
|
+
sigma = (h, h ** (sk['x'] + sk['y'] * m))
|
|
442
|
+
|
|
443
|
+
return sigma
|
|
444
|
+
|
|
445
|
+
def verify(self, message, pk, sig) -> bool:
|
|
446
|
+
"""
|
|
447
|
+
This function is used for the user to verify a signature on a specific message using the message and the public
|
|
448
|
+
key of the signer.
|
|
449
|
+
Inputs:
|
|
450
|
+
- message: The message
|
|
451
|
+
- pk: Public key
|
|
452
|
+
- sig: signature
|
|
453
|
+
Outputs:
|
|
454
|
+
- True if the signature is valid on the message by the user whose public key is pk
|
|
455
|
+
- False, otherwise
|
|
456
|
+
"""
|
|
457
|
+
sigma_1, sigma_2 = sig
|
|
458
|
+
m = self._dump_to_zp_element(message) # serialize the message to an element
|
|
459
|
+
if pair(sigma_1, pk['X_tilde'] * (pk['Y_tilde'] ** m)) == pair(sigma_2, pk['g_tilde']):
|
|
460
|
+
return True
|
|
461
|
+
return False
|
|
462
|
+
|
|
463
|
+
|
|
464
|
+
class PS_SigMultiMessage(PS_Sig):
|
|
465
|
+
|
|
466
|
+
def __init__(self, groupObj):
|
|
467
|
+
PS_Sig.__init__(self, groupObj)
|
|
468
|
+
|
|
469
|
+
def keygen(self, num_messages):
|
|
470
|
+
"""
|
|
471
|
+
This function is used to generate the secret key and the public key of the signer
|
|
472
|
+
Inputs:
|
|
473
|
+
- num_message: Number of messages
|
|
474
|
+
"""
|
|
475
|
+
g_tilde = self.group.random(G2)
|
|
476
|
+
x = self.group.random()
|
|
477
|
+
ys = [self.group.random() for i in range(num_messages)]
|
|
478
|
+
X_tilde = g_tilde ** x
|
|
479
|
+
Ys_tilde = [g_tilde ** y for y in ys]
|
|
480
|
+
|
|
481
|
+
pk = {'g_tilde': g_tilde, 'X_tilde': X_tilde, 'Ys_tilde': Ys_tilde}
|
|
482
|
+
sk = {'x': x, 'ys': ys}
|
|
483
|
+
|
|
484
|
+
return sk, pk
|
|
485
|
+
|
|
486
|
+
def sign(self, sk, messages):
|
|
487
|
+
"""
|
|
488
|
+
This function is used for the signer to sign a message
|
|
489
|
+
Inputs:
|
|
490
|
+
- sk: Secret key of the signer
|
|
491
|
+
- messages: List of messages to be signed
|
|
492
|
+
Outputs:
|
|
493
|
+
- sigma: Signature on the message
|
|
494
|
+
"""
|
|
495
|
+
ms = [self._dump_to_zp_element(message) for message in messages]
|
|
496
|
+
h = self.group.random(G1)
|
|
497
|
+
Y_multiply_m_sum = sk['ys'][0] * ms[0]
|
|
498
|
+
for i in range(1, len(ms)):
|
|
499
|
+
Y_multiply_m_sum += sk['ys'][i] * ms[i]
|
|
500
|
+
sigma = (h, h ** (sk['x'] + Y_multiply_m_sum))
|
|
501
|
+
|
|
502
|
+
return sigma
|
|
503
|
+
|
|
504
|
+
def verify(self, messages, pk, sig) -> bool:
|
|
505
|
+
"""
|
|
506
|
+
This function is used for the user to verify a signature on a specific message using the message and the public
|
|
507
|
+
key of the signer.
|
|
508
|
+
Inputs:
|
|
509
|
+
- messages: The list of messages
|
|
510
|
+
- pk: Public key
|
|
511
|
+
- sig: signature
|
|
512
|
+
Outputs:
|
|
513
|
+
- True if the signature is valid on the message by the user whose public key is pk
|
|
514
|
+
- False, otherwise
|
|
515
|
+
"""
|
|
516
|
+
sigma_1, sigma_2 = sig
|
|
517
|
+
ms = [self._dump_to_zp_element(message) for message in messages]
|
|
518
|
+
Y_tilde_pow_m_product = pk['Ys_tilde'][0] ** ms[0]
|
|
519
|
+
for i in range(1, len(ms)):
|
|
520
|
+
Y_tilde_pow_m_product *= pk['Ys_tilde'][i] ** ms[i]
|
|
521
|
+
if pair(sigma_1, pk['X_tilde'] * Y_tilde_pow_m_product) == pair(sigma_2, pk['g_tilde']):
|
|
522
|
+
return True
|
|
523
|
+
return False
|
|
524
|
+
|
|
525
|
+
|
|
526
|
+
def single_message_main(debug=False):
|
|
527
|
+
print("************************************** Single Message Main ************************************************")
|
|
528
|
+
message = "Welcome to PS signature scheme"
|
|
529
|
+
group_obj = PairingGroup('MNT224')
|
|
530
|
+
ps_sig = PS_SigSingleMessage(group_obj)
|
|
531
|
+
|
|
532
|
+
sk, pk = ps_sig.keygen()
|
|
533
|
+
if debug:
|
|
534
|
+
print("sk = ", sk)
|
|
535
|
+
print("pk = ", pk)
|
|
536
|
+
|
|
537
|
+
sigma = ps_sig.sign(sk, message)
|
|
538
|
+
if debug:
|
|
539
|
+
print("signature: ", sigma)
|
|
540
|
+
verification_res = ps_sig.verify(message, pk, sigma)
|
|
541
|
+
if verification_res:
|
|
542
|
+
print("Verification is successful")
|
|
543
|
+
else:
|
|
544
|
+
print("Error! This signature is not valid on this message")
|
|
545
|
+
print("***********************************************************************************************************")
|
|
546
|
+
|
|
547
|
+
|
|
548
|
+
def multi_message_main(debug=False):
|
|
549
|
+
print("**************************************** Multi Messages Main **********************************************")
|
|
550
|
+
messages = ["Welcome to PS signature scheme", "PS can be used in many applications", "Most importantly, it can generate anonymous signatures"]
|
|
551
|
+
group_obj = PairingGroup('MNT224')
|
|
552
|
+
ps_sig = PS_SigMultiMessage(group_obj)
|
|
553
|
+
|
|
554
|
+
sk, pk = ps_sig.keygen(len(messages))
|
|
555
|
+
if debug:
|
|
556
|
+
print("sk = ", sk)
|
|
557
|
+
print("pk = ", pk)
|
|
558
|
+
|
|
559
|
+
sigma = ps_sig.sign(sk, messages)
|
|
560
|
+
if debug:
|
|
561
|
+
print("signature: ", sigma)
|
|
562
|
+
verification_res = ps_sig.verify(messages, pk, sigma)
|
|
563
|
+
if verification_res:
|
|
564
|
+
print("Verification is successful")
|
|
565
|
+
else:
|
|
566
|
+
print("Error! This signature is not valid on this message")
|
|
567
|
+
print("***********************************************************************************************************")
|
|
568
|
+
|
|
569
|
+
|
|
570
|
+
def blinded_single_message_main(debug=False):
|
|
571
|
+
print("******************************** Blinded Single Message Main **********************************************")
|
|
572
|
+
message = "Welcome to PS signature scheme"
|
|
573
|
+
group_obj = PairingGroup('MNT224')
|
|
574
|
+
ps_sig = PS_BlindSingleMessageSig(group_obj)
|
|
575
|
+
|
|
576
|
+
sk, pk = ps_sig.keygen()
|
|
577
|
+
if debug:
|
|
578
|
+
print("sk = ", sk)
|
|
579
|
+
print("pk = ", pk)
|
|
580
|
+
|
|
581
|
+
blinded_message, t = ps_sig.blind(message, pk)
|
|
582
|
+
if debug:
|
|
583
|
+
print("Blinded Message: ", blinded_message)
|
|
584
|
+
|
|
585
|
+
# Interactive ZKP
|
|
586
|
+
# user proves knowledge of the secret message to the signer to accept to sign the blinded message
|
|
587
|
+
prover_knowledge_of_secret_message_status = ps_sig.proof_of_knowledge_of_commitment_secrets(t, [message], blinded_message, pk, group_obj, debug)
|
|
588
|
+
print("Verifier validation of the proof status: ", prover_knowledge_of_secret_message_status)
|
|
589
|
+
|
|
590
|
+
if prover_knowledge_of_secret_message_status:
|
|
591
|
+
blinded_signature = ps_sig.sign(sk, pk, blinded_message)
|
|
592
|
+
if debug:
|
|
593
|
+
print("Blinded signature: ", blinded_signature)
|
|
594
|
+
|
|
595
|
+
signature = ps_sig.unblind(blinded_signature, t)
|
|
596
|
+
if debug:
|
|
597
|
+
print("Signature: ", signature)
|
|
598
|
+
verification_res = ps_sig.verify(message, pk, signature)
|
|
599
|
+
if verification_res:
|
|
600
|
+
print("Verification is successful")
|
|
601
|
+
else:
|
|
602
|
+
print("Error! This signature is not valid on this message")
|
|
603
|
+
else:
|
|
604
|
+
print("Error! Proof of knowledge verification error")
|
|
605
|
+
print("***********************************************************************************************************")
|
|
606
|
+
|
|
607
|
+
|
|
608
|
+
def blinded_multi_message_main(debug=False):
|
|
609
|
+
print("******************************** Blinded Multi Message Main ***********************************************")
|
|
610
|
+
messages = ["Welcome to PS signature scheme", "PS can be used in many applications", "Most importantly, it can generate anonymous signatures"]
|
|
611
|
+
group_obj = PairingGroup('MNT224')
|
|
612
|
+
ps_sig = PS_BlindMultiMessageSig(group_obj)
|
|
613
|
+
|
|
614
|
+
sk, pk = ps_sig.keygen(len(messages))
|
|
615
|
+
if debug:
|
|
616
|
+
print("sk = ", sk)
|
|
617
|
+
print("pk = ", pk)
|
|
618
|
+
|
|
619
|
+
blinded_message, t = ps_sig.blind(messages, pk)
|
|
620
|
+
if debug:
|
|
621
|
+
print("Blinded Message: ", blinded_message)
|
|
622
|
+
# Interactive ZKP
|
|
623
|
+
# user proves knowledge of the secret message to the signer to accept to sign the blinded message
|
|
624
|
+
prover_knowledge_of_secret_messages_status = ps_sig.proof_of_knowledge_of_commitment_secrets(t, messages,
|
|
625
|
+
blinded_message, pk,
|
|
626
|
+
group_obj, debug)
|
|
627
|
+
print("Verifier validation of the proof status: ", prover_knowledge_of_secret_messages_status)
|
|
628
|
+
|
|
629
|
+
if prover_knowledge_of_secret_messages_status:
|
|
630
|
+
blinded_signature = ps_sig.sign(sk, pk, blinded_message)
|
|
631
|
+
if debug:
|
|
632
|
+
print("Blinded signature: ", blinded_signature)
|
|
633
|
+
|
|
634
|
+
signature = ps_sig.unblind(blinded_signature, t)
|
|
635
|
+
if debug:
|
|
636
|
+
print("Signature: ", signature)
|
|
637
|
+
|
|
638
|
+
verification_res = ps_sig.verify(messages, pk, signature)
|
|
639
|
+
if verification_res:
|
|
640
|
+
print("Verification is successful")
|
|
641
|
+
else:
|
|
642
|
+
print("Error! This signature is not valid on this message")
|
|
643
|
+
else:
|
|
644
|
+
print("Error! Proof of knowledge verification error")
|
|
645
|
+
print("***********************************************************************************************************")
|
|
646
|
+
|
|
647
|
+
|
|
648
|
+
if __name__ == "__main__":
|
|
649
|
+
debug = True
|
|
650
|
+
single_message_main(debug)
|
|
651
|
+
multi_message_main(debug)
|
|
652
|
+
blinded_single_message_main(debug)
|
|
653
|
+
blinded_multi_message_main(debug)
|
|
654
|
+
print("done")
|