Inside Bitcoin
Opening the selected file…
Inside Bitcoin
Opening the selected file…
The code behind the network, with room to understand it.
Release published 2026-10-28 · Snapshot fetched 2026-11-01. Latest stable release at fetch time; development branches and Git history are excluded. Only the selected code window and visible folders load here.
1# Test libsecp256k1' group operation implementations using prover.sage3import sys5load("group_prover.sage")6load("weierstrass_prover.sage")8def formula_secp256k1_gej_double_var(a):9"""libsecp256k1's secp256k1_gej_double_var, used by various addition functions"""10rz = a.Z * a.Y11s = a.Y^212l = a.X^213l = l * 314l = l / 215t = -s16t = t * a.X17rx = l^218rx = rx + t19rx = rx + t20s = s^221t = t + rx22ry = t * l23ry = ry + s24ry = -ry25return jacobianpoint(rx, ry, rz)27def formula_secp256k1_gej_add_var(branch, a, b):28"""libsecp256k1's secp256k1_gej_add_var"""29if branch == 0:30return (constraints(), constraints(nonzero={a.Infinity : 'a_infinite'}), b)31if branch == 1:32return (constraints(), constraints(zero={a.Infinity : 'a_finite'}, nonzero={b.Infinity : 'b_infinite'}), a)33z22 = b.Z^234z12 = a.Z^235u1 = a.X * z2236u2 = b.X * z1237s1 = a.Y * z2238s1 = s1 * b.Z39s2 = b.Y * z1240s2 = s2 * a.Z41h = -u142h = h + u243i = -s244i = i + s145if branch == 2:46r = formula_secp256k1_gej_double_var(a)47return (constraints(), constraints(zero={h : 'h=0', i : 'i=0', a.Infinity : 'a_finite', b.Infinity : 'b_finite'}), r)48if branch == 3:49return (constraints(), constraints(zero={h : 'h=0', a.Infinity : 'a_finite', b.Infinity : 'b_finite'}, nonzero={i : 'i!=0'}), point_at_infinity())50t = h * b.Z51rz = a.Z * t52h2 = h^253h2 = -h254h3 = h2 * h55t = u1 * h256rx = i^257rx = rx + h358rx = rx + t59rx = rx + t60t = t + rx61ry = t * i62h3 = h3 * s163ry = ry + h364return (constraints(), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite'}, nonzero={h : 'h!=0'}), jacobianpoint(rx, ry, rz))66def formula_secp256k1_gej_add_ge_var(branch, a, b):67"""libsecp256k1's secp256k1_gej_add_ge_var, which assume bz==1"""68if branch == 0:69return (constraints(zero={b.Z - 1 : 'b.z=1'}), constraints(nonzero={a.Infinity : 'a_infinite'}), b)70if branch == 1:71return (constraints(zero={b.Z - 1 : 'b.z=1'}), constraints(zero={a.Infinity : 'a_finite'}, nonzero={b.Infinity : 'b_infinite'}), a)72z12 = a.Z^273u1 = a.X74u2 = b.X * z1275s1 = a.Y76s2 = b.Y * z1277s2 = s2 * a.Z78h = -u179h = h + u280i = -s281i = i + s182if (branch == 2):83r = formula_secp256k1_gej_double_var(a)84return (constraints(zero={b.Z - 1 : 'b.z=1'}), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite', h : 'h=0', i : 'i=0'}), r)85if (branch == 3):86return (constraints(zero={b.Z - 1 : 'b.z=1'}), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite', h : 'h=0'}, nonzero={i : 'i!=0'}), point_at_infinity())87rz = a.Z * h88h2 = h^289h2 = -h290h3 = h2 * h91t = u1 * h292rx = i^293rx = rx + h394rx = rx + t95rx = rx + t96t = t + rx97ry = t * i98h3 = h3 * s199ry = ry + h3100return (constraints(zero={b.Z - 1 : 'b.z=1'}), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite'}, nonzero={h : 'h!=0'}), jacobianpoint(rx, ry, rz))102def formula_secp256k1_gej_add_zinv_var(branch, a, b):103"""libsecp256k1's secp256k1_gej_add_zinv_var"""104bzinv = b.Z^(-1)105if branch == 0:106rinf = b.Infinity107bzinv2 = bzinv^2108bzinv3 = bzinv2 * bzinv109rx = b.X * bzinv2110ry = b.Y * bzinv3111rz = 1112return (constraints(), constraints(nonzero={a.Infinity : 'a_infinite'}), jacobianpoint(rx, ry, rz, rinf))113if branch == 1:114return (constraints(), constraints(zero={a.Infinity : 'a_finite'}, nonzero={b.Infinity : 'b_infinite'}), a)115azz = a.Z * bzinv116z12 = azz^2117u1 = a.X118u2 = b.X * z12119s1 = a.Y120s2 = b.Y * z12121s2 = s2 * azz122h = -u1123h = h + u2124i = -s2125i = i + s1126if branch == 2:127r = formula_secp256k1_gej_double_var(a)128return (constraints(), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite', h : 'h=0', i : 'i=0'}), r)129if branch == 3:130return (constraints(), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite', h : 'h=0'}, nonzero={i : 'i!=0'}), point_at_infinity())131rz = a.Z * h132h2 = h^2133h2 = -h2134h3 = h2 * h135t = u1 * h2136rx = i^2137rx = rx + h3138rx = rx + t139rx = rx + t140t = t + rx141ry = t * i142h3 = h3 * s1143ry = ry + h3144return (constraints(), constraints(zero={a.Infinity : 'a_finite', b.Infinity : 'b_finite'}, nonzero={h : 'h!=0'}), jacobianpoint(rx, ry, rz))146def formula_secp256k1_gej_add_ge(branch, a, b):147"""libsecp256k1's secp256k1_gej_add_ge"""148zeroes = {}149nonzeroes = {}150a_infinity = False151if (branch & 2) != 0:152nonzeroes.update({a.Infinity : 'a_infinite'})153a_infinity = True154else:155zeroes.update({a.Infinity : 'a_finite'})156zz = a.Z^2157u1 = a.X158u2 = b.X * zz159s1 = a.Y160s2 = b.Y * zz161s2 = s2 * a.Z162t = u1163t = t + u2164m = s1165m = m + s2166rr = t^2167m_alt = -u2168tt = u1 * m_alt169rr = rr + tt170degenerate = (branch & 1) != 0171if degenerate:172zeroes.update({m : 'm_zero'})173else:174nonzeroes.update({m : 'm_nonzero'})175rr_alt = s1176rr_alt = rr_alt * 2177m_alt = m_alt + u1178if not degenerate:179rr_alt = rr180m_alt = m181n = m_alt^2182q = -t183q = q * n184n = n^2185if degenerate:186n = m187t = rr_alt^2188rz = a.Z * m_alt189t = t + q190rx = t191t = t * 2192t = t + q193t = t * rr_alt194t = t + n195ry = -t196ry = ry / 2197if a_infinity:198rx = b.X199ry = b.Y200rz = 1201if (branch & 4) != 0:202zeroes.update({rz : 'r.z = 0'})203return (constraints(zero={b.Z - 1 : 'b.z=1', b.Infinity : 'b_finite'}), constraints(zero=zeroes, nonzero=nonzeroes), point_at_infinity())204else:205nonzeroes.update({rz : 'r.z != 0'})206return (constraints(zero={b.Z - 1 : 'b.z=1', b.Infinity : 'b_finite'}), constraints(zero=zeroes, nonzero=nonzeroes), jacobianpoint(rx, ry, rz))208def formula_secp256k1_gej_add_ge_old(branch, a, b):209"""libsecp256k1's old secp256k1_gej_add_ge, which fails when ay+by=0 but ax!=bx"""210a_infinity = (branch & 1) != 0211zero = {}212nonzero = {}213if a_infinity:214nonzero.update({a.Infinity : 'a_infinite'})215else:216zero.update({a.Infinity : 'a_finite'})217zz = a.Z^2218u1 = a.X219u2 = b.X * zz220s1 = a.Y221s2 = b.Y * zz222s2 = s2 * a.Z223z = a.Z224t = u1225t = t + u2226m = s1227m = m + s2228n = m^2229q = n * t230n = n^2231rr = t^2232t = u1 * u2233t = -t234rr = rr + t235t = rr^2236rz = m * z237infinity = False238if (branch & 2) != 0:239if not a_infinity:240infinity = True241else:242return (constraints(zero={b.Z - 1 : 'b.z=1', b.Infinity : 'b_finite'}), constraints(nonzero={z : 'conflict_a'}, zero={z : 'conflict_b'}), point_at_infinity())243zero.update({rz : 'r.z=0'})244else:245nonzero.update({rz : 'r.z!=0'})246rz = rz * (0 if a_infinity else 2)247rx = t248q = -q249rx = rx + q250q = q * 3
Independent explanations by MyBitcoinExplorer. Not affiliated with or endorsed by Bitcoin Core. Guides are educational and do not replace the source or its tests.
Bitcoin Core source © its contributors, distributed under the MIT license. Original notices and bundled third-party licenses are retained in the source tree.