Open ebfull opened 4 years ago
Note that in settings like Bulletproofs over Ristretto255, where your k
is like 2
, this is a super efficient technique compared to previous approaches.
@ebfull wrote:
It's possible that plookup helps here too, I haven't really thought about it. But if plookup isn't available in your setting, this seems like a decent alternative.
I'm not sure the deterministic square root method pays off when Plookup is available, unless you use a table lookup for αd. Let's assume that we have a 211-size table available for some other reason — it can be a table representing any function of {0..211-1} to some arbitrary codomain. This is sufficient to do an 11-bit range check in one row. But if we want to use lookups for αd, we would need an extra, specialized table for that purpose.
Even without a table for αd, you can probably do two bits of d per row for that computation, and you can merge the boolean (actually base-4) checks for d with that. Also you can do the squarings for e2k more efficiently in PLONK; you can probably do 3 or 4 squarings per row (let's say 4). So that's ~16 rows for αd and another 8 for e2k, which is 24. But with an 11-bit table you only need 23 rows to do a 253-bit boolean decomposition.
In other words, if we're able to use table lookups for the boolean decomposition but don't have a specialized table to compute αd in the deterministic square root method, then the latter only just about breaks even (and is more complex).
Note that @dlubarov also concluded in https://github.com/mir-protocol/plonky/pull/7 that it didn't pay off for them, for similar reasons.
Our circuit is over a field
Fp
wherep - 1 = 2^k * t
witht
odd and integerk > 0
. (k
is often around32
in practice.) Leta
be a nonzero square. The prover will witnessb
such thatb^2 = a
. We wish to force the prover to witnessb
rather than-b
w.l.o.g. by distinguishing between them deterministically. The standard trick is to perform a boolean decomposition ofb
and see if e.g. the parity bit is zero, or perhaps check thatb < (p - 1) / 2
or something. Boolean decompositions of full field elements are needlessly expensive in the circuit though; here's a technique that allows us to reduce this cost.Let's rewrite
b
asb = c * alpha^d
wherec
is in the multiplicative ordert
subgroup ofFp*
,alpha
is an element of multiplicative order2^k
, andd
is an integer modulo2^k
. There is a unique solution for(c, d)
for a nonzerob
that can be obtained by the prover efficiently for smallish values ofk
. In order to distinguishb
from-b
observe that the most significant digit ofd
is set only for one of the possible values of the square root. Thus we can have the prover witnessk - 1
booleans representingd
(constraining them to the choice ofb
where the most significant digit ofd
is not set) and computealpha^d
in the circuit usingk - 2
conditional multiplications by precomputed powers ofalpha
. It then suffices to see thatc
is in the multiplicative ordert
subgroup ofFp*
to see that the choice ofb
is the only choice available to the prover for the given squarea
. This can be done by having the prover witnesse = c^{{2^k}^-1 mod t}
and computingc = e^{2^k}
in the circuit directly withk
squarings to "kill" the2^k
order subgroup. Finally, we check thatb = c * alpha^d
andb * b = a
to establish with3k - 1
multiplication constraints thatb
is a deterministic square root ofa
. Sincek
is usually around32
this is quite a bit more efficient (less than100
constraints) than a boolean decomposition of the full field element (aroundlog_2(p)
constraints).It's possible that plookup helps here too, I haven't really thought about it. But if plookup isn't available in your setting, this seems like a decent alternative.