async def verifyNonRevocation(self, proofInput: ProofInput, schemaKey, cHash, nonRevocProof: NonRevocProof) \ -> Sequence[T]: if await self._wallet.shouldUpdateAccumulator( schemaId=ID(schemaKey), ts=proofInput.ts, seqNo=proofInput.seqNo): await self._wallet.updateAccumulator(schemaId=ID(schemaKey), ts=proofInput.ts, seqNo=proofInput.seqNo) pkR = await self._wallet.getPublicKeyRevocation(ID(schemaKey)) accum = await self._wallet.getAccumulator(ID(schemaKey)) accumPk = await self._wallet.getPublicKeyAccumulator(ID(schemaKey)) CProof = nonRevocProof.CProof XList = nonRevocProof.XList group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits THatExpected = createTauListExpectedValues(pkR, accum, accumPk, CProof) THatCalc = createTauListValues(pkR, accum, XList, CProof) chNum_z = int_to_ZR(cHash, group) return [(x ** chNum_z) * y for x, y in zip(THatExpected.asList(), THatCalc.asList())]
def _genCListParams(self, schemaId, c2: NonRevocationClaim) -> NonRevocProofXList: group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits rho = group.random(cmod.ZR) r = group.random(cmod.ZR) rPrime = group.random(cmod.ZR) rPrimePrime = group.random(cmod.ZR) rPrimePrimePrime = group.random(cmod.ZR) o = group.random(cmod.ZR) oPrime = group.random(cmod.ZR) m = rho * c2.c mPrime = r * rPrimePrime t = o * c2.c tPrime = oPrime * rPrimePrime m2 = group.init(cmod.ZR, int(c2.m2)) return NonRevocProofXList(rho=rho, r=r, rPrime=rPrime, rPrimePrime=rPrimePrime, rPrimePrimePrime=rPrimePrimePrime, o=o, oPrime=oPrime, m=m, mPrime=mPrime, t=t, tPrime=tPrime, m2=m2, s=c2.v, c=c2.c)
async def genRevocationKeys( self) -> (RevocationPublicKey, RevocationSecretKey): group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits g = group.random(cmod.G1) gprime = group.random(cmod.G2) h = group.random(cmod.G1) # random element of the group G h0 = group.random(cmod.G1) h1 = group.random(cmod.G1) h2 = group.random(cmod.G1) htilde = group.random(cmod.G1) u = group.random(cmod.G2) hhat = group.random(cmod.G2) qr = group.order() # order q_R of the group x = group.random(cmod.ZR) # random(qr) sk = group.random(cmod.ZR) # random(qr) pk = g**sk y = hhat**x return (RevocationPublicKey(qr, g, gprime, h, h0, h1, h2, htilde, hhat, u, pk, y), RevocationSecretKey(x, sk))
async def genClaimInitData(self, schemaId: ID) -> ClaimInitDataType: group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits pkR = await self._wallet.getPublicKeyRevocation(schemaId) vrPrime = group.random(cmod.ZR) Ur = (pkR.h2**vrPrime) return ClaimInitDataType(U=Ur, vPrime=vrPrime)
def serializeToStr(n): if isCryptoInteger(n): return CRYPTO_INT_PREFIX + cmod.serialize(n).decode() if isInteger(n): return INT_PREFIX + str(n) if isGroupElement(n): return GROUP_PREFIX + cmod.PairingGroup(PAIRING_GROUP).serialize( n).decode() return n
def testGetHashGroup(): group = cmod.PairingGroup(PAIRING_GROUP) input = [ group.random(cmod.G1), group.random(cmod.G1), group.random(cmod.G1) ] _checkHashEqual(input)
def testToFromDictWithStrValuesSubDicts(): cmod.PairingGroup(PAIRING_GROUP) dictionary = OrderedDict( (('4', {'aaa', 'bbb'}), ('2', OrderedDict( (('33', OrderedDict((('45', 45), ('11', 11)))), ('23', OrderedDict( (('47', 47), ('34', 34))))))), ('3', 3))) assert dictionary == fromDictWithStrValues(toDictWithStrValues(dictionary))
def testGetHashMixed(): group = cmod.PairingGroup(PAIRING_GROUP) P_PRIME1, Q_PRIME1 = primes.get("prime1") input = [ P_PRIME1, Q_PRIME1, group.random(cmod.G1), group.random(cmod.G1), 0xb1134a647eb818069c089e7694f63e6d, 0x57fbf9dc8c8e6acde33de98c6d747b28c ] _checkHashEqual(input)
async def finalizeProof(self, schemaId, cH, initProof: NonRevocInitProof) -> NonRevocProof: if not initProof: return None group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits chNum_z = int_to_ZR(cH, group) XList = NonRevocProofXList.fromList([ x - chNum_z * y for x, y in zip(initProof.TauListParams.asList(), initProof.CListParams.asList()) ]) return NonRevocProof(XList, initProof.CList)
def testToFromDictWithStrValuesLists(): group = cmod.PairingGroup(PAIRING_GROUP) dictionary = OrderedDict( (('47', []), ('7', [cmod.integer(111) % 11, cmod.integer(222), cmod.integer(333) % 45]), ('6', [ group.init(cmod.ZR, 555), group.random(cmod.G1), group.random(cmod.G1) ]))) assert dictionary == fromDictWithStrValues(toDictWithStrValues(dictionary))
def deserializeFromStr(n: str): if isStr(n) and n.startswith(CRYPTO_INT_PREFIX): n = n[len(CRYPTO_INT_PREFIX):].encode() return cmod.deserialize(n) if isStr(n) and n.startswith(INT_PREFIX): n = n[len(INT_PREFIX):] return int(n) if isStr(n) and n.startswith(GROUP_PREFIX): n = n[len(GROUP_PREFIX):].encode() res = cmod.PairingGroup(PAIRING_GROUP).deserialize(n) # A fix for Identity element as serialized/deserialized not correctly if str(res) == '[0, 0]': return groupIdentityG1() return res return n
def get_hash_as_int(*args, group: cmod.PairingGroup = None): """ Enumerate over the input tuple and generate a hash using the tuple values :param args: sequence of either group or integer elements :param group: pairing group if an element is a group element :return: """ group = group if group else cmod.PairingGroup(PAIRING_GROUP) h_challenge = sha256() serialedArgs = [group.serialize(arg) if isGroupElement(arg) else cmod.Conversion.IP2OS(arg) for arg in args] for arg in sorted(serialedArgs): h_challenge.update(arg) return bytes_to_int(h_challenge.digest())
def testToFromDictWithStrValuesMixed(): group = cmod.PairingGroup(PAIRING_GROUP) dictionary = OrderedDict( (('4', {'aaa', 'bbb'}), ('2', OrderedDict( (('33', OrderedDict((('45', 45), ('11', 11)))), ('23', OrderedDict( (('47', 47), ('34', 34))))))), ('1', {}), ('3', 3), ('5', cmod.integer(111) % 11), ('7', [cmod.integer(111) % 11, cmod.integer(222), cmod.integer(333) % 45]), ('6', [ group.init(cmod.ZR, 555), group.random(cmod.G1), group.random(cmod.G1) ]), ('10', group.random(cmod.G1)))) assert dictionary == fromDictWithStrValues(toDictWithStrValues(dictionary))
async def issueNonRevocationClaim(self, schemaId: ID, Ur, iA, i) -> ( NonRevocationClaim, Accumulator, TimestampType): accum = await self._wallet.getAccumulator(schemaId) pkR = await self._wallet.getPublicKeyRevocation(schemaId) skR = await self._wallet.getSecretKeyRevocation(schemaId) g = await self._wallet.getTails(schemaId) skAccum = await self._wallet.getSecretKeyAccumulator(schemaId) m2 = await self._wallet.getContextAttr(schemaId) if accum.isFull(): raise ValueError("Accumulator is full. New one must be issued.") # TODO: currently all revo creds are issued sequentially group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits i = i if i else accum.currentI accum.currentI += 1 vrPrimeprime = group.random(cmod.ZR) c = group.random(cmod.ZR) m2 = group.init(cmod.ZR, int(m2)) sigma = (pkR.h0 * (pkR.h1 ** m2) * Ur * g[i] * ( pkR.h2 ** vrPrimeprime)) ** (1 / (skR.x + c)) omega = groupIdentityG1() for j in accum.V: omega *= g[accum.L + 1 - j + i] sigmai = pkR.g ** (1 / (skR.sk + (skAccum.gamma ** i))) ui = pkR.u ** (skAccum.gamma ** i) accum.acc *= g[accum.L + 1 - i] accum.V.add(i) witness = Witness(sigmai, ui, g[i], omega, accum.V.copy()) ts = currentTimestampMillisec() return ( NonRevocationClaim(accum.iA, sigma, c, vrPrimeprime, witness, g[i], i, m2), accum, ts)
async def issueAccumulator(self, schemaId, iA, L) \ -> ( Accumulator, TailsType, AccumulatorPublicKey, AccumulatorSecretKey): pkR = await self._wallet.getPublicKeyRevocation(schemaId) group = cmod.PairingGroup(PAIRING_GROUP) gamma = group.random(cmod.ZR) g = {} gCount = 2 * L for i in range(gCount): if i != L + 1: g[i] = pkR.g ** (gamma ** i) z = cmod.pair(pkR.g, pkR.g) ** (gamma ** (L + 1)) acc = 1 V = set() accPK = AccumulatorPublicKey(z) accSK = AccumulatorSecretKey(gamma) accum = Accumulator(iA, acc, V, L) return accum, g, accPK, accSK
async def issueAccumulator(self, schemaId, iA, L) \ -> (Accumulator, Tails, AccumulatorPublicKey, AccumulatorSecretKey): pkR = await self._wallet.getPublicKeyRevocation(schemaId) group = cmod.PairingGroup(PAIRING_GROUP) gamma = group.random(cmod.ZR) tails = Tails() gCount = 2 * L for i in range(gCount): if i != L + 1: gVal = pkR.g**(gamma**i) gPrimeVal = pkR.gprime**(gamma**i) tails.addValue(i, gVal, gPrimeVal) z = cmod.pair(pkR.g, pkR.gprime)**(gamma**(L + 1)) acc = 1 V = set() accPK = AccumulatorPublicKey(z) accSK = AccumulatorSecretKey(gamma) accum = Accumulator(iA, acc, V, L) return accum, tails, accPK, accSK
def testGroupElementSerializeToFromStr(): value = cmod.PairingGroup(PAIRING_GROUP).random(cmod.G1) assert value == deserializeFromStr(serializeToStr(value))
def groupIdentityG2(): return cmod.PairingGroup(PAIRING_GROUP).init(cmod.G2, 0)
def testGroupElementZRIdentitySerializeToFromStr(): elem = cmod.PairingGroup(PAIRING_GROUP).init(cmod.ZR, 555) identity = elem / elem assert identity == deserializeFromStr(serializeToStr(identity))
def _genTauListParams(self, schemaId) -> NonRevocProofXList: group = cmod.PairingGroup( PAIRING_GROUP) # super singular curve, 1024 bits return NonRevocProofXList(group=group)
def testGroupElementG1IdentitySerializeToFromStr(): elem = cmod.PairingGroup(PAIRING_GROUP).random(cmod.G1) identity = cmod.PairingGroup(PAIRING_GROUP).init(cmod.G1, elem / elem) assert identity == deserializeFromStr(serializeToStr(identity))
def testToFromDictWithStrValues(): group = cmod.PairingGroup(PAIRING_GROUP) dictionary = OrderedDict( (('43', '43'), ('3', 3), ('5', cmod.integer(111) % 11), ('10', group.random(cmod.G1)))) assert dictionary == fromDictWithStrValues(toDictWithStrValues(dictionary))