(Assume we perform $\text{mod} \, n$ everywhere)
Let’s define the presignature as:
$$
s = \hat k + H(\mathrm{ R'.x \;||\; msg \;||\; P.x} ) \cdot x
$$
where,
$$
\hat{k} =
\begin{cases}
k & \text{if } R'.y \text{ is even} \
-k & \text{if } R'.y \text{ is odd}
\end{cases}
$$
Now, We can compute the adaptor from the presignature in two different ways.
Method 1:
Compute $G \cdot s - e \cdot P$ which equals $\hat{k} \cdot G$
Let $\mathrm{R' = \text{lift\_x(\,presig[1:33]\,)}}$ or secp256k1_xonly_pubkey_load
Now compute the adaptor point as:
$$
T =
\begin{cases}
R' - \hat{k} \cdot G & \text{if presig[0] is 2} \
-(R' - \hat{k}\cdot G) & \text{if presig[0] is 3}
\end{cases}
$$
Method 2:
Compute $G \cdot s - e \cdot P$ which equals $\hat{k} \cdot G$
Let $\mathrm{R' = \text{cpoint(\,presig[0:33]\,)}}$ or secp256k1_pubkey_load
Now compute the adaptor point as:
$$
T =
\begin{cases}
R' - \hat{k} \cdot G & \text{if } R'.y \text{ is even} \
R' + \hat{k}\cdot G & \text{if } R'.y \text{ is odd}
\end{cases}
$$
We currently follow Method 1, which relies on a presig[0] parity check to compute the adaptor point. This makes things ugly. For instance, our current schnorr_extract_adaptor would still return some garbage T when presig[0] = 4.
I like Method 2 because it won’t rely on such a parity check. It will simply use has_even_y(R').
(Assume we perform $\text{mod} \, n$ everywhere) Let’s define the presignature as:
$$ s = \hat k + H(\mathrm{ R'.x \;||\; msg \;||\; P.x} ) \cdot x $$
where,
$$ \hat{k} = \begin{cases} k & \text{if } R'.y \text{ is even} \ -k & \text{if } R'.y \text{ is odd} \end{cases} $$
Now, We can compute the adaptor from the presignature in two different ways.
Method 1:
secp256k1_xonly_pubkey_load
$$ T = \begin{cases} R' - \hat{k} \cdot G & \text{if presig[0] is 2} \ -(R' - \hat{k}\cdot G) & \text{if presig[0] is 3} \end{cases} $$
Method 2:
secp256k1_pubkey_load
$$ T = \begin{cases} R' - \hat{k} \cdot G & \text{if } R'.y \text{ is even} \ R' + \hat{k}\cdot G & \text{if } R'.y \text{ is odd} \end{cases} $$
We currently follow Method 1, which relies on a
presig[0]
parity check to compute the adaptor point. This makes things ugly. For instance, our currentschnorr_extract_adaptor
would still return some garbageT
whenpresig[0] = 4
.I like Method 2 because it won’t rely on such a parity check. It will simply use
has_even_y(R')
.