]> git.codecow.com Git - nano25519.git/commitdiff
Simplify some arithmetic. Fix documentation.
authorChris Duncan <chris@codecow.com>
Thu, 1 Oct 2026 21:24:04 +0000 (14:24 -0700)
committerChris Duncan <chris@codecow.com>
Thu, 1 Oct 2026 21:24:04 +0000 (14:24 -0700)
src/assembly/ed25519/fe.ts
src/assembly/ed25519/ge.ts
src/assembly/ed25519/p.ts

index e157b1db6b6c9505e0e61aac39dc315714ad341f..a1f30ee041af9dea97ffa99d89972107e15541d0 100644 (file)
@@ -52,7 +52,7 @@ export function fe_0 (h: FieldElement): void {
 @inline
 export function fe_1 (h: FieldElement): void {
        fe_0(h)
-       store<i32>(changetype<usize>(h), 1, 0)
+       h[0] = 1
 }
 
 /**
index 4032647cbe040a1cafdede06ca9551745c50060f..de3c2b7bf73bb2f2fb00f6a64e6a080578e66fac 100644 (file)
@@ -94,38 +94,55 @@ const vxx: FieldElement = fe()
 const m_root_check: FieldElement = fe()
 const p_root_check: FieldElement = fe()
 /**
- * @returns -1 if bytes fail to decode to a point, 0 if decoding is successful
+ * Variable-time point negation converted from byte representation.
+ *
+ * Compiler optimization of vartime function is OK.
+ *
+ * @returns {i32} 0 if `s` decodes to a valid point, else -1
  */
 export function ge_frombytes_negate_vartime (h: ge_p3, s: StaticArray<u8>): i32 {
-       fe_frombytes(h.Y, s)
        fe_1(h.Z)
+       fe_frombytes(h.Y, s)
+
+       // u = y²-1
+       // v = dy²+1
        fe_sq(u, h.Y)
        fe_mul(v, u, ed25519_d)
-       fe_sub(u, u, h.Z) /* u = y^2-1 */
-       fe_add(v, v, h.Z) /* v = dy^2+1 */
+       u[0] -= 1
+       v[0] += 1
 
+       // v3 = v³
        fe_sq(v3, v)
-       fe_mul(v3, v3, v) /* v3 = v^3 */
+       fe_mul(v3, v3, v)
+
+       // x = uv⁷
        fe_sq(h.X, v3)
        fe_mul(h.X, h.X, v)
-       fe_mul(h.X, h.X, u) /* x = uv^7 */
+       fe_mul(h.X, h.X, u)
+
+       // x = (uv⁷)^((q-5)/8)
+       fe_pow22523(h.X, h.X)
 
-       fe_pow22523(h.X, h.X) /* x = (uv^7)^((q-5)/8) */
+       // x = uv³((uv⁷)^((q-5)/8))
        fe_mul(h.X, h.X, v3)
-       fe_mul(h.X, h.X, u) /* x = uv^3(uv^7)^((q-5)/8) */
+       fe_mul(h.X, h.X, u)
 
+       // vxx = vx²
        fe_sq(vxx, h.X)
        fe_mul(vxx, vxx, v)
-       fe_sub(m_root_check, vxx, u) /* vx^2-u */
+
+       // m = vx²-u
+       fe_sub(m_root_check, vxx, u)
        if (fe_iszero(m_root_check) == 0) {
-               fe_add(p_root_check, vxx, u) /* vx^2+u */
+               // p = vx²+u
+               fe_add(p_root_check, vxx, u)
                if (fe_iszero(p_root_check) == 0) {
                        return -1
                }
                fe_mul(h.X, h.X, fe_sqrtm1)
        }
 
-       if (fe_isnegative(h.X) == (s[31] >> 7)) { /* vartime function - compiler optimization is fine */
+       if (fe_isnegative(h.X) == (s[31] >> 7)) {
                fe_neg(h.X, h.X)
        }
        fe_mul(h.T, h.X, h.Y)
index 4d036276c66535176fe29a3407b8b74d145ecb51..c1a7abb9216ecbb548e92025b2f2e529523df5f6 100644 (file)
@@ -123,9 +123,6 @@ export function ge_p3_0 (h: ge_p3): void {
 const ge_p3_dbl_t: FieldElement = fe()
 /**
  * r = 2 * p
- *
- * p.T is used as the temporary holder for r.Y² because the parameter is unused
- * hereafter at all call sites and it eliminates an extra `t` buffer.
  */
 export function ge_p3_dbl (r: ge_p1p1, p: ge_p3): void {
        const t = ge_p3_dbl_t